name: Classic - AutoGPT Docker CI

on:
  push:
    branches: [master, dev]
    paths:
      - '.github/workflows/classic-autogpt-docker-ci.yml'
      - 'classic/original_autogpt/**'
      - 'classic/forge/**'
  pull_request:
    branches: [ master, dev, release-* ]
    paths:
      - '.github/workflows/classic-autogpt-docker-ci.yml'
      - 'classic/original_autogpt/**'
      - 'classic/forge/**'

concurrency:
  group: ${{ format('classic-autogpt-docker-ci-{0}', github.head_ref && format('pr-{0}', github.event.pull_request.number) || github.sha) }}
  cancel-in-progress: ${{ github.event_name == 'pull_request' }}

defaults:
  run:
    working-directory: classic/original_autogpt

env:
  IMAGE_NAME: auto-gpt
  DEPLOY_IMAGE_NAME: ${{ secrets.DOCKER_USER && format('{0}/', secrets.DOCKER_USER) || '' }}auto-gpt
  DEV_IMAGE_TAG: latest-dev

jobs:
  build:
    runs-on: ubuntu-latest
    strategy:
      matrix:
        build-type: [release, dev]
    steps:
      - name: Checkout repository
        uses: actions/checkout@v4

      - name: Set up Docker Buildx
        uses: docker/setup-buildx-action@v3

      - if: runner.debug
        run: |
          ls -al
          du -hs *

      - id: build
        name: Build image
        uses: docker/build-push-action@v6
        with:
          context: classic/
          file: classic/Dockerfile.autogpt
          build-args: BUILD_TYPE=${{ matrix.build-type }}
          tags: ${{ env.IMAGE_NAME }}
          labels: GIT_REVISION=${{ github.sha }}
          load: true # save to docker images
          # cache layers in GitHub Actions cache to speed up builds
          cache-from: type=gha,scope=autogpt-docker-${{ matrix.build-type }}
          cache-to: type=gha,scope=autogpt-docker-${{ matrix.build-type }},mode=max

      - name: Generate build report
        env:
          event_name: ${{ github.event_name }}
          event_ref: ${{ github.event.ref }}
          event_ref_type: ${{ github.event.ref}}

          build_type: ${{ matrix.build-type }}

          prod_branch: master
          dev_branch: dev
          repository: ${{ github.repository }}
          base_branch: ${{ github.ref_name != 'master' && github.ref_name != 'dev' && 'dev' || 'master' }}

          current_ref: ${{ github.ref_name }}
          commit_hash: ${{ github.event.after }}
          source_url: ${{ format('{0}/tree/{1}', github.event.repository.url, github.event.release && github.event.release.tag_name || github.sha) }}
          push_forced_label: ${{ github.event.forced && '☢️ forced' || '' }}

          new_commits_json: ${{ toJSON(github.event.commits) }}
          compare_url_template: ${{ format('/{0}/compare/{{base}}...{{head}}', github.repository) }}

          github_context_json: ${{ toJSON(github) }}
          job_env_json: ${{ toJSON(env) }}
          vars_json: ${{ toJSON(vars) }}

        run: .github/workflows/scripts/docker-ci-summary.sh >> $GITHUB_STEP_SUMMARY
        continue-on-error: true

  test:
    runs-on: ubuntu-latest
    timeout-minutes: 10

    services:
      minio:
        image: minio/minio:edge-cicd
        options: >
          --name=minio
          --health-interval=10s --health-timeout=5s --health-retries=3
          --health-cmd="curl -f http://localhost:9000/minio/health/live"

    steps:
      - name: Check out repository
        uses: actions/checkout@v4
        with:
          submodules: true

      - if: github.event_name == 'push'
        name: Log in to Docker hub
        uses: docker/login-action@v3
        with:
          username: ${{ secrets.DOCKER_USER }}
          password: ${{ secrets.DOCKER_PASSWORD }}

      - name: Set up Docker Buildx
        uses: docker/setup-buildx-action@v3

      - id: build
        name: Build image
        uses: docker/build-push-action@v6
        with:
          context: classic/
          file: classic/Dockerfile.autogpt
          build-args: BUILD_TYPE=dev # include pytest
          tags: >
            ${{ env.IMAGE_NAME }},
            ${{ env.DEPLOY_IMAGE_NAME }}:${{ env.DEV_IMAGE_TAG }}
          labels: GIT_REVISION=${{ github.sha }}
          load: true # save to docker images
          # cache layers in GitHub Actions cache to speed up builds
          cache-from: type=gha,scope=autogpt-docker-dev
          cache-to: type=gha,scope=autogpt-docker-dev,mode=max

      - id: test
        name: Run tests
        env:
          CI: true
          PLAIN_OUTPUT: True
          OPENAI_API_KEY: ${{ secrets.OPENAI_API_KEY }}
          S3_ENDPOINT_URL: http://minio:9000
          AWS_ACCESS_KEY_ID: minioadmin
          AWS_SECRET_ACCESS_KEY: minioadmin
        run: |
          set +e
          docker run --env CI --env OPENAI_API_KEY \
            --network container:minio \
            --env S3_ENDPOINT_URL --env AWS_ACCESS_KEY_ID --env AWS_SECRET_ACCESS_KEY \
            --entrypoint poetry ${{ env.IMAGE_NAME }} run \
            pytest -v --cov=autogpt --cov-branch --cov-report term-missing \
            --numprocesses=4 --durations=10 \
            original_autogpt/tests/unit original_autogpt/tests/integration 2>&1 | tee test_output.txt

          test_failure=${PIPESTATUS[0]}

          cat << $EOF >> $GITHUB_STEP_SUMMARY
          # Tests $([ $test_failure = 0 ] && echo '✅' || echo '❌')
          \`\`\`
          $(cat test_output.txt)
          \`\`\`
          $EOF

          exit $test_failure

      - if: github.event_name == 'push' && github.ref_name == 'master'
        name: Push image to Docker Hub
        run: docker push ${{ env.DEPLOY_IMAGE_NAME }}:${{ env.DEV_IMAGE_TAG }}
