From 604bf993043f17f07f522de15ccabc006dcced18 Mon Sep 17 00:00:00 2001 From: Lindsay Holmwood Date: Wed, 6 May 2026 17:43:56 +1000 Subject: [PATCH 1/4] ci: run @cipherstash/bench smoke tests against local Postgres MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Adds a third job (`bench-smoke-tests`) to `.github/workflows/tests.yml` that brings up the EQL-enabled Postgres container under `local/` and runs `pnpm test:local -- db-only` against it. The job is gated by a small `changes` filter job using `dorny/paths-filter@v3` so it only runs when files under `packages/bench/**`, `local/**`, or `.github/workflows/tests.yml` change. Existing `run-tests` and `e2e-tests` jobs are untouched and continue to fire on every push/PR. The smoke suite is intentionally credential-free: bench falls back to the docker-compose default DATABASE_URL, so no secrets are wired in. Note: the suite currently surfaces two known-failing assertions in `drizzle/operators.explain.test.ts` (the eq/inArray bare-equality bug). The failures will appear red on this PR — that's the intent; the fix lands in a stacked branch. Co-Authored-By: Claude Opus 4.7 (1M context) --- .github/workflows/tests.yml | 61 +++++++++++++++++++++++++++++++++++++ 1 file changed, 61 insertions(+) diff --git a/.github/workflows/tests.yml b/.github/workflows/tests.yml index bedfa0f0..f48dab4d 100644 --- a/.github/workflows/tests.yml +++ b/.github/workflows/tests.yml @@ -137,3 +137,64 @@ jobs: # job above; we filter to the new workspace here to avoid duplication. - name: Run E2E tests run: pnpm exec turbo run test:e2e --filter @cipherstash/e2e + + changes: + name: Detect changed paths + runs-on: ubuntu-latest + # Outputs a boolean `bench` consumed by bench-smoke-tests below. + # On pull_request, dorny/paths-filter uses the GitHub API (no checkout + # needed). On push, it falls back to comparing against the event's + # `before` SHA, which is fine for fast-forward pushes to main. + outputs: + bench: ${{ steps.filter.outputs.bench }} + steps: + - uses: dorny/paths-filter@v3 + id: filter + with: + filters: | + bench: + - 'packages/bench/**' + - 'local/**' + - '.github/workflows/tests.yml' + + bench-smoke-tests: + name: Run Bench Smoke Tests + needs: changes + if: needs.changes.outputs.bench == 'true' + runs-on: blacksmith-4vcpu-ubuntu-2404 + + steps: + - name: Checkout Repo + uses: actions/checkout@v6 + + - uses: pnpm/action-setup@v6.0.3 + name: Install pnpm + with: + run_install: false + + - name: Install Node.js + uses: actions/setup-node@v6 + with: + node-version: 22 + cache: 'pnpm' + + # node-pty's install hook falls back to `node-gyp rebuild` when no + # linux-x64 prebuild matches. pnpm/action-setup v6 no longer ships + # node-gyp on PATH, so install it explicitly. + - name: Install node-gyp + run: npm install -g node-gyp + + - name: Install dependencies + run: pnpm install --frozen-lockfile + + # Builds the local EQL-enabled Postgres image (local/Dockerfile), + # starts it, and waits for the pg_isready healthcheck to pass. + - name: Start local Postgres (EQL) + working-directory: local + run: docker compose up --wait --wait-timeout 60 + + # `pnpm test:local` resolves to `vitest run`; the `--` passthrough + # narrows it to __tests__/db-only.test.ts (credential-free smoke). + - name: Run bench smoke tests + working-directory: packages/bench + run: pnpm test:local -- db-only From 5c029f5d2b98c96d6090885b9839b5afae8a6e11 Mon Sep 17 00:00:00 2001 From: Lindsay Holmwood Date: Wed, 6 May 2026 20:01:53 +1000 Subject: [PATCH 2/4] ci(bench): split smoke tests into standalone workflow with paths filter Move `bench-smoke-tests` (and drop the `dorny/paths-filter` `changes` job) out of `tests.yml` into its own `.github/workflows/tests-bench.yml`. Path-gating is now handled by the workflow's own `on: push/pull_request: paths:` filter, so no extra job + dependency wiring is needed and the existing `Test JS` workflow stays untouched. Co-Authored-By: Claude Opus 4.7 (1M context) --- .github/workflows/tests-bench.yml | 58 +++++++++++++++++++++++++++++ .github/workflows/tests.yml | 61 ------------------------------- 2 files changed, 58 insertions(+), 61 deletions(-) create mode 100644 .github/workflows/tests-bench.yml diff --git a/.github/workflows/tests-bench.yml b/.github/workflows/tests-bench.yml new file mode 100644 index 00000000..5377387d --- /dev/null +++ b/.github/workflows/tests-bench.yml @@ -0,0 +1,58 @@ +name: "Test JS" + +on: + push: + branches: + - 'main' + paths: + - 'packages/bench/**' + - 'local/**' + - '.github/workflows/tests-bench.yml' + pull_request: + branches: + - "**" + paths: + - 'packages/bench/**' + - 'local/**' + - '.github/workflows/tests-bench.yml' + +jobs: + tests-bench: + name: Run Bench Smoke Tests + runs-on: blacksmith-4vcpu-ubuntu-2404 + + steps: + - name: Checkout Repo + uses: actions/checkout@v6 + + - uses: pnpm/action-setup@v6 + name: Install pnpm + with: + run_install: false + + - name: Install Node.js + uses: actions/setup-node@v6 + with: + node-version: 22 + cache: 'pnpm' + + # node-pty's install hook falls back to `node-gyp rebuild` when no + # linux-x64 prebuild matches. pnpm/action-setup v6 no longer ships + # node-gyp on PATH, so install it explicitly. + - name: Install node-gyp + run: npm install -g node-gyp + + - name: Install dependencies + run: pnpm recursive install --frozen-lockfile + + # Builds the local EQL-enabled Postgres image (local/Dockerfile), + # starts it, and waits for the pg_isready healthcheck to pass. + - name: Start local Postgres (EQL) + working-directory: local + run: docker compose up --wait --wait-timeout 60 + + # `pnpm test:local` resolves to `vitest run`; the `--` passthrough + # narrows it to __tests__/db-only.test.ts (credential-free smoke). + - name: Run bench smoke tests + working-directory: packages/bench + run: pnpm test:local -- db-only diff --git a/.github/workflows/tests.yml b/.github/workflows/tests.yml index f48dab4d..bedfa0f0 100644 --- a/.github/workflows/tests.yml +++ b/.github/workflows/tests.yml @@ -137,64 +137,3 @@ jobs: # job above; we filter to the new workspace here to avoid duplication. - name: Run E2E tests run: pnpm exec turbo run test:e2e --filter @cipherstash/e2e - - changes: - name: Detect changed paths - runs-on: ubuntu-latest - # Outputs a boolean `bench` consumed by bench-smoke-tests below. - # On pull_request, dorny/paths-filter uses the GitHub API (no checkout - # needed). On push, it falls back to comparing against the event's - # `before` SHA, which is fine for fast-forward pushes to main. - outputs: - bench: ${{ steps.filter.outputs.bench }} - steps: - - uses: dorny/paths-filter@v3 - id: filter - with: - filters: | - bench: - - 'packages/bench/**' - - 'local/**' - - '.github/workflows/tests.yml' - - bench-smoke-tests: - name: Run Bench Smoke Tests - needs: changes - if: needs.changes.outputs.bench == 'true' - runs-on: blacksmith-4vcpu-ubuntu-2404 - - steps: - - name: Checkout Repo - uses: actions/checkout@v6 - - - uses: pnpm/action-setup@v6.0.3 - name: Install pnpm - with: - run_install: false - - - name: Install Node.js - uses: actions/setup-node@v6 - with: - node-version: 22 - cache: 'pnpm' - - # node-pty's install hook falls back to `node-gyp rebuild` when no - # linux-x64 prebuild matches. pnpm/action-setup v6 no longer ships - # node-gyp on PATH, so install it explicitly. - - name: Install node-gyp - run: npm install -g node-gyp - - - name: Install dependencies - run: pnpm install --frozen-lockfile - - # Builds the local EQL-enabled Postgres image (local/Dockerfile), - # starts it, and waits for the pg_isready healthcheck to pass. - - name: Start local Postgres (EQL) - working-directory: local - run: docker compose up --wait --wait-timeout 60 - - # `pnpm test:local` resolves to `vitest run`; the `--` passthrough - # narrows it to __tests__/db-only.test.ts (credential-free smoke). - - name: Run bench smoke tests - working-directory: packages/bench - run: pnpm test:local -- db-only From 0e2f46d112e05f675abb78c6c2fc27f23380b815 Mon Sep 17 00:00:00 2001 From: Lindsay Holmwood Date: Wed, 6 May 2026 21:19:41 +1000 Subject: [PATCH 3/4] ci(bench): build @cipherstash/stack before running smoke tests MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit `pnpm test:local` runs vitest directly without going through turbo, so the `^build` dep declared on the `test` task in turbo.json doesn't fire — and `@cipherstash/stack`'s dist/-based `exports` map fails to resolve from `__tests__/harness.test.ts` and `__tests__/drizzle/operators.explain.test.ts`. Build the package explicitly via turbo (cached) before invoking vitest. Co-Authored-By: Claude Opus 4.7 (1M context) --- .github/workflows/tests-bench.yml | 7 +++++++ 1 file changed, 7 insertions(+) diff --git a/.github/workflows/tests-bench.yml b/.github/workflows/tests-bench.yml index 5377387d..d6c53696 100644 --- a/.github/workflows/tests-bench.yml +++ b/.github/workflows/tests-bench.yml @@ -45,6 +45,13 @@ jobs: - name: Install dependencies run: pnpm recursive install --frozen-lockfile + # `@cipherstash/stack` ships dist/-based `exports`; bench imports + # from it (and `@cipherstash/stack/drizzle`) so the package needs + # to be built before vitest can resolve it. Going through turbo + # also picks up `^build` deps if any are added later. + - name: Build @cipherstash/stack + run: pnpm exec turbo run build --filter @cipherstash/stack + # Builds the local EQL-enabled Postgres image (local/Dockerfile), # starts it, and waits for the pg_isready healthcheck to pass. - name: Start local Postgres (EQL) From 7275ed9bd0142b9872f34c2c3f2b0fe3f1a3d138 Mon Sep 17 00:00:00 2001 From: Lindsay Holmwood Date: Wed, 6 May 2026 21:29:52 +1000 Subject: [PATCH 4/4] ci(bench): drop `--` so vitest path filter actually narrows MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit `pnpm test:local -- db-only` was forwarding `-- db-only` to vitest, which interprets `--` as the option-terminator and ignores the trailing positional. The result: all 3 test files ran, and `harness.test.ts` + `drizzle/operators.explain.test.ts` failed in setup with `[encryption]: Not authenticated` because they need CipherStash credentials we deliberately don't wire into this job. Drop the `--`. pnpm 10 forwards script args directly, and vitest applies `db-only` as a path filter — narrowing to the credential-free `__tests__/db-only.test.ts` (4 tests). Co-Authored-By: Claude Opus 4.7 (1M context) --- .github/workflows/tests-bench.yml | 10 +++++++--- 1 file changed, 7 insertions(+), 3 deletions(-) diff --git a/.github/workflows/tests-bench.yml b/.github/workflows/tests-bench.yml index d6c53696..72ff8631 100644 --- a/.github/workflows/tests-bench.yml +++ b/.github/workflows/tests-bench.yml @@ -58,8 +58,12 @@ jobs: working-directory: local run: docker compose up --wait --wait-timeout 60 - # `pnpm test:local` resolves to `vitest run`; the `--` passthrough - # narrows it to __tests__/db-only.test.ts (credential-free smoke). + # `pnpm test:local` resolves to `vitest run`; the trailing `db-only` + # is a vitest path filter that narrows to __tests__/db-only.test.ts + # (credential-free smoke). Note: pnpm 10 forwards script args without + # `--`; using `--` here would cause vitest to treat it as the + # option-terminator and ignore the filter, running all 3 test files + # — including ones that need CipherStash credentials. - name: Run bench smoke tests working-directory: packages/bench - run: pnpm test:local -- db-only + run: pnpm test:local db-only