You signed in with another tab or window. Reload to refresh your session.You signed out in another tab or window. Reload to refresh your session.You switched accounts on another tab or window. Reload to refresh your session.Dismiss alert
feat(spec,objectql): unify developer-facing org identifier in hooks — organizationId is blessed (#3280)
The caller's active organization was surfaced to hook authors as
`ctx.session.tenantId`, while the column (`organization_id`), RLS
(`current_user.organizationId`), and seed rows already said `organization`.
A hook author had to internalize `tenantId === organizationId` to move
between surfaces.
Additive, non-breaking:
- `ctx.session.organizationId` added as the blessed name; `session.tenantId`
kept as a deprecated alias with the identical value (both from
`ExecutionContext.tenantId`, resolved from `session.activeOrganizationId`).
- `ctx.user.organizationId` added to the ergonomic user shortcut; the engine
now populates `ctx.user` at every hook event that carries a session, and it
stays undefined for system/unauthenticated writes.
Generic driver-layer tenancy (`ExecutionContext.tenantId`,
`DriverOptions.tenantId`, `SqlDriver.applyTenantScope`,
`TenancyConfig.tenantField`) is deliberately untouched — that layer's
isolation column is configurable and can carry an environment id in
database-per-tenant kernels. Docs now teach `organizationId` and distinguish
the two isolation axes (org row-scoping vs environment/database-per-tenant).
Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>
**Unify the developer-facing org identifier in JS hooks — `organizationId` is now the blessed name; `session.tenantId` becomes a deprecated alias (#3280).** The caller's active organization was surfaced to hook authors as `ctx.session.tenantId`, while everything else on the developer surface — the `organization_id` column, `current_user.organizationId` in RLS/sharing, and seed rows — already said `organization`. A hook author had to internalize the hidden equation `tenantId === organizationId` to move between surfaces. This is additive and non-breaking:
7
+
8
+
-**`ctx.session.organizationId`** is added as the blessed name; **`ctx.session.tenantId`** still carries the identical value but is marked `@deprecated` in its TSDoc. Both come from the same resolved `ExecutionContext.tenantId` (which the kernel derives from `session.activeOrganizationId`).
9
+
-**`ctx.user.organizationId`** is added to the ergonomic `user` shortcut, so a hook that needs "the current org to filter by" writes `ctx.user.organizationId` with zero relearning — matching `current_user.organizationId` (RLS) and the `organization_id` column. The engine now populates `ctx.user` (`{ id, email?, organizationId? }`) at every hook event that already carries a `session`; it stays `undefined` for system / unauthenticated writes.
10
+
11
+
**No behavior change and no breaking rename.** The generic driver-layer tenancy abstraction (`ExecutionContext.tenantId`, `DriverOptions.tenantId`, `SqlDriver.applyTenantScope`, `TenancyConfig.tenantField`) is deliberately untouched — that layer's isolation column is configurable and legitimately carries an *environment* id in per-environment (database-per-tenant) kernels. Hook-authoring docs now teach `organizationId` and distinguish the two isolation axes: **org row-scoping** (`organization_id`, shared DB) vs **environment / database-per-tenant** (`service-tenant`, `driver-turso`). Community edition never populates an org, so `organizationId` is `undefined` there.
0 commit comments