@hasna/loops 0.4.27 → 0.4.29

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 (79) hide show
  1. package/CHANGELOG.md +205 -1
  2. package/README.md +232 -49
  3. package/dist/api/index.d.ts +20 -19
  4. package/dist/api/index.js +7770 -1342
  5. package/dist/cli/index.js +2976 -966
  6. package/dist/cli/safe-error-context.d.ts +1 -0
  7. package/dist/daemon/daemon.d.ts +1 -0
  8. package/dist/daemon/index.js +1899 -499
  9. package/dist/generated/storage-kit/index.d.ts +1 -1
  10. package/dist/generated/storage-kit/mode.d.ts +6 -12
  11. package/dist/index.d.ts +3 -3
  12. package/dist/index.js +5319 -1096
  13. package/dist/lib/advancement.d.ts +52 -0
  14. package/dist/lib/agent-adapter.d.ts +20 -2
  15. package/dist/lib/auth/route-policy.d.ts +14 -0
  16. package/dist/lib/auth/tenant-auth.d.ts +38 -0
  17. package/dist/lib/cloud/mode.d.ts +2 -8
  18. package/dist/lib/cloud/storage.d.ts +1 -2
  19. package/dist/lib/cloud/transport.d.ts +4 -18
  20. package/dist/lib/errors.d.ts +43 -1
  21. package/dist/lib/executor.d.ts +9 -0
  22. package/dist/lib/format.d.ts +2 -2
  23. package/dist/lib/goal/runner.d.ts +36 -3
  24. package/dist/lib/health.d.ts +1 -1
  25. package/dist/lib/labels.d.ts +4 -0
  26. package/dist/lib/loop-status.d.ts +4 -0
  27. package/dist/lib/migration.d.ts +70 -17
  28. package/dist/lib/mode.d.ts +2 -5
  29. package/dist/lib/mode.js +28 -37
  30. package/dist/lib/route/fields.d.ts +8 -0
  31. package/dist/lib/route/index.d.ts +2 -2
  32. package/dist/lib/route/throttle.d.ts +7 -0
  33. package/dist/lib/route/types.d.ts +3 -0
  34. package/dist/lib/run-completion.d.ts +18 -0
  35. package/dist/lib/scheduler.d.ts +5 -11
  36. package/dist/lib/storage/contract.d.ts +15 -1
  37. package/dist/lib/storage/index.d.ts +1 -1
  38. package/dist/lib/storage/index.js +4083 -486
  39. package/dist/lib/storage/pg-executor.d.ts +10 -5
  40. package/dist/lib/storage/postgres-loop-storage.d.ts +52 -26
  41. package/dist/lib/storage/postgres-schema.d.ts +8 -0
  42. package/dist/lib/storage/postgres-schema.js +1326 -1
  43. package/dist/lib/storage/postgres.d.ts +3 -1
  44. package/dist/lib/storage/postgres.js +1356 -27
  45. package/dist/lib/storage/provider-credentials.d.ts +84 -0
  46. package/dist/lib/storage/shared-database-transfer.d.ts +136 -0
  47. package/dist/lib/storage/sqlite.d.ts +15 -2
  48. package/dist/lib/storage/sqlite.js +1379 -217
  49. package/dist/lib/storage/tenant-backfill-s3.d.ts +53 -0
  50. package/dist/lib/storage/tenant-backfill.d.ts +40 -0
  51. package/dist/lib/store/index.d.ts +14 -8
  52. package/dist/lib/store.d.ts +129 -7
  53. package/dist/lib/store.js +1352 -218
  54. package/dist/lib/templates.d.ts +11 -0
  55. package/dist/lib/workflow-events.d.ts +6 -0
  56. package/dist/lib/workflow-provenance.d.ts +8 -0
  57. package/dist/lib/workflow-runner.d.ts +52 -4
  58. package/dist/mcp/index.js +2074 -657
  59. package/dist/runner/index.d.ts +20 -2
  60. package/dist/runner/index.js +2146 -183
  61. package/dist/sdk/http.d.ts +364 -4
  62. package/dist/sdk/http.js +379 -1
  63. package/dist/sdk/index.d.ts +7 -2
  64. package/dist/sdk/index.js +2341 -742
  65. package/dist/serve/index.d.ts +14 -0
  66. package/dist/serve/index.js +13269 -1830
  67. package/dist/types.d.ts +75 -3
  68. package/docs/AUTOMATION_RUNTIME_DESIGN.md +32 -32
  69. package/docs/CUTOVER-RUNBOOK.md +158 -31
  70. package/docs/DEPLOYMENT_MODES.md +84 -56
  71. package/docs/RUNTIME_BOUNDARY.md +26 -26
  72. package/docs/SHARED-DATABASE-TRANSFER.md +95 -0
  73. package/docs/SHARED_KIT_EXTRACTION_INVENTORY.md +631 -0
  74. package/docs/TRANSCRIPT_LOOP_PATTERNS.md +3 -3
  75. package/docs/UNIFIED_PRODUCT_CONTRACT.md +365 -0
  76. package/docs/USAGE.md +150 -56
  77. package/docs/workflows/transcript-feedback-to-loops.json +2 -2
  78. package/package.json +8 -4
  79. package/dist/lib/storage/pg-runner-claim.d.ts +0 -40
