@substrat-run/kernel 0.136.0 → 0.137.0

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 (43) hide show
  1. package/dist/capability.d.ts +2 -0
  2. package/dist/capability.d.ts.map +1 -1
  3. package/dist/capability.js +2 -0
  4. package/dist/capability.js.map +1 -1
  5. package/dist/index.d.ts +9 -7
  6. package/dist/index.d.ts.map +1 -1
  7. package/dist/index.js +8 -6
  8. package/dist/index.js.map +1 -1
  9. package/dist/invocation-log.d.ts +25 -1
  10. package/dist/invocation-log.d.ts.map +1 -1
  11. package/dist/invocation-log.js +45 -6
  12. package/dist/invocation-log.js.map +1 -1
  13. package/dist/job-run.d.ts +77 -15
  14. package/dist/job-run.d.ts.map +1 -1
  15. package/dist/job-run.js +107 -24
  16. package/dist/job-run.js.map +1 -1
  17. package/dist/lifecycle-flow.d.ts.map +1 -1
  18. package/dist/lifecycle-flow.js +2 -1
  19. package/dist/lifecycle-flow.js.map +1 -1
  20. package/dist/permission-eval.d.ts +9 -0
  21. package/dist/permission-eval.d.ts.map +1 -1
  22. package/dist/permission-eval.js +26 -0
  23. package/dist/permission-eval.js.map +1 -1
  24. package/dist/refusal-query.d.ts +4 -1
  25. package/dist/refusal-query.d.ts.map +1 -1
  26. package/dist/refusal-query.js +6 -4
  27. package/dist/refusal-query.js.map +1 -1
  28. package/dist/refusals.d.ts +80 -8
  29. package/dist/refusals.d.ts.map +1 -1
  30. package/dist/refusals.js +141 -22
  31. package/dist/refusals.js.map +1 -1
  32. package/dist/scope-host.d.ts +30 -6
  33. package/dist/scope-host.d.ts.map +1 -1
  34. package/dist/scope-host.js.map +1 -1
  35. package/dist/system-switch-record.d.ts +27 -11
  36. package/dist/system-switch-record.d.ts.map +1 -1
  37. package/dist/system-switch-record.js +59 -24
  38. package/dist/system-switch-record.js.map +1 -1
  39. package/dist/system-switch.d.ts +41 -11
  40. package/dist/system-switch.d.ts.map +1 -1
  41. package/dist/system-switch.js +48 -15
  42. package/dist/system-switch.js.map +1 -1
  43. package/package.json +2 -2
@@ -1,5 +1,6 @@
1
1
  import { objectRef, subjectRef, } from '@substrat-run/contracts';
2
2
  import { capabilityGrantOf, capabilityLive } from './capability.js';
3
+ import { isSwitchableSubjectKind } from './system-switch.js';
3
4
  /**
4
5
  * The built-in constrained relationship-tuple evaluator (design doc §4.2, plan D-23),
5
6
  * as ONE implementation both adapters call.
@@ -49,6 +50,26 @@ const nodeObjectsOf = (node) => node.scopeId
49
50
  { obj: `tenant:${node.tenantId}`, scoped: false },
50
51
  ]
51
52
  : [{ obj: `tenant:${node.tenantId}`, scoped: false }];
53
+ /**
54
+ * "Is this subject switched off on this scope?" — asked before any tuple is read, by `check`
55
+ * and `covers` alike, so a switched-off subject is denied on the scope whatever it holds
56
+ * (#1823). OFF tombstones the subject's SCOPE-level grants, but a TENANT-level grant lives in
57
+ * the directory (and, on the Durable-Object adapter, in every scope's projection of it), and
58
+ * OFF touches neither: without this, a tenant grant made before the switch was pulled kept the
59
+ * module's authority alive on a scope its operator had switched off. Asking the scope, rather
60
+ * than tombstoning the tenant tuple, is what confines the denial to the ONE scope (the algebra
61
+ * has no per-scope negative tuple), and what makes it survive a re-projection: no projection
62
+ * writes the switch's state.
63
+ *
64
+ * The answer is the reader's `switchedOff` — one seam, so where the switch's state is read
65
+ * from is the adapter's decision and the rule is the evaluator's. Fails CLOSED when a scope
66
+ * node has no reachable store: the switch cannot be read, so no grant can be vouched for.
67
+ */
68
+ async function switchedOff(subject, node, scope) {
69
+ if (!isSwitchableSubjectKind(subject.kind) || !node.scopeId)
70
+ return false;
71
+ return scope ? await scope.switchedOff(subjectRef(subject)) : true;
72
+ }
52
73
  /**
53
74
  * Rule 3's walk, as ONE function: from `start`, look for a hit at each frontier object, then
54
75
  * expand one level of declared `parent` edges, to `ENTITY_WALK_DEPTH`. `probe` decides what a
@@ -186,6 +207,8 @@ export function createTupleEvaluator(reader) {
186
207
  const now = reader.now();
187
208
  const deny = { allowed: false, checked: permission, node };
188
209
  const scope = reader.scopeFor(node);
210
+ if (await switchedOff(subject, node, scope))
211
+ return deny;
189
212
  const getRole = roleReaderFor(node.tenantId);
190
213
  // Rule 4 — membership: the subject set is the caller plus its orgs. Shared with
191
214
  // `covers` (§ `subjectsOf`).
@@ -278,6 +301,9 @@ export function createTupleEvaluator(reader) {
278
301
  }
279
302
  const now = reader.now();
280
303
  const scope = reader.scopeFor(node);
304
+ if (await switchedOff(subject, node, scope)) {
305
+ return { covered: false, missing: [...new Set(required)] };
306
+ }
281
307
  const subjects = await subjectsOf(subject, node, now);
282
308
  const getRole = roleReaderFor(node.tenantId);
283
309
  const held = new Set();
@@ -1 +1 @@
1
- {"version":3,"file":"permission-eval.js","sourceRoot":"","sources":["../src/permission-eval.ts"],"names":[],"mappings":"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"}
1
+ {"version":3,"file":"permission-eval.js","sourceRoot":"","sources":["../src/permission-eval.ts"],"names":[],"mappings":"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"}
@@ -18,10 +18,13 @@ export interface RefusalDbRow {
18
18
  scope_id: string | null;
19
19
  entity_type: string | null;
20
20
  entity_id: string | null;
21
- from_state: string;
21
+ from_state: string | null;
22
22
  attempted_state: string | null;
23
23
  operation: string;
24
24
  invoked_operation: string | null;
25
+ guard: string | null;
26
+ /** NULL on a row written before the column; the kind implies it there. */
27
+ reason: string | null;
25
28
  actor: string;
