build(deps): bump the prod-cargo-major-dependencies group across 1 directory with 5 updates #2495
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: CI check | |
| on: | |
| pull_request: | |
| branches: | |
| - main | |
| - "[0-9]+.[0-9]+.x" | |
| paths-ignore: | |
| - "docs/**" | |
| types: | |
| - opened | |
| - reopened | |
| - synchronize | |
| - ready_for_review | |
| pull_request_review: | |
| types: | |
| - submitted | |
| push: | |
| branches: | |
| - main | |
| - trigger-ci-workflow | |
| paths-ignore: | |
| - "docs/**" | |
| workflow_dispatch: | |
| permissions: | |
| contents: write | |
| actions: read | |
| pull-requests: write | |
| env: | |
| CARGO_TERM_COLOR: always | |
| RUST_BACKTRACE: 1 | |
| RUST_LOG: debug | |
| concurrency: | |
| group: ci-${{ github.event.pull_request.number || github.ref }} | |
| cancel-in-progress: true | |
| defaults: | |
| run: | |
| shell: bash | |
| jobs: | |
| changesets: | |
| if: ${{ github.event_name != 'pull_request' || (!startsWith(github.head_ref, | |
| 'release/') && !github.event.pull_request.draft) }} | |
| uses: ./.github/workflows/changesets.yaml | |
| name: Changesets | |
| typos: | |
| name: Typos | |
| if: github.event.pull_request.draft != true && (github.event_name != | |
| 'pull_request' || !startsWith(github.head_ref, 'release/')) | |
| runs-on: ${{ github.repository == 'oxy-hq/oxy-internal' && 'ubuntu-slim' || | |
| 'ubuntu-latest' }} | |
| steps: | |
| - name: Checkout | |
| uses: actions/checkout@v6 | |
| - name: Check typos | |
| uses: crate-ci/typos@v1.45.1 | |
| fmt-web: | |
| name: Format web | |
| needs: [ changesets, typos ] | |
| concurrency: | |
| group: fmt-web-${{ github.event.pull_request.number || github.ref }} | |
| cancel-in-progress: true | |
| if: needs.changesets.outputs.web-app == 'true' | |
| runs-on: ${{ github.repository == 'oxy-hq/oxy-internal' && 'ubuntu-slim' || | |
| 'ubuntu-latest' }} | |
| steps: | |
| - uses: actions/checkout@v6 | |
| with: | |
| fetch-depth: 0 | |
| - uses: pnpm/action-setup@v5 | |
| with: | |
| run_install: false | |
| - name: Install Node.js | |
| uses: actions/setup-node@v6 | |
| id: setup-node | |
| with: | |
| node-version: 24.x | |
| cache: "pnpm" | |
| - name: Run pnpm install | |
| run: pnpm install --frozen-lockfile --prefer-offline | |
| - name: Run lint-staged | |
| shell: bash | |
| run: | | |
| if [[ "${{ github.event_name }}" == "pull_request" ]]; then | |
| pnpm lint-staged --diff="origin/${{ github.base_ref }}...origin/${{ github.head_ref }}" | |
| elif [[ "${{ github.event_name }}" == "push" ]]; then | |
| pnpm lint-staged --diff="${{ github.event.before }}...${{ github.event.after }}" | |
| fi | |
| build-web: | |
| name: Build web | |
| needs: [ changesets, typos ] | |
| concurrency: | |
| group: build-web-${{ github.event.pull_request.number || github.ref }} | |
| cancel-in-progress: true | |
| if: needs.changesets.outputs.web-app == 'true' | |
| runs-on: "ubuntu-latest" | |
| steps: | |
| - uses: actions/checkout@v6 | |
| with: | |
| fetch-depth: 0 | |
| - uses: pnpm/action-setup@v5 | |
| with: | |
| run_install: false | |
| - name: Install Node.js | |
| uses: actions/setup-node@v6 | |
| id: setup-node | |
| with: | |
| node-version: 24.x | |
| cache: "pnpm" | |
| # Cache TypeScript build info for incremental compilation | |
| # Key on tsconfig only — tsbuildinfo handles incremental source changes internally | |
| - name: Cache TypeScript build info | |
| uses: actions/cache@v5 | |
| with: | |
| path: | | |
| web-app/tsconfig.app.tsbuildinfo | |
| web-app/tsconfig.node.tsbuildinfo | |
| key: typescript-${{ runner.os }}-${{ hashFiles('web-app/tsconfig*.json') }} | |
| restore-keys: | | |
| typescript-${{ runner.os }}- | |
| # Cache Vite pre-bundled deps (only invalidates when dependencies change, not source) | |
| - name: Cache Vite | |
| uses: actions/cache@v5 | |
| with: | |
| path: | | |
| web-app/node_modules/.vite | |
| web-app/.vite | |
| key: vite-${{ runner.os }}-${{ hashFiles('**/pnpm-lock.yaml', | |
| 'web-app/vite.config.*') }} | |
| restore-keys: | | |
| vite-${{ runner.os }}- | |
| # Cache Turbo for monorepo builds | |
| - name: Cache Turbo | |
| uses: actions/cache@v5 | |
| with: | |
| path: .turbo | |
| key: turbo-${{ runner.os }}-${{ github.sha }} | |
| restore-keys: | | |
| turbo-${{ runner.os }}- | |
| - name: Install dependencies & Build web-app | |
| env: | |
| NODE_OPTIONS: "--max-old-space-size=8192" | |
| # Enable Turbo remote caching (optional - configure if using Turbo remote cache) | |
| # TURBO_TOKEN: ${{ secrets.TURBO_TOKEN }} | |
| # TURBO_TEAM: ${{ secrets.TURBO_TEAM }} | |
| run: | | |
| # Install with frozen lockfile for reproducibility | |
| pnpm install --frozen-lockfile --prefer-offline | |
| # Build using Turbo for better caching | |
| pnpm build | |
| cargo-check-and-test: | |
| concurrency: | |
| group: cargo-check-and-test-${{ matrix.task }}-${{ | |
| github.event.pull_request.number || github.ref }} | |
| cancel-in-progress: true | |
| needs: [ changesets, typos ] | |
| if: needs.changesets.outputs.oxy == 'true' | |
| name: Format cargo, check & test (${{ matrix.task }}) | |
| runs-on: "ubuntu-latest" | |
| env: | |
| OPENAI_API_KEY: ${{ secrets.OPENAI_API_KEY }} | |
| BIGQUERY_SAMPLE_KEY: ${{ secrets.BIGQUERY_SAMPLE_KEY }} | |
| GEMINI_API_KEY: "empty" | |
| ANTHROPIC_API_KEY: ${{ secrets.ANTHROPIC_API_KEY }} | |
| DOMO_DEVELOPER_TOKEN: "empty" | |
| # line-tables-only debug: sufficient for llvm-cov, ~60% smaller than default debug = 2 | |
| CARGO_PROFILE_DEV_DEBUG: "1" | |
| strategy: | |
| fail-fast: true | |
| matrix: | |
| task: [ check, test ] | |
| services: | |
| postgres: | |
| image: postgres:18-alpine | |
| env: | |
| POSTGRES_USER: admin | |
| POSTGRES_PASSWORD: password | |
| POSTGRES_DB: default | |
| ports: | |
| - 5432:5432 | |
| options: >- | |
| --health-cmd "pg_isready -U admin -d default" --health-interval 10s | |
| --health-timeout 5s --health-retries 5 | |
| steps: | |
| # - name: Free disk space | |
| # if: matrix.task == 'test' | |
| # uses: jlumbroso/free-disk-space@main | |
| # with: | |
| # tool-cache: false | |
| # android: true | |
| # dotnet: true | |
| # haskell: true | |
| # large-packages: true | |
| # docker-images: true | |
| # swap-storage: true | |
| - uses: actions/checkout@v6 | |
| with: | |
| fetch-depth: 0 | |
| - name: Collect Workflow Telemetry | |
| uses: catchpoint/workflow-telemetry-action@v2 | |
| with: | |
| theme: dark | |
| metric_frequency: 3 | |
| comment_on_pr: false | |
| - uses: rui314/setup-mold@v1 | |
| if: runner.os == 'Linux' | |
| with: | |
| make-default: true | |
| - name: Prep Rust | |
| uses: dtolnay/rust-toolchain@stable | |
| with: | |
| components: clippy, rustfmt | |
| - name: Install cargo tools | |
| uses: taiki-e/install-action@v2 | |
| with: | |
| tool: nextest | |
| - name: Prep cargo cache | |
| uses: Swatinem/rust-cache@v2 | |
| with: | |
| shared-key: ${{ matrix.task }} | |
| # protobuf is required by lance https://github.com/lancedb/lance/issues/3073 | |
| - name: Install Protoc | |
| uses: arduino/setup-protoc@v3 | |
| with: | |
| repo-token: ${{ secrets.GITHUB_TOKEN }} | |
| - name: Install PostgreSQL client | |
| run: | | |
| sudo apt-get update | |
| sudo apt-get install -y postgresql-client | |
| - name: Wait for Postgres | |
| run: | | |
| until pg_isready -h localhost -p 5432 -U admin; do | |
| echo "Waiting for Postgres..." | |
| sleep 2 | |
| done | |
| echo "Postgres is ready!" | |
| env: | |
| PGPASSWORD: password | |
| - name: Run task | |
| env: | |
| OXY_DATABASE_URL: "postgresql://admin:password@localhost:5432/default" | |
| OXY_BIN: "${{ github.workspace }}/target/ci/oxy" | |
| run: | | |
| if [[ "${{ matrix.task }}" == "check" ]]; then | |
| cargo clippy --profile ci --verbose --workspace --fix | |
| elif [[ "${{ matrix.task }}" == "test" ]]; then | |
| touch examples/bigquery-sample.key | |
| echo $BIGQUERY_SAMPLE_KEY > examples/bigquery-sample.key | |
| cargo build --profile ci | |
| ./target/ci/oxy migrate | |
| # Run tests (no coverage instrumentation) | |
| cargo nextest run --cargo-profile ci --workspace --no-fail-fast | |
| ./target/ci/oxy gen-config-schema --check | |
| fi | |
| - name: Upload oxy binary artifact | |
| if: matrix.task == 'test' | |
| uses: actions/upload-artifact@v7 | |
| with: | |
| name: oxy-binary-ci | |
| path: target/ci/oxy | |
| retention-days: 1 | |
| smoke-test-enterprise: | |
| name: Smoke test (oxy start --enterprise) | |
| needs: [ changesets, typos, cargo-check-and-test ] | |
| concurrency: | |
| group: smoke-test-enterprise-${{ github.event.pull_request.number || github.ref | |
| }} | |
| cancel-in-progress: true | |
| if: github.repository == 'oxy-hq/oxy-internal' && needs.changesets.outputs.oxy | |
| == 'true' | |
| runs-on: ubuntu-latest | |
| timeout-minutes: 20 | |
| env: | |
| OPENAI_API_KEY: ${{ secrets.OPENAI_API_KEY }} | |
| BIGQUERY_SAMPLE_KEY: ${{ secrets.BIGQUERY_SAMPLE_KEY }} | |
| GEMINI_API_KEY: "empty" | |
| ANTHROPIC_API_KEY: ${{ secrets.ANTHROPIC_API_KEY }} | |
| DOMO_DEVELOPER_TOKEN: "empty" | |
| OXY_LOG_LEVEL: debug | |
| steps: | |
| - uses: actions/checkout@v6 | |
| - uses: gacts/install-hurl@v1 | |
| - name: Download oxy binary | |
| uses: actions/download-artifact@v8 | |
| with: | |
| name: oxy-binary-ci | |
| path: ./bin | |
| - name: Make binary executable | |
| run: | | |
| chmod +x ./bin/oxy | |
| echo "$GITHUB_WORKSPACE/bin" >> $GITHUB_PATH | |
| - name: Start oxy | |
| working-directory: examples | |
| run: | | |
| oxy start --enterprise --clean & | |
| echo "OXY_PID=$!" >> $GITHUB_ENV | |
| # Wait for server (max 10 min) | |
| for i in {1..120}; do | |
| curl -sf --max-time 10 http://localhost:3000/api/health > /dev/null && break | |
| [ $i -eq 120 ] && { docker ps -a; docker logs oxy-postgres 2>&1 | tail -50; exit 1; } | |
| sleep 5 | |
| done | |
| - name: Verify containers | |
| run: | | |
| for c in oxy-postgres; do | |
| docker ps --format "{{.Names}}" | grep -q "^${c}$" || { echo "::error::$c not running"; exit 1; } | |
| done | |
| - name: Smoke test - CLI | |
| working-directory: examples | |
| run: | | |
| oxy status | |
| oxy sync -o | |
| oxy build | |
| oxy validate | |
| oxy run data_fruit/example_food_calories.sql | |
| - name: Smoke test - HTTP (Hurl) | |
| run: | | |
| set -o pipefail | |
| echo '## Smoke Test Results' >> $GITHUB_STEP_SUMMARY | |
| hurl --test tests/smoke/smoke.hurl 2>&1 | tee -a $GITHUB_STEP_SUMMARY | |
| - name: Test restart (data persistence) | |
| working-directory: examples | |
| run: | | |
| kill -TERM $OXY_PID 2>/dev/null || true | |
| for i in {1..30}; do kill -0 $OXY_PID 2>/dev/null || break; sleep 1; done | |
| sleep 2 | |
| docker volume ls | grep -q oxy || { echo "::error::Volumes not persisted"; exit 1; } | |
| oxy start --enterprise & | |
| echo "OXY_PID=$!" >> $GITHUB_ENV | |
| for i in {1..60}; do | |
| curl -sf --max-time 10 http://localhost:3000/api/health > /dev/null && break | |
| [ $i -eq 60 ] && { docker ps -a; exit 1; } | |
| sleep 5 | |
| done | |
| - name: Verify restart | |
| run: | | |
| for c in oxy-postgres; do | |
| docker ps --format "{{.Names}}" | grep -q "^${c}$" || { echo "::error::$c not running after restart"; exit 1; } | |
| done | |
| set -o pipefail | |
| hurl --test tests/smoke/smoke.hurl 2>&1 | tee -a $GITHUB_STEP_SUMMARY | |
| - name: Cleanup | |
| if: always() | |
| run: | | |
| kill -TERM $OXY_PID 2>/dev/null || true; sleep 3 | |
| docker rm -f oxy-postgres 2>/dev/null || true | |
| e2e-tests: | |
| name: E2E Tests (Playwright) | |
| needs: [ changesets, typos, cargo-check-and-test ] | |
| # 💰 COST SAVING: Only run on approved PRs, pushes to oxy-hq/oxy main, or manual trigger | |
| if: | | |
| needs.changesets.outputs.oxy == 'true' && ( | |
| github.event_name == 'workflow_dispatch' || | |
| ( | |
| github.event_name == 'push' && | |
| (needs.changesets.outputs.web-app == 'true' || needs.changesets.outputs.oxy == 'true') | |
| ) || | |
| ( | |
| github.event_name == 'pull_request_review' && | |
| github.event.review.state == 'approved' && | |
| (needs.changesets.outputs.web-app == 'true' || needs.changesets.outputs.oxy == 'true') | |
| ) | |
| ) | |
| runs-on: ubuntu-latest | |
| concurrency: | |
| group: e2e-${{ github.event.pull_request.number || github.ref }} | |
| cancel-in-progress: true | |
| env: | |
| OXY_STATE_DIR: ${{ github.workspace }}/examples | |
| OXY_DATABASE_URL: postgresql://admin:password@localhost:5432/default | |
| OPENAI_API_KEY: ${{ secrets.OPENAI_API_KEY }} | |
| BIGQUERY_SAMPLE_KEY: ${{ secrets.BIGQUERY_SAMPLE_KEY }} | |
| GEMINI_API_KEY: "empty" | |
| ANTHROPIC_API_KEY: ${{ secrets.ANTHROPIC_API_KEY }} | |
| DOMO_DEVELOPER_TOKEN: "empty" | |
| services: | |
| postgres: | |
| image: postgres:18-alpine | |
| env: | |
| POSTGRES_USER: admin | |
| POSTGRES_PASSWORD: password | |
| POSTGRES_DB: default | |
| ports: | |
| - 5432:5432 | |
| options: >- | |
| --health-cmd "pg_isready -U admin -d default" --health-interval 10s | |
| --health-timeout 5s --health-retries 5 | |
| steps: | |
| - name: Checkout code | |
| uses: actions/checkout@v6 | |
| with: | |
| fetch-depth: 0 | |
| - name: Collect Workflow Telemetry | |
| uses: catchpoint/workflow-telemetry-action@v2 | |
| with: | |
| theme: dark | |
| metric_frequency: 3 | |
| comment_on_pr: false | |
| # Download pre-built binary (shared artifact!) | |
| - name: Download oxy binary | |
| uses: actions/download-artifact@v8 | |
| with: | |
| name: oxy-binary-ci | |
| path: ./bin | |
| - name: Make binary executable | |
| run: | | |
| chmod +x ./bin/oxy | |
| echo "$GITHUB_WORKSPACE/bin" >> $GITHUB_PATH | |
| # Setup Node.js and pnpm for web-app tests | |
| - name: Setup pnpm | |
| uses: pnpm/action-setup@v5 | |
| with: | |
| run_install: false | |
| - name: Setup Node.js | |
| uses: actions/setup-node@v6 | |
| with: | |
| node-version: 24.x | |
| cache: "pnpm" | |
| # Cache Playwright browsers - significant time saver! | |
| - name: Cache Playwright browsers | |
| uses: actions/cache@v5 | |
| id: playwright-cache | |
| with: | |
| path: ~/.cache/ms-playwright | |
| key: playwright-${{ runner.os }}-${{ hashFiles('pnpm-lock.yaml') }} | |
| restore-keys: | | |
| playwright-${{ runner.os }}- | |
| # Cache Turbo for monorepo builds | |
| - name: Cache Turbo | |
| uses: actions/cache@v5 | |
| with: | |
| path: .turbo | |
| key: turbo-${{ runner.os }}-${{ github.sha }} | |
| restore-keys: | | |
| turbo-${{ runner.os }}- | |
| - name: Install dependencies | |
| env: | |
| NODE_OPTIONS: "--max-old-space-size=8192" | |
| run: pnpm install --frozen-lockfile --prefer-offline | |
| - name: Install Playwright browsers | |
| if: steps.playwright-cache.outputs.cache-hit != 'true' | |
| working-directory: web-app | |
| run: pnpm exec playwright install --with-deps chromium | |
| - name: Install Playwright system dependencies only | |
| if: steps.playwright-cache.outputs.cache-hit == 'true' | |
| working-directory: web-app | |
| run: pnpm exec playwright install-deps chromium | |
| # Setup BigQuery credentials if needed | |
| - name: Setup BigQuery credentials | |
| if: env.BIGQUERY_SAMPLE_KEY | |
| run: | | |
| touch examples/bigquery-sample.key | |
| echo "$BIGQUERY_SAMPLE_KEY" > examples/bigquery-sample.key | |
| # Run consistency tests using pre-built binary | |
| - name: Run consistency tests | |
| working-directory: demo_project | |
| run: | | |
| echo "Running consistency tests for default.agent.yml..." | |
| oxy sync -o | |
| oxy build | |
| oxy test default.agent.yml \ | |
| --format json \ | |
| --min-accuracy 0.8 \ | |
| --threshold-mode average \ | |
| | tee consistency-test-results.json | |
| echo "Consistency tests completed successfully!" | |
| - name: Upload consistency test results | |
| uses: actions/upload-artifact@v7 | |
| if: always() | |
| with: | |
| name: consistency-test-results | |
| path: demo_project/consistency-test-results.json | |
| retention-days: 1 | |
| - name: Show consistency test summary | |
| if: always() | |
| run: | | |
| if [ -f demo_project/consistency-test-results.json ]; then | |
| echo "=== Consistency Test Results ===" | |
| echo "" | |
| cat demo_project/consistency-test-results.json | |
| echo "" | |
| echo "Full results available in artifacts: consistency-test-results" | |
| else | |
| echo "No consistency test results file found" | |
| fi | |
| # Start backend server in background | |
| - name: Start Oxy backend server | |
| working-directory: examples | |
| run: | | |
| # Using pre-built binary - no compilation needed! | |
| nohup oxy serve > ../oxy-server.log 2>&1 & | |
| echo $! > /tmp/oxy-server.pid | |
| echo "Backend server started with PID: $(cat /tmp/oxy-server.pid)" | |
| # Wait for backend to be ready | |
| - name: Wait for backend server | |
| id: wait-backend | |
| run: | | |
| echo "Waiting for backend server to be ready..." | |
| timeout 10 bash -c 'until curl -k -s http://localhost:3000/api/health > /dev/null 2>&1; do echo "Waiting for health endpoint..."; sleep 2; done' | |
| echo "Backend health endpoint is responding!" | |
| # Give the backend additional time to scan and load apps from the examples directory | |
| echo "Waiting for backend to initialize apps..." | |
| sleep 10 | |
| echo "Backend server should now be fully ready!" | |
| - name: Show backend server logs if wait failed | |
| if: steps.wait-backend.outcome == 'failure' | |
| run: | | |
| echo "=== Backend Server Logs (from wait failure) ===" | |
| if [ -f oxy-server.log ]; then | |
| tail -n 200 oxy-server.log || true | |
| else | |
| echo "No server logs found at oxy-server.log" | |
| ls -la || true | |
| fi | |
| # Run E2E tests | |
| - name: Run Playwright tests | |
| id: run-playwright | |
| timeout-minutes: 20 | |
| env: | |
| PLAYWRIGHT_WORKERS: 2 | |
| run: | | |
| cd web-app | |
| pnpm test:e2e | |
| # Upload test results and traces | |
| - name: Upload Playwright report | |
| uses: actions/upload-artifact@v7 | |
| if: always() | |
| with: | |
| name: playwright-report | |
| path: web-app/playwright-report/ | |
| retention-days: 1 | |
| - name: Upload test results with traces | |
| uses: actions/upload-artifact@v7 | |
| if: failure() | |
| with: | |
| name: playwright-results | |
| path: web-app/test-results/ | |
| retention-days: 1 | |
| - name: Show trace instructions | |
| if: failure() | |
| run: | | |
| echo "━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━" | |
| echo "📹 Test traces, screenshots, and videos have been captured!" | |
| echo "━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━" | |
| echo "" | |
| echo "To view the test traces:" | |
| echo " 1. Download the 'playwright-results' artifact from this workflow run" | |
| echo " 2. Extract the zip file" | |
| echo " 3. Run: npx playwright show-trace path/to/trace.zip" | |
| echo "" | |
| echo "The trace viewer will open in your browser with:" | |
| echo " • Full test execution timeline" | |
| echo " • Screenshots at each step" | |
| echo " • Network requests/responses" | |
| echo " • Console logs" | |
| echo " • DOM snapshots" | |
| echo "" | |
| echo "━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━" | |
| # Cleanup | |
| - name: Stop backend server | |
| if: always() | |
| run: | | |
| if [ -f /tmp/oxy-server.pid ]; then | |
| kill $(cat /tmp/oxy-server.pid) || true | |
| echo "Backend server stopped" | |
| fi | |
| - name: Show server logs | |
| if: failure() | |
| run: | | |
| echo "=== Backend Server Logs ===" | |
| if [ -f oxy-server.log ]; then | |
| tail -n 200 oxy-server.log | |
| else | |
| echo "No server logs found at oxy-server.log" | |
| fi | |
| echo "" | |
| echo "=== Checking if server process is still running ===" | |
| if [ -f /tmp/oxy-server.pid ]; then | |
| ps -p $(cat /tmp/oxy-server.pid) || echo "Server process not running" | |
| fi | |
| # Send Slack notification on push failure to oxy main | |
| - name: Find Slack user | |
| if: failure() && steps.run-playwright.outcome == 'failure' && github.event_name | |
| == 'push' && github.repository == 'oxy-hq/oxy' | |
| id: find-slack-user | |
| uses: scribd/find-slack-user-action@v1 | |
| continue-on-error: true | |
| with: | |
| slack-token: ${{ secrets.SLACK_BOT_TOKEN }} | |
| email: ${{ github.event.head_commit.author.email }} | |
| - name: Prepare Slack notification message | |
| if: failure() && steps.run-playwright.outcome == 'failure' && github.event_name | |
| == 'push' && github.repository == 'oxy-hq/oxy' | |
| id: prepare-slack | |
| run: | | |
| GITHUB_USER="${{ github.event.head_commit.author.username || github.actor }}" | |
| AUTHOR_NAME="${{ github.event.head_commit.author.name || github.actor }}" | |
| SLACK_MEMBER_ID="${{ steps.find-slack-user.outputs.member-id }}" | |
| echo "GitHub user: $GITHUB_USER" | |
| echo "Slack member ID: ${SLACK_MEMBER_ID:-not found}" | |
| if [ -n "$SLACK_MEMBER_ID" ]; then | |
| echo "✓ Found Slack user for $GITHUB_USER" | |
| AUTHOR_TEXT="*Author:*\n<@${SLACK_MEMBER_ID}> (${AUTHOR_NAME})" | |
| MENTION_TEXT="<@${SLACK_MEMBER_ID}> - E2E tests failed on your commit" | |
| else | |
| echo "✗ No Slack user found for $GITHUB_USER" | |
| AUTHOR_TEXT="*Author:*\n${AUTHOR_NAME} (@${GITHUB_USER})" | |
| MENTION_TEXT="" | |
| fi | |
| # Export for next step | |
| echo "author_text<<EOF" >> $GITHUB_OUTPUT | |
| echo "$AUTHOR_TEXT" >> $GITHUB_OUTPUT | |
| echo "EOF" >> $GITHUB_OUTPUT | |
| echo "mention_text<<EOF" >> $GITHUB_OUTPUT | |
| echo "$MENTION_TEXT" >> $GITHUB_OUTPUT | |
| echo "EOF" >> $GITHUB_OUTPUT | |
| - name: Send Slack notification | |
| if: failure() && steps.run-playwright.outcome == 'failure' && github.event_name | |
| == 'push' && github.repository == 'oxy-hq/oxy' | |
| uses: slackapi/slack-github-action@v3.0.1 | |
| with: | |
| method: chat.postMessage | |
| token: ${{ secrets.SLACK_BOT_TOKEN }} | |
| payload: | | |
| { | |
| "channel": "eng-events-e2e", | |
| "text": "🚨 E2E Tests Failed on oxy Main Branch - ${{ steps.prepare-slack.outputs.mention_text || github.event.head_commit.author.name }}", | |
| "blocks": [ | |
| { | |
| "type": "header", | |
| "text": { | |
| "type": "plain_text", | |
| "text": "🚨 E2E Tests Failed on oxy Main Branch" | |
| } | |
| }, | |
| ${{ steps.prepare-slack.outputs.mention_text && format('{{ "type": "section", "text": {{ "type": "mrkdwn", "text": "{0}" }} }},', steps.prepare-slack.outputs.mention_text) || '' }} | |
| { | |
| "type": "section", | |
| "fields": [ | |
| { | |
| "type": "mrkdwn", | |
| "text": "*Repository:*\noxy-hq/oxy" | |
| }, | |
| { | |
| "type": "mrkdwn", | |
| "text": "*Branch:*\nmain" | |
| }, | |
| { | |
| "type": "mrkdwn", | |
| "text": "*Commit:*\n<${{ github.event.head_commit.url }}|${{ github.sha }}>" | |
| }, | |
| { | |
| "type": "mrkdwn", | |
| "text": "${{ steps.prepare-slack.outputs.author_text }}" | |
| } | |
| ] | |
| }, | |
| { | |
| "type": "actions", | |
| "elements": [ | |
| { | |
| "type": "button", | |
| "text": { | |
| "type": "plain_text", | |
| "text": "View Workflow Run" | |
| }, | |
| "url": "${{ github.server_url }}/${{ github.repository }}/actions/runs/${{ github.run_id }}" | |
| }, | |
| { | |
| "type": "button", | |
| "text": { | |
| "type": "plain_text", | |
| "text": "View Commit" | |
| }, | |
| "url": "${{ github.event.head_commit.url }}" | |
| } | |
| ] | |
| } | |
| ] | |
| } |