mirror of
https://github.com/supabase/supabase.git
synced 2026-06-29 11:57:37 -04:00
333097caa8
## Problem
The Selfhosted Studio E2E Tests workflow fails on community (fork) PRs
at the **configure aws credentials** step with:
> Credentials could not be loaded, please check your action inputs:
Could not load credentials from any providers
GitHub does not pass repository secrets to workflows triggered by
`pull_request` from a fork (a deliberate security measure). So on fork
PRs:
- `${{ secrets.PROD_AWS_ROLE }}` evaluates to an empty string, and
- the OIDC `id-token` token isn't available either,
so `aws-actions/configure-aws-credentials` falls through its entire
provider chain and errors out, failing the job.
## Fix
Guard the AWS credential + ECR login steps with
`!github.event.pull_request.head.repo.fork`, the same pattern already
used by the Playwright comment step in this workflow. These steps only
exist to authenticate with AWS ECR to avoid Docker pull rate limiting,
so on fork PRs we simply skip them and pull from `public.ecr.aws`
anonymously, letting the e2e tests run instead of erroring out.
<!-- This is an auto-generated comment: release notes by coderabbit.ai
-->
## Summary by CodeRabbit
* **Chores**
* Improved CI/CD pipeline security configuration to better safeguard
authentication credentials during external contributions.
<!-- end of auto-generated comment: release notes by coderabbit.ai -->
194 lines
7.1 KiB
YAML
194 lines
7.1 KiB
YAML
name: Selfhosted Studio E2E Tests
|
|
on:
|
|
push:
|
|
branches: [master]
|
|
pull_request:
|
|
|
|
# Cancel old builds on new commit for same workflow + branch/PR
|
|
concurrency:
|
|
group: ${{ github.workflow }}-${{ github.event.pull_request.number || github.ref }}
|
|
cancel-in-progress: true
|
|
|
|
jobs:
|
|
test:
|
|
name: 'E2E tests'
|
|
timeout-minutes: 60
|
|
runs-on: blacksmith-8vcpu-ubuntu-2404
|
|
strategy:
|
|
fail-fast: false
|
|
matrix:
|
|
shardIndex: [1, 2]
|
|
shardTotal: [2]
|
|
outputs:
|
|
tests_ran: ${{ steps.filter.outputs.studio == 'true' }}
|
|
|
|
permissions:
|
|
contents: read
|
|
id-token: write
|
|
env:
|
|
OPENAI_API_KEY: ${{ secrets.OPENAI_API_KEY }}
|
|
|
|
steps:
|
|
- uses: actions/checkout@08eba0b27e820071cde6df949e0beb9ba4906955 # v4.3.0
|
|
with:
|
|
persist-credentials: false
|
|
- uses: dorny/paths-filter@de90cc6fb38fc0963ad72b210f1f284cd68cea36 # v3.0.2
|
|
id: filter
|
|
with:
|
|
filters: |
|
|
studio:
|
|
- 'packages/pg-meta/**'
|
|
- 'apps/studio/**'
|
|
- 'apps/ui-library/**'
|
|
- 'apps/design-system/**'
|
|
- 'e2e/studio/**'
|
|
- 'pnpm-lock.yaml'
|
|
- '.github/workflows/studio-e2e-test.yml'
|
|
|
|
- uses: pnpm/action-setup@41ff72655975bd51cab0327fa583b6e92b6d3061 # v4.2.0
|
|
if: steps.filter.outputs.studio == 'true'
|
|
name: Install pnpm
|
|
with:
|
|
run_install: false
|
|
|
|
- name: Use Node.js
|
|
if: steps.filter.outputs.studio == 'true'
|
|
uses: actions/setup-node@49933ea5288caeca8642d1e84afbd3f7d6820020 # v4.4.0
|
|
with:
|
|
node-version-file: '.nvmrc'
|
|
cache: 'pnpm'
|
|
|
|
- name: Install dependencies
|
|
if: steps.filter.outputs.studio == 'true'
|
|
run: pnpm install --frozen-lockfile
|
|
|
|
- name: Install Playwright Browsers
|
|
if: steps.filter.outputs.studio == 'true'
|
|
run: pnpm -C e2e/studio exec playwright install chromium --with-deps --only-shell
|
|
|
|
- name: Set up NextJS/Turbo cache
|
|
if: steps.filter.outputs.studio == 'true'
|
|
uses: actions/cache@0057852bfaa89a56745cba8c7296529d2fc39830 # v4.3.0
|
|
with:
|
|
# See here for caching with `yarn`, `bun` or other package managers https://github.com/actions/cache/blob/main/examples.md or you can leverage caching with actions/setup-node https://github.com/actions/setup-node
|
|
path: |
|
|
apps/studio/.next/build
|
|
apps/studio/.next/cache
|
|
# Generate a new cache whenever packages or source files change.
|
|
key: ${{ runner.os }}-nextjs-${{ hashFiles('pnpm-lock.yaml') }}-${{ hashFiles('apps/studio/**/*.js', 'apps/studio/**/*.jsx', 'apps/studio/**/*.ts', 'apps/studio/**/*.tsx') }}
|
|
# If source files changed but packages didn't, rebuild from a prior cache.
|
|
restore-keys: |
|
|
${{ runner.os }}-nextjs-${{ hashFiles('pnpm-lock.yaml') }}-
|
|
|
|
- name: Reset supabase
|
|
if: steps.filter.outputs.studio == 'true'
|
|
run: rm -rf supabase && pnpm exec supabase init && mkdir supabase/functions
|
|
|
|
# Authenticate with AWS ECR to avoid rate limiting
|
|
- name: configure aws credentials
|
|
if: steps.filter.outputs.studio == 'true' && !github.event.pull_request.head.repo.fork
|
|
uses: aws-actions/configure-aws-credentials@5fd3084fc36e372ff1fff382a39b10d03659f355 # v2.2.0
|
|
with:
|
|
role-to-assume: ${{ secrets.PROD_AWS_ROLE }}
|
|
aws-region: us-east-1
|
|
- uses: docker/login-action@465a07811f14bebb1938fbed4728c6a1ff8901fc # v2.2.0
|
|
if: steps.filter.outputs.studio == 'true' && !github.event.pull_request.head.repo.fork
|
|
with:
|
|
registry: public.ecr.aws
|
|
|
|
- name: Pre-start diagnostics
|
|
run: |
|
|
docker ps -a
|
|
sudo ss -tlnp | grep 54322 || echo "54322 free"
|
|
|
|
- name: Start supabase
|
|
if: steps.filter.outputs.studio == 'true'
|
|
run: SKIP_ASSET_UPLOAD=1 pnpm run e2e:setup:cli
|
|
|
|
- name: Failure diagnostics
|
|
if: failure()
|
|
run: |
|
|
docker ps -a
|
|
sudo ss -tlnp | grep 54322 || echo "54322 not listening"
|
|
docker logs $(docker ps -aq) 2>&1 || true
|
|
|
|
- name: Build studio
|
|
if: steps.filter.outputs.studio == 'true'
|
|
run: SKIP_ASSET_UPLOAD=1 NODE_ENV=test NODE_OPTIONS="--max-old-space-size=4096" pnpm run build:studio
|
|
|
|
- name: 🚀 Run Playwright tests against local studio build
|
|
if: steps.filter.outputs.studio == 'true'
|
|
id: playwright
|
|
run: PWTEST_SHARD_WEIGHTS=62:38 pnpm e2e --shard=${{ matrix.shardIndex }}/${{ matrix.shardTotal }}
|
|
|
|
- name: Upload blob report to GitHub Actions Artifacts
|
|
if: always() && steps.filter.outputs.studio == 'true'
|
|
uses: actions/upload-artifact@ea165f8d65b6e75b540449e92b4886f43607fa02 # v4.6.2
|
|
with:
|
|
name: blob-report-${{ matrix.shardIndex }}
|
|
path: e2e/studio/blob-report
|
|
retention-days: 7
|
|
|
|
- name: Fail job if tests failed
|
|
if: steps.filter.outputs.studio == 'true' && steps.playwright.outcome != 'success'
|
|
run: |
|
|
echo "E2E tests failed" >&2
|
|
exit 1
|
|
|
|
merge-reports:
|
|
name: 'E2E reports'
|
|
# Merge reports after playwright-tests, even if some shards have failed
|
|
if: ${{ !cancelled() && needs.test.outputs.tests_ran == 'true' }}
|
|
needs: [test]
|
|
runs-on: blacksmith-4vcpu-ubuntu-2404
|
|
permissions:
|
|
contents: write
|
|
pull-requests: write
|
|
steps:
|
|
- uses: actions/checkout@08eba0b27e820071cde6df949e0beb9ba4906955 # v4.3.0
|
|
with:
|
|
persist-credentials: false
|
|
- name: Use Node.js
|
|
uses: actions/setup-node@49933ea5288caeca8642d1e84afbd3f7d6820020 # v4.4.0
|
|
with:
|
|
node-version-file: '.nvmrc'
|
|
|
|
- name: Download blob reports from GitHub Actions Artifacts
|
|
uses: actions/download-artifact@634f93cb2916e3fdff6788551b99b062d0335ce0 # v 5.0.0
|
|
with:
|
|
path: e2e/studio/blob-report
|
|
pattern: blob-report-*
|
|
merge-multiple: true
|
|
|
|
- name: Merge Playwright reports
|
|
run: npx playwright merge-reports --config=e2e/studio/playwright.merge.config.ts -- e2e/studio/blob-report
|
|
|
|
- uses: actions/upload-artifact@ea165f8d65b6e75b540449e92b4886f43607fa02 # v4.6.2
|
|
with:
|
|
name: playwright-artifacts
|
|
path: |
|
|
e2e/studio/playwright-report/
|
|
e2e/studio/test-results/
|
|
retention-days: 7
|
|
|
|
- name: Comment Playwright test results on PR
|
|
if: always() && github.event_name == 'pull_request' && !github.event.pull_request.head.repo.fork
|
|
uses: daun/playwright-report-comment@be9e270edd5ad86038604d3caa84a819a6ff6fed # v3.10.0
|
|
with:
|
|
report-file: e2e/studio/test-results/test-results.json
|
|
comment-title: '🎭 Playwright Test Results'
|
|
|
|
merge-results:
|
|
name: 'E2E results'
|
|
runs-on: ubuntu-latest
|
|
permissions: {}
|
|
needs: [test]
|
|
if: ${{ !cancelled() && needs.test.outputs.tests_ran == 'true' }}
|
|
steps:
|
|
- name: All tests ok
|
|
if: ${{ !(contains(needs.*.result, 'failure')) }}
|
|
run: exit 0
|
|
- name: Some tests failed
|
|
if: ${{ contains(needs.*.result, 'failure') }}
|
|
run: exit 1
|