name: Nightly on: workflow_dispatch: schedule: - cron: "0 3 * * *" permissions: contents: read env: SYSTEM_DEPS: libheif-examples libheif-plugin-x265 libheif-plugin-libde265 libimage-exiftool-perl imagemagick ghostscript libjxl-tools libopenjp2-tools ffmpeg qpdf jobs: e2e-full: name: E2E Full (${{ matrix.shard }}/4) runs-on: ubuntu-latest timeout-minutes: 60 services: postgres: image: postgres:17-alpine env: POSTGRES_USER: snapotter POSTGRES_PASSWORD: snapotter POSTGRES_DB: snapotter ports: - 5432:5432 options: >- --health-cmd "pg_isready -U snapotter" --health-interval 5s --health-timeout 3s --health-retries 10 redis: image: redis:8-alpine ports: - 6379:6379 options: >- --health-cmd "redis-cli ping" --health-interval 5s --health-timeout 3s --health-retries 10 strategy: fail-fast: false matrix: shard: [1, 2, 3, 4] steps: - uses: actions/checkout@df4cb1c069e1874edd31b4311f1884172cec0e10 # v6.0.3 - name: Install system dependencies run: sudo apt-get update -qq && sudo apt-get install -y --no-install-recommends $SYSTEM_DEPS - uses: ./.github/actions/setup - name: Get Playwright version id: pw-version run: echo "version=$(node -p "require('@playwright/test/package.json').version")" >> "$GITHUB_OUTPUT" - name: Cache Playwright browsers uses: actions/cache@27d5ce7f107fe9357f9df03efb73ab90386fccae # v5.0.5 with: path: ~/.cache/ms-playwright key: playwright-${{ runner.os }}-${{ steps.pw-version.outputs.version }} - name: Install Playwright Chromium run: pnpm playwright install --with-deps chromium - name: Run full e2e suite (shard) run: pnpm playwright test --project=chromium --shard=${{ matrix.shard }}/4 env: PW_WORKERS: "2" - name: Upload report on failure uses: actions/upload-artifact@043fb46d1a93c77aae656e7c1c64a875d1fc6a0a # v7.0.1 if: failure() with: name: e2e-full-report-shard-${{ matrix.shard }} path: playwright-report/ retention-days: 7 e2e-serial: name: E2E Serial Bucket runs-on: ubuntu-latest timeout-minutes: 60 services: postgres: image: postgres:17-alpine env: POSTGRES_USER: snapotter POSTGRES_PASSWORD: snapotter POSTGRES_DB: snapotter ports: - 5432:5432 options: >- --health-cmd "pg_isready -U snapotter" --health-interval 5s --health-timeout 3s --health-retries 10 redis: image: redis:8-alpine ports: - 6379:6379 options: >- --health-cmd "redis-cli ping" --health-interval 5s --health-timeout 3s --health-retries 10 steps: - uses: actions/checkout@df4cb1c069e1874edd31b4311f1884172cec0e10 # v6.0.3 - name: Install system dependencies run: sudo apt-get update -qq && sudo apt-get install -y --no-install-recommends $SYSTEM_DEPS - uses: ./.github/actions/setup - name: Get Playwright version id: pw-version run: echo "version=$(node -p "require('@playwright/test/package.json').version")" >> "$GITHUB_OUTPUT" - name: Cache Playwright browsers uses: actions/cache@27d5ce7f107fe9357f9df03efb73ab90386fccae # v5.0.5 with: path: ~/.cache/ms-playwright key: playwright-${{ runner.os }}-${{ steps.pw-version.outputs.version }} - name: Install Playwright Chromium run: pnpm playwright install --with-deps chromium - name: Run serial bucket (global-state specs) run: pnpm playwright test --project=chromium-serial --workers=1 - name: Upload report on failure uses: actions/upload-artifact@043fb46d1a93c77aae656e7c1c64a875d1fc6a0a # v7.0.1 if: failure() with: name: e2e-serial-report path: playwright-report/ retention-days: 7 e2e-cross-browser: name: E2E Cross-Browser (Firefox + WebKit) runs-on: ubuntu-latest timeout-minutes: 30 services: postgres: image: postgres:17-alpine env: POSTGRES_USER: snapotter POSTGRES_PASSWORD: snapotter POSTGRES_DB: snapotter ports: - 5432:5432 options: >- --health-cmd "pg_isready -U snapotter" --health-interval 5s --health-timeout 3s --health-retries 10 redis: image: redis:8-alpine ports: - 6379:6379 options: >- --health-cmd "redis-cli ping" --health-interval 5s --health-timeout 3s --health-retries 10 steps: - uses: actions/checkout@df4cb1c069e1874edd31b4311f1884172cec0e10 # v6.0.3 - uses: ./.github/actions/setup - name: Get Playwright version id: pw-version run: echo "version=$(node -p "require('@playwright/test/package.json').version")" >> "$GITHUB_OUTPUT" - name: Cache Playwright browsers uses: actions/cache@27d5ce7f107fe9357f9df03efb73ab90386fccae # v5.0.5 with: path: ~/.cache/ms-playwright key: playwright-all-${{ runner.os }}-${{ steps.pw-version.outputs.version }} - name: Install Playwright browsers run: pnpm playwright install --with-deps chromium firefox webkit - name: Run cross-browser spec run: pnpm playwright test --project=firefox --project=webkit env: PW_WORKERS: "1" - name: Upload report on failure uses: actions/upload-artifact@043fb46d1a93c77aae656e7c1c64a875d1fc6a0a # v7.0.1 if: failure() with: name: e2e-cross-browser-report path: playwright-report/ retention-days: 7 docker-e2e: name: Docker Container E2E runs-on: ubuntu-latest timeout-minutes: 60 steps: - uses: actions/checkout@df4cb1c069e1874edd31b4311f1884172cec0e10 # v6.0.3 - name: Run container test suite run: docker compose -f docker/docker-compose.test.yml up --build --exit-code-from test-e2e extended-matrix: name: Extended Matrix + Fuzz runs-on: ubuntu-latest timeout-minutes: 90 steps: - uses: actions/checkout@df4cb1c069e1874edd31b4311f1884172cec0e10 # v6.0.3 - name: Install system dependencies run: sudo apt-get update -qq && sudo apt-get install -y --no-install-recommends $SYSTEM_DEPS - name: Allow ImageMagick to read EPS/PS via Ghostscript delegate run: | POLICY_FILE=$(find /etc/ImageMagick* -name policy.xml 2>/dev/null | head -1) if [ -n "$POLICY_FILE" ]; then sudo sed -i 's/- --health-cmd "pg_isready -U snapotter" --health-interval 5s --health-timeout 3s --health-retries 10 redis: image: redis:8-alpine ports: - 6379:6379 options: >- --health-cmd "redis-cli ping" --health-interval 5s --health-timeout 3s --health-retries 10 steps: - uses: actions/checkout@df4cb1c069e1874edd31b4311f1884172cec0e10 # v6.0.3 - name: Install system dependencies run: sudo apt-get update -qq && sudo apt-get install -y --no-install-recommends $SYSTEM_DEPS - uses: ./.github/actions/setup - uses: actions/setup-python@a309ff8b426b58ec0e2a45f0f869d46889d02405 # v6.2.0 with: python-version: "3.12" - name: Install Schemathesis run: pip install schemathesis - name: Start API server run: | mkdir -p /tmp/st-data AUTH_ENABLED=false ANALYTICS_ENABLED=false \ DATABASE_URL=postgres://snapotter:snapotter@localhost:5432/snapotter \ REDIS_URL=redis://localhost:6379 \ WORKSPACE_PATH=/tmp/st-data/workspace DATA_DIR=/tmp/st-data \ pnpm --filter @snapotter/api dev & for i in $(seq 1 60); do if curl -fsS http://localhost:13490/api/v1/health > /dev/null 2>&1; then echo "API up after ${i}s"; exit 0 fi sleep 1 done echo "API failed to start"; exit 1 - name: Fuzz tool endpoints from the OpenAPI spec run: | schemathesis run http://localhost:13490/api/v1/openapi.yaml \ --url http://localhost:13490 \ --checks not_a_server_error \ --include-path-regex "^/api/v1/(tools|health|info)" \ --max-examples 25 \ --report junit \ --report-dir st-report - name: Upload fuzz report uses: actions/upload-artifact@043fb46d1a93c77aae656e7c1c64a875d1fc6a0a # v7.0.1 if: always() with: name: schemathesis-report path: st-report/ retention-days: 14 coverage-report: name: Coverage Report runs-on: ubuntu-latest timeout-minutes: 90 steps: - uses: actions/checkout@df4cb1c069e1874edd31b4311f1884172cec0e10 # v6.0.3 - name: Install system dependencies run: sudo apt-get update -qq && sudo apt-get install -y --no-install-recommends $SYSTEM_DEPS - name: Allow ImageMagick to read EPS/PS via Ghostscript delegate run: | POLICY_FILE=$(find /etc/ImageMagick* -name policy.xml 2>/dev/null | head -1) if [ -n "$POLICY_FILE" ]; then sudo sed -i 's/