26
29
  impersonation: string | null;
27
30
  invocation_id: string | null;
@@ -1 +1 @@
1
- {"version":3,"file":"refusal-query.d.ts","sourceRoot":"","sources":["../src/refusal-query.ts"],"names":[],"mappings":"AAAA,OAAO,EAKL,KAAK,aAAa,EAClB,KAAK,aAAa,EACnB,MAAM,yBAAyB,CAAC;AAKjC;;;;;;;;GAQG;AAEH,kFAAkF;AAClF,eAAO,MAAM,eAAe,QAE+C,CAAC;AAE5E,0DAA0D;AAC1D,MAAM,WAAW,YAAY;IAC3B,EAAE,EAAE,MAAM,CAAC;IACX,IAAI,EAAE,MAAM,CAAC;IACb,SAAS,EAAE,MAAM,CAAC;IAClB,QAAQ,EAAE,MAAM,GAAG,IAAI,CAAC;IACxB,WAAW,EAAE,MAAM,GAAG,IAAI,CAAC;IAC3B,SAAS,EAAE,MAAM,GAAG,IAAI,CAAC;IACzB,UAAU,EAAE,MAAM,CAAC;IACnB,eAAe,EAAE,MAAM,GAAG,IAAI,CAAC;IAC/B,SAAS,EAAE,MAAM,CAAC;IAClB,iBAAiB,EAAE,MAAM,GAAG,IAAI,CAAC;IACjC,KAAK,EAAE,MAAM,CAAC;IACd,aAAa,EAAE,MAAM,GAAG,IAAI,CAAC;IAC7B,aAAa,EAAE,MAAM,GAAG,IAAI,CAAC;IAC7B,EAAE,EAAE,MAAM,CAAC;IACX,UAAU,EAAE,MAAM,GAAG,IAAI,CAAC;CAC3B;AAKD;;;;GAIG;AACH,wBAAgB,aAAa,CAAC,GAAG,EAAE,YAAY,GAAG,aAAa,CAuB9D;AAED,wDAAwD;AACxD,wBAAgB,gBAAgB,CAAC,MAAM,CAAC,EAAE,aAAa,GAAG;IAAE,GAAG,EAAE,MAAM,CAAC;IAAC,MAAM,EAAE,CAAC,MAAM,GAAG,MAAM,CAAC,EAAE,CAAA;CAAE,CA4BrG"}
1
+ {"version":3,"file":"refusal-query.d.ts","sourceRoot":"","sources":["../src/refusal-query.ts"],"names":[],"mappings":"AAAA,OAAO,EAKL,KAAK,aAAa,EAClB,KAAK,aAAa,EACnB,MAAM,yBAAyB,CAAC;AAKjC;;;;;;;;GAQG;AAEH,kFAAkF;AAClF,eAAO,MAAM,eAAe,QAE8D,CAAC;AAE3F,0DAA0D;AAC1D,MAAM,WAAW,YAAY;IAC3B,EAAE,EAAE,MAAM,CAAC;IACX,IAAI,EAAE,MAAM,CAAC;IACb,SAAS,EAAE,MAAM,CAAC;IAClB,QAAQ,EAAE,MAAM,GAAG,IAAI,CAAC;IACxB,WAAW,EAAE,MAAM,GAAG,IAAI,CAAC;IAC3B,SAAS,EAAE,MAAM,GAAG,IAAI,CAAC;IACzB,UAAU,EAAE,MAAM,GAAG,IAAI,CAAC;IAC1B,eAAe,EAAE,MAAM,GAAG,IAAI,CAAC;IAC/B,SAAS,EAAE,MAAM,CAAC;IAClB,iBAAiB,EAAE,MAAM,GAAG,IAAI,CAAC;IACjC,KAAK,EAAE,MAAM,GAAG,IAAI,CAAC;IACrB,0EAA0E;IAC1E,MAAM,EAAE,MAAM,GAAG,IAAI,CAAC;IACtB,KAAK,EAAE,MAAM,CAAC;IACd,aAAa,EAAE,MAAM,GAAG,IAAI,CAAC;IAC7B,aAAa,EAAE,MAAM,GAAG,IAAI,CAAC;IAC7B,EAAE,EAAE,MAAM,CAAC;IACX,UAAU,EAAE,MAAM,GAAG,IAAI,CAAC;CAC3B;AAKD;;;;GAIG;AACH,wBAAgB,aAAa,CAAC,GAAG,EAAE,YAAY,GAAG,aAAa,CAwB9D;AAED,wDAAwD;AACxD,wBAAgB,gBAAgB,CAAC,MAAM,CAAC,EAAE,aAAa,GAAG;IAAE,GAAG,EAAE,MAAM,CAAC;IAAC,MAAM,EAAE,CAAC,MAAM,GAAG,MAAM,CAAC,EAAE,CAAA;CAAE,CA6BrG"}
@@ -13,8 +13,8 @@ import { rowDecoder, UNDECODED_ACTOR } from './row-decode.js';
13
13
  */
14
14
  /** Every column of `_substrat_refusals`, in the order `mapRefusalRow` expects. */
15
15
  export const REFUSAL_COLUMNS = 'id, kind, tenant_id, scope_id, entity_type, entity_id, from_state, attempted_state, operation,' +
16
- ' invoked_operation, actor, impersonation, invocation_id, at, drained_at';
17
- /** The problem code each recorded kind was refused with — the 409's `reason`. */
16
+ ' invoked_operation, guard, reason, actor, impersonation, invocation_id, at, drained_at';
17
+ /** The problem code a row written before the `reason` column was refused with, by kind. */
18
18
  const REASON_OF_KIND = { transition: INVALID_TRANSITION };
