Repository navigation
Conversation
Pin the full Better Auth dependency family to the schema-compatible version and add a manifest regression test for fresh package consumers.\n\nFixes #1 Signed-off-by: 서재원 <cinos81@gmail.com>
This reverts commit 96598ba.
|
Confirming this fix targets a live, repo-wide CI problem — with a reproduction and the concrete mechanism. Root cause, reproduced. The committed lockfile currently pins the family to 1.6.22, so local Why 1.7 breaks auth specifically. better-auth 1.7.0 ships breaking schema changes — most relevantly "Accounts now require Observed impact. On the shared PR preview lane this shows up as a consistent block of Pinning the whole family to an exact, schema-compatible (Reproduced locally; I did not run the auth E2E under 1.7 — that path needs the preview deploy — but the resolution float and the 1.7 schema break are both verified above.) |
Better Auth >=1.4.0-beta.18 <1.7.7 is affected by GHSA-965c-763c-88jm (critical; no 1.6 backport), so this moves forward instead of pinning 1.6.25. Exact-pin approach from #1062 (@shoveller). - Pin better-auth, @better-auth/core, drizzle-adapter, telemetry to exactly 1.7.7 and better-auth-cloudflare to exactly 0.4.1; drizzle-orm peer ^0.45.2, and the create-app starter template to match. - Both lockfiles regenerated with npm 10. packages/core/package-lock.json was already out of sync on main (graphql/graphql-yoga missing; npm ci failed). - Organization field mapping uses the drizzle property key `tenantId` (1.7.3+ validates the drizzle schema at startup). - `updatedAt` default and on-update on the auth_tenant* drizzle tables (no migration). - Verification values consumed from D1 (`storeInDatabase`, a single atomic DELETE ... RETURNING); rate-limit counters in memory; own KV SecondaryStorage typed against Better Auth's full interface (KV has no atomic getAndDelete / increment). - Plugins passed inside withCloudflare so its plugin and storage check run (this also mounts its session-gated GET /auth/cloudflare/geolocation). - Organization endpoints closed in two layers: app.ts returns 404 for /auth/organization/*, and Better Auth `disabledPaths` lists every path the organization plugin mounts (derived from the plugin, so a new endpoint is covered). Either layer alone holds. Tenants belong to TenantService; with the mapping fixed, these endpoints would otherwise let a tenant member with the org `admin` role rewrite auth_tenant.domain (host routing). allowUserToCreateOrganization: false as well. - Passwords capped at 128 characters wherever SonicJS sets one (routes, create-sonicjs prompt/flag, self-host seed); 1.7 refuses longer ones at sign-in. - Docker rate-limit comment corrected: clients can rotate cf-connecting-ip / x-real-ip for a fresh bucket there (same on 1.6). - Tests over real Better Auth + SQLite, including password rows written outside Better Auth (POST /auth/register, join, seeds) and organization update / invite-member under each guard layer alone, with a positive control; harness applies 0003; E2E spec 112. Fixes #1061. Refs #1054. Supersedes #1062.
* fix(auth): move to Better Auth 1.7.7 and better-auth-cloudflare 0.4.1 Better Auth >=1.4.0-beta.18 <1.7.7 is affected by GHSA-965c-763c-88jm (critical; no 1.6 backport), so this moves forward instead of pinning 1.6.25. Exact-pin approach from #1062 (@shoveller). - Pin better-auth, @better-auth/core, drizzle-adapter, telemetry to exactly 1.7.7 and better-auth-cloudflare to exactly 0.4.1; drizzle-orm peer ^0.45.2, and the create-app starter template to match. - Both lockfiles regenerated with npm 10. packages/core/package-lock.json was already out of sync on main (graphql/graphql-yoga missing; npm ci failed). - Organization field mapping uses the drizzle property key `tenantId` (1.7.3+ validates the drizzle schema at startup). - `updatedAt` default and on-update on the auth_tenant* drizzle tables (no migration). - Verification values consumed from D1 (`storeInDatabase`, a single atomic DELETE ... RETURNING); rate-limit counters in memory; own KV SecondaryStorage typed against Better Auth's full interface (KV has no atomic getAndDelete / increment). - Plugins passed inside withCloudflare so its plugin and storage check run (this also mounts its session-gated GET /auth/cloudflare/geolocation). - Organization endpoints closed in two layers: app.ts returns 404 for /auth/organization/*, and Better Auth `disabledPaths` lists every path the organization plugin mounts (derived from the plugin, so a new endpoint is covered). Either layer alone holds. Tenants belong to TenantService; with the mapping fixed, these endpoints would otherwise let a tenant member with the org `admin` role rewrite auth_tenant.domain (host routing). allowUserToCreateOrganization: false as well. - Passwords capped at 128 characters wherever SonicJS sets one (routes, create-sonicjs prompt/flag, self-host seed); 1.7 refuses longer ones at sign-in. - Docker rate-limit comment corrected: clients can rotate cf-connecting-ip / x-real-ip for a fresh bucket there (same on 1.6). - Tests over real Better Auth + SQLite, including password rows written outside Better Auth (POST /auth/register, join, seeds) and organization update / invite-member under each guard layer alone, with a positive control; harness applies 0003; E2E spec 112. Fixes #1061. Refs #1054. Supersedes #1062. * fix(auth): harden Better Auth 1.7.7 upgrade review findings Address 6 code-review findings from PR #1103: 1. Rename E2E spec 112 → 124 (R11 numbering convention) 2. Organization 404 guard: app.all instead of GET/POST only, covers all HTTP methods; add explicit /auth/organization (bare path) route 3. organizationPaths filter: also match bare '/organization' endpoint 4. secondary-storage set(): treat ttl≤0 as immediate delete instead of clamping to 60s 5. secondaryStorage key: omit from options when CACHE_KV is absent, avoiding a present-but-undefined key 6. createAuth: warn when extendBetterAuth removes disabledPaths Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com> * fix(e2e): stabilize redirect management test (80-redirect-management) Two bugs causing hard failure in CI: 1. Post-submit navigation race: waitForLoadState('networkidle') resolves before the server-side redirect fires, so toHaveURL sees the edit URL. Fix: waitForURL with 15s timeout instead. 2. Non-unique destination: retries accumulate redirects all sharing destination '/updated-destination-3', causing strict mode violations. Fix: timestamp-based unique destinations, and assert on the source+destination compound selector. Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com> * fix(redirect): swap HTMX 400 error responses into form-messages HTMX 1.x does not swap 4xx responses by default, so server-rendered validation errors (duplicate source URL) were silently dropped. Add a beforeSwap handler that allows 400/422 responses to be swapped into #form-messages. Also stabilize the E2E test: wait for the POST response and assert 400 status instead of a fixed 1s timeout, and use waitForURL for the first create's post-submit redirect. Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com> * fix(e2e): add polling for cache invalidation test (cross-isolate delay) Cloudflare Workers can route sequential requests to different isolates, each with its own in-memory cache. A POST (create/update) invalidates the cache on one isolate, but a subsequent GET may hit a different isolate still serving stale data. Add a poll-and-retry helper so the test tolerates the propagation delay instead of failing deterministically on multi-isolate deployments. Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com> * fix(tests): address PR review comments — edge cases and assertions - Add below-floor assertion (1.7.6 < 1.7.7) in version guard test - Add ttl<=0 delete-path coverage in secondary-storage test - Cover bare /auth/organization path in E2E org-endpoint test - Fail on OAuth 5xx instead of skipping in GHSA test - Assert pollListForItem precondition in cache-invalidation update test Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com> --------- Co-authored-by: Mark McIntosh <mmcintosh@infowall.com> Co-authored-by: Claude Opus 4.6 (1M context) <noreply@anthropic.com>
|
Thanks for jumping on the Better Auth version pin @shoveller — that was a timely catch to keep things stable. 🙏 This is superseded by #1133, which upgrades to Better Auth 1.7.7 (a full upgrade rather than a pin to 1.6.25) and has been merged to Closing in favour of the merged upgrade. |
Description
Prevents fresh
@sonicjs-cms/coreconsumers from resolving Better Auth 1.7.x before SonicJS has migrated itsauth_accountschema to the new issuer-scoped account identity model.Fixes #1061
Changes
better-auth,@better-auth/core,@better-auth/drizzle-adapter, and@better-auth/telemetryto the repository-tested1.6.25release..worktrees/directory used for isolated contribution work.@better-auth/coreis intentionally direct: a packed-consumer check showed that pinning only the other three packages still allowed peer dependency resolution to install@better-auth/core@1.7.1alongside 1.6.25.This urgent patch does not change the database schema or runtime auth code. A coordinated Better Auth 1.7 issuer migration remains follow-up work.
Testing
Unit Tests
better-auth-dependency-compat.test.tsPackage Consumer Check
packages/corewithnpm pack--package-lock-only1.6.25:better-auth@better-auth/core@better-auth/drizzle-adapter@better-auth/telemetryOther Verification
npm run lint --workspace=@sonicjs-cms/core(passes with existing warnings)npm run type-checknpm run build:coregit diff --checkKnown Repository Baseline Issue
npm ci --ignore-scriptscurrently fails before installation because the checked-in root lockfile already drifts from unrelated workspace manifests (esbuild,eslint, andsharp). The repository CI usesnpm install, which succeeds. This PR deliberately avoids including the resulting 1,500+ lines of unrelated lockfile churn.Screenshots/Videos
Not applicable; no UI changes.
Checklist