temporarily-disable-download-notify-again #722
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
| # Auto-triggered on merge to `test`. Builds changed service images, pushes to | |
| # ghcr.io, then updates image tags in icipe-official/VA-Cube-Configs. | |
| # | |
| # Repository secrets used by this workflow: | |
| # GITHUB_TOKEN - auto-provided by Actions; do not set manually | |
| # TOKEN_KEY_UAT - baked into the `ui` image at build time as | |
| # NEXT_PUBLIC_TOKEN_KEY. Rotating requires a UI rebuild. | |
| # REPO_ACCESS_TOKEN - PAT with contents:write on icipe-official/VA-Cube-Configs. | |
| # Used by the update-configs job to push the image-tag commit. | |
| # | |
| # Edit secrets at: Settings -> Secrets and variables -> Actions. | |
| # Full reference + rotation steps: docs/SMG/08-deployment.md | |
| # ("Managing the test/UAT secrets"). | |
| name: Build and Push Docker Images | |
| on: | |
| push: | |
| branches: | |
| - test | |
| - main | |
| pull_request: | |
| types: [closed] | |
| branches: | |
| - test | |
| - main | |
| workflow_dispatch: | |
| inputs: | |
| branch: | |
| description: "Branch to check for changes" | |
| required: true | |
| default: "test" | |
| services: | |
| description: 'Comma-separated list of services to build (e.g., ui,api,help,tileserver,umami,ingestionapi,nginx,occurrencegeojob) or "all"' | |
| required: true | |
| default: "all" | |
| jobs: | |
| set-deployment-environment: | |
| name: Set the GitHub deployment environment to use based on git branch. | |
| runs-on: ubuntu-latest | |
| outputs: | |
| deployment_environment: ${{ steps.determine-env.outputs.deployment_environment }} | |
| steps: | |
| - id: determine-env | |
| run: | | |
| # For pull_request events, use base_ref (target branch) | |
| # For push events, use ref_name (current branch) | |
| # For workflow_dispatch, use the branch input | |
| if [ "${{ github.event_name }}" = "pull_request" ]; then | |
| TARGET_BRANCH="${{ github.base_ref }}" | |
| elif [ "${{ github.event_name }}" = "workflow_dispatch" ]; then | |
| TARGET_BRANCH="${{ github.event.inputs.branch }}" | |
| else | |
| TARGET_BRANCH="${{ github.ref_name }}" | |
| fi | |
| if [ "$TARGET_BRANCH" = "main" ]; then | |
| echo "deployment_environment=production" >> $GITHUB_OUTPUT | |
| elif [ "$TARGET_BRANCH" = "test" ]; then | |
| echo "deployment_environment=test" >> $GITHUB_OUTPUT | |
| fi | |
| detect-changes: | |
| name: Detect changes for ${{ needs.set-deployment-environment.outputs.deployment_environment }} deployment environment | |
| needs: set-deployment-environment | |
| runs-on: ubuntu-latest | |
| environment: ${{ needs.set-deployment-environment.outputs.deployment_environment }} | |
| outputs: | |
| changed_services: ${{ steps.detect-changes.outputs.changed_services }} | |
| api_changed: ${{ steps.detect-changes.outputs.api_changed }} | |
| ui_changed: ${{ steps.detect-changes.outputs.ui_changed }} | |
| occurrencegeojob_changed: ${{ steps.detect-changes.outputs.occurrencegeojob_changed }} | |
| steps: | |
| - uses: actions/checkout@v3 | |
| with: | |
| fetch-depth: 0 | |
| - name: Set Diff Range | |
| id: diff-range | |
| run: | | |
| if [[ "${{ github.event_name }}" == "pull_request" && "${{ github.event.pull_request.merged }}" == "true" ]]; then | |
| echo "HEAD_SHA=$(git rev-parse HEAD)" >> $GITHUB_ENV | |
| echo "BASE_SHA=$(git rev-parse HEAD^1)" >> $GITHUB_ENV | |
| else | |
| echo "HEAD_SHA=$(git rev-parse HEAD)" >> $GITHUB_ENV | |
| echo "BASE_SHA=$(git rev-parse HEAD^1)" >> $GITHUB_ENV | |
| fi | |
| - name: Detect Changed Services | |
| id: detect-changes | |
| run: | | |
| declare -A SERVICES=( | |
| ["ui"]="src/UI" | |
| ["api"]="src/API" | |
| ["help"]="src/Help" | |
| ["tileserver"]="src/TileServer" | |
| ["docker-umami"]="src/Docker/umami" # changed to docker-umami for avaialable public ghcr | |
| ["ingestionapi"]="src/IngestionAPI" | |
| ["nginx"]="src/Docker/nginx" | |
| ["occurrencegeojob"]="src/OccurrenceGeoJob" | |
| ) | |
| CHANGED_SERVICES="" | |
| API_CHANGED="false" | |
| UI_CHANGED="false" | |
| OCCURRENCEGEOJOB_CHANGED="false" | |
| for service in "${!SERVICES[@]}"; do | |
| if git diff --name-only "$BASE_SHA" "$HEAD_SHA" | grep -q "^${SERVICES[$service]}/"; then | |
| CHANGED_SERVICES+="$service," | |
| if [[ "$service" == "api" ]]; then API_CHANGED="true"; fi | |
| if [[ "$service" == "ui" ]]; then UI_CHANGED="true"; fi | |
| if [[ "$service" == "occurrencegeojob" ]]; then OCCURRENCEGEOJOB_CHANGED="true"; fi | |
| fi | |
| done | |
| echo "changed_services=${CHANGED_SERVICES%,}" >> $GITHUB_OUTPUT | |
| echo "api_changed=$API_CHANGED" >> $GITHUB_OUTPUT | |
| echo "ui_changed=$UI_CHANGED" >> $GITHUB_OUTPUT | |
| echo "occurrencegeojob_changed=$OCCURRENCEGEOJOB_CHANGED" >> $GITHUB_OUTPUT | |
| api-ci: | |
| name: API CI for ${{ needs.set-deployment-environment.outputs.deployment_environment }} deployment environment | |
| runs-on: ubuntu-latest | |
| needs: [set-deployment-environment, detect-changes] | |
| environment: ${{ needs.set-deployment-environment.outputs.deployment_environment }} | |
| if: | | |
| needs.detect-changes.outputs.api_changed == 'true' || | |
| ( | |
| github.event_name == 'workflow_dispatch' && | |
| ( | |
| contains(github.event.inputs.services, 'api') || | |
| github.event.inputs.services == 'all' | |
| ) | |
| ) | |
| defaults: | |
| run: | |
| working-directory: src/API | |
| steps: | |
| - uses: actions/checkout@v3 | |
| - uses: actions/setup-node@v3 | |
| with: | |
| node-version: 22 | |
| cache: "npm" | |
| - run: npm ci | |
| - run: npm run build | |
| - run: npm run lint | |
| ui-ci: | |
| name: UI CI for ${{ needs.set-deployment-environment.outputs.deployment_environment }} deployment environment | |
| runs-on: ubuntu-latest | |
| needs: [set-deployment-environment, detect-changes] | |
| environment: ${{ needs.set-deployment-environment.outputs.deployment_environment }} | |
| if: | | |
| needs.detect-changes.outputs.ui_changed == 'true' || | |
| ( | |
| github.event_name == 'workflow_dispatch' && | |
| ( | |
| contains(github.event.inputs.services, 'ui') || | |
| github.event.inputs.services == 'all' | |
| ) | |
| ) | |
| defaults: | |
| run: | |
| working-directory: src/UI | |
| steps: | |
| - uses: actions/checkout@v3 | |
| - uses: actions/setup-node@v3 | |
| with: | |
| node-version: 18 | |
| cache: "npm" | |
| - run: npm ci | |
| - run: npm run build | |
| - run: npm run lint | |
| occurrencegeojob-ci: | |
| name: OccurrenceGeoJob CI for ${{ needs.set-deployment-environment.outputs.deployment_environment }} deployment environment | |
| runs-on: ubuntu-latest | |
| needs: [set-deployment-environment, detect-changes] | |
| environment: ${{ needs.set-deployment-environment.outputs.deployment_environment }} | |
| if: | | |
| needs.detect-changes.outputs.occurrencegeojob_changed == 'true' || | |
| ( | |
| github.event_name == 'workflow_dispatch' && | |
| ( | |
| contains(github.event.inputs.services, 'occurrencegeojob') || | |
| github.event.inputs.services == 'all' | |
| ) | |
| ) | |
| defaults: | |
| run: | |
| working-directory: src/OccurrenceGeoJob | |
| steps: | |
| - uses: actions/checkout@v3 | |
| - uses: actions/setup-node@v3 | |
| with: | |
| node-version: 20 | |
| cache: "npm" | |
| - run: npm ci | |
| - run: npm run build | |
| - run: npm run lint | |
| build-and-push: | |
| name: Build and Push Docker Images for ${{ needs.set-deployment-environment.outputs.deployment_environment }} deployment environment | |
| runs-on: ubuntu-latest | |
| environment: ${{ needs.set-deployment-environment.outputs.deployment_environment }} | |
| needs: | |
| [ | |
| set-deployment-environment, | |
| detect-changes, | |
| api-ci, | |
| ui-ci, | |
| occurrencegeojob-ci, | |
| ] | |
| if: | | |
| always() && | |
| ( | |
| github.event_name == 'workflow_dispatch' || | |
| needs.detect-changes.outputs.changed_services != '' | |
| ) && | |
| ( | |
| needs.api-ci.result != 'failure' && | |
| needs.ui-ci.result != 'failure' && | |
| needs.occurrencegeojob-ci.result != 'failure' | |
| ) | |
| # --- ADD OR UPDATE THIS OUTPUTS SECTION --- | |
| outputs: | |
| short_sha: ${{ steps.build-push-step.outputs.short_sha }} | |
| built_services_with_sha: ${{ steps.build-push-step.outputs.built_services_with_sha }} # <--- NEW OUTPUT HERE | |
| # ------------------------------------------- | |
| steps: | |
| - name: Checkout Code | |
| uses: actions/checkout@v3 | |
| with: | |
| fetch-depth: 0 | |
| - name: Log in to GitHub Container Registry | |
| uses: docker/login-action@v2 | |
| with: | |
| registry: ghcr.io | |
| username: ${{ github.actor }} | |
| password: ${{ secrets.GITHUB_TOKEN }} | |
| - name: Determine SHA prefix based on environment | |
| id: sha-prefix | |
| run: | | |
| if [ "${{ needs.set-deployment-environment.outputs.deployment_environment }}" = "production" ]; then | |
| echo "SHA_PREFIX=production-" >> $GITHUB_OUTPUT | |
| elif [ "${{ needs.set-deployment-environment.outputs.deployment_environment }}" = "test" ]; then | |
| echo "SHA_PREFIX=test-" >> $GITHUB_OUTPUT | |
| else | |
| echo "SHA_PREFIX=" >> $GITHUB_OUTPUT | |
| fi | |
| - name: Build and Push Images | |
| id: build-push-step # Make sure this step has an ID | |
| run: | | |
| declare -A SERVICES=( | |
| ["ui"]="src/UI" | |
| ["api"]="src/API" | |
| ["help"]="src/Help" | |
| ["tileserver"]="src/TileServer" | |
| ["docker-umami"]="src/Docker/umami" # changed to docker-umami for avaialable public ghcr | |
| ["ingestionapi"]="src/IngestionAPI" | |
| ["nginx"]="src/Docker/nginx" | |
| ["occurrencegeojob"]="src/OccurrenceGeoJob" | |
| ) | |
| SELECTED="${{ needs.detect-changes.outputs.changed_services }}" | |
| if [[ "${{ github.event_name }}" == "workflow_dispatch" ]]; then | |
| SELECTED="${{ github.event.inputs.services }}" | |
| if [[ "$SELECTED" == "all" ]]; then | |
| SELECTED=$(IFS=','; echo "${!SERVICES[*]}" | tr ' ' ',') | |
| fi | |
| fi | |
| IFS=',' read -ra TO_BUILD <<< "$SELECTED" | |
| SHORT_SHA=$(git rev-parse --short HEAD) | |
| echo "Detected SHORT_SHA: $SHORT_SHA" | |
| echo "short_sha=$SHORT_SHA" >> $GITHUB_OUTPUT # This exports the overall SHA | |
| # --- NEW LOGIC: Prepare output for built services and their SHAs --- | |
| BUILT_SERVICES_OUTPUT="" | |
| first_service=true | |
| cd src | |
| chmod +x buildVersionFiles.sh | |
| ./buildVersionFiles.sh | |
| cd .. | |
| # Get the SHA prefix based on environment | |
| SHA_PREFIX="${{ steps.sha-prefix.outputs.SHA_PREFIX }}" | |
| echo "Using SHA prefix: $SHA_PREFIX" | |
| for image_name in "${TO_BUILD[@]}"; do | |
| dir="${SERVICES[$image_name]}" | |
| echo "Building and pushing $image_name from $dir" | |
| LATEST_TAG="ghcr.io/${{ github.repository_owner }}/${image_name}:latest" | |
| PREFIXED_SHA="${SHA_PREFIX}${SHORT_SHA}" | |
| SHA_TAG="ghcr.io/${{ github.repository_owner }}/${image_name}:${PREFIXED_SHA}" | |
| if [[ "$image_name" == "ui" ]]; then | |
| docker build \ | |
| --build-arg NEXT_PUBLIC_TOKEN_KEY="${{ secrets.TOKEN_KEY_UAT }}" \ | |
| --build-arg NEXT_PUBLIC_AUTH_ENDPOINT="${{ secrets.NEXT_PUBLIC_AUTH_ENDPOINT }}" \ | |
| --build-arg NEXT_PUBLIC_ANALYTICS_ID="${{ secrets.NEXT_PUBLIC_ANALYTICS_ID }}" \ | |
| --build-arg NEXT_PUBLIC_ANALYTICS_URL="${{ secrets.NEXT_PUBLIC_ANALYTICS_URL }}" \ | |
| --build-arg NEXT_PUBLIC_MAX_UPLOAD_SIZE="${{ secrets.NEXT_PUBLIC_MAX_UPLOAD_SIZE }}" \ | |
| --no-cache \ | |
| -t "$LATEST_TAG" -t "$SHA_TAG" "$dir" | |
| elif [[ "$image_name" == "docker-umami" ]]; then | |
| docker build \ | |
| --build-arg BASE_PATH="${{ secrets.UMAMI_BUILD_ARG_BASE_PATH }}" \ | |
| --no-cache \ | |
| -t "$LATEST_TAG" -t "$SHA_TAG" "$dir" | |
| else | |
| docker build -t "$LATEST_TAG" -t "$SHA_TAG" "$dir" | |
| fi | |
| docker push "$LATEST_TAG" | |
| docker push "$SHA_TAG" | |
| # Append to output string in 'service_name:sha' format with prefix | |
| if [ "$first_service" = true ]; then | |
| BUILT_SERVICES_OUTPUT+="${image_name}:${PREFIXED_SHA}" | |
| first_service=false | |
| else | |
| BUILT_SERVICES_OUTPUT+=",${image_name}:${PREFIXED_SHA}" | |
| fi | |
| done | |
| # Export the list of built services and their specific SHAs | |
| echo "built_services_with_sha=$BUILT_SERVICES_OUTPUT" >> $GITHUB_OUTPUT | |
| # ----------------------------------------------------------- | |
| update-configs: | |
| name: Update Values YAML with SHA Tags for ${{ needs.set-deployment-environment.outputs.deployment_environment }} deployment environment | |
| runs-on: ubuntu-latest | |
| needs: [set-deployment-environment, build-and-push] | |
| if: always() # Keep this as 'always()' for now for continued debugging. | |
| permissions: | |
| contents: write | |
| steps: | |
| - name: Checkout VA-Cube-Configs repository | |
| uses: actions/checkout@v4 | |
| with: | |
| repository: icipe-official/VA-Cube-Configs | |
| ssh-key: ${{ secrets.VA_CUBE_CONFIG_SSH_KEY }} # Switch to deploy keys | |
| path: VA-Cube-Configs # Checkout into this subdirectory | |
| fetch-depth: 0 | |
| - name: Set up YQ (YAML processor) | |
| run: | | |
| sudo wget https://github.com/mikefarah/yq/releases/latest/download/yq_linux_amd64 -O /usr/local/bin/yq && sudo chmod +x /usr/local/bin/yq | |
| - name: Determine helm values file path and SHA prefix | |
| id: helm-path | |
| run: | | |
| if [ "${{ needs.set-deployment-environment.outputs.deployment_environment }}" = "production" ]; then | |
| echo "HELM_VALUES_PATH=app-prod/helm-values.yaml" >> $GITHUB_OUTPUT | |
| echo "SHA_PREFIX=production-" >> $GITHUB_OUTPUT | |
| elif [ "${{ needs.set-deployment-environment.outputs.deployment_environment }}" = "test" ]; then | |
| echo "HELM_VALUES_PATH=app/helm-values.yaml" >> $GITHUB_OUTPUT | |
| echo "SHA_PREFIX=test-" >> $GITHUB_OUTPUT | |
| else | |
| echo "HELM_VALUES_PATH=values.yaml" >> $GITHUB_OUTPUT | |
| echo "SHA_PREFIX=" >> $GITHUB_OUTPUT | |
| fi | |
| echo "GIT_BRANCH=main" >> $GITHUB_OUTPUT | |
| - name: Update values.yaml with new SHA Tags | |
| run: | | |
| set -euo pipefail | |
| updated_any=0 | |
| # Get the helm values file path and SHA prefix based on environment | |
| HELM_FILE="${{ steps.helm-path.outputs.HELM_VALUES_PATH }}" | |
| GIT_BRANCH="${{ steps.helm-path.outputs.GIT_BRANCH }}" | |
| SHA_PREFIX="${{ steps.helm-path.outputs.SHA_PREFIX }}" | |
| echo "Updating helm values file: $HELM_FILE" | |
| echo "Target branch: $GIT_BRANCH" | |
| echo "SHA prefix: $SHA_PREFIX" | |
| # --- Get the new output from build-and-push job --- | |
| BUILT_SERVICES_WITH_SHA="${{ needs.build-and-push.outputs.built_services_with_sha }}" | |
| echo "Services built and their SHAs received: ${BUILT_SERVICES_WITH_SHA}" | |
| # Exit gracefully if no services were built/pushed | |
| if [ -z "$BUILT_SERVICES_WITH_SHA" ]; then | |
| echo "No services reported as built in the previous job. No values.yaml updates will be performed." | |
| exit 0 # Exit with success | |
| fi | |
| # Loop through the 'service_name:sha' pairs and update only those tags | |
| IFS=',' read -ra BUILT_SERVICE_PAIRS <<< "$BUILT_SERVICES_WITH_SHA" | |
| for pair in "${BUILT_SERVICE_PAIRS[@]}"; do | |
| img_key=$(echo "$pair" | cut -d':' -f1) # Extract service name | |
| current_image_sha=$(echo "$pair" | cut -d':' -f2) # Extract SHA which already includes prefix | |
| if [[ "$img_key" == "docker-umami" ]]; then | |
| img_key="umami" | |
| fi | |
| yq_path=".images.${img_key}.tag" | |
| # Reference the appropriate helm-values.yaml file | |
| EXISTING_TAG=$(yq e "${yq_path}" VA-Cube-Configs/$HELM_FILE || echo "NOT_FOUND") | |
| if [[ "$EXISTING_TAG" != "$current_image_sha" ]]; then | |
| echo "Updating ${yq_path} from '${EXISTING_TAG}' to '${current_image_sha}'" | |
| # Reference the appropriate helm-values.yaml file | |
| yq e "${yq_path} = \"${current_image_sha}\"" -i VA-Cube-Configs/$HELM_FILE | |
| updated_any=1 | |
| else | |
| echo "${img_key} tag in $HELM_FILE is already up to date: ${current_image_sha}" | |
| fi | |
| done | |
| if [ "$updated_any" -eq 1 ]; then | |
| echo "Changes detected in $HELM_FILE. Committing and pushing." | |
| # Change directory to the checked-out repo before git commands | |
| cd VA-Cube-Configs | |
| git config user.name "github-actions[bot]" | |
| git config user.email "github-actions[bot]@users.noreply.github.com" | |
| git add $HELM_FILE | |
| git commit -m "chore(deps): Update image tags to latest SHAs for ${{ needs.set-deployment-environment.outputs.deployment_environment }} deployment environment" || echo "No changes to commit" | |
| # Push using the SSH deploy key to the other repository | |
| git push git@github.com:/icipe-official/VA-Cube-Configs.git HEAD:$GIT_BRANCH | |
| else | |
| echo "No image tag updates required." | |
| fi |