@nodii/saga 0.6.0 → 0.7.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.
@@ -1,17 +1,25 @@
1
- import { type SagaAdminServiceOpts, type SagaStateRow } from "./types";
2
- export interface GetSagaRequest {
1
+ import { type SagaAdminAuthorizer, type SagaAdminServiceOpts, type SagaStateRow } from "./types";
2
+ /** Fields every admin RPC carries so the authorizer can gate the call. The
3
+ * caller resolves `actorPermissions` upstream from the verified actor
4
+ * envelope (`@nodii/grpc-auth`) and forwards it on the request. */
5
+ export interface AdminAuthFields {
6
+ /** Caller's effective permission set (resolved upstream). */
7
+ actorPermissions?: readonly string[];
8
+ /** Opaque actor id (audit + row-scoped checks). */
9
+ actorId?: string;
10
+ }
11
+ export interface GetSagaRequest extends AdminAuthFields {
3
12
  sagaId: string;
4
13
  }
5
- export interface ListSagasRequest {
14
+ export interface ListSagasRequest extends AdminAuthFields {
6
15
  tenantId?: string;
7
16
  status?: string;
8
17
  type?: string;
9
18
  limit?: number;
10
19
  }
11
- export interface WriteRpcRequest {
20
+ export interface WriteRpcRequest extends AdminAuthFields {
12
21
  sagaId: string;
13
22
  justification: string;
14
- actorId?: string;
15
23
  }
16
24
  export interface RetryStepRequest extends WriteRpcRequest {
17
25
  stepName: string;
@@ -51,5 +59,11 @@ export interface SagaAdminServer {
51
59
  ok: true;
52
60
  }>;
53
61
  }
62
+ /**
63
+ * Default admin authorizer (§ 5.10): pure permission-set membership over the
64
+ * locked SAGA_ADMIN_PERMISSIONS. No allow-all fallback (R1) — an op whose
65
+ * required permission is absent from `actorPermissions` is denied.
66
+ */
67
+ export declare const defaultSagaAdminAuthorizer: SagaAdminAuthorizer;
54
68
  export declare function createSagaAdminServer(opts: SagaAdminServiceOpts): SagaAdminServer;
55
69
  //# sourceMappingURL=admin-service.d.ts.map
@@ -1 +1 @@
1
- {"version":3,"file":"admin-service.d.ts","sourceRoot":"","sources":["../src/admin-service.ts"],"names":[],"mappings":"AASA,OAAO,EACL,KAAK,oBAAoB,EACzB,KAAK,YAAY,EAGlB,MAAM,SAAS,CAAC;AAEjB,MAAM,WAAW,cAAc;IAC7B,MAAM,EAAE,MAAM,CAAC;CAChB;AAED,MAAM,WAAW,gBAAgB;IAC/B,QAAQ,CAAC,EAAE,MAAM,CAAC;IAClB,MAAM,CAAC,EAAE,MAAM,CAAC;IAChB,IAAI,CAAC,EAAE,MAAM,CAAC;IACd,KAAK,CAAC,EAAE,MAAM,CAAC;CAChB;AAED,MAAM,WAAW,eAAe;IAC9B,MAAM,EAAE,MAAM,CAAC;IACf,aAAa,EAAE,MAAM,CAAC;IACtB,OAAO,CAAC,EAAE,MAAM,CAAC;CAClB;AAED,MAAM,WAAW,gBAAiB,SAAQ,eAAe;IACvD,QAAQ,EAAE,MAAM,CAAC;CAClB;AAED,MAAM,WAAW,eAAgB,SAAQ,eAAe;IACtD,QAAQ,EAAE,MAAM,CAAC;CAClB;AAED,MAAM,WAAW,sBAAuB,SAAQ,eAAe;IAC7D,QAAQ,CAAC,EAAE,MAAM,CAAC;CACnB;AAED,MAAM,WAAW,8BAA+B,SAAQ,eAAe;IACrE,aAAa,CAAC,EAAE,MAAM,CAAC;CACxB;AAED,MAAM,WAAW,iBAAkB,SAAQ,eAAe;IACxD,MAAM,EAAE,MAAM,CAAC;CAChB;AAED,MAAM,WAAW,eAAe;IAC9B,OAAO,CAAC,GAAG,EAAE,cAAc,GAAG,OAAO,CAAC;QAAE,IAAI,EAAE,YAAY,GAAG,IAAI,CAAA;KAAE,CAAC,CAAC;IACrE,SAAS,CAAC,GAAG,EAAE,gBAAgB,GAAG,OAAO,CAAC;QAAE,KAAK,EAAE,YAAY,EAAE,CAAA;KAAE,CAAC,CAAC;IACrE,SAAS,CAAC,GAAG,EAAE,gBAAgB,GAAG,OAAO,CAAC;QAAE,EAAE,EAAE,IAAI,CAAA;KAAE,CAAC,CAAC;IACxD,QAAQ,CAAC,GAAG,EAAE,eAAe,GAAG,OAAO,CAAC;QAAE,EAAE,EAAE,IAAI,CAAA;KAAE,CAAC,CAAC;IACtD,eAAe,CAAC,GAAG,EAAE,sBAAsB,GAAG,OAAO,CAAC;QAAE,EAAE,EAAE,IAAI,CAAA;KAAE,CAAC,CAAC;IACpE,uBAAuB,CACrB,GAAG,EAAE,8BAA8B,GAClC,OAAO,CAAC;QAAE,EAAE,EAAE,IAAI,CAAA;KAAE,CAAC,CAAC;IACzB,UAAU,CAAC,GAAG,EAAE,iBAAiB,GAAG,OAAO,CAAC;QAAE,EAAE,EAAE,IAAI,CAAA;KAAE,CAAC,CAAC;CAC3D;AAED,wBAAgB,qBAAqB,CACnC,IAAI,EAAE,oBAAoB,GACzB,eAAe,CAsKjB"}
1
+ {"version":3,"file":"admin-service.d.ts","sourceRoot":"","sources":["../src/admin-service.ts"],"names":[],"mappings":"AAcA,OAAO,EAEL,KAAK,mBAAmB,EAExB,KAAK,oBAAoB,EACzB,KAAK,YAAY,EAKlB,MAAM,SAAS,CAAC;AAEjB;;oEAEoE;AACpE,MAAM,WAAW,eAAe;IAC9B,6DAA6D;IAC7D,gBAAgB,CAAC,EAAE,SAAS,MAAM,EAAE,CAAC;IACrC,mDAAmD;IACnD,OAAO,CAAC,EAAE,MAAM,CAAC;CAClB;AAED,MAAM,WAAW,cAAe,SAAQ,eAAe;IACrD,MAAM,EAAE,MAAM,CAAC;CAChB;AAED,MAAM,WAAW,gBAAiB,SAAQ,eAAe;IACvD,QAAQ,CAAC,EAAE,MAAM,CAAC;IAClB,MAAM,CAAC,EAAE,MAAM,CAAC;IAChB,IAAI,CAAC,EAAE,MAAM,CAAC;IACd,KAAK,CAAC,EAAE,MAAM,CAAC;CAChB;AAED,MAAM,WAAW,eAAgB,SAAQ,eAAe;IACtD,MAAM,EAAE,MAAM,CAAC;IACf,aAAa,EAAE,MAAM,CAAC;CACvB;AAED,MAAM,WAAW,gBAAiB,SAAQ,eAAe;IACvD,QAAQ,EAAE,MAAM,CAAC;CAClB;AAED,MAAM,WAAW,eAAgB,SAAQ,eAAe;IACtD,QAAQ,EAAE,MAAM,CAAC;CAClB;AAED,MAAM,WAAW,sBAAuB,SAAQ,eAAe;IAC7D,QAAQ,CAAC,EAAE,MAAM,CAAC;CACnB;AAED,MAAM,WAAW,8BAA+B,SAAQ,eAAe;IACrE,aAAa,CAAC,EAAE,MAAM,CAAC;CACxB;AAED,MAAM,WAAW,iBAAkB,SAAQ,eAAe;IACxD,MAAM,EAAE,MAAM,CAAC;CAChB;AAED,MAAM,WAAW,eAAe;IAC9B,OAAO,CAAC,GAAG,EAAE,cAAc,GAAG,OAAO,CAAC;QAAE,IAAI,EAAE,YAAY,GAAG,IAAI,CAAA;KAAE,CAAC,CAAC;IACrE,SAAS,CAAC,GAAG,EAAE,gBAAgB,GAAG,OAAO,CAAC;QAAE,KAAK,EAAE,YAAY,EAAE,CAAA;KAAE,CAAC,CAAC;IACrE,SAAS,CAAC,GAAG,EAAE,gBAAgB,GAAG,OAAO,CAAC;QAAE,EAAE,EAAE,IAAI,CAAA;KAAE,CAAC,CAAC;IACxD,QAAQ,CAAC,GAAG,EAAE,eAAe,GAAG,OAAO,CAAC;QAAE,EAAE,EAAE,IAAI,CAAA;KAAE,CAAC,CAAC;IACtD,eAAe,CAAC,GAAG,EAAE,sBAAsB,GAAG,OAAO,CAAC;QAAE,EAAE,EAAE,IAAI,CAAA;KAAE,CAAC,CAAC;IACpE,uBAAuB,CACrB,GAAG,EAAE,8BAA8B,GAClC,OAAO,CAAC;QAAE,EAAE,EAAE,IAAI,CAAA;KAAE,CAAC,CAAC;IACzB,UAAU,CAAC,GAAG,EAAE,iBAAiB,GAAG,OAAO,CAAC;QAAE,EAAE,EAAE,IAAI,CAAA;KAAE,CAAC,CAAC;CAC3D;AAED;;;;GAIG;AACH,eAAO,MAAM,0BAA0B,EAAE,mBACc,CAAC;AAExD,wBAAgB,qBAAqB,CACnC,IAAI,EAAE,oBAAoB,GACzB,eAAe,CA6OjB"}
@@ -1,14 +1,26 @@
1
- // SagaAdminService factory — § 5.10. v0.1.0 ships the JSON-RPC-style
2
- // surface; the real gRPC proto + codegen + Pane wiring lands in
3
- // saga-v0.1.x. Stubs for the 4 write RPCs throw NotImplementedError AFTER
4
- // validating `justification` — that keeps the audit shape correct in the
5
- // rejection path.
1
+ // SagaAdminService factory — § 5.10.
6
2
  //
7
- // Two read RPCs (`GetSaga`, `ListSagas`) are fully wired against the
8
- // pluggable SagaStateStore.
9
- import { JustificationRequired, MIN_JUSTIFICATION_CHARS, } from "./types";
3
+ // Every RPC is gated on the locked SAGA_ADMIN_PERMISSIONS 5.10) via the
4
+ // pluggable SagaAdminAuthorizer (default = permission-set membership over
5
+ // the caller's `actorPermissions`). Administrative saga operations are
6
+ // privileged — force-compensate / cancel / retry / skip / manual-resolve
7
+ // directly mutate saga state outside the normal step flow — so an
8
+ // unauthorized caller is rejected with SagaAdminUnauthorized BEFORE any
9
+ // state write, and an `*_unauthorized` audit row records the denied attempt.
10
+ //
11
+ // Read RPCs (`GetSaga`, `ListSagas`) are gated on READ; the 5 write RPCs map
12
+ // to RETRY / SKIP / COMPENSATE / MANUAL_RESOLVE per the locked permission
13
+ // catalog. Write RPCs additionally validate `justification` (min 20 chars).
14
+ import { JustificationRequired, MIN_JUSTIFICATION_CHARS, SAGA_ADMIN_PERMISSIONS, SagaAdminUnauthorized, } from "./types";
15
+ /**
16
+ * Default admin authorizer (§ 5.10): pure permission-set membership over the
17
+ * locked SAGA_ADMIN_PERMISSIONS. No allow-all fallback (R1) — an op whose
18
+ * required permission is absent from `actorPermissions` is denied.
19
+ */
20
+ export const defaultSagaAdminAuthorizer = (ctx) => ctx.actorPermissions.includes(ctx.requiredPermission);
10
21
  export function createSagaAdminServer(opts) {
11
22
  const { stateStore, audit } = opts;
23
+ const authorizer = opts.authorizer ?? defaultSagaAdminAuthorizer;
12
24
  const validateJustification = (justification) => {
13
25
  if (typeof justification !== "string" ||
14
26
  justification.length < MIN_JUSTIFICATION_CHARS) {
@@ -25,13 +37,45 @@ export function createSagaAdminServer(opts) {
25
37
  payload,
26
38
  });
27
39
  };
40
+ /**
41
+ * Authorize an admin op against its locked permission. Emits an
42
+ * `*_unauthorized` audit row and throws SagaAdminUnauthorized on denial,
43
+ * BEFORE any state mutation. The authorizer is async-tolerant so a remote
44
+ * RBAC resolver can be plugged in.
45
+ */
46
+ const authorize = async (method, requiredPermission, sagaId, fields) => {
47
+ const ctx = {
48
+ method,
49
+ requiredPermission,
50
+ sagaId,
51
+ actorPermissions: fields.actorPermissions ?? [],
52
+ actorId: fields.actorId,
53
+ };
54
+ let allowed;
55
+ try {
56
+ allowed = await authorizer(ctx);
57
+ }
58
+ catch {
59
+ // A throwing authorizer is treated as a hard denial (fail-closed, R1).
60
+ allowed = false;
61
+ }
62
+ if (!allowed) {
63
+ await emitAdminAudit(`${auditActionFor(method)}_unauthorized`, sagaId, {
64
+ required_permission: requiredPermission,
65
+ actor_id: fields.actorId ?? null,
66
+ });
67
+ throw new SagaAdminUnauthorized(method, requiredPermission);
68
+ }
69
+ };
28
70
  return {
29
71
  async GetSaga(req) {
72
+ await authorize("GetSaga", SAGA_ADMIN_PERMISSIONS.READ, req.sagaId, req);
30
73
  await emitAdminAudit("saga_admin_get_saga", req.sagaId);
31
74
  const saga = await stateStore.getSaga(req.sagaId);
32
75
  return { saga };
33
76
  },
34
77
  async ListSagas(req) {
78
+ await authorize("ListSagas", SAGA_ADMIN_PERMISSIONS.READ, req.tenantId ?? "*", req);
35
79
  await emitAdminAudit("saga_admin_list_sagas", req.tenantId ?? "*");
36
80
  // Per § 5.5 list() is optional on SagaStateStore — stores that omit it
37
81
  // return []. Production-bound stores (Drizzle) MUST implement it.
@@ -46,6 +90,7 @@ export function createSagaAdminServer(opts) {
46
90
  return { sagas: rows.slice(0, limit) };
47
91
  },
48
92
  async RetryStep(req) {
93
+ await authorize("RetryStep", SAGA_ADMIN_PERMISSIONS.RETRY, req.sagaId, req);
49
94
  validateJustification(req.justification);
50
95
  await emitAdminAudit("saga_admin_retry_step", req.sagaId, {
51
96
  step: req.stepName,
@@ -66,6 +111,7 @@ export function createSagaAdminServer(opts) {
66
111
  return { ok: true };
67
112
  },
68
113
  async SkipStep(req) {
114
+ await authorize("SkipStep", SAGA_ADMIN_PERMISSIONS.SKIP, req.sagaId, req);
69
115
  validateJustification(req.justification);
70
116
  await emitAdminAudit("saga_admin_skip_step", req.sagaId, {
71
117
  step: req.stepName,
@@ -92,6 +138,7 @@ export function createSagaAdminServer(opts) {
92
138
  return { ok: true };
93
139
  },
94
140
  async ForceCompensate(req) {
141
+ await authorize("ForceCompensate", SAGA_ADMIN_PERMISSIONS.COMPENSATE, req.sagaId, req);
95
142
  validateJustification(req.justification);
96
143
  await emitAdminAudit("saga_admin_force_compensate", req.sagaId, {
97
144
  from_step: req.fromStep,
@@ -111,6 +158,7 @@ export function createSagaAdminServer(opts) {
111
158
  return { ok: true };
112
159
  },
113
160
  async MarkManuallyCompensated(req) {
161
+ await authorize("MarkManuallyCompensated", SAGA_ADMIN_PERMISSIONS.MANUAL_RESOLVE, req.sagaId, req);
114
162
  validateJustification(req.justification);
115
163
  await emitAdminAudit("saga_admin_mark_manually_compensated", req.sagaId, {
116
164
  resolution_ref: req.resolutionRef,
@@ -141,6 +189,10 @@ export function createSagaAdminServer(opts) {
141
189
  return { ok: true };
142
190
  },
143
191
  async CancelSaga(req) {
192
+ // Cancel is a terminal compensate-class admin op; the locked
193
+ // permission catalog (§ 5.10) has no dedicated CANCEL string, so it
194
+ // is gated on COMPENSATE (same privilege tier as force-compensate).
195
+ await authorize("CancelSaga", SAGA_ADMIN_PERMISSIONS.COMPENSATE, req.sagaId, req);
144
196
  validateJustification(req.justification);
145
197
  await emitAdminAudit("saga_admin_cancel", req.sagaId, {
146
198
  reason: req.reason,
@@ -158,4 +210,29 @@ export function createSagaAdminServer(opts) {
158
210
  },
159
211
  };
160
212
  }
213
+ /**
214
+ * Map an RPC method name → its audit-action stem, so the unauthorized
215
+ * audit row reuses the same `saga_admin_*` family as the success path
216
+ * (e.g. `RetryStep` → `saga_admin_retry_step` → `saga_admin_retry_step_unauthorized`).
217
+ */
218
+ function auditActionFor(method) {
219
+ switch (method) {
220
+ case "GetSaga":
221
+ return "saga_admin_get_saga";
222
+ case "ListSagas":
223
+ return "saga_admin_list_sagas";
224
+ case "RetryStep":
225
+ return "saga_admin_retry_step";
226
+ case "SkipStep":
227
+ return "saga_admin_skip_step";
228
+ case "ForceCompensate":
229
+ return "saga_admin_force_compensate";
230
+ case "MarkManuallyCompensated":
231
+ return "saga_admin_mark_manually_compensated";
232
+ case "CancelSaga":
233
+ return "saga_admin_cancel";
234
+ default:
235
+ return `saga_admin_${method.toLowerCase()}`;
236
+ }
237
+ }
161
238
  //# sourceMappingURL=admin-service.js.map
@@ -1 +1 @@
1
- {"version":3,"file":"admin-service.js","sourceRoot":"","sources":["../src/admin-service.ts"],"names":[],"mappings":"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"}
1
+ {"version":3,"file":"admin-service.js","sourceRoot":"","sources":["../src/admin-service.ts"],"names":[],"mappings":"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"}
package/dist/index.d.ts CHANGED
@@ -8,8 +8,8 @@ export { emitSagaSignal, awaitSagaSignal, awaitChildren, awaitAnySibling, getSib
8
8
  export { sagaCallable, SAGA_CALLABLE_METADATA, readSagaCallableConfig, readSagaCallableRegistry, _resetDecoratorRegistryForTests, } from "./decorator";
9
9
  export type { SagaCallableMethod } from "./decorator";
10
10
  export { sagaContext } from "./interceptor";
11
- export { createSagaAdminServer } from "./admin-service";
12
- export type { CancelSagaRequest, ForceCompensateRequest, GetSagaRequest, ListSagasRequest, MarkManuallyCompensatedRequest, RetryStepRequest, SagaAdminServer, SkipStepRequest, WriteRpcRequest, } from "./admin-service";
11
+ export { createSagaAdminServer, defaultSagaAdminAuthorizer, } from "./admin-service";
12
+ export type { AdminAuthFields, CancelSagaRequest, ForceCompensateRequest, GetSagaRequest, ListSagasRequest, MarkManuallyCompensatedRequest, RetryStepRequest, SagaAdminServer, SkipStepRequest, WriteRpcRequest, } from "./admin-service";
13
13
  export { PostgresSagaStateStore, type PostgresSagaStateStoreOpts, } from "./state-store/postgres";
14
14
  export { RedisSignalBus, type RedisSignalBusOpts, } from "./signal-bus/redis-stream";
15
15
  export { beginAsyncStep, completeAsyncStep, getCompletedAsyncOutput, SagaPausedSentinel, } from "./async-step";
@@ -19,6 +19,8 @@ export { createParticipantWorker, ParticipantOutboxTableInvalid, ParticipantWork
19
19
  export type { CreateParticipantWorkerOpts, ParticipantBeginEvent, ParticipantHandler, ParticipantHandlerCtx, ParticipantSqlClient, ParticipantSqlTx, ParticipantWorkerHandle, } from "./participant-worker";
20
20
  export { applySagaMigrations, getSagaStateMigrationSQL } from "./migrations";
21
21
  export { uuidv7, isUuidv7 } from "./uuid";
22
- export { MIN_JUSTIFICATION_CHARS, SAGA_ADMIN_PERMISSIONS, SagaError, SagaIdempotencyRequired, SagaNotInitialized, SagaContextRequired, SagaStepFailed, SagaCompensationFailed, JustificationRequired, SagaTypeNotRegistered, NoActiveSaga, NotImplementedError, } from "./types";
23
- export type { CompensationLogEntry, CreateSagaOpts, IdempotencyShim, ResumeContext, SagaAdminPermission, SagaAdminServiceOpts, SagaCallableConfig, SagaContextInterceptorOpts, SagaHandle, SagaInterceptorCall, SagaSignalBus, SagaStateRow, SagaStateStore, SagaStatus, StepOpts, TelemetryAuditEmitter, } from "./types";
22
+ export { MIN_JUSTIFICATION_CHARS, SAGA_ADMIN_PERMISSIONS, SagaError, SagaIdempotencyRequired, SagaNotInitialized, SagaContextRequired, SagaStepFailed, SagaCompensationFailed, JustificationRequired, SagaAdminUnauthorized, SagaTypeNotRegistered, NoActiveSaga, NotImplementedError, } from "./types";
23
+ export type { CompensationLogEntry, CreateSagaOpts, IdempotencyShim, ResumeContext, SagaAdminAuthContext, SagaAdminAuthorizer, SagaAdminPermission, SagaAdminServiceOpts, SagaCallableConfig, SagaContextInterceptorOpts, SagaHandle, SagaInterceptorCall, SagaSignalBus, SagaStateRow, SagaStateStore, SagaStatus, StepOpts, TelemetryAuditEmitter, UndoStackEntry, } from "./types";
24
+ export { recoverUndoStack } from "./saga";
25
+ export type { UndoResolver, RecoverUndoStackResult } from "./saga";
24
26
  //# sourceMappingURL=index.d.ts.map
@@ -1 +1 @@
1
- {"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../src/index.ts"],"names":[],"mappings":"AAgBA,eAAO,MAAM,QAAQ,SAAS,CAAC;AAC/B,eAAO,MAAM,OAAO,UAAU,CAAC;AAE/B,OAAO,EAAE,QAAQ,EAAE,aAAa,EAAE,cAAc,EAAE,MAAM,QAAQ,CAAC;AACjE,YAAY,EAAE,cAAc,EAAE,kBAAkB,EAAE,MAAM,QAAQ,CAAC;AAEjE,OAAO,EACL,UAAU,EACV,QAAQ,EACR,IAAI,EACJ,YAAY,EACZ,MAAM,EACN,WAAW,GACZ,MAAM,QAAQ,CAAC;AAEhB,OAAO,EACL,YAAY,EACZ,iBAAiB,EACjB,iBAAiB,EACjB,sBAAsB,GACvB,MAAM,YAAY,CAAC;AAEpB,OAAO,EACL,cAAc,EACd,eAAe,EACf,aAAa,EACb,eAAe,EACf,WAAW,GACZ,MAAM,WAAW,CAAC;AAEnB,OAAO,EACL,YAAY,EACZ,sBAAsB,EACtB,sBAAsB,EACtB,wBAAwB,EACxB,+BAA+B,GAChC,MAAM,aAAa,CAAC;AACrB,YAAY,EAAE,kBAAkB,EAAE,MAAM,aAAa,CAAC;AAEtD,OAAO,EAAE,WAAW,EAAE,MAAM,eAAe,CAAC;AAE5C,OAAO,EAAE,qBAAqB,EAAE,MAAM,iBAAiB,CAAC;AACxD,YAAY,EACV,iBAAiB,EACjB,sBAAsB,EACtB,cAAc,EACd,gBAAgB,EAChB,8BAA8B,EAC9B,gBAAgB,EAChB,eAAe,EACf,eAAe,EACf,eAAe,GAChB,MAAM,iBAAiB,CAAC;AAGzB,OAAO,EACL,sBAAsB,EACtB,KAAK,0BAA0B,GAChC,MAAM,wBAAwB,CAAC;AAChC,OAAO,EACL,cAAc,EACd,KAAK,kBAAkB,GACxB,MAAM,2BAA2B,CAAC;AAGnC,OAAO,EACL,cAAc,EACd,iBAAiB,EACjB,uBAAuB,EACvB,kBAAkB,GACnB,MAAM,cAAc,CAAC;AACtB,OAAO,EAAE,eAAe,EAAE,MAAM,UAAU,CAAC;AAC3C,YAAY,EAAE,cAAc,EAAE,gBAAgB,EAAE,MAAM,UAAU,CAAC;AAGjE,OAAO,EACL,uBAAuB,EACvB,6BAA6B,EAC7B,wBAAwB,GACzB,MAAM,sBAAsB,CAAC;AAC9B,YAAY,EACV,2BAA2B,EAC3B,qBAAqB,EACrB,kBAAkB,EAClB,qBAAqB,EACrB,oBAAoB,EACpB,gBAAgB,EAChB,uBAAuB,GACxB,MAAM,sBAAsB,CAAC;AAG9B,OAAO,EAAE,mBAAmB,EAAE,wBAAwB,EAAE,MAAM,cAAc,CAAC;AAE7E,OAAO,EAAE,MAAM,EAAE,QAAQ,EAAE,MAAM,QAAQ,CAAC;AAE1C,OAAO,EACL,uBAAuB,EACvB,sBAAsB,EAEtB,SAAS,EACT,uBAAuB,EACvB,kBAAkB,EAClB,mBAAmB,EACnB,cAAc,EACd,sBAAsB,EACtB,qBAAqB,EACrB,qBAAqB,EACrB,YAAY,EACZ,mBAAmB,GACpB,MAAM,SAAS,CAAC;AAEjB,YAAY,EACV,oBAAoB,EACpB,cAAc,EACd,eAAe,EACf,aAAa,EACb,mBAAmB,EACnB,oBAAoB,EACpB,kBAAkB,EAClB,0BAA0B,EAC1B,UAAU,EACV,mBAAmB,EACnB,aAAa,EACb,YAAY,EACZ,cAAc,EACd,UAAU,EACV,QAAQ,EACR,qBAAqB,GACtB,MAAM,SAAS,CAAC"}
1
+ {"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../src/index.ts"],"names":[],"mappings":"AAgBA,eAAO,MAAM,QAAQ,SAAS,CAAC;AAC/B,eAAO,MAAM,OAAO,UAAU,CAAC;AAE/B,OAAO,EAAE,QAAQ,EAAE,aAAa,EAAE,cAAc,EAAE,MAAM,QAAQ,CAAC;AACjE,YAAY,EAAE,cAAc,EAAE,kBAAkB,EAAE,MAAM,QAAQ,CAAC;AAEjE,OAAO,EACL,UAAU,EACV,QAAQ,EACR,IAAI,EACJ,YAAY,EACZ,MAAM,EACN,WAAW,GACZ,MAAM,QAAQ,CAAC;AAEhB,OAAO,EACL,YAAY,EACZ,iBAAiB,EACjB,iBAAiB,EACjB,sBAAsB,GACvB,MAAM,YAAY,CAAC;AAEpB,OAAO,EACL,cAAc,EACd,eAAe,EACf,aAAa,EACb,eAAe,EACf,WAAW,GACZ,MAAM,WAAW,CAAC;AAEnB,OAAO,EACL,YAAY,EACZ,sBAAsB,EACtB,sBAAsB,EACtB,wBAAwB,EACxB,+BAA+B,GAChC,MAAM,aAAa,CAAC;AACrB,YAAY,EAAE,kBAAkB,EAAE,MAAM,aAAa,CAAC;AAEtD,OAAO,EAAE,WAAW,EAAE,MAAM,eAAe,CAAC;AAE5C,OAAO,EACL,qBAAqB,EACrB,0BAA0B,GAC3B,MAAM,iBAAiB,CAAC;AACzB,YAAY,EACV,eAAe,EACf,iBAAiB,EACjB,sBAAsB,EACtB,cAAc,EACd,gBAAgB,EAChB,8BAA8B,EAC9B,gBAAgB,EAChB,eAAe,EACf,eAAe,EACf,eAAe,GAChB,MAAM,iBAAiB,CAAC;AAGzB,OAAO,EACL,sBAAsB,EACtB,KAAK,0BAA0B,GAChC,MAAM,wBAAwB,CAAC;AAChC,OAAO,EACL,cAAc,EACd,KAAK,kBAAkB,GACxB,MAAM,2BAA2B,CAAC;AAGnC,OAAO,EACL,cAAc,EACd,iBAAiB,EACjB,uBAAuB,EACvB,kBAAkB,GACnB,MAAM,cAAc,CAAC;AACtB,OAAO,EAAE,eAAe,EAAE,MAAM,UAAU,CAAC;AAC3C,YAAY,EAAE,cAAc,EAAE,gBAAgB,EAAE,MAAM,UAAU,CAAC;AAGjE,OAAO,EACL,uBAAuB,EACvB,6BAA6B,EAC7B,wBAAwB,GACzB,MAAM,sBAAsB,CAAC;AAC9B,YAAY,EACV,2BAA2B,EAC3B,qBAAqB,EACrB,kBAAkB,EAClB,qBAAqB,EACrB,oBAAoB,EACpB,gBAAgB,EAChB,uBAAuB,GACxB,MAAM,sBAAsB,CAAC;AAG9B,OAAO,EAAE,mBAAmB,EAAE,wBAAwB,EAAE,MAAM,cAAc,CAAC;AAE7E,OAAO,EAAE,MAAM,EAAE,QAAQ,EAAE,MAAM,QAAQ,CAAC;AAE1C,OAAO,EACL,uBAAuB,EACvB,sBAAsB,EAEtB,SAAS,EACT,uBAAuB,EACvB,kBAAkB,EAClB,mBAAmB,EACnB,cAAc,EACd,sBAAsB,EACtB,qBAAqB,EACrB,qBAAqB,EACrB,qBAAqB,EACrB,YAAY,EACZ,mBAAmB,GACpB,MAAM,SAAS,CAAC;AAEjB,YAAY,EACV,oBAAoB,EACpB,cAAc,EACd,eAAe,EACf,aAAa,EACb,oBAAoB,EACpB,mBAAmB,EACnB,mBAAmB,EACnB,oBAAoB,EACpB,kBAAkB,EAClB,0BAA0B,EAC1B,UAAU,EACV,mBAAmB,EACnB,aAAa,EACb,YAAY,EACZ,cAAc,EACd,UAAU,EACV,QAAQ,EACR,qBAAqB,EACrB,cAAc,GACf,MAAM,SAAS,CAAC;AAEjB,OAAO,EAAE,gBAAgB,EAAE,MAAM,QAAQ,CAAC;AAC1C,YAAY,EAAE,YAAY,EAAE,sBAAsB,EAAE,MAAM,QAAQ,CAAC"}
package/dist/index.js CHANGED
@@ -21,7 +21,7 @@ export { registerSaga, getRegisteredSaga, hasRegisteredSaga, _resetRegistryForTe
21
21
  export { emitSagaSignal, awaitSagaSignal, awaitChildren, awaitAnySibling, getSiblings, } from "./signals";
22
22
  export { sagaCallable, SAGA_CALLABLE_METADATA, readSagaCallableConfig, readSagaCallableRegistry, _resetDecoratorRegistryForTests, } from "./decorator";
23
23
  export { sagaContext } from "./interceptor";
24
- export { createSagaAdminServer } from "./admin-service";
24
+ export { createSagaAdminServer, defaultSagaAdminAuthorizer, } from "./admin-service";
25
25
  // Production-bound state-store + signal-bus.
26
26
  export { PostgresSagaStateStore, } from "./state-store/postgres";
27
27
  export { RedisSignalBus, } from "./signal-bus/redis-stream";
@@ -35,5 +35,6 @@ export { applySagaMigrations, getSagaStateMigrationSQL } from "./migrations";
35
35
  export { uuidv7, isUuidv7 } from "./uuid";
36
36
  export { MIN_JUSTIFICATION_CHARS, SAGA_ADMIN_PERMISSIONS,
37
37
  // Typed-error hierarchy.
38
- SagaError, SagaIdempotencyRequired, SagaNotInitialized, SagaContextRequired, SagaStepFailed, SagaCompensationFailed, JustificationRequired, SagaTypeNotRegistered, NoActiveSaga, NotImplementedError, } from "./types";
38
+ SagaError, SagaIdempotencyRequired, SagaNotInitialized, SagaContextRequired, SagaStepFailed, SagaCompensationFailed, JustificationRequired, SagaAdminUnauthorized, SagaTypeNotRegistered, NoActiveSaga, NotImplementedError, } from "./types";
39
+ export { recoverUndoStack } from "./saga";
39
40
  //# sourceMappingURL=index.js.map
package/dist/index.js.map CHANGED
@@ -1 +1 @@
1
- {"version":3,"file":"index.js","sourceRoot":"","sources":["../src/index.ts"],"names":[],"mappings":"AAAA,sCAAsC;AACtC,EAAE;AACF,mEAAmE;AACnE,6CAA6C;AAC7C,EAAE;AACF,2CAA2C;AAC3C,uEAAuE;AACvE,+EAA+E;AAC/E,sDAAsD;AACtD,mCAAmC;AACnC,0EAA0E;AAC1E,4EAA4E;AAC5E,EAAE;AACF,2EAA2E;AAC3E,gFAAgF;AAEhF,MAAM,CAAC,MAAM,QAAQ,GAAG,MAAM,CAAC;AAC/B,MAAM,CAAC,MAAM,OAAO,GAAG,OAAO,CAAC;AAE/B,OAAO,EAAE,QAAQ,EAAE,aAAa,EAAE,cAAc,EAAE,MAAM,QAAQ,CAAC;AAGjE,OAAO,EACL,UAAU,EACV,QAAQ,EACR,IAAI,EACJ,YAAY,EACZ,MAAM,EACN,WAAW,GACZ,MAAM,QAAQ,CAAC;AAEhB,OAAO,EACL,YAAY,EACZ,iBAAiB,EACjB,iBAAiB,EACjB,sBAAsB,GACvB,MAAM,YAAY,CAAC;AAEpB,OAAO,EACL,cAAc,EACd,eAAe,EACf,aAAa,EACb,eAAe,EACf,WAAW,GACZ,MAAM,WAAW,CAAC;AAEnB,OAAO,EACL,YAAY,EACZ,sBAAsB,EACtB,sBAAsB,EACtB,wBAAwB,EACxB,+BAA+B,GAChC,MAAM,aAAa,CAAC;AAGrB,OAAO,EAAE,WAAW,EAAE,MAAM,eAAe,CAAC;AAE5C,OAAO,EAAE,qBAAqB,EAAE,MAAM,iBAAiB,CAAC;AAaxD,6CAA6C;AAC7C,OAAO,EACL,sBAAsB,GAEvB,MAAM,wBAAwB,CAAC;AAChC,OAAO,EACL,cAAc,GAEf,MAAM,2BAA2B,CAAC;AAEnC,iCAAiC;AACjC,OAAO,EACL,cAAc,EACd,iBAAiB,EACjB,uBAAuB,EACvB,kBAAkB,GACnB,MAAM,cAAc,CAAC;AACtB,OAAO,EAAE,eAAe,EAAE,MAAM,UAAU,CAAC;AAG3C,uDAAuD;AACvD,OAAO,EACL,uBAAuB,EACvB,6BAA6B,EAC7B,wBAAwB,GACzB,MAAM,sBAAsB,CAAC;AAW9B,cAAc;AACd,OAAO,EAAE,mBAAmB,EAAE,wBAAwB,EAAE,MAAM,cAAc,CAAC;AAE7E,OAAO,EAAE,MAAM,EAAE,QAAQ,EAAE,MAAM,QAAQ,CAAC;AAE1C,OAAO,EACL,uBAAuB,EACvB,sBAAsB;AACtB,yBAAyB;AACzB,SAAS,EACT,uBAAuB,EACvB,kBAAkB,EAClB,mBAAmB,EACnB,cAAc,EACd,sBAAsB,EACtB,qBAAqB,EACrB,qBAAqB,EACrB,YAAY,EACZ,mBAAmB,GACpB,MAAM,SAAS,CAAC"}
1
+ {"version":3,"file":"index.js","sourceRoot":"","sources":["../src/index.ts"],"names":[],"mappings":"AAAA,sCAAsC;AACtC,EAAE;AACF,mEAAmE;AACnE,6CAA6C;AAC7C,EAAE;AACF,2CAA2C;AAC3C,uEAAuE;AACvE,+EAA+E;AAC/E,sDAAsD;AACtD,mCAAmC;AACnC,0EAA0E;AAC1E,4EAA4E;AAC5E,EAAE;AACF,2EAA2E;AAC3E,gFAAgF;AAEhF,MAAM,CAAC,MAAM,QAAQ,GAAG,MAAM,CAAC;AAC/B,MAAM,CAAC,MAAM,OAAO,GAAG,OAAO,CAAC;AAE/B,OAAO,EAAE,QAAQ,EAAE,aAAa,EAAE,cAAc,EAAE,MAAM,QAAQ,CAAC;AAGjE,OAAO,EACL,UAAU,EACV,QAAQ,EACR,IAAI,EACJ,YAAY,EACZ,MAAM,EACN,WAAW,GACZ,MAAM,QAAQ,CAAC;AAEhB,OAAO,EACL,YAAY,EACZ,iBAAiB,EACjB,iBAAiB,EACjB,sBAAsB,GACvB,MAAM,YAAY,CAAC;AAEpB,OAAO,EACL,cAAc,EACd,eAAe,EACf,aAAa,EACb,eAAe,EACf,WAAW,GACZ,MAAM,WAAW,CAAC;AAEnB,OAAO,EACL,YAAY,EACZ,sBAAsB,EACtB,sBAAsB,EACtB,wBAAwB,EACxB,+BAA+B,GAChC,MAAM,aAAa,CAAC;AAGrB,OAAO,EAAE,WAAW,EAAE,MAAM,eAAe,CAAC;AAE5C,OAAO,EACL,qBAAqB,EACrB,0BAA0B,GAC3B,MAAM,iBAAiB,CAAC;AAczB,6CAA6C;AAC7C,OAAO,EACL,sBAAsB,GAEvB,MAAM,wBAAwB,CAAC;AAChC,OAAO,EACL,cAAc,GAEf,MAAM,2BAA2B,CAAC;AAEnC,iCAAiC;AACjC,OAAO,EACL,cAAc,EACd,iBAAiB,EACjB,uBAAuB,EACvB,kBAAkB,GACnB,MAAM,cAAc,CAAC;AACtB,OAAO,EAAE,eAAe,EAAE,MAAM,UAAU,CAAC;AAG3C,uDAAuD;AACvD,OAAO,EACL,uBAAuB,EACvB,6BAA6B,EAC7B,wBAAwB,GACzB,MAAM,sBAAsB,CAAC;AAW9B,cAAc;AACd,OAAO,EAAE,mBAAmB,EAAE,wBAAwB,EAAE,MAAM,cAAc,CAAC;AAE7E,OAAO,EAAE,MAAM,EAAE,QAAQ,EAAE,MAAM,QAAQ,CAAC;AAE1C,OAAO,EACL,uBAAuB,EACvB,sBAAsB;AACtB,yBAAyB;AACzB,SAAS,EACT,uBAAuB,EACvB,kBAAkB,EAClB,mBAAmB,EACnB,cAAc,EACd,sBAAsB,EACtB,qBAAqB,EACrB,qBAAqB,EACrB,qBAAqB,EACrB,YAAY,EACZ,mBAAmB,GACpB,MAAM,SAAS,CAAC;AAwBjB,OAAO,EAAE,gBAAgB,EAAE,MAAM,QAAQ,CAAC"}
@@ -1,6 +1,16 @@
1
1
  type SqlClient = {
2
2
  unsafe: (sql: string, args?: unknown[]) => Promise<any>;
3
3
  };
4
+ /**
5
+ * Return the canonical A1 RLS DDL for `saga_state`. Returns the inlined
6
+ * constant verbatim — no runtime `@nodii/db-rls` call (see `SAGA_STATE_RLS_DDL`).
7
+ */
8
+ export declare function generateSagaStateRlsDdl(): string;
9
+ /**
10
+ * Return the canonical A1 RLS DDL for `saga_outbox`. Inlined constant verbatim —
11
+ * no runtime `@nodii/db-rls` call (see `SAGA_OUTBOX_RLS_DDL`).
12
+ */
13
+ export declare function generateSagaOutboxRlsDdl(): string;
4
14
  export declare function getSagaStateMigrationSQL(): string;
5
15
  /**
6
16
  * Apply the saga_state + saga_outbox migrations idempotently. Safe to call
@@ -13,7 +23,15 @@ export declare function getSagaStateMigrationSQL(): string;
13
23
  * whitespace blocks are skipped.
14
24
  */
15
25
  export declare function applySagaMigrations(sql: SqlClient): Promise<void>;
16
- /** Internal — exported only for unit-test coverage on the splitter. */
26
+ /**
27
+ * Internal — exported only for unit-test coverage on the splitter.
28
+ *
29
+ * Dollar-quote-aware: a `$$`-delimited body (e.g. the D412 `DO $$ ... $$;`
30
+ * guarded TEXT→UUID migration) may contain inner lines ending in `;` that
31
+ * must NOT terminate the statement. We track an open `$tag$` ... `$tag$`
32
+ * span and only honor a trailing `;` as a statement boundary when no dollar
33
+ * quote is open. (postgres.js sends each split statement via `.unsafe`.)
34
+ */
17
35
  export declare function splitStatements(ddl: string): string[];
18
36
  export {};
19
37
  //# sourceMappingURL=index.d.ts.map
@@ -1 +1 @@
1
- {"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../../src/migrations/index.ts"],"names":[],"mappings":"AAOA,KAAK,SAAS,GAAG;IAEf,MAAM,EAAE,CAAC,GAAG,EAAE,MAAM,EAAE,IAAI,CAAC,EAAE,OAAO,EAAE,KAAK,OAAO,CAAC,GAAG,CAAC,CAAC;CACzD,CAAC;AAgEF,wBAAgB,wBAAwB,IAAI,MAAM,CAEjD;AAED;;;;;;;;;GASG;AACH,wBAAsB,mBAAmB,CAAC,GAAG,EAAE,SAAS,GAAG,OAAO,CAAC,IAAI,CAAC,CAMvE;AAED,uEAAuE;AACvE,wBAAgB,eAAe,CAAC,GAAG,EAAE,MAAM,GAAG,MAAM,EAAE,CAerD"}
1
+ {"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../../src/migrations/index.ts"],"names":[],"mappings":"AAOA,KAAK,SAAS,GAAG;IAEf,MAAM,EAAE,CAAC,GAAG,EAAE,MAAM,EAAE,IAAI,CAAC,EAAE,OAAO,EAAE,KAAK,OAAO,CAAC,GAAG,CAAC,CAAC;CACzD,CAAC;AA8CF;;;GAGG;AACH,wBAAgB,uBAAuB,IAAI,MAAM,CAEhD;AA8CD;;;GAGG;AACH,wBAAgB,wBAAwB,IAAI,MAAM,CAEjD;AAgGD,wBAAgB,wBAAwB,IAAI,MAAM,CAEjD;AAED;;;;;;;;;GASG;AACH,wBAAsB,mBAAmB,CAAC,GAAG,EAAE,SAAS,GAAG,OAAO,CAAC,IAAI,CAAC,CAMvE;AAED;;;;;;;;GAQG;AACH,wBAAgB,eAAe,CAAC,GAAG,EAAE,MAAM,GAAG,MAAM,EAAE,CAwBrD"}
@@ -4,6 +4,106 @@
4
4
  // per-service migration runner. The SQL is shipped alongside this module
5
5
  // as `001-saga-state.sql` so a service that uses a different runner
6
6
  // (Flyway, golang-migrate, alembic, etc.) can copy it directly.
7
+ /**
8
+ * Canonical A1 RLS DDL for `saga_state` (D412 / 08-rls v7 § 4) — INLINED as a
9
+ * string constant so the runtime + published `@nodii/saga` package carry NO
10
+ * dependency on `@nodii/db-rls` (a runtime/peer dep would pull the whole RLS
11
+ * pooling + migrate-gen surface into saga and trigger a version cascade).
12
+ *
13
+ * saga_state does full CRUD, so it carries all four verbs: 1 owner policy + 4
14
+ * authenticated policies + 4 services policies, plus the per-role GRANTs.
15
+ * Postgres has no `CREATE POLICY IF NOT EXISTS`, so each `CREATE POLICY` is
16
+ * preceded by a matching `DROP POLICY IF EXISTS ... ;` to keep the migration
17
+ * idempotent. ENABLE + GRANT are already idempotent.
18
+ *
19
+ * This block is byte-equal to `@nodii/db-rls`'s
20
+ * `withRls("saga_state", { allow: ["SELECT","INSERT","UPDATE","DELETE"] })` +
21
+ * `generateTableGrants(...)` output (with the DROP-before-CREATE
22
+ * interleaving + grants reordered after ENABLE). The byte-equality is asserted
23
+ * in `tests/rls.integration.test.ts` against the live db-rls generators
24
+ * (db-rls is a DEV/test-only dependency that guards canonical drift — it is
25
+ * NEVER imported by shipped saga source). The vendored copy in
26
+ * `001-saga-state.sql` is byte-equal to this constant (sans the DO-block ALTER
27
+ * which lives above the table DDL there).
28
+ */
29
+ const SAGA_STATE_RLS_DDL = `ALTER TABLE saga_state ENABLE ROW LEVEL SECURITY;
30
+ GRANT SELECT, INSERT, UPDATE, DELETE ON saga_state TO nodii_services;
31
+ GRANT SELECT, INSERT, UPDATE, DELETE ON saga_state TO authenticated;
32
+ DROP POLICY IF EXISTS saga_state_owner_policy ON saga_state;
33
+ CREATE POLICY saga_state_owner_policy ON saga_state FOR ALL TO nodii_owner USING (true) WITH CHECK (true);
34
+ DROP POLICY IF EXISTS saga_state_auth_select_policy ON saga_state;
35
+ CREATE POLICY saga_state_auth_select_policy ON saga_state FOR SELECT TO authenticated USING (tenant_id IN (SELECT auth.user_tenant_ids(auth.get_user_id())));
36
+ DROP POLICY IF EXISTS saga_state_auth_insert_policy ON saga_state;
37
+ CREATE POLICY saga_state_auth_insert_policy ON saga_state FOR INSERT TO authenticated WITH CHECK (tenant_id IN (SELECT auth.user_tenant_ids(auth.get_user_id())));
38
+ DROP POLICY IF EXISTS saga_state_auth_update_policy ON saga_state;
39
+ CREATE POLICY saga_state_auth_update_policy ON saga_state FOR UPDATE TO authenticated USING (tenant_id IN (SELECT auth.user_tenant_ids(auth.get_user_id()))) WITH CHECK (tenant_id IN (SELECT auth.user_tenant_ids(auth.get_user_id())));
40
+ DROP POLICY IF EXISTS saga_state_auth_delete_policy ON saga_state;
41
+ CREATE POLICY saga_state_auth_delete_policy ON saga_state FOR DELETE TO authenticated USING (tenant_id IN (SELECT auth.user_tenant_ids(auth.get_user_id())));
42
+ DROP POLICY IF EXISTS saga_state_svc_select_policy ON saga_state;
43
+ CREATE POLICY saga_state_svc_select_policy ON saga_state FOR SELECT TO nodii_services USING (tenant_id = auth.get_tenant_id());
44
+ DROP POLICY IF EXISTS saga_state_svc_insert_policy ON saga_state;
45
+ CREATE POLICY saga_state_svc_insert_policy ON saga_state FOR INSERT TO nodii_services WITH CHECK (tenant_id = auth.get_tenant_id());
46
+ DROP POLICY IF EXISTS saga_state_svc_update_policy ON saga_state;
47
+ CREATE POLICY saga_state_svc_update_policy ON saga_state FOR UPDATE TO nodii_services USING (tenant_id = auth.get_tenant_id()) WITH CHECK (tenant_id = auth.get_tenant_id());
48
+ DROP POLICY IF EXISTS saga_state_svc_delete_policy ON saga_state;
49
+ CREATE POLICY saga_state_svc_delete_policy ON saga_state FOR DELETE TO nodii_services USING (tenant_id = auth.get_tenant_id());`;
50
+ /**
51
+ * Return the canonical A1 RLS DDL for `saga_state`. Returns the inlined
52
+ * constant verbatim — no runtime `@nodii/db-rls` call (see `SAGA_STATE_RLS_DDL`).
53
+ */
54
+ export function generateSagaStateRlsDdl() {
55
+ return SAGA_STATE_RLS_DDL;
56
+ }
57
+ /**
58
+ * Canonical A1 RLS DDL for `saga_outbox` (D412 / 08-rls v7 § 1.1 — "every table
59
+ * with a `tenant_id` column gets the 5-policy A1 RLS, no exceptions"). The
60
+ * Pattern-2 outbox is tenant-scoped (every begin/completion row carries the
61
+ * saga's `tenant_id`) and `readOutboxForSaga` filters by `saga_id` ONLY — so RLS
62
+ * is the sole tenant-isolation boundary on this table, exactly as for
63
+ * `saga_state`.
64
+ *
65
+ * Identical structure to `SAGA_STATE_RLS_DDL` (1 owner + 4 authenticated + 4
66
+ * services policies + per-role GRANTs), retargeted to `saga_outbox`; byte-equal
67
+ * to `withRls("saga_outbox", { allow: [...] })` + `generateTableGrants(...)`,
68
+ * asserted in `tests/rls.integration.test.ts`.
69
+ *
70
+ * `saga_outbox.tenant_id` is `UUID` but — unlike `saga_state` — intentionally
71
+ * NULLABLE: the participant-worker writes a NULL tenant for tenant-less sagas
72
+ * (participant-worker.ts) and `createSaga` permits an absent tenant. Under these
73
+ * policies a NULL-tenant row is invisible to every non-owner role
74
+ * (`NULL = auth.get_tenant_id()` and `NULL IN (...)` are both NULL/false), i.e.
75
+ * owner-only — a safe, non-leaking outcome. A1 mandates the 5-policy RLS on
76
+ * every `tenant_id` table; it does NOT mandate NOT NULL (that is a `saga_state`
77
+ * choice), so this is fully A1-conformant.
78
+ */
79
+ const SAGA_OUTBOX_RLS_DDL = `ALTER TABLE saga_outbox ENABLE ROW LEVEL SECURITY;
80
+ GRANT SELECT, INSERT, UPDATE, DELETE ON saga_outbox TO nodii_services;
81
+ GRANT SELECT, INSERT, UPDATE, DELETE ON saga_outbox TO authenticated;
82
+ DROP POLICY IF EXISTS saga_outbox_owner_policy ON saga_outbox;
83
+ CREATE POLICY saga_outbox_owner_policy ON saga_outbox FOR ALL TO nodii_owner USING (true) WITH CHECK (true);
84
+ DROP POLICY IF EXISTS saga_outbox_auth_select_policy ON saga_outbox;
85
+ CREATE POLICY saga_outbox_auth_select_policy ON saga_outbox FOR SELECT TO authenticated USING (tenant_id IN (SELECT auth.user_tenant_ids(auth.get_user_id())));
86
+ DROP POLICY IF EXISTS saga_outbox_auth_insert_policy ON saga_outbox;
87
+ CREATE POLICY saga_outbox_auth_insert_policy ON saga_outbox FOR INSERT TO authenticated WITH CHECK (tenant_id IN (SELECT auth.user_tenant_ids(auth.get_user_id())));
88
+ DROP POLICY IF EXISTS saga_outbox_auth_update_policy ON saga_outbox;
89
+ CREATE POLICY saga_outbox_auth_update_policy ON saga_outbox FOR UPDATE TO authenticated USING (tenant_id IN (SELECT auth.user_tenant_ids(auth.get_user_id()))) WITH CHECK (tenant_id IN (SELECT auth.user_tenant_ids(auth.get_user_id())));
90
+ DROP POLICY IF EXISTS saga_outbox_auth_delete_policy ON saga_outbox;
91
+ CREATE POLICY saga_outbox_auth_delete_policy ON saga_outbox FOR DELETE TO authenticated USING (tenant_id IN (SELECT auth.user_tenant_ids(auth.get_user_id())));
92
+ DROP POLICY IF EXISTS saga_outbox_svc_select_policy ON saga_outbox;
93
+ CREATE POLICY saga_outbox_svc_select_policy ON saga_outbox FOR SELECT TO nodii_services USING (tenant_id = auth.get_tenant_id());
94
+ DROP POLICY IF EXISTS saga_outbox_svc_insert_policy ON saga_outbox;
95
+ CREATE POLICY saga_outbox_svc_insert_policy ON saga_outbox FOR INSERT TO nodii_services WITH CHECK (tenant_id = auth.get_tenant_id());
96
+ DROP POLICY IF EXISTS saga_outbox_svc_update_policy ON saga_outbox;
97
+ CREATE POLICY saga_outbox_svc_update_policy ON saga_outbox FOR UPDATE TO nodii_services USING (tenant_id = auth.get_tenant_id()) WITH CHECK (tenant_id = auth.get_tenant_id());
98
+ DROP POLICY IF EXISTS saga_outbox_svc_delete_policy ON saga_outbox;
99
+ CREATE POLICY saga_outbox_svc_delete_policy ON saga_outbox FOR DELETE TO nodii_services USING (tenant_id = auth.get_tenant_id());`;
100
+ /**
101
+ * Return the canonical A1 RLS DDL for `saga_outbox`. Inlined constant verbatim —
102
+ * no runtime `@nodii/db-rls` call (see `SAGA_OUTBOX_RLS_DDL`).
103
+ */
104
+ export function generateSagaOutboxRlsDdl() {
105
+ return SAGA_OUTBOX_RLS_DDL;
106
+ }
7
107
  /**
8
108
  * Canonical saga_state + saga_outbox migration. Kept inline here (NOT
9
109
  * read from disk at runtime) so the published artifact + the synthetic-
@@ -15,7 +115,7 @@
15
115
  const SAGA_STATE_MIGRATION_SQL = `
16
116
  CREATE TABLE IF NOT EXISTS saga_state (
17
117
  id TEXT PRIMARY KEY,
18
- tenant_id TEXT,
118
+ tenant_id UUID NOT NULL,
19
119
  type TEXT NOT NULL,
20
120
  status TEXT NOT NULL,
21
121
  current_step TEXT,
@@ -34,6 +134,7 @@ CREATE TABLE IF NOT EXISTS saga_state (
34
134
  failure_reason TEXT,
35
135
  failure_step TEXT,
36
136
  compensation_log JSONB NOT NULL DEFAULT '[]'::jsonb,
137
+ undo_stack JSONB NOT NULL DEFAULT '[]'::jsonb,
37
138
  last_admin_action TEXT,
38
139
  last_admin_actor_id TEXT,
39
140
  last_admin_at TIMESTAMPTZ,
@@ -41,6 +142,21 @@ CREATE TABLE IF NOT EXISTS saga_state (
41
142
  cancel_reason TEXT
42
143
  );
43
144
  ALTER TABLE saga_state ADD COLUMN IF NOT EXISTS reaper_grace_ms BIGINT;
145
+ ALTER TABLE saga_state ADD COLUMN IF NOT EXISTS undo_stack JSONB NOT NULL DEFAULT '[]'::jsonb;
146
+ DO $$
147
+ BEGIN
148
+ IF EXISTS (
149
+ SELECT 1 FROM information_schema.columns
150
+ WHERE table_schema = current_schema()
151
+ AND table_name = 'saga_state'
152
+ AND column_name = 'tenant_id'
153
+ AND data_type <> 'uuid'
154
+ ) THEN
155
+ EXECUTE 'ALTER TABLE saga_state ALTER COLUMN tenant_id TYPE uuid USING tenant_id::uuid';
156
+ END IF;
157
+ END
158
+ $$;
159
+ ALTER TABLE saga_state ALTER COLUMN tenant_id SET NOT NULL;
44
160
  CREATE UNIQUE INDEX IF NOT EXISTS saga_state_trigger_trace_id_uniq
45
161
  ON saga_state (trigger_trace_id);
46
162
  CREATE INDEX IF NOT EXISTS saga_state_dead_letter_idx
@@ -57,13 +173,29 @@ CREATE TABLE IF NOT EXISTS saga_outbox (
57
173
  step_name TEXT NOT NULL,
58
174
  event_type TEXT NOT NULL,
59
175
  payload JSONB NOT NULL,
60
- tenant_id TEXT,
176
+ tenant_id UUID,
61
177
  created_at TIMESTAMPTZ NOT NULL DEFAULT now(),
62
178
  delivered_at TIMESTAMPTZ
63
179
  );
64
180
  CREATE INDEX IF NOT EXISTS saga_outbox_saga_idx ON saga_outbox (saga_id, created_at);
65
181
  CREATE INDEX IF NOT EXISTS saga_outbox_undelivered_idx ON saga_outbox (delivered_at)
66
182
  WHERE delivered_at IS NULL;
183
+ DO $$
184
+ BEGIN
185
+ IF EXISTS (
186
+ SELECT 1 FROM information_schema.columns
187
+ WHERE table_schema = current_schema()
188
+ AND table_name = 'saga_outbox'
189
+ AND column_name = 'tenant_id'
190
+ AND data_type <> 'uuid'
191
+ ) THEN
192
+ EXECUTE 'ALTER TABLE saga_outbox ALTER COLUMN tenant_id TYPE uuid USING tenant_id::uuid';
193
+ EXECUTE 'UPDATE saga_outbox o SET tenant_id = s.tenant_id FROM saga_state s WHERE o.saga_id = s.id AND o.tenant_id IS NULL';
194
+ END IF;
195
+ END
196
+ $$;
197
+ ${generateSagaStateRlsDdl()}
198
+ ${generateSagaOutboxRlsDdl()}
67
199
  `.trim();
68
200
  export function getSagaStateMigrationSQL() {
69
201
  return SAGA_STATE_MIGRATION_SQL;
@@ -85,16 +217,35 @@ export async function applySagaMigrations(sql) {
85
217
  await sql.unsafe(stmt);
86
218
  }
87
219
  }
88
- /** Internal — exported only for unit-test coverage on the splitter. */
220
+ /**
221
+ * Internal — exported only for unit-test coverage on the splitter.
222
+ *
223
+ * Dollar-quote-aware: a `$$`-delimited body (e.g. the D412 `DO $$ ... $$;`
224
+ * guarded TEXT→UUID migration) may contain inner lines ending in `;` that
225
+ * must NOT terminate the statement. We track an open `$tag$` ... `$tag$`
226
+ * span and only honor a trailing `;` as a statement boundary when no dollar
227
+ * quote is open. (postgres.js sends each split statement via `.unsafe`.)
228
+ */
89
229
  export function splitStatements(ddl) {
90
230
  const out = [];
91
231
  let buf = "";
232
+ let openTag = null;
92
233
  for (const rawLine of ddl.split("\n")) {
93
234
  const line = rawLine.trim();
94
- if (!line || line.startsWith("--"))
235
+ // Skip comment-only / blank lines, but only when we're not inside a
236
+ // dollar-quoted body (a `--` inside `$$` is body text, not a comment).
237
+ if (openTag === null && (!line || line.startsWith("--")))
95
238
  continue;
96
239
  buf = buf ? `${buf}\n${rawLine}` : rawLine;
97
- if (line.endsWith(";")) {
240
+ // Toggle dollar-quote state across every `$tag$` token on this line.
241
+ for (const m of rawLine.matchAll(/\$[A-Za-z0-9_]*\$/g)) {
242
+ const tag = m[0];
243
+ if (openTag === null)
244
+ openTag = tag;
245
+ else if (openTag === tag)
246
+ openTag = null;
247
+ }
248
+ if (openTag === null && line.endsWith(";")) {
98
249
  const cleaned = buf.trim();
99
250
  if (cleaned)
100
251
  out.push(cleaned);
@@ -1 +1 @@
1
- {"version":3,"file":"index.js","sourceRoot":"","sources":["../../src/migrations/index.ts"],"names":[],"mappings":"AAAA,4EAA4E;AAC5E,EAAE;AACF,0EAA0E;AAC1E,yEAAyE;AACzE,oEAAoE;AACpE,gEAAgE;AAOhE;;;;;;;GAOG;AACH,MAAM,wBAAwB,GAAG;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;CAoDhC,CAAC,IAAI,EAAE,CAAC;AAET,MAAM,UAAU,wBAAwB;IACtC,OAAO,wBAAwB,CAAC;AAClC,CAAC;AAED;;;;;;;;;GASG;AACH,MAAM,CAAC,KAAK,UAAU,mBAAmB,CAAC,GAAc;IACtD,MAAM,GAAG,GAAG,wBAAwB,EAAE,CAAC;IACvC,MAAM,UAAU,GAAG,eAAe,CAAC,GAAG,CAAC,CAAC;IACxC,KAAK,MAAM,IAAI,IAAI,UAAU,EAAE,CAAC;QAC9B,MAAM,GAAG,CAAC,MAAM,CAAC,IAAI,CAAC,CAAC;IACzB,CAAC;AACH,CAAC;AAED,uEAAuE;AACvE,MAAM,UAAU,eAAe,CAAC,GAAW;IACzC,MAAM,GAAG,GAAa,EAAE,CAAC;IACzB,IAAI,GAAG,GAAG,EAAE,CAAC;IACb,KAAK,MAAM,OAAO,IAAI,GAAG,CAAC,KAAK,CAAC,IAAI,CAAC,EAAE,CAAC;QACtC,MAAM,IAAI,GAAG,OAAO,CAAC,IAAI,EAAE,CAAC;QAC5B,IAAI,CAAC,IAAI,IAAI,IAAI,CAAC,UAAU,CAAC,IAAI,CAAC;YAAE,SAAS;QAC7C,GAAG,GAAG,GAAG,CAAC,CAAC,CAAC,GAAG,GAAG,KAAK,OAAO,EAAE,CAAC,CAAC,CAAC,OAAO,CAAC;QAC3C,IAAI,IAAI,CAAC,QAAQ,CAAC,GAAG,CAAC,EAAE,CAAC;YACvB,MAAM,OAAO,GAAG,GAAG,CAAC,IAAI,EAAE,CAAC;YAC3B,IAAI,OAAO;gBAAE,GAAG,CAAC,IAAI,CAAC,OAAO,CAAC,CAAC;YAC/B,GAAG,GAAG,EAAE,CAAC;QACX,CAAC;IACH,CAAC;IACD,IAAI,GAAG,CAAC,IAAI,EAAE;QAAE,GAAG,CAAC,IAAI,CAAC,GAAG,CAAC,IAAI,EAAE,CAAC,CAAC;IACrC,OAAO,GAAG,CAAC;AACb,CAAC"}
1
+ {"version":3,"file":"index.js","sourceRoot":"","sources":["../../src/migrations/index.ts"],"names":[],"mappings":"AAAA,4EAA4E;AAC5E,EAAE;AACF,0EAA0E;AAC1E,yEAAyE;AACzE,oEAAoE;AACpE,gEAAgE;AAOhE;;;;;;;;;;;;;;;;;;;;;GAqBG;AACH,MAAM,kBAAkB,GAAG;;;;;;;;;;;;;;;;;;;;gIAoBqG,CAAC;AAEjI;;;GAGG;AACH,MAAM,UAAU,uBAAuB;IACrC,OAAO,kBAAkB,CAAC;AAC5B,CAAC;AAED;;;;;;;;;;;;;;;;;;;;;GAqBG;AACH,MAAM,mBAAmB,GAAG;;;;;;;;;;;;;;;;;;;;kIAoBsG,CAAC;AAEnI;;;GAGG;AACH,MAAM,UAAU,wBAAwB;IACtC,OAAO,mBAAmB,CAAC;AAC7B,CAAC;AAED;;;;;;;GAOG;AACH,MAAM,wBAAwB,GAAG;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;EAkF/B,uBAAuB,EAAE;EACzB,wBAAwB,EAAE;CAC3B,CAAC,IAAI,EAAE,CAAC;AAET,MAAM,UAAU,wBAAwB;IACtC,OAAO,wBAAwB,CAAC;AAClC,CAAC;AAED;;;;;;;;;GASG;AACH,MAAM,CAAC,KAAK,UAAU,mBAAmB,CAAC,GAAc;IACtD,MAAM,GAAG,GAAG,wBAAwB,EAAE,CAAC;IACvC,MAAM,UAAU,GAAG,eAAe,CAAC,GAAG,CAAC,CAAC;IACxC,KAAK,MAAM,IAAI,IAAI,UAAU,EAAE,CAAC;QAC9B,MAAM,GAAG,CAAC,MAAM,CAAC,IAAI,CAAC,CAAC;IACzB,CAAC;AACH,CAAC;AAED;;;;;;;;GAQG;AACH,MAAM,UAAU,eAAe,CAAC,GAAW;IACzC,MAAM,GAAG,GAAa,EAAE,CAAC;IACzB,IAAI,GAAG,GAAG,EAAE,CAAC;IACb,IAAI,OAAO,GAAkB,IAAI,CAAC;IAClC,KAAK,MAAM,OAAO,IAAI,GAAG,CAAC,KAAK,CAAC,IAAI,CAAC,EAAE,CAAC;QACtC,MAAM,IAAI,GAAG,OAAO,CAAC,IAAI,EAAE,CAAC;QAC5B,oEAAoE;QACpE,uEAAuE;QACvE,IAAI,OAAO,KAAK,IAAI,IAAI,CAAC,CAAC,IAAI,IAAI,IAAI,CAAC,UAAU,CAAC,IAAI,CAAC,CAAC;YAAE,SAAS;QACnE,GAAG,GAAG,GAAG,CAAC,CAAC,CAAC,GAAG,GAAG,KAAK,OAAO,EAAE,CAAC,CAAC,CAAC,OAAO,CAAC;QAC3C,qEAAqE;QACrE,KAAK,MAAM,CAAC,IAAI,OAAO,CAAC,QAAQ,CAAC,oBAAoB,CAAC,EAAE,CAAC;YACvD,MAAM,GAAG,GAAG,CAAC,CAAC,CAAC,CAAC,CAAC;YACjB,IAAI,OAAO,KAAK,IAAI;gBAAE,OAAO,GAAG,GAAG,CAAC;iBAC/B,IAAI,OAAO,KAAK,GAAG;gBAAE,OAAO,GAAG,IAAI,CAAC;QAC3C,CAAC;QACD,IAAI,OAAO,KAAK,IAAI,IAAI,IAAI,CAAC,QAAQ,CAAC,GAAG,CAAC,EAAE,CAAC;YAC3C,MAAM,OAAO,GAAG,GAAG,CAAC,IAAI,EAAE,CAAC;YAC3B,IAAI,OAAO;gBAAE,GAAG,CAAC,IAAI,CAAC,OAAO,CAAC,CAAC;YAC/B,GAAG,GAAG,EAAE,CAAC;QACX,CAAC;IACH,CAAC;IACD,IAAI,GAAG,CAAC,IAAI,EAAE;QAAE,GAAG,CAAC,IAAI,CAAC,GAAG,CAAC,IAAI,EAAE,CAAC,CAAC;IACrC,OAAO,GAAG,CAAC;AACb,CAAC"}
package/dist/saga.d.ts CHANGED
@@ -45,4 +45,44 @@ export declare function stepParallel<O>(steps: {
45
45
  export declare function cancel(sagaId: string, reason: string): Promise<void>;
46
46
  /** Read-only accessor for the active saga handle in scope. */
47
47
  export declare function currentSaga(): SagaHandle | null;
48
+ /**
49
+ * Resolves the undo function for a step on the RECOVERY path. A fresh
50
+ * process has lost the in-memory undo closures, so it must re-bind them
51
+ * from its registered saga handlers. Given the persisted step name +
52
+ * output, return the undo callable, or `null` if the step has no
53
+ * compensation (logged as `skipped_no_undo`).
54
+ */
55
+ export type UndoResolver = (stepName: string, output: unknown) => ((output: unknown) => Promise<void>) | null;
56
+ /** Outcome of {@link recoverUndoStack}. */
57
+ export interface RecoverUndoStackResult {
58
+ /** Number of durable undo entries found for the saga. */
59
+ loaded: number;
60
+ /** Steps whose undo ran successfully. */
61
+ undone: string[];
62
+ /** Steps that had no undo (logged skipped_no_undo). */
63
+ skipped: string[];
64
+ /** Steps whose undo threw (logged undo_failed). */
65
+ failed: string[];
66
+ /** Terminal status the saga settled on after recovery. */
67
+ status: "compensated" | "compensated_with_errors" | "compensation_failed";
68
+ }
69
+ /**
70
+ * § 5.8 RECOVERY — reload the durable undo stack from the state store and
71
+ * run the pending compensations in reverse on a FRESH process.
72
+ *
73
+ * This is the entrypoint that makes undo-stack durability meaningful: after
74
+ * a process restart mid-saga, the in-memory undo map is gone, but the
75
+ * `saga_state.undo_stack` column persisted every completed step's
76
+ * compensation (step name + output + mode). A recovery worker (or the
77
+ * reaper) calls this with an {@link UndoResolver} that re-binds each step's
78
+ * undo fn from the registered saga handler; the function then walks the
79
+ * stack in reverse, runs each undo, appends to `compensation_log`, sets the
80
+ * terminal status, and clears the durable stack.
81
+ *
82
+ * Mirrors the in-process {@link runCompensation} semantics: a strict-mode
83
+ * undo failure halts with `compensation_failed` (leaving the remaining
84
+ * entries durable for a later re-attempt); best-effort failures continue
85
+ * and settle on `compensated_with_errors`.
86
+ */
87
+ export declare function recoverUndoStack(sagaId: string, resolve: UndoResolver): Promise<RecoverUndoStackResult>;
48
88
  //# sourceMappingURL=saga.d.ts.map
@@ -1 +1 @@
1
- {"version":3,"file":"saga.d.ts","sourceRoot":"","sources":["../src/saga.ts"],"names":[],"mappings":"AAoBA,OAAO,EAEL,KAAK,cAAc,EAEnB,KAAK,UAAU,EAEf,KAAK,QAAQ,EAGd,MAAM,SAAS,CAAC;AAoFjB;;;;;;;GAOG;AACH,wBAAsB,UAAU,CAAC,CAAC,EAChC,IAAI,EAAE,cAAc,EACpB,EAAE,EAAE,MAAM,OAAO,CAAC,CAAC,CAAC,GACnB,OAAO,CAAC,CAAC,CAAC,CA8EZ;AAED;;;;;;;GAOG;AACH,wBAAsB,QAAQ,CAAC,CAAC,EAC9B,MAAM,EAAE,MAAM,EACd,EAAE,EAAE,MAAM,OAAO,CAAC,CAAC,CAAC,GACnB,OAAO,CAAC,CAAC,CAAC,CAGZ;AAED;;;;;;;;;;;;GAYG;AACH,wBAAsB,IAAI,CAAC,CAAC,EAAE,IAAI,EAAE,MAAM,EAAE,IAAI,EAAE,QAAQ,CAAC,CAAC,CAAC,GAAG,OAAO,CAAC,CAAC,CAAC,CAgGzE;AAeD;;;;;GAKG;AACH,wBAAsB,YAAY,CAAC,CAAC,EAClC,KAAK,EAAE;IAAE,IAAI,EAAE,MAAM,CAAC;IAAC,IAAI,EAAE,QAAQ,CAAC,CAAC,CAAC,CAAA;CAAE,EAAE,GAC3C,OAAO,CAAC,CAAC,EAAE,CAAC,CAEd;AAuFD,oEAAoE;AACpE,wBAAsB,MAAM,CAAC,MAAM,EAAE,MAAM,EAAE,MAAM,EAAE,MAAM,GAAG,OAAO,CAAC,IAAI,CAAC,CAE1E;AAED,8DAA8D;AAC9D,wBAAgB,WAAW,IAAI,UAAU,GAAG,IAAI,CAE/C"}
1
+ {"version":3,"file":"saga.d.ts","sourceRoot":"","sources":["../src/saga.ts"],"names":[],"mappings":"AAoBA,OAAO,EAEL,KAAK,cAAc,EAEnB,KAAK,UAAU,EAEf,KAAK,QAAQ,EAId,MAAM,SAAS,CAAC;AAwGjB;;;;;;;GAOG;AACH,wBAAsB,UAAU,CAAC,CAAC,EAChC,IAAI,EAAE,cAAc,EACpB,EAAE,EAAE,MAAM,OAAO,CAAC,CAAC,CAAC,GACnB,OAAO,CAAC,CAAC,CAAC,CAuFZ;AAED;;;;;;;GAOG;AACH,wBAAsB,QAAQ,CAAC,CAAC,EAC9B,MAAM,EAAE,MAAM,EACd,EAAE,EAAE,MAAM,OAAO,CAAC,CAAC,CAAC,GACnB,OAAO,CAAC,CAAC,CAAC,CAGZ;AAED;;;;;;;;;;;;GAYG;AACH,wBAAsB,IAAI,CAAC,CAAC,EAAE,IAAI,EAAE,MAAM,EAAE,IAAI,EAAE,QAAQ,CAAC,CAAC,CAAC,GAAG,OAAO,CAAC,CAAC,CAAC,CA6GzE;AAeD;;;;;GAKG;AACH,wBAAsB,YAAY,CAAC,CAAC,EAClC,KAAK,EAAE;IAAE,IAAI,EAAE,MAAM,CAAC;IAAC,IAAI,EAAE,QAAQ,CAAC,CAAC,CAAC,CAAA;CAAE,EAAE,GAC3C,OAAO,CAAC,CAAC,EAAE,CAAC,CAEd;AA4FD,oEAAoE;AACpE,wBAAsB,MAAM,CAAC,MAAM,EAAE,MAAM,EAAE,MAAM,EAAE,MAAM,GAAG,OAAO,CAAC,IAAI,CAAC,CAE1E;AAED,8DAA8D;AAC9D,wBAAgB,WAAW,IAAI,UAAU,GAAG,IAAI,CAE/C;AAED;;;;;;GAMG;AACH,MAAM,MAAM,YAAY,GAAG,CACzB,QAAQ,EAAE,MAAM,EAChB,MAAM,EAAE,OAAO,KACZ,CAAC,CAAC,MAAM,EAAE,OAAO,KAAK,OAAO,CAAC,IAAI,CAAC,CAAC,GAAG,IAAI,CAAC;AAEjD,2CAA2C;AAC3C,MAAM,WAAW,sBAAsB;IACrC,yDAAyD;IACzD,MAAM,EAAE,MAAM,CAAC;IACf,yCAAyC;IACzC,MAAM,EAAE,MAAM,EAAE,CAAC;IACjB,uDAAuD;IACvD,OAAO,EAAE,MAAM,EAAE,CAAC;IAClB,mDAAmD;IACnD,MAAM,EAAE,MAAM,EAAE,CAAC;IACjB,0DAA0D;IAC1D,MAAM,EAAE,aAAa,GAAG,yBAAyB,GAAG,qBAAqB,CAAC;CAC3E;AAED;;;;;;;;;;;;;;;;;GAiBG;AACH,wBAAsB,gBAAgB,CACpC,MAAM,EAAE,MAAM,EACd,OAAO,EAAE,YAAY,GACpB,OAAO,CAAC,sBAAsB,CAAC,CAgFjC"}