name: E2E Test Suite on: push: branches: [main, develop] pull_request: branches: [main, develop] schedule: # Nightly regression at 2:00 AM UTC - cron: '0 2 * * *' workflow_dispatch: inputs: suite: description: 'Test suite to run' required: false default: 'all' type: choice options: - all - smoke - critical - api - chaos # Cancel in-progress runs for the same branch concurrency: group: e2e-${{ github.ref }} cancel-in-progress: true env: NODE_VERSION: '20' PORT: 10000 jobs: # ============================================================ # Job 1: Smoke Tests (P0) - Every push, fast # ============================================================ smoke: name: Smoke Tests (P0) runs-on: ubuntu-latest timeout-minutes: 10 steps: - name: Checkout repository uses: actions/checkout@v4 - name: Setup Node.js uses: actions/setup-node@v4 with: node-version: ${{ env.NODE_VERSION }} cache: 'npm' - name: Install dependencies run: npm ci - name: Install Playwright browsers (Chromium only for smoke) run: npx playwright install chromium --with-deps - name: Build application run: npm run build - name: Start server run: npm run start & env: NODE_ENV: production - name: Wait for server to be ready run: npx wait-on http://localhost:${{ env.PORT }} --timeout 60000 - name: Run smoke tests (Chromium only) run: npx playwright test tests/e2e-smoke-suite.spec.ts --project=chromium --reporter=list - name: Upload smoke test results uses: actions/upload-artifact@v4 if: always() with: name: smoke-test-results-${{ github.run_number }} path: | playwright-report/ test-results/ retention-days: 7 # ============================================================ # Job 2: Critical User Journeys (P0) - Every push # ============================================================ critical-paths: name: Critical User Journeys runs-on: ubuntu-latest timeout-minutes: 20 needs: smoke steps: - name: Checkout repository uses: actions/checkout@v4 - name: Setup Node.js uses: actions/setup-node@v4 with: node-version: ${{ env.NODE_VERSION }} cache: 'npm' - name: Install dependencies run: npm ci - name: Install Playwright browsers run: npx playwright install chromium firefox --with-deps - name: Build application run: npm run build - name: Start server run: npm run start & env: NODE_ENV: production - name: Wait for server to be ready run: npx wait-on http://localhost:${{ env.PORT }} --timeout 60000 - name: Run critical path tests run: npx playwright test tests/e2e-critical-paths.spec.ts --project=chromium --project=firefox - name: Upload test results uses: actions/upload-artifact@v4 if: always() with: name: critical-paths-results-${{ github.run_number }} path: playwright-report/ retention-days: 14 # ============================================================ # Job 3: API Integration Tests - Every push # ============================================================ api-tests: name: API Integration Tests runs-on: ubuntu-latest timeout-minutes: 10 needs: smoke steps: - name: Checkout repository uses: actions/checkout@v4 - name: Setup Node.js uses: actions/setup-node@v4 with: node-version: ${{ env.NODE_VERSION }} cache: 'npm' - name: Install dependencies run: npm ci - name: Install Playwright (for API testing) run: npx playwright install chromium --with-deps - name: Build application run: npm run build - name: Start server run: npm run start & env: NODE_ENV: production - name: Wait for server run: npx wait-on http://localhost:${{ env.PORT }} --timeout 60000 - name: Run API integration tests run: npx playwright test tests/api-integration.spec.ts --project=chromium - name: Upload API test results uses: actions/upload-artifact@v4 if: always() with: name: api-test-results-${{ github.run_number }} path: playwright-report/ retention-days: 14 # ============================================================ # Job 4: Form Tests - PR and nightly # ============================================================ form-tests: name: Form Interaction Tests runs-on: ubuntu-latest timeout-minutes: 20 if: github.event_name == 'pull_request' || github.event_name == 'schedule' || github.event_name == 'workflow_dispatch' steps: - name: Checkout repository uses: actions/checkout@v4 - name: Setup Node.js uses: actions/setup-node@v4 with: node-version: ${{ env.NODE_VERSION }} cache: 'npm' - name: Install dependencies run: npm ci - name: Install Playwright browsers run: npx playwright install chromium --with-deps - name: Build application run: npm run build - name: Start server run: npm run start & env: NODE_ENV: production - name: Wait for server run: npx wait-on http://localhost:${{ env.PORT }} --timeout 60000 - name: Run contact form tests run: npx playwright test tests/contact-form.spec.ts tests/e2e-form-interactions.spec.ts --project=chromium - name: Run newsletter subscription tests run: npx playwright test tests/newsletter-subscription.spec.ts --project=chromium - name: Upload form test results uses: actions/upload-artifact@v4 if: always() with: name: form-test-results-${{ github.run_number }} path: playwright-report/ retention-days: 14 # ============================================================ # Job 5: Chaos / Destructive Tests - Nightly and manual # ============================================================ chaos-tests: name: Destructive & Chaos Tests runs-on: ubuntu-latest timeout-minutes: 30 if: github.event_name == 'schedule' || github.event_name == 'workflow_dispatch' steps: - name: Checkout repository uses: actions/checkout@v4 - name: Setup Node.js uses: actions/setup-node@v4 with: node-version: ${{ env.NODE_VERSION }} cache: 'npm' - name: Install dependencies run: npm ci - name: Install Playwright browsers run: npx playwright install chromium --with-deps - name: Build application run: npm run build - name: Start server run: npm run start & env: NODE_ENV: production - name: Wait for server run: npx wait-on http://localhost:${{ env.PORT }} --timeout 60000 - name: Run destructive/chaos tests run: npx playwright test tests/destructive-chaos.spec.ts --project=chromium continue-on-error: true # Chaos tests may find real bugs - name: Upload chaos test results uses: actions/upload-artifact@v4 if: always() with: name: chaos-test-results-${{ github.run_number }} path: playwright-report/ retention-days: 30 # ============================================================ # Job 6: Cross-Browser Regression - Nightly and manual # ============================================================ cross-browser: name: Cross-Browser Regression runs-on: ubuntu-latest timeout-minutes: 45 if: github.event_name == 'schedule' || github.event_name == 'workflow_dispatch' strategy: matrix: browser: [chromium, firefox, webkit] fail-fast: false # Continue testing other browsers even if one fails steps: - name: Checkout repository uses: actions/checkout@v4 - name: Setup Node.js uses: actions/setup-node@v4 with: node-version: ${{ env.NODE_VERSION }} cache: 'npm' - name: Install dependencies run: npm ci - name: Install Playwright browser (${{ matrix.browser }}) run: npx playwright install ${{ matrix.browser }} --with-deps - name: Build application run: npm run build - name: Start server run: npm run start & env: NODE_ENV: production - name: Wait for server run: npx wait-on http://localhost:${{ env.PORT }} --timeout 60000 - name: Run regression suite (${{ matrix.browser }}) run: | npx playwright test \ tests/e2e-smoke-suite.spec.ts \ tests/navigation.spec.ts \ tests/blog.spec.ts \ tests/portfolio.spec.ts \ --project=${{ matrix.browser }} - name: Upload cross-browser results uses: actions/upload-artifact@v4 if: always() with: name: cross-browser-${{ matrix.browser }}-${{ github.run_number }} path: playwright-report/ retention-days: 30 # ============================================================ # Job 7: Mobile Testing - Nightly # ============================================================ mobile-tests: name: Mobile Device Tests runs-on: ubuntu-latest timeout-minutes: 30 if: github.event_name == 'schedule' || github.event_name == 'workflow_dispatch' steps: - name: Checkout repository uses: actions/checkout@v4 - name: Setup Node.js uses: actions/setup-node@v4 with: node-version: ${{ env.NODE_VERSION }} cache: 'npm' - name: Install dependencies run: npm ci - name: Install Playwright browsers run: npx playwright install chromium webkit --with-deps - name: Build application run: npm run build - name: Start server run: npm run start & env: NODE_ENV: production - name: Wait for server run: npx wait-on http://localhost:${{ env.PORT }} --timeout 60000 - name: Run mobile tests run: npx playwright test --project='Mobile Chrome' --project='Mobile Safari' - name: Upload mobile test results uses: actions/upload-artifact@v4 if: always() with: name: mobile-test-results-${{ github.run_number }} path: playwright-report/ retention-days: 14 # ============================================================ # Job 8: Security Header Tests - PR and nightly # ============================================================ security-tests: name: Security Header Tests runs-on: ubuntu-latest timeout-minutes: 10 if: github.event_name == 'pull_request' || github.event_name == 'schedule' steps: - name: Checkout repository uses: actions/checkout@v4 - name: Setup Node.js uses: actions/setup-node@v4 with: node-version: ${{ env.NODE_VERSION }} cache: 'npm' - name: Install dependencies run: npm ci - name: Install Playwright run: npx playwright install chromium --with-deps - name: Build application run: npm run build - name: Start server run: npm run start & env: NODE_ENV: production - name: Wait for server run: npx wait-on http://localhost:${{ env.PORT }} --timeout 60000 - name: Run security header tests run: npx playwright test tests/security-headers.test.ts --project=chromium - name: Upload security test results uses: actions/upload-artifact@v4 if: always() with: name: security-test-results-${{ github.run_number }} path: playwright-report/ retention-days: 30 # ============================================================ # Job 9: Test Report Summary # ============================================================ report: name: Test Report Summary runs-on: ubuntu-latest needs: [smoke, critical-paths, api-tests] if: always() steps: - name: Download all test artifacts uses: actions/download-artifact@v4 with: path: all-results/ - name: Generate test summary run: | echo "## E2E Test Results Summary" >> $GITHUB_STEP_SUMMARY echo "" >> $GITHUB_STEP_SUMMARY echo "| Suite | Status |" >> $GITHUB_STEP_SUMMARY echo "|-------|--------|" >> $GITHUB_STEP_SUMMARY echo "| Smoke Tests | ${{ needs.smoke.result }} |" >> $GITHUB_STEP_SUMMARY echo "| Critical Paths | ${{ needs.critical-paths.result }} |" >> $GITHUB_STEP_SUMMARY echo "| API Integration | ${{ needs.api-tests.result }} |" >> $GITHUB_STEP_SUMMARY echo "" >> $GITHUB_STEP_SUMMARY echo "**Run:** #${{ github.run_number }}" >> $GITHUB_STEP_SUMMARY echo "**Branch:** ${{ github.ref_name }}" >> $GITHUB_STEP_SUMMARY echo "**Commit:** ${{ github.sha }}" >> $GITHUB_STEP_SUMMARY