| 123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198 |
- # GitHub Actions CI/CD Pipeline for Test Execution
- # Generated by BMad TEA Agent - Test Architect Module
- # Optimized for: Playwright/Cypress, Parallel Sharding, Burn-In Loop
- name: Test Pipeline
- on:
- push:
- branches: [main, develop]
- pull_request:
- branches: [main, develop]
- schedule:
- # Weekly burn-in on Sundays at 2 AM UTC
- - cron: "0 2 * * 0"
- concurrency:
- group: ${{ github.workflow }}-${{ github.ref }}
- cancel-in-progress: true
- jobs:
- # Lint stage - Code quality checks
- lint:
- name: Lint
- runs-on: ubuntu-latest
- timeout-minutes: 5
- steps:
- - uses: actions/checkout@v4
- - name: Determine Node version
- id: node-version
- run: |
- if [ -f .nvmrc ]; then
- echo "value=$(cat .nvmrc)" >> "$GITHUB_OUTPUT"
- echo "Using Node from .nvmrc"
- else
- echo "value=24" >> "$GITHUB_OUTPUT"
- echo "Using default Node 24 (current LTS)"
- fi
- - name: Setup Node.js
- uses: actions/setup-node@v4
- with:
- node-version: ${{ steps.node-version.outputs.value }}
- cache: "npm"
- - name: Install dependencies
- run: npm ci
- - name: Run linter
- run: npm run lint
- # Test stage - Parallel execution with sharding
- test:
- name: Test (Shard ${{ matrix.shard }})
- runs-on: ubuntu-latest
- timeout-minutes: 30
- needs: lint
- strategy:
- fail-fast: false
- matrix:
- shard: [1, 2, 3, 4]
- steps:
- - uses: actions/checkout@v4
- - name: Determine Node version
- id: node-version
- run: |
- if [ -f .nvmrc ]; then
- echo "value=$(cat .nvmrc)" >> "$GITHUB_OUTPUT"
- echo "Using Node from .nvmrc"
- else
- echo "value=22" >> "$GITHUB_OUTPUT"
- echo "Using default Node 22 (current LTS)"
- fi
- - name: Setup Node.js
- uses: actions/setup-node@v4
- with:
- node-version: ${{ steps.node-version.outputs.value }}
- cache: "npm"
- - name: Cache Playwright browsers
- uses: actions/cache@v4
- with:
- path: ~/.cache/ms-playwright
- key: ${{ runner.os }}-playwright-${{ hashFiles('**/package-lock.json') }}
- restore-keys: |
- ${{ runner.os }}-playwright-
- - name: Install dependencies
- run: npm ci
- - name: Install Playwright browsers
- run: npx playwright install --with-deps chromium
- - name: Run tests (shard ${{ matrix.shard }}/4)
- run: npm run test:e2e -- --shard=${{ matrix.shard }}/4
- - name: Upload test results
- if: failure()
- uses: actions/upload-artifact@v4
- with:
- name: test-results-${{ matrix.shard }}
- path: |
- test-results/
- playwright-report/
- retention-days: 30
- # Burn-in stage - Flaky test detection
- burn-in:
- name: Burn-In (Flaky Detection)
- runs-on: ubuntu-latest
- timeout-minutes: 60
- needs: test
- # Only run burn-in on PRs to main/develop or on schedule
- if: github.event_name == 'pull_request' || github.event_name == 'schedule'
- steps:
- - uses: actions/checkout@v4
- - name: Determine Node version
- id: node-version
- run: |
- if [ -f .nvmrc ]; then
- echo "value=$(cat .nvmrc)" >> "$GITHUB_OUTPUT"
- echo "Using Node from .nvmrc"
- else
- echo "value=22" >> "$GITHUB_OUTPUT"
- echo "Using default Node 22 (current LTS)"
- fi
- - name: Setup Node.js
- uses: actions/setup-node@v4
- with:
- node-version: ${{ steps.node-version.outputs.value }}
- cache: "npm"
- - name: Cache Playwright browsers
- uses: actions/cache@v4
- with:
- path: ~/.cache/ms-playwright
- key: ${{ runner.os }}-playwright-${{ hashFiles('**/package-lock.json') }}
- - name: Install dependencies
- run: npm ci
- - name: Install Playwright browsers
- run: npx playwright install --with-deps chromium
- - name: Run burn-in loop (10 iterations)
- run: |
- echo "🔥 Starting burn-in loop - detecting flaky tests"
- for i in {1..10}; do
- echo "━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━"
- echo "🔥 Burn-in iteration $i/10"
- echo "━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━"
- npm run test:e2e || exit 1
- done
- echo "✅ Burn-in complete - no flaky tests detected"
- - name: Upload burn-in failure artifacts
- if: failure()
- uses: actions/upload-artifact@v4
- with:
- name: burn-in-failures
- path: |
- test-results/
- playwright-report/
- retention-days: 30
- # Report stage - Aggregate and publish results
- report:
- name: Test Report
- runs-on: ubuntu-latest
- needs: [test, burn-in]
- if: always()
- steps:
- - name: Download all artifacts
- uses: actions/download-artifact@v4
- with:
- path: artifacts
- - name: Generate summary
- run: |
- echo "## Test Execution Summary" >> $GITHUB_STEP_SUMMARY
- echo "" >> $GITHUB_STEP_SUMMARY
- echo "- **Status**: ${{ needs.test.result }}" >> $GITHUB_STEP_SUMMARY
- echo "- **Burn-in**: ${{ needs.burn-in.result }}" >> $GITHUB_STEP_SUMMARY
- echo "- **Shards**: 4" >> $GITHUB_STEP_SUMMARY
- echo "" >> $GITHUB_STEP_SUMMARY
- if [ "${{ needs.burn-in.result }}" == "failure" ]; then
- echo "⚠️ **Flaky tests detected** - Review burn-in artifacts" >> $GITHUB_STEP_SUMMARY
- fi
|