Bump dorny/paths-filter from 3 to 4 in the github-actions group #163
Workflow file for this run
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
| name: Build and Deploy | |
| on: | |
| push: | |
| branches: [main] | |
| paths-ignore: | |
| - 'Infra/**' | |
| - '.github/workflows/deploy-infrastructure.yml' | |
| pull_request: | |
| branches: [main] | |
| paths-ignore: | |
| - 'Infra/**' | |
| workflow_dispatch: | |
| permissions: | |
| id-token: write | |
| contents: read | |
| defaults: | |
| run: | |
| shell: pwsh | |
| env: | |
| DOTNET_VERSION: '10.0.x' | |
| NODE_VERSION: '22.x' | |
| PNPM_VERSION: '11.1.1' | |
| FRONTEND_PROJECT_PATH: 'GillyTracker.Web' | |
| TERRAFORM_VERSION: '1.14.6' | |
| jobs: | |
| # Build and test backend and frontend | |
| build: | |
| runs-on: ubuntu-latest | |
| steps: | |
| - uses: actions/checkout@v6 | |
| - name: Setup .NET | |
| uses: actions/setup-dotnet@v5 | |
| with: | |
| dotnet-version: ${{ env.DOTNET_VERSION }} | |
| global-json-file: global.json | |
| - name: Setup pnpm | |
| uses: pnpm/action-setup@v6 | |
| with: | |
| version: ${{ env.PNPM_VERSION }} | |
| - name: Setup Node.js | |
| uses: actions/setup-node@v6 | |
| with: | |
| node-version: ${{ env.NODE_VERSION }} | |
| cache: 'pnpm' | |
| cache-dependency-path: ${{ env.FRONTEND_PROJECT_PATH }}/pnpm-lock.yaml | |
| - name: Install frontend dependencies | |
| working-directory: ${{ env.FRONTEND_PROJECT_PATH }} | |
| run: pnpm install --frozen-lockfile | |
| - name: Lint frontend | |
| working-directory: ${{ env.FRONTEND_PROJECT_PATH }} | |
| run: pnpm run lint | |
| - name: Build frontend | |
| working-directory: ${{ env.FRONTEND_PROJECT_PATH }} | |
| run: pnpm run build | |
| env: | |
| BACKEND_URL: '' | |
| - name: Restore .NET dependencies | |
| run: dotnet restore | |
| - name: Build | |
| run: dotnet build --no-restore --configuration Release | |
| - name: Restore dotnet tool | |
| run: dotnet tool restore | |
| - name: Check for Pending Database Changes | |
| run: | | |
| dotnet ef migrations has-pending-model-changes ` | |
| --configuration Release ` | |
| --project GillyTracker.Data/GillyTracker.Data.csproj ` | |
| --startup-project GillyTracker.AppHost/GillyTracker.AppHost.csproj | |
| - name: Install Playwright browsers | |
| run: pwsh GillyTracker.UITests/bin/Release/net10.0/playwright.ps1 install --with-deps | |
| # Microsoft Testing Platform can stop the run once 10 tests fail in CI: | |
| # https://learn.microsoft.com/dotnet/core/testing/microsoft-testing-platform-cli-options | |
| # To enable retries, add Microsoft.Testing.Extensions.Retry to the test project, then pass | |
| # --retry-failed-tests plus --retry-failed-tests-max-percentage <value> to skip reruns when too many tests fail: | |
| # https://learn.microsoft.com/dotnet/core/testing/microsoft-testing-platform-retry#retry-1 | |
| - name: Test | |
| run: dotnet test --no-build --configuration Release --verbosity normal --maximum-failed-tests 10 | |
| env: | |
| DOTNET_BUILD_CONFIGURATION: Release | |
| - name: Upload test failure screenshots | |
| if: failure() | |
| uses: actions/upload-artifact@v7 | |
| with: | |
| name: test-failure-screenshots | |
| path: '**/TestResults/screenshots/*.png' | |
| if-no-files-found: ignore | |
| retention-days: 7 | |
| - name: Upload test failure logs | |
| if: failure() | |
| uses: actions/upload-artifact@v7 | |
| with: | |
| name: test-failure-logs | |
| path: '**/TestResults/logs/*.log' | |
| if-no-files-found: ignore | |
| retention-days: 7 | |
| - name: Publish | |
| run: dotnet publish --configuration Release --no-build | |
| - name: Build Database Bundle | |
| if: github.event_name == 'workflow_dispatch' || github.ref == 'refs/heads/main' | |
| run: | | |
| dotnet ef migrations bundle ` | |
| --self-contained ` | |
| --no-build ` | |
| --configuration Release ` | |
| --project GillyTracker.Data/GillyTracker.Data.csproj ` | |
| --startup-project .\GillyTracker.AppHost\GillyTracker.AppHost.csproj ` | |
| --output efbundle | |
| - name: Azure Login | |
| if: github.event_name == 'workflow_dispatch' || github.ref == 'refs/heads/main' | |
| uses: azure/login@v3 | |
| with: | |
| client-id: ${{ secrets.ARM_CLIENT_ID }} | |
| tenant-id: ${{ secrets.ARM_TENANT_ID }} | |
| subscription-id: ${{ secrets.ARM_SUBSCRIPTION_ID }} | |
| - name: Upload DB Migration | |
| if: github.event_name == 'workflow_dispatch' || github.ref == 'refs/heads/main' | |
| uses: Keboo/sa-upload@v1 | |
| with: | |
| name: efbundle | |
| path: 'efbundle' | |
| storage-account: keboogithub | |
| container-name: gillytracker | |
| create-container: true | |
| - name: Upload frontend artifact | |
| if: github.event_name == 'workflow_dispatch' || github.ref == 'refs/heads/main' | |
| uses: actions/upload-artifact@v7 | |
| with: | |
| name: frontend | |
| path: ${{ env.FRONTEND_PROJECT_PATH }}/dist | |
| retention-days: 1 | |
| automerge: | |
| if: ${{ github.event_name == 'pull_request' && github.actor == 'dependabot[bot]' }} | |
| needs: [build] | |
| runs-on: ubuntu-latest | |
| permissions: | |
| pull-requests: write | |
| contents: write | |
| steps: | |
| - name: Enable auto-merge for Dependabot PRs | |
| run: gh pr merge --auto --squash "${{ github.event.pull_request.number }}" | |
| env: | |
| GH_TOKEN: ${{ secrets.GITHUB_TOKEN }} | |
| GH_REPO: ${{ github.repository }} | |
| # Get infrastructure outputs from Terraform state | |
| get-infrastructure-outputs: | |
| runs-on: ubuntu-latest | |
| if: github.event_name == 'workflow_dispatch' || (github.event_name == 'push' && github.ref == 'refs/heads/main') | |
| environment: production | |
| outputs: | |
| acr_login_server: ${{ steps.terraform-outputs.outputs.acr_login_server }} | |
| backend_container_app_name: ${{ steps.terraform-outputs.outputs.backend_container_app_name }} | |
| backend_url: ${{ steps.terraform-outputs.outputs.backend_url }} | |
| resource_group_name: ${{ steps.terraform-outputs.outputs.resource_group_name }} | |
| static_web_app_name: ${{ steps.terraform-outputs.outputs.static_web_app_name }} | |
| static_web_app_api_key: ${{ steps.terraform-outputs.outputs.static_web_app_api_key }} | |
| database_connection_string: ${{ steps.terraform-outputs.outputs.database_connection_string }} | |
| applicationinsights_connection_string: ${{ steps.terraform-outputs.outputs.applicationinsights_connection_string }} | |
| steps: | |
| - uses: actions/checkout@v6 | |
| - name: Setup Terraform | |
| uses: hashicorp/setup-terraform@v4 | |
| with: | |
| terraform_version: ${{ env.TERRAFORM_VERSION }} | |
| terraform_wrapper: false | |
| - name: Azure Login | |
| uses: azure/login@v3 | |
| with: | |
| client-id: ${{ secrets.ARM_CLIENT_ID }} | |
| tenant-id: ${{ secrets.ARM_TENANT_ID }} | |
| subscription-id: ${{ secrets.ARM_SUBSCRIPTION_ID }} | |
| - name: Terraform Init | |
| working-directory: Infra | |
| run: terraform init | |
| env: | |
| ARM_CLIENT_ID: ${{ secrets.ARM_CLIENT_ID }} | |
| ARM_SUBSCRIPTION_ID: ${{ secrets.ARM_SUBSCRIPTION_ID }} | |
| ARM_TENANT_ID: ${{ secrets.ARM_TENANT_ID }} | |
| ARM_USE_OIDC: true | |
| - name: Get Terraform Outputs | |
| id: terraform-outputs | |
| working-directory: Infra | |
| shell: bash | |
| run: | | |
| echo "acr_login_server=$(terraform output -raw acr_login_server)" >> $GITHUB_OUTPUT | |
| echo "backend_container_app_name=$(terraform output -raw backend_container_app_name)" >> $GITHUB_OUTPUT | |
| echo "resource_group_name=$(terraform output -raw resource_group_name)" >> $GITHUB_OUTPUT | |
| echo "static_web_app_name=$(terraform output -raw static_web_app_name)" >> $GITHUB_OUTPUT | |
| echo "static_web_app_api_key=$(terraform output -raw static_web_app_api_key)" >> $GITHUB_OUTPUT | |
| echo "backend_url=$(terraform output -raw backend_url)" >> $GITHUB_OUTPUT | |
| echo "database_connection_string=$(terraform output -raw database_connection_string)" >> $GITHUB_OUTPUT | |
| echo "applicationinsights_connection_string=$(terraform output -raw applicationinsights_connection_string)" >> $GITHUB_OUTPUT | |
| env: | |
| ARM_CLIENT_ID: ${{ secrets.ARM_CLIENT_ID }} | |
| ARM_SUBSCRIPTION_ID: ${{ secrets.ARM_SUBSCRIPTION_ID }} | |
| ARM_TENANT_ID: ${{ secrets.ARM_TENANT_ID }} | |
| ARM_USE_OIDC: true | |
| deploy-database: | |
| runs-on: ubuntu-latest | |
| needs: [build, get-infrastructure-outputs] | |
| if: github.event_name == 'workflow_dispatch' || (github.event_name == 'push' && github.ref == 'refs/heads/main') | |
| environment: production | |
| steps: | |
| - name: Azure Login | |
| uses: azure/login@v3 | |
| with: | |
| client-id: ${{ secrets.ARM_CLIENT_ID }} | |
| tenant-id: ${{ secrets.ARM_TENANT_ID }} | |
| subscription-id: ${{ secrets.ARM_SUBSCRIPTION_ID }} | |
| - name: Download DB Migration Bundle | |
| uses: Keboo/sa-download@v1 | |
| with: | |
| name: efbundle | |
| storage-account: keboogithub | |
| container-name: gillytracker | |
| - name: Apply Migration | |
| run: | | |
| chmod +x efbundle | |
| $env:ConnectionStrings__Database = '${{ needs.get-infrastructure-outputs.outputs.database_connection_string }}' | |
| ./efbundle | |
| if ($LASTEXITCODE -eq 0) { | |
| rm efbundle | |
| exit 0 | |
| } | |
| rm efbundle | |
| throw "Migration bundle failed." | |
| # Build and push Docker image for backend | |
| deploy-backend: | |
| runs-on: ubuntu-latest | |
| needs: [build, get-infrastructure-outputs] | |
| if: github.event_name == 'workflow_dispatch' || (github.event_name == 'push' && github.ref == 'refs/heads/main') | |
| environment: production | |
| steps: | |
| - uses: actions/checkout@v6 | |
| - name: Setup .NET | |
| uses: actions/setup-dotnet@v5 | |
| with: | |
| dotnet-version: ${{ env.DOTNET_VERSION }} | |
| global-json-file: global.json | |
| - name: Setup pnpm | |
| uses: pnpm/action-setup@v6 | |
| with: | |
| version: ${{ env.PNPM_VERSION }} | |
| - name: Setup Node.js | |
| uses: actions/setup-node@v6 | |
| with: | |
| node-version: ${{ env.NODE_VERSION }} | |
| cache: 'pnpm' | |
| cache-dependency-path: ${{ env.FRONTEND_PROJECT_PATH }}/pnpm-lock.yaml | |
| - name: Azure Login | |
| uses: azure/login@v3 | |
| with: | |
| client-id: ${{ secrets.ARM_CLIENT_ID }} | |
| tenant-id: ${{ secrets.ARM_TENANT_ID }} | |
| subscription-id: ${{ secrets.ARM_SUBSCRIPTION_ID }} | |
| - name: Log in to Azure Container Registry | |
| run: | | |
| az acr login --name ${{ needs.get-infrastructure-outputs.outputs.acr_login_server }} | |
| - name: dotnet publish | |
| run: dotnet publish .\GillyTracker\GillyTracker.csproj --configuration Release -r linux-x64 --self-contained -t:PublishContainer -p:ContainerRegistry=${{ needs.get-infrastructure-outputs.outputs.acr_login_server }} -p:ContainerImageTags="${{ github.sha }}" | |
| - name: Update Container App | |
| run: | | |
| az containerapp update ` | |
| --name ${{ needs.get-infrastructure-outputs.outputs.backend_container_app_name }} ` | |
| --resource-group ${{ needs.get-infrastructure-outputs.outputs.resource_group_name }} ` | |
| --image ${{ needs.get-infrastructure-outputs.outputs.acr_login_server }}/gillytracker:${{ github.sha }} | |
| # Deploy frontend to Azure Static Web Apps | |
| deploy-frontend: | |
| runs-on: ubuntu-latest | |
| needs: [build, get-infrastructure-outputs] | |
| if: github.event_name == 'workflow_dispatch' || (github.event_name == 'push' && github.ref == 'refs/heads/main') | |
| environment: production | |
| steps: | |
| - uses: actions/checkout@v6 | |
| - name: Setup pnpm | |
| uses: pnpm/action-setup@v6 | |
| with: | |
| version: ${{ env.PNPM_VERSION }} | |
| - name: Setup Node.js | |
| uses: actions/setup-node@v6 | |
| with: | |
| node-version: ${{ env.NODE_VERSION }} | |
| cache: 'pnpm' | |
| cache-dependency-path: ${{ env.FRONTEND_PROJECT_PATH }}/pnpm-lock.yaml | |
| - name: Install frontend dependencies | |
| working-directory: ${{ env.FRONTEND_PROJECT_PATH }} | |
| run: pnpm install --frozen-lockfile | |
| - name: Build frontend for production | |
| working-directory: ${{ env.FRONTEND_PROJECT_PATH }} | |
| run: pnpm run build | |
| env: | |
| BACKEND_URL: ${{ needs.get-infrastructure-outputs.outputs.backend_url }} | |
| # BACKEND_URL: 'TODO' # This should be set to the backend_url, if you use the generated ACA endpoint you may run into issues with cross origin issues. | |
| APPLICATIONINSIGHTS_CONNECTION_STRING: ${{ needs.get-infrastructure-outputs.outputs.applicationinsights_connection_string }} | |
| - name: Deploy to Azure Static Web Apps | |
| uses: Azure/static-web-apps-deploy@v1 | |
| with: | |
| azure_static_web_apps_api_token: ${{ needs.get-infrastructure-outputs.outputs.static_web_app_api_key }} | |
| repo_token: ${{ secrets.GITHUB_TOKEN }} | |
| action: 'upload' | |
| app_location: '${{ env.FRONTEND_PROJECT_PATH }}/dist' | |
| skip_app_build: true | |
| skip_api_build: true |