19
19
  /**
20
20
  * Turn a stored row into the contract shape, tolerantly (#1636's rule for the denial log):
@@ -28,14 +28,15 @@ export function mapRefusalRow(row) {
28
28
  return d.finish({
29
29
  id: d.required('id', shape.id, row.id),
30
30
  kind,
31
- reason: REASON_OF_KIND[kind] ?? null,
31
+ reason: d.nullable('reason', shape.reason, row.reason ?? null) ?? REASON_OF_KIND[kind] ?? null,
32
+ guard: d.nullable('guard', shape.guard, row.guard ?? null),
32
33
  actor: d.json('actor', shape.actor, row.actor, UNDECODED_ACTOR),
33
34
  actorKind: actorKindOf(row.actor),
34
35
  tenantId: d.required('tenant_id', shape.tenantId, row.tenant_id),
35
36
  scopeId: d.nullable('scope_id', shape.scopeId, row.scope_id ?? null),
36
37
  entityType: d.nullable('entity_type', shape.entityType, row.entity_type ?? null),
37
38
  entityId: d.nullable('entity_id', shape.entityId, row.entity_id ?? null),
38
- fromState: d.required('from_state', shape.fromState, row.from_state),
39
+ fromState: d.nullable('from_state', shape.fromState, row.from_state ?? null),
39
40
  attemptedState: d.nullable('attempted_state', shape.attemptedState, row.attempted_state ?? null),
40
41
  operation: d.required('operation', shape.operation, row.operation),
41
42
  invokedOperation: d.nullable('invoked_operation', shape.invokedOperation, row.invoked_operation ?? null),
@@ -56,6 +57,7 @@ export function refusalListQuery(filter) {
56
57
  parts.push(`${column} = ?`);
57
58
  params.push(value);
58
59
  };
60
+ eq('kind', f.kind);
59
61
  eq('entity_type', f.entityType);
60
62
  eq('entity_id', f.entityId);
61
63
  eq('actor', f.actor === undefined ? undefined : storedActor(f.actor));
@@ -1 +1 @@
1
- {"version":3,"file":"refusal-query.js","sourceRoot":"","sources":["../src/refusal-query.ts"],"names":[],"mappings":"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"}
1
+ {"version":3,"file":"refusal-query.js","sourceRoot":"","sources":["../src/refusal-query.ts"],"names":[],"mappings":"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"}
@@ -1,11 +1,12 @@
1
1
  /**
2
- * Refused transitions, recorded (#1745).
2
+ * Refused transitions and refusing guards, recorded (#1745).
3
3
  *
4
4
  * An illegal move is refused inside the operation by `assertTransition`, which throws a
5
- * `conflict`. The operation's transaction rolls back with it, so nothing about the attempt
6
- * survives — the denial log holds permission refusals only, and the outbox only what
7
- * committed. That made "someone tried to reopen a closed conversation twelve times" a fact
8
- * nobody could see: not on the process map, not in a finding.
5
+ * `conflict`; a manifest-declared guard (K-38) refuses the operation it stands before the
6
+ * same way, before the handler runs. The operation's transaction rolls back with either, so
7
+ * nothing about the attempt survives — the denial log holds permission refusals only, and
8
+ * the outbox only what committed. That made "someone tried to reopen a closed conversation
9
+ * twelve times" a fact nobody could see: not on the process map, not in a finding.
9
10
  *
10
11
  * Recorded the way a denial is (K-35): on the failure path, AFTER the rollback, as a write
11
12
  * of its own, so the attempt survives the transaction that refused it. Kernel-owned and
@@ -14,13 +15,84 @@
14
15
  *
15
16
  * Only a refusal that FAILED the operation is recorded. One a vertical caught inside
16
17
  * `ctx.atomic` and recovered from is the vertical's business — its operation committed.
18
+ *
19
+ * **What a row holds, and what it never does.** Keys and vocabulary only: the record's type
20
+ * (held to the entity-type grammar, `refusalEntityType`) and id, state names, operation and
21
+ * predicate names, the problem code (held to the `problemReason` grammar), the actor's id
22
+ * and the call's. Never the error's message, the operation's input, or a guard's config —
23
+ * any of those can quote what a person typed. So a row has nothing for a subject erasure to rewrite
24
+ * (master-plan §5.3: pseudonymous keys and transaction facts remain), which is the denial
25
+ * log's position too, and it is kept the way the denial log is: `drained_at` marks a shipped
26
+ * row, and rows drain rather than expire.
17
27
  */
18
28
  import { refusedTransitionOf, type RefusedTransition } from '@substrat-run/contracts';
