@nodii/db-rls 0.2.2 → 0.3.1

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (44) hide show
  1. package/dist/configure.d.ts +25 -8
  2. package/dist/configure.d.ts.map +1 -1
  3. package/dist/configure.js +48 -17
  4. package/dist/configure.js.map +1 -1
  5. package/dist/context.d.ts +8 -6
  6. package/dist/context.d.ts.map +1 -1
  7. package/dist/context.js +27 -6
  8. package/dist/context.js.map +1 -1
  9. package/dist/drizzle-client.d.ts +9 -2
  10. package/dist/drizzle-client.d.ts.map +1 -1
  11. package/dist/drizzle-client.js +28 -2
  12. package/dist/drizzle-client.js.map +1 -1
  13. package/dist/drizzle-policies.d.ts +23 -0
  14. package/dist/drizzle-policies.d.ts.map +1 -0
  15. package/dist/drizzle-policies.js +114 -0
  16. package/dist/drizzle-policies.js.map +1 -0
  17. package/dist/index.d.ts +8 -5
  18. package/dist/index.d.ts.map +1 -1
  19. package/dist/index.js +21 -9
  20. package/dist/index.js.map +1 -1
  21. package/dist/init.d.ts +14 -5
  22. package/dist/init.d.ts.map +1 -1
  23. package/dist/init.js +20 -4
  24. package/dist/init.js.map +1 -1
  25. package/dist/metrics.d.ts +28 -0
  26. package/dist/metrics.d.ts.map +1 -0
  27. package/dist/metrics.js +263 -0
  28. package/dist/metrics.js.map +1 -0
  29. package/dist/migrate-guard.d.ts +14 -0
  30. package/dist/migrate-guard.d.ts.map +1 -0
  31. package/dist/migrate-guard.js +33 -0
  32. package/dist/migrate-guard.js.map +1 -0
  33. package/dist/pg-pool-adapter.d.ts.map +1 -1
  34. package/dist/pg-pool-adapter.js +78 -25
  35. package/dist/pg-pool-adapter.js.map +1 -1
  36. package/dist/postgres-js-client.d.ts +60 -0
  37. package/dist/postgres-js-client.d.ts.map +1 -0
  38. package/dist/postgres-js-client.js +223 -0
  39. package/dist/postgres-js-client.js.map +1 -0
  40. package/dist/types.d.ts +29 -0
  41. package/dist/types.d.ts.map +1 -1
  42. package/dist/types.js +30 -0
  43. package/dist/types.js.map +1 -1
  44. package/package.json +20 -5
@@ -1,16 +1,23 @@
1
1
  import type { Pool } from "pg";