@@ -8,12 +8,11 @@ export interface PgExecutorOptions {
8
8
  idleTimeoutMillis?: number;
9
9
  }
10
10
  /**
11
- * `PostgresQueryExecutor` backed by a live `pg.Pool` via the vendored kit.
11
+ * `PostgresQueryExecutor` backed by a live `pg.Pool` via the generated kit.
12
12
  *
13
- * Transaction support is intentionally omitted: `PostgresStorage.migrate`
14
- * treats DDL as idempotent (`CREATE ... IF NOT EXISTS` + a checksum ledger), so
15
- * a pooled sequential apply is correct and avoids binding every inner
16
- * `execute` to a single dedicated client.
13
+ * Transactions bind every statement to one dedicated pool client. This is
14
+ * required both for atomic migration+ledger writes and request-scoped RLS
15
+ * settings established with `SET LOCAL`.
17
16
  */
18
17
  export declare class PgPoolExecutor implements PostgresQueryExecutor {
19
18
  private readonly client;
@@ -23,5 +22,11 @@ export declare class PgPoolExecutor implements PostgresQueryExecutor {
23
22
  get queryClient(): PoolQueryClient;
24
23
  query<T extends Record<string, unknown>>(sql: string, params?: readonly unknown[]): Promise<T[]>;
25
24
  execute(sql: string, params?: readonly unknown[]): Promise<void>;
25
+ transaction<T>(fn: (executor: PostgresQueryExecutor) => Promise<T>): Promise<T>;
26
+ withRequestContext<T>(context: {
27
+ tenantId: string;
28
+ principalId: string;
29
+ requestId: string;
30
+ }, fn: (client: PoolQueryClient) => Promise<T>): Promise<T>;
26
31
  close(): Promise<void>;
27
32
  }
@@ -1,23 +1,29 @@
1
- import type { RecoverExpiredRunLeasesResult } from "../store.js";
1
+ import type { RecoverExpiredRunLeasesResult, RecoveredLeaseRunPage } from "../store.js";
2
2
  import { Store } from "../store.js";
3
3
  import type { PoolQueryClient } from "../../generated/storage-kit/query.js";
4
4
  import type { LoopStorageContract, LoopStorageMethodName } from "./contract.js";
5
- /** Thrown by store methods that are not yet ported to the Postgres backend. */
6
- export declare class NotImplementedError extends Error {
7
- readonly code = "not_implemented";
8
- constructor(method: string);
9
- }
10
5
  type M<K extends LoopStorageMethodName> = Store[K] extends (...a: infer A) => infer R ? {
11
6
  args: A;
12
7
  result: R;
13
8
  } : never;
9
+ export interface TenantStorageContext {
10
+ tenantId: string;
11
+ principalId: string;
12
+ requestId: string;
13
+ }
14
14
  export declare class PostgresLoopStorage implements LoopStorageContract {
15
- private readonly client;
16
15
  readonly backend = "postgres";
17
16
  readonly supportsRemoteRunners = true;
18
- constructor(client: PoolQueryClient);
17
+ readonly tenantId: string;
18
+ readonly principalId: string;
19
+ readonly requestId: string;
20
+ private readonly client;
21
+ constructor(client: PoolQueryClient, context: TenantStorageContext, opts?: {
22
+ contextAlreadyBound?: boolean;
23
+ });
19
24
  close(): Promise<void>;
20
25
  private assertDaemonLeaseFence;
26
+ private lockWorkflowRun;
21
27
  private loadLoop;
22
28
  private loadRun;
23
29
  private loadRunBySlot;
@@ -25,18 +31,24 @@ export declare class PostgresLoopStorage implements LoopStorageContract {
25
31
  private setWorkItemsForLoop;
26
32
  private setWorkItemsForWorkflowRun;
27
33
  private cascadeWorkItemsForLoopRun;
34
+ private maybeArchiveGeneratedRouteWorkflow;
28
35
  createLoop(...args: M<"createLoop">["args"]): Promise<M<"createLoop">["result"]>;
29
36
  getLoop(...args: M<"getLoop">["args"]): Promise<M<"getLoop">["result"]>;
30
37
  findLoopByName(...args: M<"findLoopByName">["args"]): Promise<M<"findLoopByName">["result"]>;
31
38
  requireLoop(...args: M<"requireLoop">["args"]): Promise<M<"requireLoop">["result"]>;
39
+ requireUniqueLoop(...args: M<"requireUniqueLoop">["args"]): Promise<M<"requireUniqueLoop">["result"]>;
32
40
  listLoops(...args: M<"listLoops">["args"]): Promise<M<"listLoops">["result"]>;
33
41
  dueLoops(...args: M<"dueLoops">["args"]): Promise<M<"dueLoops">["result"]>;
34
42
  updateLoop(...args: M<"updateLoop">["args"]): Promise<M<"updateLoop">["result"]>;
43
+ advanceLoopIfCurrent(...args: M<"advanceLoopIfCurrent">["args"]): Promise<M<"advanceLoopIfCurrent">["result"]>;
44
+ tripCircuitBreakerIfCurrent(...args: M<"tripCircuitBreakerIfCurrent">["args"]): Promise<M<"tripCircuitBreakerIfCurrent">["result"]>;
35
45
  renameLoop(...args: M<"renameLoop">["args"]): Promise<M<"renameLoop">["result"]>;
36
46
  archiveLoop(...args: M<"archiveLoop">["args"]): Promise<M<"archiveLoop">["result"]>;
37
47
  unarchiveLoop(...args: M<"unarchiveLoop">["args"]): Promise<M<"unarchiveLoop">["result"]>;
38
48
  deleteLoop(...args: M<"deleteLoop">["args"]): Promise<M<"deleteLoop">["result"]>;
39
49
  private requireLoopIn;
50
+ private requireUniqueLoopIn;
51
+ private requireArchiveMutationLoopIn;
40
52
  countLoops(...args: M<"countLoops">["args"]): Promise<M<"countLoops">["result"]>;
41
53
  upsertMigrationWorkflow(...args: M<"upsertMigrationWorkflow">["args"]): Promise<M<"upsertMigrationWorkflow">["result"]>;
42
54
  upsertMigrationLoop(...args: M<"upsertMigrationLoop">["args"]): Promise<M<"upsertMigrationLoop">["result"]>;
@@ -44,6 +56,7 @@ export declare class PostgresLoopStorage implements LoopStorageContract {
44
56
  createSkippedRun(...args: M<"createSkippedRun">["args"]): Promise<M<"createSkippedRun">["result"]>;
45
57
  getRun(...args: M<"getRun">["args"]): Promise<M<"getRun">["result"]>;
46
58
  getRunBySlot(...args: M<"getRunBySlot">["args"]): Promise<M<"getRunBySlot">["result"]>;
59
+ nextRetryableRun(...args: M<"nextRetryableRun">["args"]): Promise<M<"nextRetryableRun">["result"]>;
47
60
  /**
48
61
  * Claim a specific loop slot for a runner.
49
62
  *
@@ -62,6 +75,7 @@ export declare class PostgresLoopStorage implements LoopStorageContract {
62
75
  heartbeatRunLease(...args: M<"heartbeatRunLease">["args"]): Promise<M<"heartbeatRunLease">["result"]>;
63
76
  recordRunProcess(...args: M<"recordRunProcess">["args"]): Promise<M<"recordRunProcess">["result"]>;
64
77
  listRuns(...args: M<"listRuns">["args"]): Promise<M<"listRuns">["result"]>;
78
+ listRecoveredLeaseRunsPage(...args: M<"listRecoveredLeaseRunsPage">["args"]): Promise<RecoveredLeaseRunPage>;
65
79
  writeRunReceipt(...args: M<"writeRunReceipt">["args"]): Promise<M<"writeRunReceipt">["result"]>;
66
80
  getRunReceipt(...args: M<"getRunReceipt">["args"]): Promise<M<"getRunReceipt">["result"]>;
67
81
  listRunReceipts(...args: M<"listRunReceipts">["args"]): Promise<M<"listRunReceipts">["result"]>;
@@ -71,9 +85,7 @@ export declare class PostgresLoopStorage implements LoopStorageContract {
71
85
  * Recover expired run leases. Divergence from sqlite (documented): the remote
72
86
  * backend cannot inspect local process liveness, so an expired lease is always
73
87
  * abandoned (never "deferred because the local process is still alive"). The
74
- * `deferred` array is therefore always empty here. The generated-route
75
- * workflow archival side effect is not ported (route automation is a TIER 2
76
- * path); the core guarantee — no run stays `running` past its lease — holds.
88
+ * `deferred` array is therefore always empty here.
77
89
  */
78
90
  recoverExpiredRunLeasesDetailed(...args: M<"recoverExpiredRunLeasesDetailed">["args"]): Promise<RecoverExpiredRunLeasesResult>;
79
91
  pruneHistory(...args: M<"pruneHistory">["args"]): Promise<M<"pruneHistory">["result"]>;
@@ -101,20 +113,34 @@ export declare class PostgresLoopStorage implements LoopStorageContract {
101
113
  listGoalRuns(...args: M<"listGoalRuns">["args"]): Promise<M<"listGoalRuns">["result"]>;
102
114
  createWorkflow(...args: M<"createWorkflow">["args"]): Promise<M<"createWorkflow">["result"]>;
103
115
  archiveWorkflow(...args: M<"archiveWorkflow">["args"]): Promise<M<"archiveWorkflow">["result"]>;
104
- createWorkflowInvocation(): never;
105
- upsertWorkflowWorkItem(): never;
106
- admitWorkflowWorkItem(): never;
107
- createGoal(): never;
108
- createGoalPlanNodes(): never;
109
- updateGoalStatus(): never;
110
- updateGoalPlanNode(): never;
111
- recordGoalEvent(): never;
112
- createWorkflowRun(): never;
113
- startWorkflowStepRun(): never;
114
- recoverWorkflowRun(): never;
115
- finalizeWorkflowStepRun(): never;
116
- finalizeWorkflowRun(): never;
117
- appendWorkflowEvent(): never;
116
+ createWorkflowInvocation(...args: M<"createWorkflowInvocation">["args"]): Promise<M<"createWorkflowInvocation">["result"]>;
117
+ upsertWorkflowWorkItem(...args: M<"upsertWorkflowWorkItem">["args"]): Promise<M<"upsertWorkflowWorkItem">["result"]>;
118
+ admitWorkflowWorkItem(...args: M<"admitWorkflowWorkItem">["args"]): Promise<M<"admitWorkflowWorkItem">["result"]>;
119
+ createGoal(...args: M<"createGoal">["args"]): Promise<M<"createGoal">["result"]>;
120
+ requireGoal(...args: M<"requireGoal">["args"]): Promise<M<"requireGoal">["result"]>;
121
+ findGoalByContext(...args: M<"findGoalByContext">["args"]): Promise<M<"findGoalByContext">["result"]>;
122
+ private mapGoalPlanNode;
123
+ createGoalPlanNodes(...args: M<"createGoalPlanNodes">["args"]): Promise<M<"createGoalPlanNodes">["result"]>;
124
+ updateGoalStatus(...args: M<"updateGoalStatus">["args"]): Promise<M<"updateGoalStatus">["result"]>;
125
+ updateGoalPlanNode(...args: M<"updateGoalPlanNode">["args"]): Promise<M<"updateGoalPlanNode">["result"]>;
126
+ recordGoalEvent(...args: M<"recordGoalEvent">["args"]): Promise<M<"recordGoalEvent">["result"]>;
127
+ requireWorkflow(...args: M<"requireWorkflow">["args"]): Promise<M<"requireWorkflow">["result"]>;
128
+ createWorkflowRun(...args: M<"createWorkflowRun">["args"]): Promise<M<"createWorkflowRun">["result"]>;
129
+ requireWorkflowRun(...args: M<"requireWorkflowRun">["args"]): Promise<M<"requireWorkflowRun">["result"]>;
130
+ isWorkflowRunTerminal(...args: M<"isWorkflowRunTerminal">["args"]): Promise<M<"isWorkflowRunTerminal">["result"]>;
131
+ startWorkflowStepRun(...args: M<"startWorkflowStepRun">["args"]): Promise<M<"startWorkflowStepRun">["result"]>;
132
+ markWorkflowStepPid(...args: M<"markWorkflowStepPid">["args"]): Promise<M<"markWorkflowStepPid">["result"]>;
133
+ recordWorkflowStepProgress(...args: M<"recordWorkflowStepProgress">["args"]): Promise<M<"recordWorkflowStepProgress">["result"]>;
134
+ recoverWorkflowRun(...args: M<"recoverWorkflowRun">["args"]): Promise<M<"recoverWorkflowRun">["result"]>;
135
+ finalizeWorkflowStepRun(...args: M<"finalizeWorkflowStepRun">["args"]): Promise<M<"finalizeWorkflowStepRun">["result"]>;
136
+ skipWorkflowStepRun(...args: M<"skipWorkflowStepRun">["args"]): Promise<M<"skipWorkflowStepRun">["result"]>;
137
+ private setWorkflowWorkItemsForWorkflowRun;
138
+ private demoteNonProductiveWorkItems;
139
+ finalizeWorkflowRun(...args: M<"finalizeWorkflowRun">["args"]): Promise<M<"finalizeWorkflowRun">["result"]>;
140
+ private appendWorkflowEventWithClient;
141
+ appendWorkflowEvent(...args: M<"appendWorkflowEvent">["args"]): Promise<M<"appendWorkflowEvent">["result"]>;
118
142
  }
119
- export declare function createPostgresLoopStorage(client: PoolQueryClient): PostgresLoopStorage;
143
+ export declare function createPostgresLoopStorage(client: PoolQueryClient, context: TenantStorageContext, opts?: {
144
+ contextAlreadyBound?: boolean;
145
+ }): PostgresLoopStorage;
120
146
  export {};
@@ -1,4 +1,12 @@
1
1
  import type { StorageMigration } from "./contract.js";
2
2
  export declare const POSTGRES_MIGRATION_LEDGER_TABLE = "open_loops_schema_migrations";
3
+ export declare const POSTGRES_MIGRATION_ADVISORY_LOCK_SQL = "SELECT pg_advisory_xact_lock(1330466384, 1280262987)";
3
4
  export declare function checksumStorageSql(sql: string): string;
5
+ export declare const POSTGRES_TENANT_BOOTSTRAP_ROLES_SQL: string;
6
+ export declare const POSTGRES_TENANT_CLUSTER_ROLE_EXCLUSIVITY_SQL: string;
7
+ export declare const POSTGRES_TENANT_BOOTSTRAP_MEMBERSHIPS_SQL: string;
8
+ export declare const POSTGRES_TENANT_PRIVILEGED_MEMBERSHIPS_SQL: string;
9
+ export declare const POSTGRES_TENANT_SERVICE_ROLE_MEMBERSHIPS_SQL: string;
10
+ export declare const POSTGRES_TENANT_UNSAFE_SERVICE_MEMBERSHIPS_SQL: string;
11
+ export declare const POSTGRES_TENANT_SERVICE_MEMBER_CLEANUP_SQL: string;
4
12
  export declare const POSTGRES_STORAGE_MIGRATIONS: readonly StorageMigration[];