19
- export declare const REFUSALS_DDL = "\n CREATE TABLE IF NOT EXISTS _substrat_refusals (\n id TEXT PRIMARY KEY,\n -- 'transition' today; a guard refusal (K-38) is the next kind, recorded the same way.\n kind TEXT NOT NULL,\n tenant_id TEXT NOT NULL,\n scope_id TEXT,\n -- The record the move was refused on. NULL when the caller of assertTransition did\n -- not name it: the attempt is still recorded, and cannot be counted against an entity.\n entity_type TEXT,\n entity_id TEXT,\n from_state TEXT NOT NULL,\n -- Where the operation leads where it IS legal; NULL when that is not one state.\n attempted_state TEXT,\n -- The lifecycle's operation (what the edge is keyed by) and the invoke() string the\n -- call ran as; the same today for every caller, kept apart because they need not be.\n operation TEXT NOT NULL,\n invoked_operation TEXT,\n actor TEXT NOT NULL,\n impersonation TEXT,\n invocation_id TEXT,\n at TEXT NOT NULL,\n drained_at TEXT\n );\n -- The process map's read: one entity type's refusals in a window.\n CREATE INDEX IF NOT EXISTS _substrat_refusals_entity_at ON _substrat_refusals (entity_type, at);\n";
29
+ /** The table alone — what `REFUSALS_REBUILD` creates under its scratch name. */
30
+ export declare const REFUSALS_TABLE_DDL = "\n CREATE TABLE IF NOT EXISTS _substrat_refusals (\n id TEXT PRIMARY KEY,\n -- 'transition' (assertTransition) or 'guard' (a manifest-declared guard, K-38).\n kind TEXT NOT NULL,\n tenant_id TEXT NOT NULL,\n scope_id TEXT,\n -- The record the refusal was about. NULL when the refusing code did not name it: the\n -- attempt is still recorded, and cannot be counted against an entity.\n entity_type TEXT,\n entity_id TEXT,\n -- The state the record was in. NULL on a guard row: a guard stands before an operation,\n -- and the kernel that ran it cannot know the state of the record behind it.\n from_state TEXT,\n -- Where the operation leads where it IS legal; NULL when that is not one state.\n attempted_state TEXT,\n -- The lifecycle's operation (what the edge is keyed by), or the one a guard stands\n -- before, and the invoke() string the call ran as.\n operation TEXT NOT NULL,\n invoked_operation TEXT,\n -- The guard's named predicate; NULL on a transition row.\n guard TEXT,\n -- The problem code the operation failed with (the 409's reason). NULL on a row written\n -- before the column, where the kind implies it.\n reason TEXT,\n actor TEXT NOT NULL,\n impersonation TEXT,\n invocation_id TEXT,\n at TEXT NOT NULL,\n drained_at TEXT\n );\n";
31
+ /** The process map's read: one entity type's refusals in a window. */
32
+ export declare const REFUSALS_INDEX = "\n CREATE INDEX IF NOT EXISTS _substrat_refusals_entity_at ON _substrat_refusals (entity_type, at);\n";
33
+ /**
34
+ * The table and its index. The adapters interpolate the two literals above instead, which
35
+ * is what `lint:spine-ddl` can resolve; this is for a caller that wants the whole thing.
36
+ */
37
+ export declare const REFUSALS_DDL: string;
38
+ /**
39
+ * `_substrat_refusals` rebuilt to the shape above on a store created before guard refusals:
40
+ * `from_state` loses its NOT NULL and `guard` / `reason` join. Create-copy-drop-rename,
41
+ * because SQLite cannot relax a constraint in place — `SCHEDULE_STATE_REBUILD`'s shape and
42
+ * reasons (#1288), detected the same way (`refusalsAdmitGuards`, off `sqlite_master.sql`,
43
+ * which DO SQLite serves and `PRAGMA` does not).
44
+ *
45
+ * The new table is `REFUSALS_TABLE_DDL` under a temporary name, so the rebuilt shape cannot drift
46
+ * from the created one, and every row is copied verbatim: the two new columns are NULL on a
47
+ * transition row written before them, which the reader takes as "implied by the kind". The
48
+ * index is dropped with the old table and created again on the renamed one.
49
+ *
50
+ * **Run inside the adapter's transaction API**, as both callers do: un-wrapped, a stop
51
+ * between the DROP and the RENAME leaves the next wake's `CREATE TABLE IF NOT EXISTS` an
52
+ * empty table of the new shape, detection reads it as migrated, and the copied rows are
53
+ * orphaned in the scratch table. The leading `DROP TABLE IF EXISTS` makes a re-run start
54
+ * clean. A restore never reaches this: it builds the table from the current DDL and loads a
55
+ * legacy dump's rows by column name.
56
+ */
57
+ export declare const REFUSALS_REBUILD: string;
58
+ /**
59
+ * Whether a store's `_substrat_refusals` already admits a guard row, read off the `sql`
60
+ * column of `sqlite_master`. `false` means `REFUSALS_REBUILD` is due.
61
+ */
62
+ export declare function refusalsAdmitGuards(tableSql: string): boolean;
63
+ /**
64
+ * A guard refusal, as the kernel records it: which predicate refused which operation, with
65
+ * which problem code, about which record. Stamped on the thrown error by the adapter that
66
+ * ran the guard (`markGuardRefusal`), under a registered symbol for `RefusedTransition`'s
67
+ * reason — none of it belongs in the problem document the caller is handed.
68
+ */
69
+ export interface RefusedGuard {
70
+ kind: 'guard';
71
+ predicate: string;
72
+ /** The operation the guard stands before. */
73
+ operation: string;
74
+ /** The problem's `reason` code (`keptReason`), or null when it carried none. */
75
+ reason: string | null;
76
+ entityType: string | null;
77
+ entityId: string | null;
78
+ }
79
+ /**
80
+ * Mark a guard predicate's throw as a refusal, when it is one — called by both adapters'
81
+ * `runGuards` around each predicate, so the two cannot disagree about what counts.
82
+ *
83
+ * A refusal is a `conflict`: what a predicate throws to say "not yet" (`protocol_required`).
84
+ * Anything else — a validation failure, a bug, a denied check (which the denial log has) —
85
+ * is not a guard refusing, and is left unmarked. So is a throw that already carries a
86
+ * refused transition: it is recorded once, as the transition it is.
87
+ */
88
+ export declare function markGuardRefusal(err: unknown, predicate: string, operation: string): void;
89
+ /** The refusal an operation failed with — a transition, a guard, or null for anything else. */
90
+ export declare function refusalOf(err: unknown): RefusedTransition | RefusedGuard | null;
20
91
  export interface RefusalRow {
21
92
  tenantId: string;
22
93
  scopeId: string | null;
23
- refused: RefusedTransition;
94
+ /** What `refusalOf` returned. A `RefusedTransition` carries no `kind`: it is one. */
95
+ refused: RefusedTransition | RefusedGuard;
24
96
  invokedOperation: string | null;
25
97
  /** The actor, as the outbox stores one: JSON. */
26
98
  actor: string;
@@ -33,6 +105,6 @@ export declare function refusalInsert(row: RefusalRow): {
33
105
  sql: string;
34
106
  params: (string | null)[];
35
107
  };
36
- /** The refused transition an operation failed with, or null — what the adapters branch on. */
108
+ /** The refused transition an operation failed with, or null. */
37
109
  export { refusedTransitionOf };
38
110
  //# sourceMappingURL=refusals.d.ts.map
@@ -1 +1 @@
1
- {"version":3,"file":"refusals.d.ts","sourceRoot":"","sources":["../src/refusals.ts"],"names":[],"mappings":"AAAA;;;;;;;;;;;;;;;;GAgBG;AACH,OAAO,EAAE,mBAAmB,EAAE,KAAK,iBAAiB,EAAE,MAAM,yBAAyB,CAAC;AAGtF,eAAO,MAAM,YAAY,qoCA0BxB,CAAC;AAEF,MAAM,WAAW,UAAU;IACzB,QAAQ,EAAE,MAAM,CAAC;IACjB,OAAO,EAAE,MAAM,GAAG,IAAI,CAAC;IACvB,OAAO,EAAE,iBAAiB,CAAC;IAC3B,gBAAgB,EAAE,MAAM,GAAG,IAAI,CAAC;IAChC,iDAAiD;IACjD,KAAK,EAAE,MAAM,CAAC;IACd,aAAa,EAAE,MAAM,GAAG,IAAI,CAAC;IAC7B,YAAY,EAAE,MAAM,GAAG,IAAI,CAAC;IAC5B,EAAE,EAAE,MAAM,CAAC;CACZ;AAED,8EAA8E;AAC9E,wBAAgB,aAAa,CAAC,GAAG,EAAE,UAAU,GAAG;IAAE,GAAG,EAAE,MAAM,CAAC;IAAC,MAAM,EAAE,CAAC,MAAM,GAAG,IAAI,CAAC,EAAE,CAAA;CAAE,CAsBzF;AAED,8FAA8F;AAC9F,OAAO,EAAE,mBAAmB,EAAE,CAAC"}
1
+ {"version":3,"file":"refusals.d.ts","sourceRoot":"","sources":["../src/refusals.ts"],"names":[],"mappings":"AAAA;;;;;;;;;;;;;;;;;;;;;;;;;;GA0BG;AACH,OAAO,EAOL,mBAAmB,EACnB,KAAK,iBAAiB,EACvB,MAAM,yBAAyB,CAAC;AAGjC,gFAAgF;AAChF,eAAO,MAAM,kBAAkB,+zCA+B9B,CAAC;AAEF,sEAAsE;AACtE,eAAO,MAAM,cAAc,2GAE1B,CAAC;AAEF;;;GAGG;AACH,eAAO,MAAM,YAAY,QAAsC,CAAC;AAEhE;;;;;;;;;;;;;;;;;;GAkBG;AACH,eAAO,MAAM,gBAAgB,QAY5B,CAAC;AAEF;;;GAGG;AACH,wBAAgB,mBAAmB,CAAC,QAAQ,EAAE,MAAM,GAAG,OAAO,CAG7D;AAED;;;;;GAKG;AACH,MAAM,WAAW,YAAY;IAC3B,IAAI,EAAE,OAAO,CAAC;IACd,SAAS,EAAE,MAAM,CAAC;IAClB,6CAA6C;IAC7C,SAAS,EAAE,MAAM,CAAC;IAClB,gFAAgF;IAChF,MAAM,EAAE,MAAM,GAAG,IAAI,CAAC;IACtB,UAAU,EAAE,MAAM,GAAG,IAAI,CAAC;IAC1B,QAAQ,EAAE,MAAM,GAAG,IAAI,CAAC;CACzB;AAID;;;;;;;;GAQG;AACH,wBAAgB,gBAAgB,CAAC,GAAG,EAAE,OAAO,EAAE,SAAS,EAAE,MAAM,EAAE,SAAS,EAAE,MAAM,GAAG,IAAI,CAYzF;AAYD,+FAA+F;AAC/F,wBAAgB,SAAS,CAAC,GAAG,EAAE,OAAO,GAAG,iBAAiB,GAAG,YAAY,GAAG,IAAI,CAM/E;AAED,MAAM,WAAW,UAAU;IACzB,QAAQ,EAAE,MAAM,CAAC;IACjB,OAAO,EAAE,MAAM,GAAG,IAAI,CAAC;IACvB,qFAAqF;IACrF,OAAO,EAAE,iBAAiB,GAAG,YAAY,CAAC;IAC1C,gBAAgB,EAAE,MAAM,GAAG,IAAI,CAAC;IAChC,iDAAiD;IACjD,KAAK,EAAE,MAAM,CAAC;IACd,aAAa,EAAE,MAAM,GAAG,IAAI,CAAC;IAC7B,YAAY,EAAE,MAAM,GAAG,IAAI,CAAC;IAC5B,EAAE,EAAE,MAAM,CAAC;CACZ;AAED,8EAA8E;AAC9E,wBAAgB,aAAa,CAAC,GAAG,EAAE,UAAU,GAAG;IAAE,GAAG,EAAE,MAAM,CAAC;IAAC,MAAM,EAAE,CAAC,MAAM,GAAG,IAAI,CAAC,EAAE,CAAA;CAAE,CA+BzF;AAED,gEAAgE;AAChE,OAAO,EAAE,mBAAmB,EAAE,CAAC"}
package/dist/refusals.js CHANGED
@@ -1,11 +1,12 @@
1
1
  /**
2
- * Refused transitions, recorded (#1745).
2
+ * Refused transitions and refusing guards, recorded (#1745).
3
3
  *
4
4
  * An illegal move is refused inside the operation by `assertTransition`, which throws a
5
- * `conflict`. The operation's transaction rolls back with it, so nothing about the attempt
6
- * survives — the denial log holds permission refusals only, and the outbox only what
7
- * committed. That made "someone tried to reopen a closed conversation twelve times" a fact
8
- * nobody could see: not on the process map, not in a finding.
5
+ * `conflict`; a manifest-declared guard (K-38) refuses the operation it stands before the
6
+ * same way, before the handler runs. The operation's transaction rolls back with either, so
7
+ * nothing about the attempt survives — the denial log holds permission refusals only, and
8
+ * the outbox only what committed. That made "someone tried to reopen a closed conversation
9
+ * twelve times" a fact nobody could see: not on the process map, not in a finding.
9
10
  *
10
11
  * Recorded the way a denial is (K-35): on the failure path, AFTER the rollback, as a write
11
12
  * of its own, so the attempt survives the transaction that refused it. Kernel-owned and
@@ -14,53 +15,171 @@
14
15
  *
15
16
  * Only a refusal that FAILED the operation is recorded. One a vertical caught inside
16
17
  * `ctx.atomic` and recovered from is the vertical's business — its operation committed.
18
+ *
19
+ * **What a row holds, and what it never does.** Keys and vocabulary only: the record's type
20
+ * (held to the entity-type grammar, `refusalEntityType`) and id, state names, operation and
21
+ * predicate names, the problem code (held to the `problemReason` grammar), the actor's id
22
+ * and the call's. Never the error's message, the operation's input, or a guard's config —
23
+ * any of those can quote what a person typed. So a row has nothing for a subject erasure to rewrite
24
+ * (master-plan §5.3: pseudonymous keys and transaction facts remain), which is the denial
25
+ * log's position too, and it is kept the way the denial log is: `drained_at` marks a shipped
26
+ * row, and rows drain rather than expire.
17
27
  */
18
- import { refusedTransitionOf } from '@substrat-run/contracts';
28
+ import { errorCodeOf, INVALID_TRANSITION, problemReason, UNRECOGNIZED_REFUSAL_REASON, refusalEntityType, refusedRecordOf, refusedTransitionOf, } from '@substrat-run/contracts';
19
29
  import { ulid } from './ulid.js';
20
- export const REFUSALS_DDL = `
30
+ /** The table alone — what `REFUSALS_REBUILD` creates under its scratch name. */
31
+ export const REFUSALS_TABLE_DDL = `
21
32
  CREATE TABLE IF NOT EXISTS _substrat_refusals (
22
33
  id TEXT PRIMARY KEY,
23
- -- 'transition' today; a guard refusal (K-38) is the next kind, recorded the same way.
34
+ -- 'transition' (assertTransition) or 'guard' (a manifest-declared guard, K-38).
24
35
  kind TEXT NOT NULL,
25
36
  tenant_id TEXT NOT NULL,
26
37
  scope_id TEXT,
27
- -- The record the move was refused on. NULL when the caller of assertTransition did
28
- -- not name it: the attempt is still recorded, and cannot be counted against an entity.
38
+ -- The record the refusal was about. NULL when the refusing code did not name it: the
39
+ -- attempt is still recorded, and cannot be counted against an entity.
29
40
  entity_type TEXT,
30
41
  entity_id TEXT,
31
- from_state TEXT NOT NULL,
42
+ -- The state the record was in. NULL on a guard row: a guard stands before an operation,
43
+ -- and the kernel that ran it cannot know the state of the record behind it.
44
+ from_state TEXT,
32
45
  -- Where the operation leads where it IS legal; NULL when that is not one state.
33
46
  attempted_state TEXT,
34
- -- The lifecycle's operation (what the edge is keyed by) and the invoke() string the
35
- -- call ran as; the same today for every caller, kept apart because they need not be.
47
+ -- The lifecycle's operation (what the edge is keyed by), or the one a guard stands
48
+ -- before, and the invoke() string the call ran as.
36
49
  operation TEXT NOT NULL,
37
50
  invoked_operation TEXT,
51
+ -- The guard's named predicate; NULL on a transition row.
52
+ guard TEXT,
53
+ -- The problem code the operation failed with (the 409's reason). NULL on a row written
54
+ -- before the column, where the kind implies it.
55
+ reason TEXT,
38
56
  actor TEXT NOT NULL,
39
57
  impersonation TEXT,
40
58
  invocation_id TEXT,
41
59
  at TEXT NOT NULL,
42
60
  drained_at TEXT
43
61
  );
44
- -- The process map's read: one entity type's refusals in a window.
62
+ `;
63
+ /** The process map's read: one entity type's refusals in a window. */
64
+ export const REFUSALS_INDEX = `
45
65
  CREATE INDEX IF NOT EXISTS _substrat_refusals_entity_at ON _substrat_refusals (entity_type, at);
46
66
  `;
67
+ /**
68
+ * The table and its index. The adapters interpolate the two literals above instead, which
69
+ * is what `lint:spine-ddl` can resolve; this is for a caller that wants the whole thing.
70
+ */
71
+ export const REFUSALS_DDL = REFUSALS_TABLE_DDL + REFUSALS_INDEX;
72
+ /**
73
+ * `_substrat_refusals` rebuilt to the shape above on a store created before guard refusals:
74
+ * `from_state` loses its NOT NULL and `guard` / `reason` join. Create-copy-drop-rename,
75
+ * because SQLite cannot relax a constraint in place — `SCHEDULE_STATE_REBUILD`'s shape and
76
+ * reasons (#1288), detected the same way (`refusalsAdmitGuards`, off `sqlite_master.sql`,
77
+ * which DO SQLite serves and `PRAGMA` does not).
78
+ *
79
+ * The new table is `REFUSALS_TABLE_DDL` under a temporary name, so the rebuilt shape cannot drift
80
+ * from the created one, and every row is copied verbatim: the two new columns are NULL on a
81
+ * transition row written before them, which the reader takes as "implied by the kind". The
82
+ * index is dropped with the old table and created again on the renamed one.
83
+ *
84
+ * **Run inside the adapter's transaction API**, as both callers do: un-wrapped, a stop
85
+ * between the DROP and the RENAME leaves the next wake's `CREATE TABLE IF NOT EXISTS` an
86
+ * empty table of the new shape, detection reads it as migrated, and the copied rows are
87
+ * orphaned in the scratch table. The leading `DROP TABLE IF EXISTS` makes a re-run start
88
+ * clean. A restore never reaches this: it builds the table from the current DDL and loads a
89
+ * legacy dump's rows by column name.
90
+ */
91
+ export const REFUSALS_REBUILD = `
92
+ DROP TABLE IF EXISTS _substrat_refusals_new;
93
+ ${REFUSALS_TABLE_DDL.replace('CREATE TABLE IF NOT EXISTS _substrat_refusals (', 'CREATE TABLE _substrat_refusals_new (')}
94
+ INSERT INTO _substrat_refusals_new
95
+ (id, kind, tenant_id, scope_id, entity_type, entity_id, from_state, attempted_state,
96
+ operation, invoked_operation, actor, impersonation, invocation_id, at, drained_at)
97
+ SELECT id, kind, tenant_id, scope_id, entity_type, entity_id, from_state, attempted_state,
98
+ operation, invoked_operation, actor, impersonation, invocation_id, at, drained_at
99
+ FROM _substrat_refusals;
100
+ DROP TABLE _substrat_refusals;
101
+ ALTER TABLE _substrat_refusals_new RENAME TO _substrat_refusals;
102
+ ${REFUSALS_INDEX}
103
+ `;
104
+ /**
105
+ * Whether a store's `_substrat_refusals` already admits a guard row, read off the `sql`
106
+ * column of `sqlite_master`. `false` means `REFUSALS_REBUILD` is due.
107
+ */
108
+ export function refusalsAdmitGuards(tableSql) {
109
+ // Line-anchored: the stored DDL keeps its comments, and a comment may say "guard".
110
+ return /^\s*guard TEXT,?\s*$/m.test(tableSql);
111
+ }
112
+ const REFUSED_GUARD = Symbol.for('substrat.refused-guard');
113
+ /**
114
+ * Mark a guard predicate's throw as a refusal, when it is one — called by both adapters'
115
+ * `runGuards` around each predicate, so the two cannot disagree about what counts.
116
+ *
117
+ * A refusal is a `conflict`: what a predicate throws to say "not yet" (`protocol_required`).
118
+ * Anything else — a validation failure, a bug, a denied check (which the denial log has) —
119
+ * is not a guard refusing, and is left unmarked. So is a throw that already carries a
120
+ * refused transition: it is recorded once, as the transition it is.
121
+ */
122
+ export function markGuardRefusal(err, predicate, operation) {
123
+ if (err === null || typeof err !== 'object' || refusedTransitionOf(err))
124
+ return;
125
+ if (errorCodeOf(err) !== 'conflict')
126
+ return;
127
+ const record = refusedRecordOf(err);
128
+ err[REFUSED_GUARD] = {
129
+ kind: 'guard',
130
+ predicate,
131
+ operation,
132
+ reason: keptReason(err.extensions?.reason),
133
+ entityType: record?.entityType ?? null,
134
+ entityId: record?.entityId ?? null,
135
+ };
136
+ }
137
+ /**
138
+ * The reason a row keeps: the problem's code when it is one (`problemReason`), the fixed
139
+ * `UNRECOGNIZED_REFUSAL_REASON` when it is anything else, null when there was none. The
140
+ * wire accepts any non-empty string here, so a predicate could put request text in it.
141
+ */
142
+ function keptReason(reason) {
143
+ if (reason === undefined || reason === null)
144
+ return null;
145
+ return problemReason.safeParse(reason).success ? reason : UNRECOGNIZED_REFUSAL_REASON;
146
+ }
147
+ /** The refusal an operation failed with — a transition, a guard, or null for anything else. */
148
+ export function refusalOf(err) {
149
+ const transition = refusedTransitionOf(err);
150
+ if (transition)
151
+ return transition;
152
+ if (err === null || typeof err !== 'object')
153
+ return null;
154
+ const g = err[REFUSED_GUARD];
155
+ return g !== null && typeof g === 'object' ? g : null;
156
+ }
47
157
  /** The one INSERT both adapters run, so the rows they write cannot differ. */
48
158
  export function refusalInsert(row) {
159
+ const r = row.refused;
160
+ const guard = 'kind' in r && r.kind === 'guard' ? r : null;
161
+ const transition = guard ? null : r;
49
162
  return {
50
163
  sql: `INSERT INTO _substrat_refusals
51
164
  (id, kind, tenant_id, scope_id, entity_type, entity_id, from_state, attempted_state,
52
- operation, invoked_operation, actor, impersonation, invocation_id, at)
53
- VALUES (?, 'transition', ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?)`,
165
+ operation, invoked_operation, guard, reason, actor, impersonation, invocation_id, at)
166
+ VALUES (?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?)`,
54
167
  params: [
55
168
  ulid(),
169
+ guard ? 'guard' : 'transition',
56
170
  row.tenantId,
57
171
  row.scopeId,
58
- row.refused.entityType,
59
- row.refused.entityId,
60
- row.refused.from,
61
- row.refused.attempted,
62
- row.refused.operation,
172
+ // The type reaches here from code that may be handed request data; kept only when it
173
+ // is spelled as one. The id stays: it is the record's key, the join every log shares.
174
+ refusalEntityType(r.entityType),
175
+ r.entityId,
176
+ transition?.from ?? null,
177
+ transition?.attempted ?? null,
178
+ r.operation,
63
179
  row.invokedOperation,
180
+ guard?.predicate ?? null,
181
+ // Bounded here too, the one INSERT, so no caller of this function can keep raw text.
182
+ guard ? keptReason(guard.reason) : INVALID_TRANSITION,
64
183
  row.actor,
65
184
  row.impersonation,
66
185
  row.invocationId,
@@ -68,6 +187,6 @@ export function refusalInsert(row) {
68
187
  ],
69
188
  };
70
189
  }
71
- /** The refused transition an operation failed with, or null — what the adapters branch on. */
190
+ /** The refused transition an operation failed with, or null. */
72
191
  export { refusedTransitionOf };
73
192
  //# sourceMappingURL=refusals.js.map
@@ -1 +1 @@
1
- {"version":3,"file":"refusals.js","sourceRoot":"","sources":["../src/refusals.ts"],"names":[],"mappings":"AAAA;;;;;;;;;;;;;;;;GAgBG;AACH,OAAO,EAAE,mBAAmB,EAA0B,MAAM,yBAAyB,CAAC;AACtF,OAAO,EAAE,IAAI,EAAE,MAAM,WAAW,CAAC;AAEjC,MAAM,CAAC,MAAM,YAAY,GAAG;;;;;;;;;;;;;;;;;;;;;;;;;;CA0B3B,CAAC;AAcF,8EAA8E;AAC9E,MAAM,UAAU,aAAa,CAAC,GAAe;IAC3C,OAAO;QACL,GAAG,EAAE;;;uEAG8D;QACnE,MAAM,EAAE;YACN,IAAI,EAAE;YACN,GAAG,CAAC,QAAQ;YACZ,GAAG,CAAC,OAAO;YACX,GAAG,CAAC,OAAO,CAAC,UAAU;YACtB,GAAG,CAAC,OAAO,CAAC,QAAQ;YACpB,GAAG,CAAC,OAAO,CAAC,IAAI;YAChB,GAAG,CAAC,OAAO,CAAC,SAAS;YACrB,GAAG,CAAC,OAAO,CAAC,SAAS;YACrB,GAAG,CAAC,gBAAgB;YACpB,GAAG,CAAC,KAAK;YACT,GAAG,CAAC,aAAa;YACjB,GAAG,CAAC,YAAY;YAChB,GAAG,CAAC,EAAE;SACP;KACF,CAAC;AACJ,CAAC;AAED,8FAA8F;AAC9F,OAAO,EAAE,mBAAmB,EAAE,CAAC"}
1
+ {"version":3,"file":"refusals.js","sourceRoot":"","sources":["../src/refusals.ts"],"names":[],"mappings":"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"}
@@ -846,7 +846,8 @@ export interface ScheduleRunReport {
846
846
  * The module is switched off on this scope (#1666) — every `skipped` above is that,
847
847
  * not a cadence window. Optional and absent otherwise, so a stored or pre-widening
848
848
  * report stays valid. A module a PITR rewind holds off until its switch is back in the
849
- * scope (#1819, Cloudflare only) reports the same.
849
+ * scope (#1819, Cloudflare only) reports the same. The system door refuses that module's
850
+ * other calls too, a job run's among them (#1834).
850
851
  */
851
852
  switchedOff?: true;
852
853
  /**
@@ -1471,8 +1472,10 @@ export interface HostAdmin {
1471
1472
  * with `conflict`: restore is the lever; a grant is not. A grant that went through would
1472
1473
  * hand the module's system authority back to a job run or a `getSystemScope` invoke
1473
1474
  * while its schedules stayed off. Only `restoreToSystem` turns the switch back on.
1474
- * (A TENANT-level grant — `node.scopeId` null — is not checked: the switch lives in each
1475
- * scope's storage and the directory cannot see it. Nothing in the platform writes one.)
1475
+ * A TENANT-level grant (`node.scopeId` null) is refused the same way while the directory
1476
+ * records the module off on any scope of the tenant (#1743). One that already existed when
1477
+ * a scope was switched off gives the module nothing there: the evaluator denies a
1478
+ * switched-off subject on its scope whatever it holds (#1823).
1476
1479
  */
1477
1480
  grantToSystem(actor: PlatformActorId, grant: SystemGrant): Promise<void>;
1478
1481
  /**
@@ -1489,7 +1492,8 @@ export interface HostAdmin {
1489
1492
  * `restoreToSystem`;
1490
1493
  * - anything acting with the module's system authority is denied by its own
1491
1494
  * `ctx.check` — a resumable job run (#1577) fails its step, a `getSystemScope` invoke
1492
- * is refused;
1495
+ * is refused — including authority from a TENANT-level grant, which OFF cannot
1496
+ * tombstone: the evaluator reads the marker before any grant (#1823);
1493
1497
  * - and nothing can hand that authority back: `grantToSystem` refuses, and a reconcile
1494
1498
  * seats no `system:` grant for the module, not even one a newer version declares.
1495
1499
  * `restoreToSystem` is the only way back.
@@ -1502,8 +1506,14 @@ export interface HostAdmin {
1502
1506
  * atomic: this order fails toward "an intent with no outcome", never toward "a switch
1503
1507
  * that moved with no row".
1504
1508
  *
1505
- * Throws `not_found` when the scope holds no `system:<module>` grant at all — a typo in
1506
- * an emergency must not answer "done". On a host that delegates to the deployment
1509
+ * Throws `not_found` when the module has no authority reaching the scope at all — no
1510
+ * `system:<module>` grant on the scope and no live tenant-level one (#1823) — so a typo in
1511
+ * an emergency does not answer "done". A module whose only authority there is a
1512
+ * tenant-level grant IS switched: OFF writes the marker and tombstones nothing.
1513
+ *
1514
+ * The directory's record of the switch is written BEFORE the scope moves and taken back if
1515
+ * the move throws or holds nothing (#1823), so #1743's tenant-level refusal has no window to
1516
+ * miss. On a host that delegates to the deployment
1507
1517
  * serving the scope, the write happens THERE and the audit rows HERE.
1508
1518
  */
1509
1519
  revokeFromSystem(actor: PlatformActorId, input: SystemSwitch): Promise<SystemSwitchResult>;
@@ -1545,6 +1555,14 @@ export interface HostAdmin {
1545
1555
  * `systemGrantsStatus` reports both side by side (`schedules` and `recorded`).
1546
1556
  */
1547
1557
  listSystemSwitches(actor: PlatformActorId, filter?: SystemSwitchRecordFilter): Promise<SystemSwitchRecord[]>;
1558
+ /**
1559
+ * Which of these modules the tenant holds a live TENANT-level `system:` grant for (#1823).
1560
+ * A module whose only authority on a scope is such a grant has nothing in the scope's
1561
+ * storage, so a switch carried into a deployment (a hosted provision, reconcile or restore)
1562
+ * names these as `tenantHeld`, and the deployment's in-unit OFF holds them too. Order follows
1563
+ * `moduleIds`. Access-logged (K-24), as the fleet read is.
1564
+ */
1565
+ tenantHeldSystemModules(actor: PlatformActorId, tenantId: TenantId, moduleIds: readonly ModuleId[]): Promise<ModuleId[]>;
1548
1566
  /**
1549
1567
  * Put the directory's OFF positions back into one scope (#1674), for a scope whose storage
1550
1568
  * lost them: a wipe then re-provision, or a restore of a dump taken before the switch was
@@ -3871,6 +3889,12 @@ export interface ScopeHost {
3871
3889
  * one enforcement path, `ctx.check` stays the single gate, no bypass. Events it
3872
3890
  * emits are stamped `{ system: moduleId }`. `ctx.principal` carries the module id
3873
3891
  * so the type holds, but it is **not a person**.
3892
+ *
3893
+ * **It is the one door for that authority** (#1834). A schedule's fire and a job run's
3894
+ * `pass.scope()` both act through it, and so does `getSystemAttachments`. On the hosted adapter it
3895
+ * also refuses (`forbidden`) a module a PITR rewind holds off (#1819), at every call it makes,
3896
+ * not only when it is opened: each call is pinned to the scope instance the door checked, and
3897
+ * a call landing on a restarted one (a rewound scope always is) is checked again first.
3874
3898
  */
3875
3899
  getSystemScope(moduleId: ModuleId, tenantId: TenantId, scopeId: ScopeId): Promise<ScopeStub>;
3876
3900
  /**