2
- import { DbRlsError, type PoolKind } from "./types";
2
+ import { type DbRlsMode, DbRlsError, type PoolKind } from "./types";
3
+ export interface ConfigureDbRlsPools {
4
+ owner: Pool;
5
+ services?: Pool;
6
+ authenticated?: Pool;
7
+ }
3
8
  export interface ConfigureDbRlsOpts {
4
9
  /** Per `nodii-libs/telemetry.md` § 5.4. Used in error messages + spans. */
5
10
  serviceName: string;
6
- /** Underlying pg.Pool instances per role. Caller owns lifecycle. */
7
- pools: {
8
- owner: Pool;
9
- services: Pool;
10
- authenticated: Pool;
11
- };
11
+ /** Underlying pg.Pool instances per role. Caller owns lifecycle. In
12
+ * `2-pool` mode only `owner` (and optionally `services`) are required;
13
+ * `authenticated` must be absent. */
14
+ pools: ConfigureDbRlsPools;
15
+ /** Pool topology mode. Defaults to `"3-pool"`. Set `"2-pool"` for
16
+ * nodii-auth-shape services per 08-rls § 7. */
17
+ mode?: DbRlsMode;
12
18
  /** Enable role-name validation at boot (default true). Set false in
13
- * unit tests that wire raw postgres without dedicated roles. */
19
+ * unit tests that wire raw postgres without dedicated roles. In
20
+ * 2-pool mode, only the pools actually supplied are validated. */
14
21
  validateRoles?: boolean;
15
22
  /** Slow-acquire threshold in ms — propagated to PgClientPool. */
16
23
  slowAcquireMs?: number;
@@ -41,5 +48,15 @@ export declare class PoolCredentialMismatch extends DbRlsError {
41
48
  * per the spec's failure modes.
42
49
  */
43
50
  export declare function configureDbRls(opts: ConfigureDbRlsOpts): Promise<void>;
51
+ /**
52
+ * Convenience wrapper for nodii-auth-shape services per 08-rls § 7.
53
+ * Equivalent to `configureDbRls({ ..., mode: "2-pool" })`.
54
+ */
55
+ export declare function configureDbRls2Pool(opts: Omit<ConfigureDbRlsOpts, "mode"> & {
56
+ pools: {
57
+ owner: Pool;
58
+ services?: Pool;
59
+ };
60
+ }): Promise<void>;
44
61
  export declare function _resetConfigureForTests(): void;
45
62
  //# sourceMappingURL=configure.d.ts.map
@@ -1 +1 @@
1
- {"version":3,"file":"configure.d.ts","sourceRoot":"","sources":["../src/configure.ts"],"names":[],"mappings":"AAWA,OAAO,KAAK,EAAE,IAAI,EAAE,MAAM,IAAI,CAAC;AAC/B,OAAO,EAAE,UAAU,EAAE,KAAK,QAAQ,EAAE,MAAM,SAAS,CAAC;AAIpD,MAAM,WAAW,kBAAkB;IACjC,2EAA2E;IAC3E,WAAW,EAAE,MAAM,CAAC;IACpB,oEAAoE;IACpE,KAAK,EAAE;QACL,KAAK,EAAE,IAAI,CAAC;QACZ,QAAQ,EAAE,IAAI,CAAC;QACf,aAAa,EAAE,IAAI,CAAC;KACrB,CAAC;IACF;qEACiE;IACjE,aAAa,CAAC,EAAE,OAAO,CAAC;IACxB,iEAAiE;IACjE,aAAa,CAAC,EAAE,MAAM,CAAC;IACvB,uCAAuC;IACvC,aAAa,CAAC,EAAE,CAAC,IAAI,EAAE;QAAE,IAAI,EAAE,QAAQ,CAAC;QAAC,UAAU,EAAE,MAAM,CAAA;KAAE,KAAK,IAAI,CAAC;IACvE,uDAAuD;IACvD,UAAU,CAAC,EAAE,CAAC,IAAI,EAAE;QAClB,IAAI,EAAE,QAAQ,CAAC;QACf,OAAO,EAAE,WAAW,GAAG,aAAa,GAAG,OAAO,CAAC;QAC/C,UAAU,EAAE,MAAM,CAAC;KACpB,KAAK,IAAI,CAAC;CACZ;AAQD,qBAAa,sBAAuB,SAAQ,UAAU;IACpD,QAAQ,CAAC,IAAI,EAAE,QAAQ,CAAC;IACxB,QAAQ,CAAC,QAAQ,EAAE,MAAM,CAAC;IAC1B,QAAQ,CAAC,MAAM,EAAE,MAAM,CAAC;gBACZ,IAAI,EAAE,QAAQ,EAAE,QAAQ,EAAE,MAAM,EAAE,MAAM,EAAE,MAAM;CAS7D;AAED;;;;;;;GAOG;AACH,wBAAsB,cAAc,CAAC,IAAI,EAAE,kBAAkB,GAAG,OAAO,CAAC,IAAI,CAAC,CA8B5E;AAgBD,wBAAgB,uBAAuB,IAAI,IAAI,CAE9C"}
1
+ {"version":3,"file":"configure.d.ts","sourceRoot":"","sources":["../src/configure.ts"],"names":[],"mappings":"AAcA,OAAO,KAAK,EAAE,IAAI,EAAE,MAAM,IAAI,CAAC;AAC/B,OAAO,EAEL,KAAK,SAAS,EACd,UAAU,EACV,KAAK,QAAQ,EACd,MAAM,SAAS,CAAC;AAIjB,MAAM,WAAW,mBAAmB;IAClC,KAAK,EAAE,IAAI,CAAC;IACZ,QAAQ,CAAC,EAAE,IAAI,CAAC;IAChB,aAAa,CAAC,EAAE,IAAI,CAAC;CACtB;AAED,MAAM,WAAW,kBAAkB;IACjC,2EAA2E;IAC3E,WAAW,EAAE,MAAM,CAAC;IACpB;;0CAEsC;IACtC,KAAK,EAAE,mBAAmB,CAAC;IAC3B;oDACgD;IAChD,IAAI,CAAC,EAAE,SAAS,CAAC;IACjB;;uEAEmE;IACnE,aAAa,CAAC,EAAE,OAAO,CAAC;IACxB,iEAAiE;IACjE,aAAa,CAAC,EAAE,MAAM,CAAC;IACvB,uCAAuC;IACvC,aAAa,CAAC,EAAE,CAAC,IAAI,EAAE;QAAE,IAAI,EAAE,QAAQ,CAAC;QAAC,UAAU,EAAE,MAAM,CAAA;KAAE,KAAK,IAAI,CAAC;IACvE,uDAAuD;IACvD,UAAU,CAAC,EAAE,CAAC,IAAI,EAAE;QAClB,IAAI,EAAE,QAAQ,CAAC;QACf,OAAO,EAAE,WAAW,GAAG,aAAa,GAAG,OAAO,CAAC;QAC/C,UAAU,EAAE,MAAM,CAAC;KACpB,KAAK,IAAI,CAAC;CACZ;AAQD,qBAAa,sBAAuB,SAAQ,UAAU;IACpD,QAAQ,CAAC,IAAI,EAAE,QAAQ,CAAC;IACxB,QAAQ,CAAC,QAAQ,EAAE,MAAM,CAAC;IAC1B,QAAQ,CAAC,MAAM,EAAE,MAAM,CAAC;gBACZ,IAAI,EAAE,QAAQ,EAAE,QAAQ,EAAE,MAAM,EAAE,MAAM,EAAE,MAAM;CAS7D;AAED;;;;;;;GAOG;AACH,wBAAsB,cAAc,CAAC,IAAI,EAAE,kBAAkB,GAAG,OAAO,CAAC,IAAI,CAAC,CAqD5E;AAED;;;GAGG;AACH,wBAAsB,mBAAmB,CACvC,IAAI,EAAE,IAAI,CAAC,kBAAkB,EAAE,MAAM,CAAC,GAAG;IACvC,KAAK,EAAE;QAAE,KAAK,EAAE,IAAI,CAAC;QAAC,QAAQ,CAAC,EAAE,IAAI,CAAA;KAAE,CAAC;CACzC,GACA,OAAO,CAAC,IAAI,CAAC,CAMf;AAgBD,wBAAgB,uBAAuB,IAAI,IAAI,CAE9C"}
package/dist/configure.js CHANGED
@@ -8,7 +8,10 @@
8
8
  // wiring code.
9
9
  // - Service name binding (currently used for log lines; future
10
10
  // telemetry resource attribute).
11
- import { DbRlsError } from "./types";
11
+ //
12
+ // v0.2.x supports the `2-pool` mode per 08-rls § 7 — nodii-auth boots
13
+ // with owner + (optional) services only.
14
+ import { DbRlsConfigError, DbRlsError, } from "./types";
12
15
  import { _resetForTests as resetInit, initDbRls } from "./init";
13
16
  import { PgClientPool } from "./pg-pool-adapter";
14
17
  const EXPECTED_ROLES = {
@@ -37,11 +40,24 @@ export class PoolCredentialMismatch extends DbRlsError {
37
40
  * per the spec's failure modes.
38
41
  */
39
42
  export async function configureDbRls(opts) {
43
+ const mode = opts.mode ?? "3-pool";
40
44
  const validate = opts.validateRoles ?? true;
45
+ if (mode === "3-pool") {
46
+ if (!opts.pools.services || !opts.pools.authenticated) {
47
+ throw new DbRlsConfigError("configureDbRls: 3-pool mode requires owner + services + authenticated pools. Either supply both, or set mode: '2-pool'.");
48
+ }
49
+ }
50
+ if (mode === "2-pool" && opts.pools.authenticated) {
51
+ throw new DbRlsConfigError("configureDbRls: 2-pool mode must not supply an 'authenticated' pool — the 2-pool exception per 08-rls § 7 has no user-context. Use mode: '3-pool' instead.");
52
+ }
41
53
  if (validate) {
42
54
  await assertPoolRole(opts.pools.owner, "owner");
43
- await assertPoolRole(opts.pools.services, "services");
44
- await assertPoolRole(opts.pools.authenticated, "authenticated");
55
+ if (opts.pools.services) {
56
+ await assertPoolRole(opts.pools.services, "services");
57
+ }
58
+ if (opts.pools.authenticated) {
59
+ await assertPoolRole(opts.pools.authenticated, "authenticated");
60
+ }
45
61
  }
46
62
  const owner = new PgClientPool({
47
63
  pool: opts.pools.owner,
@@ -50,21 +66,36 @@ export async function configureDbRls(opts) {
50
66
  onSlowAcquire: opts.onSlowAcquire,
51
67
  onTxFinish: opts.onTxFinish,
52
68
  });
53
- const services = new PgClientPool({
54
- pool: opts.pools.services,
55
- kind: "services",
56
- slowAcquireMs: opts.slowAcquireMs,
57
- onSlowAcquire: opts.onSlowAcquire,
58
- onTxFinish: opts.onTxFinish,
59
- });
60
- const authenticated = new PgClientPool({
61
- pool: opts.pools.authenticated,
62
- kind: "authenticated",
63
- slowAcquireMs: opts.slowAcquireMs,
64
- onSlowAcquire: opts.onSlowAcquire,
65
- onTxFinish: opts.onTxFinish,
69
+ const services = opts.pools.services
70
+ ? new PgClientPool({
71
+ pool: opts.pools.services,
72
+ kind: "services",
73
+ slowAcquireMs: opts.slowAcquireMs,
74
+ onSlowAcquire: opts.onSlowAcquire,
75
+ onTxFinish: opts.onTxFinish,
76
+ })
77
+ : undefined;
78
+ const authenticated = opts.pools.authenticated
79
+ ? new PgClientPool({
80
+ pool: opts.pools.authenticated,
81
+ kind: "authenticated",
82
+ slowAcquireMs: opts.slowAcquireMs,
83
+ onSlowAcquire: opts.onSlowAcquire,
84
+ onTxFinish: opts.onTxFinish,
85
+ })
86
+ : undefined;
87
+ initDbRls({ owner, services, authenticated, mode });
88
+ }
89
+ /**
90
+ * Convenience wrapper for nodii-auth-shape services per 08-rls § 7.
91
+ * Equivalent to `configureDbRls({ ..., mode: "2-pool" })`.
92
+ */
93
+ export async function configureDbRls2Pool(opts) {
94
+ return configureDbRls({
95
+ ...opts,
96
+ mode: "2-pool",
97
+ pools: { owner: opts.pools.owner, services: opts.pools.services },
66
98
  });
67
- initDbRls({ owner, services, authenticated });
68
99
  }
69
100
  async function assertPoolRole(pool, kind) {
70
101
  const expected = EXPECTED_ROLES[kind];
@@ -1 +1 @@
1
- {"version":3,"file":"configure.js","sourceRoot":"","sources":["../src/configure.ts"],"names":[],"mappings":"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"}
1
+ {"version":3,"file":"configure.js","sourceRoot":"","sources":["../src/configure.ts"],"names":[],"mappings":"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"}
package/dist/context.d.ts CHANGED
@@ -1,3 +1,4 @@
1
+ import { type OwnerContextOpts } from "./migrate-guard";
1
2
  import { type AutoDispatchOpts, type PgTx, type SystemContextOpts, type UserContextOpts } from "./types";
2
3
  /**
3
4
  * withUserContext — opens a tx on the `authenticated` pool, sets
@@ -19,13 +20,14 @@ export declare function withSystemContext<T>(opts: SystemContextOpts, fn: (tx: P
19
20
  * withOwnerContext — opens a tx on the `owner` (nodii_owner BYPASSRLS)
20
21
  * pool. No GUCs are set — owner is the migrations-only context.
21
22
  *
22
- * NOTE: v0.1.0 ships this on the runtime barrel for symmetry. The spec
23
- * § 5.3 + § Open Q3 calls out that future v0.1.x moves this to
24
- * `@nodii/db-rls/migrate` sub-package + adds a `NODII_ENV=migrate`
25
- * runtime guard. Documented as `// TODO db-rls-v0.1.x: move to /migrate
26
- * sub-package + NODII_ENV guard`.
23
+ * Per `08-rls-doctrine § 10.2`, callers MUST satisfy the migrate guard:
24
+ * - `NODII_ENV=migrate` (typical migration runner shape), OR
25
+ * - explicit `{ allowOutsideMigrate: true, reason: "..." }` with an
26
+ * operator-attested reason (ops tooling shape).
27
+ *
28
+ * Throws `OwnerContextOutsideMigrate` if neither is satisfied.
27
29
  */
28
- export declare function withOwnerContext<T>(fn: (tx: PgTx) => Promise<T>): Promise<T>;
30
+ export declare function withOwnerContext<T>(fnOrOpts: OwnerContextOpts | ((tx: PgTx) => Promise<T>), maybeFn?: (tx: PgTx) => Promise<T>): Promise<T>;
29
31
  /**
30
32
  * autoDispatch — chooses the right pool based on what's bound.
31
33
  *
@@ -1 +1 @@
1
- {"version":3,"file":"context.d.ts","sourceRoot":"","sources":["../src/context.ts"],"names":[],"mappings":"AAQA,OAAO,EACL,KAAK,gBAAgB,EAErB,KAAK,IAAI,EACT,KAAK,iBAAiB,EAEtB,KAAK,eAAe,EACrB,MAAM,SAAS,CAAC;AAEjB;;;;;;;;GAQG;AACH,wBAAsB,eAAe,CAAC,CAAC,EACrC,IAAI,EAAE,eAAe,EACrB,EAAE,EAAE,CAAC,EAAE,EAAE,IAAI,KAAK,OAAO,CAAC,CAAC,CAAC,GAC3B,OAAO,CAAC,CAAC,CAAC,CAcZ;AAED;;;;GAIG;AACH,wBAAsB,iBAAiB,CAAC,CAAC,EACvC,IAAI,EAAE,iBAAiB,EACvB,EAAE,EAAE,CAAC,EAAE,EAAE,IAAI,KAAK,OAAO,CAAC,CAAC,CAAC,GAC3B,OAAO,CAAC,CAAC,CAAC,CAUZ;AAED;;;;;;;;;GASG;AACH,wBAAsB,gBAAgB,CAAC,CAAC,EACtC,EAAE,EAAE,CAAC,EAAE,EAAE,IAAI,KAAK,OAAO,CAAC,CAAC,CAAC,GAC3B,OAAO,CAAC,CAAC,CAAC,CASZ;AAED;;;;;;;;;;;;GAYG;AACH,wBAAsB,YAAY,CAAC,CAAC,EAClC,IAAI,EAAE,gBAAgB,EACtB,EAAE,EAAE,CAAC,EAAE,EAAE,IAAI,KAAK,OAAO,CAAC,CAAC,CAAC,GAC3B,OAAO,CAAC,CAAC,CAAC,CAeZ"}
1
+ {"version":3,"file":"context.d.ts","sourceRoot":"","sources":["../src/context.ts"],"names":[],"mappings":"AASA,OAAO,EAAwB,KAAK,gBAAgB,EAAE,MAAM,iBAAiB,CAAC;AAC9E,OAAO,EACL,KAAK,gBAAgB,EAErB,KAAK,IAAI,EACT,KAAK,iBAAiB,EAEtB,KAAK,eAAe,EACrB,MAAM,SAAS,CAAC;AAEjB;;;;;;;;GAQG;AACH,wBAAsB,eAAe,CAAC,CAAC,EACrC,IAAI,EAAE,eAAe,EACrB,EAAE,EAAE,CAAC,EAAE,EAAE,IAAI,KAAK,OAAO,CAAC,CAAC,CAAC,GAC3B,OAAO,CAAC,CAAC,CAAC,CAcZ;AAED;;;;GAIG;AACH,wBAAsB,iBAAiB,CAAC,CAAC,EACvC,IAAI,EAAE,iBAAiB,EACvB,EAAE,EAAE,CAAC,EAAE,EAAE,IAAI,KAAK,OAAO,CAAC,CAAC,CAAC,GAC3B,OAAO,CAAC,CAAC,CAAC,CAUZ;AAED;;;;;;;;;;GAUG;AACH,wBAAsB,gBAAgB,CAAC,CAAC,EACtC,QAAQ,EAAE,gBAAgB,GAAG,CAAC,CAAC,EAAE,EAAE,IAAI,KAAK,OAAO,CAAC,CAAC,CAAC,CAAC,EACvD,OAAO,CAAC,EAAE,CAAC,EAAE,EAAE,IAAI,KAAK,OAAO,CAAC,CAAC,CAAC,GACjC,OAAO,CAAC,CAAC,CAAC,CAiBZ;AAiBD;;;;;;;;;;;;GAYG;AACH,wBAAsB,YAAY,CAAC,CAAC,EAClC,IAAI,EAAE,gBAAgB,EACtB,EAAE,EAAE,CAAC,EAAE,EAAE,IAAI,KAAK,OAAO,CAAC,CAAC,CAAC,GAC3B,OAAO,CAAC,CAAC,CAAC,CAeZ"}
package/dist/context.js CHANGED
@@ -5,6 +5,8 @@
5
5
  // commits / rollbacks per the underlying PgPool's withTransaction
6
6
  // contract.
7
7
  import { requirePool } from "./init";
8
+ import { recordOwnerContextInvocation } from "./metrics";
9
+ import { assertMigrateAllowed } from "./migrate-guard";
8
10
  import { MissingTenantContext, TransactionRolledBack, } from "./types";
9
11
  /**
10
12
  * withUserContext — opens a tx on the `authenticated` pool, sets
@@ -52,13 +54,23 @@ export async function withSystemContext(opts, fn) {
52
54
  * withOwnerContext — opens a tx on the `owner` (nodii_owner BYPASSRLS)
53
55
  * pool. No GUCs are set — owner is the migrations-only context.
54
56
  *
55
- * NOTE: v0.1.0 ships this on the runtime barrel for symmetry. The spec
56
- * § 5.3 + § Open Q3 calls out that future v0.1.x moves this to
57
- * `@nodii/db-rls/migrate` sub-package + adds a `NODII_ENV=migrate`
58
- * runtime guard. Documented as `// TODO db-rls-v0.1.x: move to /migrate
59
- * sub-package + NODII_ENV guard`.
57
+ * Per `08-rls-doctrine § 10.2`, callers MUST satisfy the migrate guard:
58
+ * - `NODII_ENV=migrate` (typical migration runner shape), OR
59
+ * - explicit `{ allowOutsideMigrate: true, reason: "..." }` with an
60
+ * operator-attested reason (ops tooling shape).
61
+ *
62
+ * Throws `OwnerContextOutsideMigrate` if neither is satisfied.
60
63
  */
61
- export async function withOwnerContext(fn) {
64
+ export async function withOwnerContext(fnOrOpts, maybeFn) {
65
+ const { opts, fn } = normalizeOwnerArgs(fnOrOpts, maybeFn);
66
+ try {
67
+ assertMigrateAllowed(opts);
68
+ }
69
+ catch (err) {
70
+ recordOwnerContextInvocation("refused");
71
+ throw err;
72
+ }
73
+ recordOwnerContextInvocation("allowed");
62
74
  const pool = requirePool("owner");
63
75
  return pool.withTransaction(async (tx) => {
64
76
  try {
@@ -69,6 +81,15 @@ export async function withOwnerContext(fn) {
69
81
  }
70
82
  });
71
83
  }
84
+ function normalizeOwnerArgs(fnOrOpts, maybeFn) {
85
+ if (typeof fnOrOpts === "function") {
86
+ return { opts: {}, fn: fnOrOpts };
87
+ }
88
+ if (!maybeFn) {
89
+ throw new TypeError("withOwnerContext: when opts are passed, the second argument must be the callback.");
90
+ }
91
+ return { opts: fnOrOpts, fn: maybeFn };
92
+ }
72
93
  /**
73
94
  * autoDispatch — chooses the right pool based on what's bound.
74
95
  *
@@ -1 +1 @@
1
- {"version":3,"file":"context.js","sourceRoot":"","sources":["../src/context.ts"],"names":[],"mappings":"AAAA,gDAAgD;AAChD,EAAE;AACF,uEAAuE;AACvE,0EAA0E;AAC1E,kEAAkE;AAClE,YAAY;AAEZ,OAAO,EAAE,WAAW,EAAE,MAAM,QAAQ,CAAC;AACrC,OAAO,EAEL,oBAAoB,EAGpB,qBAAqB,GAEtB,MAAM,SAAS,CAAC;AAEjB;;;;;;;;GAQG;AACH,MAAM,CAAC,KAAK,UAAU,eAAe,CACnC,IAAqB,EACrB,EAA4B;IAE5B,MAAM,IAAI,GAAG,WAAW,CAAC,eAAe,CAAC,CAAC;IAC1C,OAAO,IAAI,CAAC,eAAe,CAAC,KAAK,EAAE,EAAE,EAAE,EAAE;QACvC,MAAM,EAAE,CAAC,SAAS,CAAC,cAAc,EAAE,IAAI,CAAC,MAAM,CAAC,CAAC;QAChD,MAAM,EAAE,CAAC,SAAS,CAAC,gBAAgB,EAAE,IAAI,CAAC,QAAQ,CAAC,CAAC;QACpD,IAAI,IAAI,CAAC,QAAQ,KAAK,SAAS,EAAE,CAAC;YAChC,MAAM,EAAE,CAAC,SAAS,CAAC,gBAAgB,EAAE,IAAI,CAAC,QAAQ,CAAC,CAAC;QACtD,CAAC;QACD,IAAI,CAAC;YACH,OAAO,MAAM,EAAE,CAAC,EAAE,CAAC,CAAC;QACtB,CAAC;QAAC,OAAO,KAAK,EAAE,CAAC;YACf,MAAM,IAAI,qBAAqB,CAAC,KAAK,CAAC,CAAC;QACzC,CAAC;IACH,CAAC,CAAC,CAAC;AACL,CAAC;AAED;;;;GAIG;AACH,MAAM,CAAC,KAAK,UAAU,iBAAiB,CACrC,IAAuB,EACvB,EAA4B;IAE5B,MAAM,IAAI,GAAG,WAAW,CAAC,UAAU,CAAC,CAAC;IACrC,OAAO,IAAI,CAAC,eAAe,CAAC,KAAK,EAAE,EAAE,EAAE,EAAE;QACvC,MAAM,EAAE,CAAC,SAAS,CAAC,eAAe,EAAE,IAAI,CAAC,QAAQ,CAAC,CAAC;QACnD,IAAI,CAAC;YACH,OAAO,MAAM,EAAE,CAAC,EAAE,CAAC,CAAC;QACtB,CAAC;QAAC,OAAO,KAAK,EAAE,CAAC;YACf,MAAM,IAAI,qBAAqB,CAAC,KAAK,CAAC,CAAC;QACzC,CAAC;IACH,CAAC,CAAC,CAAC;AACL,CAAC;AAED;;;;;;;;;GASG;AACH,MAAM,CAAC,KAAK,UAAU,gBAAgB,CACpC,EAA4B;IAE5B,MAAM,IAAI,GAAG,WAAW,CAAC,OAAO,CAAC,CAAC;IAClC,OAAO,IAAI,CAAC,eAAe,CAAC,KAAK,EAAE,EAAE,EAAE,EAAE;QACvC,IAAI,CAAC;YACH,OAAO,MAAM,EAAE,CAAC,EAAE,CAAC,CAAC;QACtB,CAAC;QAAC,OAAO,KAAK,EAAE,CAAC;YACf,MAAM,IAAI,qBAAqB,CAAC,KAAK,CAAC,CAAC;QACzC,CAAC;IACH,CAAC,CAAC,CAAC;AACL,CAAC;AAED;;;;;;;;;;;;GAYG;AACH,MAAM,CAAC,KAAK,UAAU,YAAY,CAChC,IAAsB,EACtB,EAA4B;IAE5B,IAAI,IAAI,CAAC,WAAW,EAAE,CAAC;QACrB,OAAO,eAAe,CACpB;YACE,MAAM,EAAE,IAAI,CAAC,WAAW,CAAC,MAAM;YAC/B,QAAQ,EAAE,IAAI,CAAC,WAAW,CAAC,QAAQ;YACnC,QAAQ,EAAE,IAAI,CAAC,WAAW,CAAC,QAAQ;SACpC,EACD,EAAE,CACH,CAAC;IACJ,CAAC;IACD,IAAI,IAAI,CAAC,QAAQ,KAAK,SAAS,EAAE,CAAC;QAChC,OAAO,iBAAiB,CAAC,EAAE,QAAQ,EAAE,IAAI,CAAC,QAAQ,EAAE,EAAE,EAAE,CAAC,CAAC;IAC5D,CAAC;IACD,MAAM,IAAI,oBAAoB,EAAE,CAAC;AACnC,CAAC"}
1
+ {"version":3,"file":"context.js","sourceRoot":"","sources":["../src/context.ts"],"names":[],"mappings":"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"}
@@ -1,4 +1,5 @@
1
1
  import { type NodePgDatabase } from "drizzle-orm/node-postgres";
2
+ import { type OwnerContextOpts } from "./migrate-guard";
2
3
  import type { SystemContextOpts, UserContextOpts } from "./types";
3
4
  type DrizzleClient<TSchema extends Record<string, unknown> = Record<string, unknown>> = NodePgDatabase<TSchema>;
4
5
  /**
@@ -15,8 +16,14 @@ export declare function withUserContextDb<T, TSchema extends Record<string, unkn
15
16
  export declare function withSystemContextDb<T, TSchema extends Record<string, unknown> = Record<string, unknown>>(opts: SystemContextOpts, fn: (db: DrizzleClient<TSchema>) => Promise<T>): Promise<T>;
16
17
  /**
17
18
  * withOwnerContext (Drizzle variant) — opens a tx on the `owner`
18
- * (BYPASSRLS) pool; no GUCs. Migrations only per § 5.3 + Q3.
19
+ * (BYPASSRLS) pool; no GUCs.
20
+ *
21
+ * Per `08-rls-doctrine § 10.2`, callers MUST satisfy the migrate guard:
22
+ * - `NODII_ENV=migrate`, OR
23
+ * - explicit `{ allowOutsideMigrate: true, reason: "..." }`.
24
+ *
25
+ * Throws `OwnerContextOutsideMigrate` if neither is satisfied.
19
26
  */
20
- export declare function withOwnerContextDb<T, TSchema extends Record<string, unknown> = Record<string, unknown>>(fn: (db: DrizzleClient<TSchema>) => Promise<T>): Promise<T>;
27
+ export declare function withOwnerContextDb<T, TSchema extends Record<string, unknown> = Record<string, unknown>>(fnOrOpts: OwnerContextOpts | ((db: DrizzleClient<TSchema>) => Promise<T>), maybeFn?: (db: DrizzleClient<TSchema>) => Promise<T>): Promise<T>;
21
28
  export type { DrizzleClient, NodePgDatabase };
22
29
  //# sourceMappingURL=drizzle-client.d.ts.map
@@ -1 +1 @@
1
- {"version":3,"file":"drizzle-client.d.ts","sourceRoot":"","sources":["../src/drizzle-client.ts"],"names":[],"mappings":"AAmBA,OAAO,EAAW,KAAK,cAAc,EAAE,MAAM,2BAA2B,CAAC;AAKzE,OAAO,KAAK,EAAE,iBAAiB,EAAE,eAAe,EAAE,MAAM,SAAS,CAAC;AAOlE,KAAK,aAAa,CAChB,OAAO,SAAS,MAAM,CAAC,MAAM,EAAE,OAAO,CAAC,GAAG,MAAM,CAAC,MAAM,EAAE,OAAO,CAAC,IAC/D,cAAc,CAAC,OAAO,CAAC,CAAC;AAmD5B;;;;;GAKG;AACH,wBAAsB,iBAAiB,CACrC,CAAC,EACD,OAAO,SAAS,MAAM,CAAC,MAAM,EAAE,OAAO,CAAC,GAAG,MAAM,CAAC,MAAM,EAAE,OAAO,CAAC,EAEjE,IAAI,EAAE,eAAe,EACrB,EAAE,EAAE,CAAC,EAAE,EAAE,aAAa,CAAC,OAAO,CAAC,KAAK,OAAO,CAAC,CAAC,CAAC,GAC7C,OAAO,CAAC,CAAC,CAAC,CAoBZ;AAED;;;GAGG;AACH,wBAAsB,mBAAmB,CACvC,CAAC,EACD,OAAO,SAAS,MAAM,CAAC,MAAM,EAAE,OAAO,CAAC,GAAG,MAAM,CAAC,MAAM,EAAE,OAAO,CAAC,EAEjE,IAAI,EAAE,iBAAiB,EACvB,EAAE,EAAE,CAAC,EAAE,EAAE,aAAa,CAAC,OAAO,CAAC,KAAK,OAAO,CAAC,CAAC,CAAC,GAC7C,OAAO,CAAC,CAAC,CAAC,CAUZ;AAED;;;GAGG;AACH,wBAAsB,kBAAkB,CACtC,CAAC,EACD,OAAO,SAAS,MAAM,CAAC,MAAM,EAAE,OAAO,CAAC,GAAG,MAAM,CAAC,MAAM,EAAE,OAAO,CAAC,EACjE,EAAE,EAAE,CAAC,EAAE,EAAE,aAAa,CAAC,OAAO,CAAC,KAAK,OAAO,CAAC,CAAC,CAAC,GAAG,OAAO,CAAC,CAAC,CAAC,CAO5D;AAED,YAAY,EAAE,aAAa,EAAE,cAAc,EAAE,CAAC"}
1
+ {"version":3,"file":"drizzle-client.d.ts","sourceRoot":"","sources":["../src/drizzle-client.ts"],"names":[],"mappings":"AAmBA,OAAO,EAAW,KAAK,cAAc,EAAE,MAAM,2BAA2B,CAAC;AAKzE,OAAO,EAAwB,KAAK,gBAAgB,EAAE,MAAM,iBAAiB,CAAC;AAE9E,OAAO,KAAK,EAAE,iBAAiB,EAAE,eAAe,EAAE,MAAM,SAAS,CAAC;AAOlE,KAAK,aAAa,CAChB,OAAO,SAAS,MAAM,CAAC,MAAM,EAAE,OAAO,CAAC,GAAG,MAAM,CAAC,MAAM,EAAE,OAAO,CAAC,IAC/D,cAAc,CAAC,OAAO,CAAC,CAAC;AAmD5B;;;;;GAKG;AACH,wBAAsB,iBAAiB,CACrC,CAAC,EACD,OAAO,SAAS,MAAM,CAAC,MAAM,EAAE,OAAO,CAAC,GAAG,MAAM,CAAC,MAAM,EAAE,OAAO,CAAC,EAEjE,IAAI,EAAE,eAAe,EACrB,EAAE,EAAE,CAAC,EAAE,EAAE,aAAa,CAAC,OAAO,CAAC,KAAK,OAAO,CAAC,CAAC,CAAC,GAC7C,OAAO,CAAC,CAAC,CAAC,CAoBZ;AAED;;;GAGG;AACH,wBAAsB,mBAAmB,CACvC,CAAC,EACD,OAAO,SAAS,MAAM,CAAC,MAAM,EAAE,OAAO,CAAC,GAAG,MAAM,CAAC,MAAM,EAAE,OAAO,CAAC,EAEjE,IAAI,EAAE,iBAAiB,EACvB,EAAE,EAAE,CAAC,EAAE,EAAE,aAAa,CAAC,OAAO,CAAC,KAAK,OAAO,CAAC,CAAC,CAAC,GAC7C,OAAO,CAAC,CAAC,CAAC,CAUZ;AAED;;;;;;;;;GASG;AACH,wBAAsB,kBAAkB,CACtC,CAAC,EACD,OAAO,SAAS,MAAM,CAAC,MAAM,EAAE,OAAO,CAAC,GAAG,MAAM,CAAC,MAAM,EAAE,OAAO,CAAC,EAEjE,QAAQ,EAAE,gBAAgB,GAAG,CAAC,CAAC,EAAE,EAAE,aAAa,CAAC,OAAO,CAAC,KAAK,OAAO,CAAC,CAAC,CAAC,CAAC,EACzE,OAAO,CAAC,EAAE,CAAC,EAAE,EAAE,aAAa,CAAC,OAAO,CAAC,KAAK,OAAO,CAAC,CAAC,CAAC,GACnD,OAAO,CAAC,CAAC,CAAC,CAeZ;AAoBD,YAAY,EAAE,aAAa,EAAE,cAAc,EAAE,CAAC"}
@@ -18,6 +18,8 @@
18
18
  // services using the raw `PgTx` surface.
19
19
  import { drizzle } from "drizzle-orm/node-postgres";
20
20
  import { requirePool } from "./init";
21
+ import { recordOwnerContextInvocation } from "./metrics";
22
+ import { assertMigrateAllowed } from "./migrate-guard";
21
23
  import { PgClientPool } from "./pg-pool-adapter";
22
24
  import { MissingTenantContext, TransactionRolledBack } from "./types";
23
25
  function clientFor(_pool) {
@@ -100,10 +102,34 @@ export async function withSystemContextDb(opts, fn) {
100
102
  }
101
103
  /**
102
104
  * withOwnerContext (Drizzle variant) — opens a tx on the `owner`
103
- * (BYPASSRLS) pool; no GUCs. Migrations only per § 5.3 + Q3.
105
+ * (BYPASSRLS) pool; no GUCs.
106
+ *
107
+ * Per `08-rls-doctrine § 10.2`, callers MUST satisfy the migrate guard:
108
+ * - `NODII_ENV=migrate`, OR
109
+ * - explicit `{ allowOutsideMigrate: true, reason: "..." }`.
110
+ *
111
+ * Throws `OwnerContextOutsideMigrate` if neither is satisfied.
104
112
  */
105
- export async function withOwnerContextDb(fn) {
113
+ export async function withOwnerContextDb(fnOrOpts, maybeFn) {
114
+ const { opts, fn } = normalizeOwnerDbArgs(fnOrOpts, maybeFn);
115
+ try {
116
+ assertMigrateAllowed(opts);
117
+ }
118
+ catch (err) {
119
+ recordOwnerContextInvocation("refused");
120
+ throw err;
121
+ }
122
+ recordOwnerContextInvocation("allowed");
106
123
  const pool = requireRealPool("owner");
107
124
  return withRealTx(pool, async () => { }, (db) => fn(db));
108
125
  }
126
+ function normalizeOwnerDbArgs(fnOrOpts, maybeFn) {
127
+ if (typeof fnOrOpts === "function") {
128
+ return { opts: {}, fn: fnOrOpts };
129
+ }
130
+ if (!maybeFn) {
131
+ throw new TypeError("withOwnerContextDb: when opts are passed, the second argument must be the callback.");
132
+ }
133
+ return { opts: fnOrOpts, fn: maybeFn };
134
+ }
109
135
  //# sourceMappingURL=drizzle-client.js.map
@@ -1 +1 @@
1
- {"version":3,"file":"drizzle-client.js","sourceRoot":"","sources":["../src/drizzle-client.ts"],"names":[],"mappings":"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"}
1
+ {"version":3,"file":"drizzle-client.js","sourceRoot":"","sources":["../src/drizzle-client.ts"],"names":[],"mappings":"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"}
@@ -0,0 +1,23 @@
1
+ import type { PgColumn, PgPolicy } from "drizzle-orm/pg-core";
2
+ import type { WithRlsOpts } from "./rls-policy-gen";
3
+ /**
4
+ * Returns the canonical 5-policy Drizzle constructs (per doctrine § 4)
5
+ * for a tenant-scoped table.
6
+ *
7
+ * Default (`allow=["SELECT","INSERT"]`) emits:
8
+ *
9
+ * 1. `<table>_owner` FOR ALL TO nodii_owner USING (true) WITH CHECK (true)
10
+ * 2. `<table>_auth_select` FOR SELECT TO authenticated USING (<col> IN (SELECT auth.user_tenant_ids(auth.get_user_id())))
11
+ * 3. `<table>_auth_insert` FOR INSERT TO authenticated WITH CHECK (...)
12
+ * 4. `<table>_svc_select` FOR SELECT TO nodii_services USING (<col> = auth.get_tenant_id())
13
+ * 5. `<table>_svc_insert` FOR INSERT TO nodii_services WITH CHECK (...)
14
+ *
15
+ * Extending `allow` to include `"UPDATE"` / `"DELETE"` adds the
16
+ * corresponding verb policies for both auth + svc.
17
+ *
18
+ * `t.tenantId` must be a Drizzle column reference (used to thread the
19
+ * column name + table binding into the policy `link(table)` step that
20
+ * drizzle-kit performs).
21
+ */
22
+ export declare function withRls(tenantCol: PgColumn, opts?: WithRlsOpts): PgPolicy[];
23
+ //# sourceMappingURL=drizzle-policies.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"drizzle-policies.d.ts","sourceRoot":"","sources":["../src/drizzle-policies.ts"],"names":[],"mappings":"AA8BA,OAAO,KAAK,EAAE,QAAQ,EAAE,QAAQ,EAAE,MAAM,qBAAqB,CAAC;AAE9D,OAAO,KAAK,EAAW,WAAW,EAAE,MAAM,kBAAkB,CAAC;AAI7D;;;;;;;;;;;;;;;;;;GAkBG;AACH,wBAAgB,OAAO,CACrB,SAAS,EAAE,QAAQ,EACnB,IAAI,GAAE,WAAgB,GACrB,QAAQ,EAAE,CAsCZ"}
@@ -0,0 +1,114 @@
1
+ // Drizzle table-builder helper — `withRls(t.tenantId)` per doctrine § 4.2.
2
+ //
3
+ // Exposed via subpath `@nodii/db-rls/drizzle`. Returns an array of
4
+ // `PgPolicy` constructs that consumers spread into Drizzle's third-arg
5
+ // extras callback:
6
+ //
7
+ // import { withRls } from "@nodii/db-rls/drizzle";
8
+ //
9
+ // export const billingInvoices = pgTable("billing_invoices", {
10
+ // id: uuid("id").primaryKey().defaultRandom(),
11
+ // tenantId: uuid("tenant_id").notNull(),
12
+ // amount: integer("amount").notNull(),
13
+ // }, (t) => [
14
+ // ...withRls(t.tenantId), // default 5 policies
15
+ // // OR with extra verbs:
16
+ // // ...withRls(t.tenantId, { allow: ["SELECT","INSERT","UPDATE","DELETE"] }),
17
+ // ]);
18
+ //
19
+ // Drizzle-kit reads these PgPolicy constructs and emits the canonical
20
+ // 5-policy DDL (§ 4) into the generated migration SQL. Naming follows
21
+ // doctrine § 4 exactly: `<table>_owner`, `<table>_auth_select`,
22
+ // `<table>_auth_insert`, `<table>_svc_select`, `<table>_svc_insert`
23
+ // (no `_policy` suffix).
24
+ //
25
+ // The legacy string-DDL `withRls(table: string)` helper exported from
26
+ // `@nodii/db-rls` (main barrel) keeps its `*_policy` suffix for backwards
27
+ // parity with v0.1.x consumers — both surfaces ship.
28
+ import { getTableName, sql } from "drizzle-orm";
29
+ import { pgPolicy } from "drizzle-orm/pg-core";
30
+ const DEFAULT_ALLOW = ["SELECT", "INSERT"];
31
+ /**
32
+ * Returns the canonical 5-policy Drizzle constructs (per doctrine § 4)
33
+ * for a tenant-scoped table.
34
+ *
35
+ * Default (`allow=["SELECT","INSERT"]`) emits:
36
+ *
37
+ * 1. `<table>_owner` FOR ALL TO nodii_owner USING (true) WITH CHECK (true)
38
+ * 2. `<table>_auth_select` FOR SELECT TO authenticated USING (<col> IN (SELECT auth.user_tenant_ids(auth.get_user_id())))
39
+ * 3. `<table>_auth_insert` FOR INSERT TO authenticated WITH CHECK (...)
40
+ * 4. `<table>_svc_select` FOR SELECT TO nodii_services USING (<col> = auth.get_tenant_id())
41
+ * 5. `<table>_svc_insert` FOR INSERT TO nodii_services WITH CHECK (...)
42
+ *
43
+ * Extending `allow` to include `"UPDATE"` / `"DELETE"` adds the
44
+ * corresponding verb policies for both auth + svc.
45
+ *
46
+ * `t.tenantId` must be a Drizzle column reference (used to thread the
47
+ * column name + table binding into the policy `link(table)` step that
48
+ * drizzle-kit performs).
49
+ */
50
+ export function withRls(tenantCol, opts = {}) {
51
+ const verbs = opts.allow && opts.allow.length > 0 ? opts.allow : DEFAULT_ALLOW;
52
+ const tableName = getTableName(tenantCol.table);
53
+ const policyBase = unqualifiedName(tableName);
54
+ const tenantColumn = opts.tenantColumn ?? tenantCol.name;
55
+ // Authenticated predicate: tenant_id IN (SELECT auth.user_tenant_ids(auth.get_user_id()))
56
+ const authPredicate = sql.raw(`${tenantColumn} IN (SELECT auth.user_tenant_ids(auth.get_user_id()))`);
57
+ // Services predicate: tenant_id = auth.get_tenant_id()
58
+ const svcPredicate = sql.raw(`${tenantColumn} = auth.get_tenant_id()`);
59
+ const policies = [];
60
+ // 1. Owner FOR ALL.
61
+ policies.push(pgPolicy(`${policyBase}_owner`, {
62
+ as: "permissive",
63
+ for: "all",
64
+ to: "nodii_owner",
65
+ using: sql `true`,
66
+ withCheck: sql `true`,
67
+ }));
68
+ // 2. authenticated per verb.
69
+ for (const verb of verbs) {
70
+ policies.push(authPolicyFor(policyBase, verb, authPredicate));
71
+ }
72
+ // 3. nodii_services per verb.
73
+ for (const verb of verbs) {
74
+ policies.push(svcPolicyFor(policyBase, verb, svcPredicate));
75
+ }
76
+ return policies;
77
+ }
78
+ function authPolicyFor(policyBase, verb, predicate) {
79
+ const name = `${policyBase}_auth_${verb.toLowerCase()}`;
80
+ return pgPolicy(name, {
81
+ as: "permissive",
82
+ for: drizzleFor(verb),
83
+ to: "authenticated",
84
+ ...predicates(verb, predicate),
85
+ });
86
+ }
87
+ function svcPolicyFor(policyBase, verb, predicate) {
88
+ const name = `${policyBase}_svc_${verb.toLowerCase()}`;
89
+ return pgPolicy(name, {
90
+ as: "permissive",
91
+ for: drizzleFor(verb),
92
+ to: "nodii_services",
93
+ ...predicates(verb, predicate),
94
+ });
95
+ }
96
+ function drizzleFor(verb) {
97
+ return verb.toLowerCase();
98
+ }
99
+ function predicates(verb, predicate) {
100
+ switch (verb) {
101
+ case "INSERT":
102
+ return { withCheck: predicate };
103
+ case "UPDATE":
104
+ return { using: predicate, withCheck: predicate };
105
+ default:
106
+ // SELECT, DELETE
107
+ return { using: predicate };
108
+ }
109
+ }
110
+ function unqualifiedName(table) {
111
+ const tail = table.includes(".") ? (table.split(".").pop() ?? table) : table;
112
+ return tail.replace(/^"|"$/g, "");
113
+ }
114
+ //# sourceMappingURL=drizzle-policies.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"drizzle-policies.js","sourceRoot":"","sources":["../src/drizzle-policies.ts"],"names":[],"mappings":"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"}
package/dist/index.d.ts CHANGED
@@ -1,14 +1,16 @@
1
1
  export declare const LIB_NAME = "db-rls";
2
- export declare const VERSION = "0.1.1";
2
+ export declare const VERSION = "0.2.3";
3
3
  export { initDbRls, requireDbRls, getDbRlsOrNull, requirePool, _resetForTests, } from "./init";
4
4
  export type { InitDbRlsConfig, ResolvedDbRls } from "./init";
5
- export { configureDbRls, PoolCredentialMismatch, _resetConfigureForTests, } from "./configure";
6
- export type { ConfigureDbRlsOpts } from "./configure";
5
+ export { configureDbRls, configureDbRls2Pool, PoolCredentialMismatch, _resetConfigureForTests, } from "./configure";
6
+ export type { ConfigureDbRlsOpts, ConfigureDbRlsPools, } from "./configure";
7
7
  export { PgClientPool } from "./pg-pool-adapter";
8
8
  export type { PgPoolAdapterOpts } from "./pg-pool-adapter";
9
9
  export { withUserContext, withSystemContext, withOwnerContext, autoDispatch, } from "./context";
10
10
  export { withUserContextDb, withSystemContextDb, withOwnerContextDb, } from "./drizzle-client";
11
11
  export type { DrizzleClient, NodePgDatabase } from "./drizzle-client";
12
+ export type { OwnerContextOpts } from "./migrate-guard";
13
+ export { assertMigrateAllowed } from "./migrate-guard";
12
14
  export { AUTH_SCHEMA_SQL, AUTH_SCHEMA_GRANTS_SQL, applyAuthSchemaMigrations, authSchemaFullSql, } from "./auth-schema";
13
15
  export type { SqlExecutor } from "./auth-schema";
14
16
  export { withRls, generateTableGrants } from "./rls-policy-gen";
@@ -18,6 +20,7 @@ export type { MigrateGenInput, MigrateGenResult } from "./migrate-gen";
18
20
  export { generateRlsPolicy, authSchemaHelpers } from "./rls-policy";
19
21
  export { InMemoryPgPool } from "./in-memory-pool";
20
22
  export type { TranscriptEntry } from "./in-memory-pool";
21
- export { DbRlsError, DbRlsNotInitialized, PoolUnavailable, MissingTenantContext, TransactionRolledBack, } from "./types";
22
- export type { AuthContext, AutoDispatchOpts, GenerateRlsPolicyOpts, PgPool, PgTx, PoolKind, SystemContextOpts, UserContextOpts, } from "./types";
23
+ export { DB_RLS_METRIC_VOCABULARY, _resetMetricsWarnLedgerForTests, } from "./metrics";
24
+ export { DbRlsConfigError, DbRlsError, DbRlsNotInitialized, MissingTenantContext, OwnerContextOutsideMigrate, PoolUnavailable, TransactionRolledBack, } from "./types";
25
+ export type { AuthContext, AutoDispatchOpts, DbRlsMode, GenerateRlsPolicyOpts, PgPool, PgTx, PoolKind, SystemContextOpts, UserContextOpts, } from "./types";
23
26
  //# sourceMappingURL=index.d.ts.map
@@ -1 +1 @@
1
- {"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../src/index.ts"],"names":[],"mappings":"AAuBA,eAAO,MAAM,QAAQ,WAAW,CAAC;AACjC,eAAO,MAAM,OAAO,UAAU,CAAC;AAE/B,OAAO,EACL,SAAS,EACT,YAAY,EACZ,cAAc,EACd,WAAW,EACX,cAAc,GACf,MAAM,QAAQ,CAAC;AAChB,YAAY,EAAE,eAAe,EAAE,aAAa,EAAE,MAAM,QAAQ,CAAC;AAE7D,OAAO,EACL,cAAc,EACd,sBAAsB,EACtB,uBAAuB,GACxB,MAAM,aAAa,CAAC;AACrB,YAAY,EAAE,kBAAkB,EAAE,MAAM,aAAa,CAAC;AAEtD,OAAO,EAAE,YAAY,EAAE,MAAM,mBAAmB,CAAC;AACjD,YAAY,EAAE,iBAAiB,EAAE,MAAM,mBAAmB,CAAC;AAE3D,OAAO,EACL,eAAe,EACf,iBAAiB,EACjB,gBAAgB,EAChB,YAAY,GACb,MAAM,WAAW,CAAC;AAEnB,OAAO,EACL,iBAAiB,EACjB,mBAAmB,EACnB,kBAAkB,GACnB,MAAM,kBAAkB,CAAC;AAC1B,YAAY,EAAE,aAAa,EAAE,cAAc,EAAE,MAAM,kBAAkB,CAAC;AAEtE,OAAO,EACL,eAAe,EACf,sBAAsB,EACtB,yBAAyB,EACzB,iBAAiB,GAClB,MAAM,eAAe,CAAC;AACvB,YAAY,EAAE,WAAW,EAAE,MAAM,eAAe,CAAC;AAEjD,OAAO,EAAE,OAAO,EAAE,mBAAmB,EAAE,MAAM,kBAAkB,CAAC;AAChE,YAAY,EAAE,OAAO,EAAE,WAAW,EAAE,MAAM,kBAAkB,CAAC;AAE7D,OAAO,EACL,UAAU,EACV,gBAAgB,EAChB,oBAAoB,EACpB,oBAAoB,GACrB,MAAM,eAAe,CAAC;AACvB,YAAY,EAAE,eAAe,EAAE,gBAAgB,EAAE,MAAM,eAAe,CAAC;AAIvE,OAAO,EAAE,iBAAiB,EAAE,iBAAiB,EAAE,MAAM,cAAc,CAAC;AAEpE,OAAO,EAAE,cAAc,EAAE,MAAM,kBAAkB,CAAC;AAClD,YAAY,EAAE,eAAe,EAAE,MAAM,kBAAkB,CAAC;AAExD,OAAO,EACL,UAAU,EACV,mBAAmB,EACnB,eAAe,EACf,oBAAoB,EACpB,qBAAqB,GACtB,MAAM,SAAS,CAAC;AAEjB,YAAY,EACV,WAAW,EACX,gBAAgB,EAChB,qBAAqB,EACrB,MAAM,EACN,IAAI,EACJ,QAAQ,EACR,iBAAiB,EACjB,eAAe,GAChB,MAAM,SAAS,CAAC"}
1
+ {"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../src/index.ts"],"names":[],"mappings":"AAiCA,eAAO,MAAM,QAAQ,WAAW,CAAC;AACjC,eAAO,MAAM,OAAO,UAAU,CAAC;AAE/B,OAAO,EACL,SAAS,EACT,YAAY,EACZ,cAAc,EACd,WAAW,EACX,cAAc,GACf,MAAM,QAAQ,CAAC;AAChB,YAAY,EAAE,eAAe,EAAE,aAAa,EAAE,MAAM,QAAQ,CAAC;AAE7D,OAAO,EACL,cAAc,EACd,mBAAmB,EACnB,sBAAsB,EACtB,uBAAuB,GACxB,MAAM,aAAa,CAAC;AACrB,YAAY,EACV,kBAAkB,EAClB,mBAAmB,GACpB,MAAM,aAAa,CAAC;AAErB,OAAO,EAAE,YAAY,EAAE,MAAM,mBAAmB,CAAC;AACjD,YAAY,EAAE,iBAAiB,EAAE,MAAM,mBAAmB,CAAC;AAE3D,OAAO,EACL,eAAe,EACf,iBAAiB,EACjB,gBAAgB,EAChB,YAAY,GACb,MAAM,WAAW,CAAC;AAEnB,OAAO,EACL,iBAAiB,EACjB,mBAAmB,EACnB,kBAAkB,GACnB,MAAM,kBAAkB,CAAC;AAC1B,YAAY,EAAE,aAAa,EAAE,cAAc,EAAE,MAAM,kBAAkB,CAAC;AAEtE,YAAY,EAAE,gBAAgB,EAAE,MAAM,iBAAiB,CAAC;AACxD,OAAO,EAAE,oBAAoB,EAAE,MAAM,iBAAiB,CAAC;AAEvD,OAAO,EACL,eAAe,EACf,sBAAsB,EACtB,yBAAyB,EACzB,iBAAiB,GAClB,MAAM,eAAe,CAAC;AACvB,YAAY,EAAE,WAAW,EAAE,MAAM,eAAe,CAAC;AAEjD,OAAO,EAAE,OAAO,EAAE,mBAAmB,EAAE,MAAM,kBAAkB,CAAC;AAChE,YAAY,EAAE,OAAO,EAAE,WAAW,EAAE,MAAM,kBAAkB,CAAC;AAE7D,OAAO,EACL,UAAU,EACV,gBAAgB,EAChB,oBAAoB,EACpB,oBAAoB,GACrB,MAAM,eAAe,CAAC;AACvB,YAAY,EAAE,eAAe,EAAE,gBAAgB,EAAE,MAAM,eAAe,CAAC;AAIvE,OAAO,EAAE,iBAAiB,EAAE,iBAAiB,EAAE,MAAM,cAAc,CAAC;AAEpE,OAAO,EAAE,cAAc,EAAE,MAAM,kBAAkB,CAAC;AAClD,YAAY,EAAE,eAAe,EAAE,MAAM,kBAAkB,CAAC;AAExD,OAAO,EACL,wBAAwB,EACxB,+BAA+B,GAChC,MAAM,WAAW,CAAC;AAEnB,OAAO,EACL,gBAAgB,EAChB,UAAU,EACV,mBAAmB,EACnB,oBAAoB,EACpB,0BAA0B,EAC1B,eAAe,EACf,qBAAqB,GACtB,MAAM,SAAS,CAAC;AAEjB,YAAY,EACV,WAAW,EACX,gBAAgB,EAChB,SAAS,EACT,qBAAqB,EACrB,MAAM,EACN,IAAI,EACJ,QAAQ,EACR,iBAAiB,EACjB,eAAe,GAChB,MAAM,SAAS,CAAC"}
package/dist/index.js CHANGED
@@ -1,32 +1,43 @@
1
- // @nodii/db-rls — v0.1.1 public barrel.
1
+ // @nodii/db-rls — v0.2.3 public barrel.
2
2
  //
3
3
  // Spec: planning hub feature_doc serviceId=nodii-libs docKey=db-rls
4
- // (A1 posture — RLS on every tenant-scoped table — locked 2026-05-25).
4
+ // + global doctrine `08-rls-doctrine.md` (A1 posture — RLS on every
5
+ // tenant-scoped table — operator-confirmed 2026-06-02).
5
6
  // Polyglot ship: TS + Python + Go in parity.
6
7
  //
7
- // v0.1.1 surface:
8
- // - configureDbRls (real pg.Pool-aware boot helper) + initDbRls (raw)
8
+ // v0.2.3 surface (additive over v0.1.1):
9
+ // - configureDbRls (3-pool) + configureDbRls2Pool (2-pool exception
10
+ // per 08-rls § 7) + initDbRls (raw)
9
11
  // - PgClientPool (wraps pg.Pool → PgPool interface)
10
12
  // - InMemoryPgPool (still exported — used by upstream tests)
11
13
  // - withUserContext / withSystemContext / withOwnerContext / autoDispatch
12
14
  // (operates on the substrate-agnostic PgTx)
13
15
  // - withUserContextDb / withSystemContextDb / withOwnerContextDb
14
16
  // (Drizzle-bound; require a real PgClientPool)
17
+ // - withOwnerContext now enforces NODII_ENV=migrate per 08-rls § 10.2
15
18
  // - applyAuthSchemaMigrations + AUTH_SCHEMA_SQL + AUTH_SCHEMA_GRANTS_SQL
16
- // - withRls() (RLS-policy DDL generator per § 5.5)
19
+ // - withRls() (legacy DDL-string generator per § 5.5; keeps *_policy suffix)
20
+ // - withRls() Drizzle table-builder (subpath `@nodii/db-rls/drizzle`)
21
+ // per doctrine § 4.2 — emits canonical 5-policy DDL via Drizzle's
22
+ // pgPolicy constructs, naming follows doctrine § 4 (no `_policy` suffix)
23
+ // - postgres-js adapter (subpath `@nodii/db-rls/postgres-js`) — nodii-auth
24
+ // and other postgres-js consumers
25
+ // - DB_RLS_METRIC_VOCABULARY + 9 locked metrics + 2 spans per § 5.10
17
26
  // - generateRlsPolicy / authSchemaHelpers (deprecated aliases, kept for
18
27
  // parity-fence + parity with the v0.1.0 surface; no NotImplemented paths)
19
28
  // - migrateGen + runMigrateGenCli + userTenantIdsRealSql + userTenantIdsStubSql
20
29
  // - Typed errors: DbRlsError + DbRlsNotInitialized + PoolUnavailable +
21
30
  // MissingTenantContext + TransactionRolledBack +
22
- // PoolCredentialMismatch
31
+ // PoolCredentialMismatch + OwnerContextOutsideMigrate +
32
+ // DbRlsConfigError
23
33
  export const LIB_NAME = "db-rls";
24
- export const VERSION = "0.1.1";
34
+ export const VERSION = "0.2.3";
25
35
  export { initDbRls, requireDbRls, getDbRlsOrNull, requirePool, _resetForTests, } from "./init";
26
- export { configureDbRls, PoolCredentialMismatch, _resetConfigureForTests, } from "./configure";
36
+ export { configureDbRls, configureDbRls2Pool, PoolCredentialMismatch, _resetConfigureForTests, } from "./configure";
27
37
  export { PgClientPool } from "./pg-pool-adapter";
28
38
  export { withUserContext, withSystemContext, withOwnerContext, autoDispatch, } from "./context";
29
39
  export { withUserContextDb, withSystemContextDb, withOwnerContextDb, } from "./drizzle-client";
40
+ export { assertMigrateAllowed } from "./migrate-guard";
30
41
  export { AUTH_SCHEMA_SQL, AUTH_SCHEMA_GRANTS_SQL, applyAuthSchemaMigrations, authSchemaFullSql, } from "./auth-schema";
31
42
  export { withRls, generateTableGrants } from "./rls-policy-gen";
32
43
  export { migrateGen, runMigrateGenCli, userTenantIdsRealSql, userTenantIdsStubSql, } from "./migrate-gen";
@@ -34,5 +45,6 @@ export { migrateGen, runMigrateGenCli, userTenantIdsRealSql, userTenantIdsStubSq
34
45
  // names. Both are byte-equal SQL helpers — no NotImplemented paths.
35
46
  export { generateRlsPolicy, authSchemaHelpers } from "./rls-policy";
36
47
  export { InMemoryPgPool } from "./in-memory-pool";
37
- export { DbRlsError, DbRlsNotInitialized, PoolUnavailable, MissingTenantContext, TransactionRolledBack, } from "./types";
48
+ export { DB_RLS_METRIC_VOCABULARY, _resetMetricsWarnLedgerForTests, } from "./metrics";
49
+ export { DbRlsConfigError, DbRlsError, DbRlsNotInitialized, MissingTenantContext, OwnerContextOutsideMigrate, PoolUnavailable, TransactionRolledBack, } from "./types";
38
50
  //# sourceMappingURL=index.js.map