Pre-Release Validation #2
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: Pre-Release Validation | |
| on: | |
| workflow_dispatch: | |
| inputs: | |
| target_version: | |
| description: 'Target version for release (e.g., 1.17.0)' | |
| required: false | |
| type: string | |
| concurrency: | |
| group: pre-release-${{ github.ref }} | |
| cancel-in-progress: false # Don't cancel pre-release validations | |
| jobs: | |
| # Stage 1: Full Unit Test Suite (Parallel) | |
| backend-full-tests: | |
| name: Backend Full Test Suite | |
| runs-on: ubuntu-latest | |
| timeout-minutes: 15 | |
| services: | |
| postgres: | |
| image: postgis/postgis:17-3.5 | |
| env: | |
| POSTGRES_DB: geopulse_test | |
| POSTGRES_USER: geopulse_test | |
| POSTGRES_PASSWORD: testpass | |
| ports: | |
| - 5432:5432 | |
| options: >- | |
| --health-cmd "pg_isready -U geopulse_test -d geopulse_test" | |
| --health-interval 10s | |
| --health-timeout 5s | |
| --health-retries 5 | |
| steps: | |
| - name: Checkout code | |
| uses: actions/checkout@v4 | |
| - name: Set up Java 25 | |
| uses: actions/setup-java@v4 | |
| with: | |
| java-version: '25' | |
| distribution: 'temurin' | |
| cache: 'maven' | |
| - name: Cache Maven dependencies | |
| uses: actions/cache@v4 | |
| with: | |
| path: ~/.m2/repository | |
| key: ${{ runner.os }}-maven-${{ hashFiles('**/pom.xml') }} | |
| restore-keys: | | |
| ${{ runner.os }}-maven- | |
| - name: Run all backend tests | |
| run: ./mvnw -pl backend clean test | |
| env: | |
| QUARKUS_DATASOURCE_JDBC_URL: jdbc:postgresql://localhost:5432/geopulse_test | |
| QUARKUS_DATASOURCE_USERNAME: geopulse_test | |
| QUARKUS_DATASOURCE_PASSWORD: testpass | |
| - name: Upload test results | |
| if: always() | |
| uses: actions/upload-artifact@v4 | |
| with: | |
| name: backend-full-test-results | |
| path: backend/target/surefire-reports/ | |
| retention-days: 30 | |
| frontend-full-tests: | |
| name: Frontend Full Test Suite | |
| runs-on: ubuntu-latest | |
| timeout-minutes: 15 | |
| steps: | |
| - name: Checkout code | |
| uses: actions/checkout@v4 | |
| - name: Set up Node.js | |
| uses: actions/setup-node@v4 | |
| with: | |
| node-version: '20' | |
| cache: 'npm' | |
| cache-dependency-path: frontend/package-lock.json | |
| - name: Install dependencies | |
| run: | | |
| cd frontend | |
| npm ci | |
| - name: Run all frontend tests | |
| run: | | |
| cd frontend | |
| npm run test:run | |
| - name: Upload test results | |
| if: always() | |
| uses: actions/upload-artifact@v4 | |
| with: | |
| name: frontend-full-test-results | |
| path: frontend/coverage/ | |
| retention-days: 30 | |
| code-quality-full: | |
| name: Code Quality Analysis | |
| runs-on: ubuntu-latest | |
| timeout-minutes: 10 | |
| steps: | |
| - name: Checkout code | |
| uses: actions/checkout@v4 | |
| - name: Set up Java 25 | |
| uses: actions/setup-java@v4 | |
| with: | |
| java-version: '25' | |
| distribution: 'temurin' | |
| cache: 'maven' | |
| - name: Run PMD analysis | |
| run: ./mvnw -pl backend pmd:check | |
| continue-on-error: true | |
| - name: Show PMD violations | |
| if: always() | |
| run: | | |
| if [ -f backend/target/pmd.xml ]; then | |
| echo "=== PMD Violations ===" | |
| cat backend/target/pmd.xml | |
| fi | |
| - name: Upload PMD report | |
| if: always() | |
| uses: actions/upload-artifact@v4 | |
| with: | |
| name: pmd-full-report | |
| path: backend/target/pmd.xml | |
| retention-days: 30 | |
| # Stage 2: Full E2E Suite | |
| full-e2e-tests: | |
| name: Full E2E Test Suite | |
| runs-on: ubuntu-latest | |
| needs: [backend-full-tests, frontend-full-tests] | |
| timeout-minutes: 50 | |
| steps: | |
| - name: Checkout code | |
| uses: actions/checkout@v4 | |
| - name: Set up Docker Buildx | |
| uses: docker/setup-buildx-action@v3 | |
| - name: Start E2E environment | |
| run: | | |
| docker compose -f tests/docker-compose.e2e.yml up -d geopulse-postgres-e2e geopulse-backend-e2e geopulse-ui-e2e | |
| - name: Wait for services to be healthy | |
| run: | | |
| echo "Waiting for backend to be ready..." | |
| timeout 120 bash -c 'until curl -f http://localhost:8081/api/health; do echo "Waiting..."; sleep 5; done' | |
| echo "Waiting for frontend to be ready..." | |
| timeout 60 bash -c 'until curl -f http://localhost:5556; do echo "Waiting..."; sleep 5; done' | |
| echo "All services are ready!" | |
| - name: Set up Node.js | |
| uses: actions/setup-node@v4 | |
| with: | |
| node-version: '20' | |
| cache: 'npm' | |
| cache-dependency-path: tests/package-lock.json | |
| - name: Install Playwright dependencies | |
| run: | | |
| cd tests | |
| npm ci | |
| npx playwright install --with-deps chromium | |
| - name: Run full E2E test suite | |
| run: | | |
| cd tests | |
| npm run test:e2e | |
| env: | |
| BASE_URL: http://localhost:5556 | |
| CI: true | |
| - name: Upload Playwright HTML report | |
| if: always() | |
| uses: actions/upload-artifact@v4 | |
| with: | |
| name: playwright-full-report | |
| path: tests/playwright-report/ | |
| retention-days: 30 | |
| - name: Upload test results | |
| if: always() | |
| uses: actions/upload-artifact@v4 | |
| with: | |
| name: playwright-full-results | |
| path: tests/test-results/ | |
| retention-days: 30 | |
| - name: Upload test videos | |
| if: failure() | |
| uses: actions/upload-artifact@v4 | |
| with: | |
| name: test-videos | |
| path: tests/test-results/**/*.webm | |
| retention-days: 30 | |
| - name: Upload test screenshots | |
| if: failure() | |
| uses: actions/upload-artifact@v4 | |
| with: | |
| name: test-screenshots | |
| path: tests/test-results/**/*.png | |
| retention-days: 30 | |
| - name: Show environment logs on failure | |
| if: failure() | |
| run: | | |
| echo "=== Backend logs ===" | |
| docker logs geopulse-backend-e2e || true | |
| echo "" | |
| echo "=== Frontend logs ===" | |
| docker logs geopulse-ui-e2e || true | |
| echo "" | |
| echo "=== Database logs ===" | |
| docker logs geopulse-postgres-e2e || true | |
| - name: Cleanup | |
| if: always() | |
| run: | | |
| docker compose -f tests/docker-compose.e2e.yml down -v || echo "Cleanup failed but continuing" | |
| docker system prune -f || true | |
| # Stage 4: Infrastructure Validation | |
| helm-validation: | |
| name: Helm Chart Validation | |
| runs-on: ubuntu-latest | |
| timeout-minutes: 10 | |
| steps: | |
| - name: Checkout code | |
| uses: actions/checkout@v4 | |
| - name: Set up Helm | |
| uses: azure/setup-helm@v4 | |
| with: | |
| version: 'latest' | |
| - name: Lint Helm charts | |
| run: | | |
| helm lint helm/geopulse | |
| - name: Verify Helm templates | |
| run: | | |
| helm template test-release helm/geopulse --debug > /dev/null | |
| echo "✅ Helm templates are valid" | |
| docker-compose-validation: | |
| name: Docker Compose Validation | |
| runs-on: ubuntu-latest | |
| timeout-minutes: 10 | |
| steps: | |
| - name: Checkout code | |
| uses: actions/checkout@v4 | |
| - name: Validate docker-compose files | |
| run: | | |
| docker compose -f tests/docker-compose.e2e.yml config > /dev/null | |
| echo "✅ Docker Compose configuration is valid" | |
| # Success marker job | |
| validation-success: | |
| name: Pre-Release Validation Success | |
| runs-on: ubuntu-latest | |
| needs: | |
| - backend-full-tests | |
| - frontend-full-tests | |
| - full-e2e-tests | |
| - helm-validation | |
| - docker-compose-validation | |
| if: success() | |
| steps: | |
| - name: Mark validation successful | |
| run: | | |
| echo "✅ Pre-release validation passed for SHA: ${{ github.sha }}" | |
| echo "✅ Target version: ${{ inputs.target_version || 'not specified' }}" | |
| echo "" | |
| echo "Safe to create release tag!" | |
| echo "" | |
| echo "Next steps:" | |
| echo "1. git tag -a v${{ inputs.target_version || 'X.Y.Z' }} -m \"Release ${{ inputs.target_version || 'X.Y.Z' }}\"" | |
| echo "2. git push origin v${{ inputs.target_version || 'X.Y.Z' }}" | |
| # Summary job | |
| validation-summary: | |
| name: Pre-Release Summary | |
| runs-on: ubuntu-latest | |
| needs: | |
| - backend-full-tests | |
| - frontend-full-tests | |
| - full-e2e-tests | |
| - helm-validation | |
| - docker-compose-validation | |
| if: always() | |
| steps: | |
| - name: Check validation status | |
| run: | | |
| echo "=== Pre-Release Validation Summary ===" | |
| echo "Backend Tests: ${{ needs.backend-full-tests.result }}" | |
| echo "Frontend Tests: ${{ needs.frontend-full-tests.result }}" | |
| echo "E2E Tests: ${{ needs.full-e2e-tests.result }}" | |
| echo "Helm Validation: ${{ needs.helm-validation.result }}" | |
| echo "Docker Compose: ${{ needs.docker-compose-validation.result }}" | |
| echo "" | |
| if [[ "${{ needs.backend-full-tests.result }}" != "success" ]] || \ | |
| [[ "${{ needs.frontend-full-tests.result }}" != "success" ]] || \ | |
| [[ "${{ needs.full-e2e-tests.result }}" != "success" ]] || \ | |
| [[ "${{ needs.helm-validation.result }}" != "success" ]] || \ | |
| [[ "${{ needs.docker-compose-validation.result }}" != "success" ]]; then | |
| echo "❌ Pre-release validation FAILED" | |
| echo "" | |
| echo "DO NOT create release tag!" | |
| echo "Fix the issues and re-run this workflow." | |
| exit 1 | |
| fi | |
| echo "✅ All validation checks passed!" |