@sonamu-kit/tasks 0.0.1

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (280) hide show
  1. package/.swcrc +17 -0
  2. package/README.md +7 -0
  3. package/dist/backend.d.ts +107 -0
  4. package/dist/backend.d.ts.map +1 -0
  5. package/dist/backend.js +3 -0
  6. package/dist/backend.js.map +1 -0
  7. package/dist/chaos.test.d.ts +2 -0
  8. package/dist/chaos.test.d.ts.map +1 -0
  9. package/dist/chaos.test.js +92 -0
  10. package/dist/chaos.test.js.map +1 -0
  11. package/dist/client.d.ts +178 -0
  12. package/dist/client.d.ts.map +1 -0
  13. package/dist/client.js +223 -0
  14. package/dist/client.js.map +1 -0
  15. package/dist/client.test.d.ts +2 -0
  16. package/dist/client.test.d.ts.map +1 -0
  17. package/dist/client.test.js +339 -0
  18. package/dist/client.test.js.map +1 -0
  19. package/dist/config.d.ts +22 -0
  20. package/dist/config.d.ts.map +1 -0
  21. package/dist/config.js +23 -0
  22. package/dist/config.js.map +1 -0
  23. package/dist/config.test.d.ts +2 -0
  24. package/dist/config.test.d.ts.map +1 -0
  25. package/dist/config.test.js +24 -0
  26. package/dist/config.test.js.map +1 -0
  27. package/dist/core/duration.d.ts +22 -0
  28. package/dist/core/duration.d.ts.map +1 -0
  29. package/dist/core/duration.js +64 -0
  30. package/dist/core/duration.js.map +1 -0
  31. package/dist/core/duration.test.d.ts +2 -0
  32. package/dist/core/duration.test.d.ts.map +1 -0
  33. package/dist/core/duration.test.js +265 -0
  34. package/dist/core/duration.test.js.map +1 -0
  35. package/dist/core/error.d.ts +15 -0
  36. package/dist/core/error.d.ts.map +1 -0
  37. package/dist/core/error.js +25 -0
  38. package/dist/core/error.js.map +1 -0
  39. package/dist/core/error.test.d.ts +2 -0
  40. package/dist/core/error.test.d.ts.map +1 -0
  41. package/dist/core/error.test.js +63 -0
  42. package/dist/core/error.test.js.map +1 -0
  43. package/dist/core/json.d.ts +5 -0
  44. package/dist/core/json.d.ts.map +1 -0
  45. package/dist/core/json.js +3 -0
  46. package/dist/core/json.js.map +1 -0
  47. package/dist/core/result.d.ts +22 -0
  48. package/dist/core/result.d.ts.map +1 -0
  49. package/dist/core/result.js +22 -0
  50. package/dist/core/result.js.map +1 -0
  51. package/dist/core/result.test.d.ts +2 -0
  52. package/dist/core/result.test.d.ts.map +1 -0
  53. package/dist/core/result.test.js +19 -0
  54. package/dist/core/result.test.js.map +1 -0
  55. package/dist/core/retry.d.ts +21 -0
  56. package/dist/core/retry.d.ts.map +1 -0
  57. package/dist/core/retry.js +25 -0
  58. package/dist/core/retry.js.map +1 -0
  59. package/dist/core/retry.test.d.ts +2 -0
  60. package/dist/core/retry.test.d.ts.map +1 -0
  61. package/dist/core/retry.test.js +37 -0
  62. package/dist/core/retry.test.js.map +1 -0
  63. package/dist/core/schema.d.ts +57 -0
  64. package/dist/core/schema.d.ts.map +1 -0
  65. package/dist/core/schema.js +4 -0
  66. package/dist/core/schema.js.map +1 -0
  67. package/dist/core/step.d.ts +96 -0
  68. package/dist/core/step.d.ts.map +1 -0
  69. package/dist/core/step.js +78 -0
  70. package/dist/core/step.js.map +1 -0
  71. package/dist/core/step.test.d.ts +2 -0
  72. package/dist/core/step.test.d.ts.map +1 -0
  73. package/dist/core/step.test.js +356 -0
  74. package/dist/core/step.test.js.map +1 -0
  75. package/dist/core/workflow.d.ts +78 -0
  76. package/dist/core/workflow.d.ts.map +1 -0
  77. package/dist/core/workflow.js +46 -0
  78. package/dist/core/workflow.js.map +1 -0
  79. package/dist/core/workflow.test.d.ts +2 -0
  80. package/dist/core/workflow.test.d.ts.map +1 -0
  81. package/dist/core/workflow.test.js +172 -0
  82. package/dist/core/workflow.test.js.map +1 -0
  83. package/dist/database/backend.d.ts +60 -0
  84. package/dist/database/backend.d.ts.map +1 -0
  85. package/dist/database/backend.js +387 -0
  86. package/dist/database/backend.js.map +1 -0
  87. package/dist/database/backend.test.d.ts +2 -0
  88. package/dist/database/backend.test.d.ts.map +1 -0
  89. package/dist/database/backend.test.js +17 -0
  90. package/dist/database/backend.test.js.map +1 -0
  91. package/dist/database/backend.testsuite.d.ts +20 -0
  92. package/dist/database/backend.testsuite.d.ts.map +1 -0
  93. package/dist/database/backend.testsuite.js +1174 -0
  94. package/dist/database/backend.testsuite.js.map +1 -0
  95. package/dist/database/base.d.ts +12 -0
  96. package/dist/database/base.d.ts.map +1 -0
  97. package/dist/database/base.js +19 -0
  98. package/dist/database/base.js.map +1 -0
  99. package/dist/database/migrations/20251212000000_0_init.js +9 -0
  100. package/dist/database/migrations/20251212000000_0_init.js.map +1 -0
  101. package/dist/database/migrations/20251212000000_1_tables.js +88 -0
  102. package/dist/database/migrations/20251212000000_1_tables.js.map +1 -0
  103. package/dist/database/migrations/20251212000000_2_fk.js +48 -0
  104. package/dist/database/migrations/20251212000000_2_fk.js.map +1 -0
  105. package/dist/database/migrations/20251212000000_3_indexes.js +107 -0
  106. package/dist/database/migrations/20251212000000_3_indexes.js.map +1 -0
  107. package/dist/database/pubsub.d.ts +17 -0
  108. package/dist/database/pubsub.d.ts.map +1 -0
  109. package/dist/database/pubsub.js +70 -0
  110. package/dist/database/pubsub.js.map +1 -0
  111. package/dist/database/pubsub.test.d.ts +2 -0
  112. package/dist/database/pubsub.test.d.ts.map +1 -0
  113. package/dist/database/pubsub.test.js +86 -0
  114. package/dist/database/pubsub.test.js.map +1 -0
  115. package/dist/errors.d.ts +8 -0
  116. package/dist/errors.d.ts.map +1 -0
  117. package/dist/errors.js +21 -0
  118. package/dist/errors.js.map +1 -0
  119. package/dist/execution.d.ts +82 -0
  120. package/dist/execution.d.ts.map +1 -0
  121. package/dist/execution.js +182 -0
  122. package/dist/execution.js.map +1 -0
  123. package/dist/execution.test.d.ts +2 -0
  124. package/dist/execution.test.d.ts.map +1 -0
  125. package/dist/execution.test.js +556 -0
  126. package/dist/execution.test.js.map +1 -0
  127. package/dist/index.d.ts +8 -0
  128. package/dist/index.d.ts.map +1 -0
  129. package/dist/index.js +6 -0
  130. package/dist/index.js.map +1 -0
  131. package/dist/internal.d.ts +12 -0
  132. package/dist/internal.d.ts.map +1 -0
  133. package/dist/internal.js +5 -0
  134. package/dist/internal.js.map +1 -0
  135. package/dist/practices/01-remote-workflow.d.ts +2 -0
  136. package/dist/practices/01-remote-workflow.d.ts.map +1 -0
  137. package/dist/practices/01-remote-workflow.js +69 -0
  138. package/dist/practices/01-remote-workflow.js.map +1 -0
  139. package/dist/practices/01-remote.d.ts +2 -0
  140. package/dist/practices/01-remote.d.ts.map +1 -0
  141. package/dist/practices/01-remote.js +87 -0
  142. package/dist/practices/01-remote.js.map +1 -0
  143. package/dist/practices/02-local.d.ts +2 -0
  144. package/dist/practices/02-local.d.ts.map +1 -0
  145. package/dist/practices/02-local.js +84 -0
  146. package/dist/practices/02-local.js.map +1 -0
  147. package/dist/practices/03-local-retry.d.ts +2 -0
  148. package/dist/practices/03-local-retry.d.ts.map +1 -0
  149. package/dist/practices/03-local-retry.js +85 -0
  150. package/dist/practices/03-local-retry.js.map +1 -0
  151. package/dist/practices/04-scheduler-dispose.d.ts +2 -0
  152. package/dist/practices/04-scheduler-dispose.d.ts.map +1 -0
  153. package/dist/practices/04-scheduler-dispose.js +65 -0
  154. package/dist/practices/04-scheduler-dispose.js.map +1 -0
  155. package/dist/practices/05-router.d.ts +2 -0
  156. package/dist/practices/05-router.d.ts.map +1 -0
  157. package/dist/practices/05-router.js +80 -0
  158. package/dist/practices/05-router.js.map +1 -0
  159. package/dist/registry.d.ts +33 -0
  160. package/dist/registry.d.ts.map +1 -0
  161. package/dist/registry.js +54 -0
  162. package/dist/registry.js.map +1 -0
  163. package/dist/registry.test.d.ts +2 -0
  164. package/dist/registry.test.d.ts.map +1 -0
  165. package/dist/registry.test.js +95 -0
  166. package/dist/registry.test.js.map +1 -0
  167. package/dist/scheduler.d.ts +22 -0
  168. package/dist/scheduler.d.ts.map +1 -0
  169. package/dist/scheduler.js +117 -0
  170. package/dist/scheduler.js.map +1 -0
  171. package/dist/tasks/index.d.ts +4 -0
  172. package/dist/tasks/index.d.ts.map +1 -0
  173. package/dist/tasks/index.js +5 -0
  174. package/dist/tasks/index.js.map +1 -0
  175. package/dist/tasks/local-task.d.ts +6 -0
  176. package/dist/tasks/local-task.d.ts.map +1 -0
  177. package/dist/tasks/local-task.js +95 -0
  178. package/dist/tasks/local-task.js.map +1 -0
  179. package/dist/tasks/remote-task.d.ts +11 -0
  180. package/dist/tasks/remote-task.d.ts.map +1 -0
  181. package/dist/tasks/remote-task.js +213 -0
  182. package/dist/tasks/remote-task.js.map +1 -0
  183. package/dist/tasks/shared.d.ts +8 -0
  184. package/dist/tasks/shared.d.ts.map +1 -0
  185. package/dist/tasks/shared.js +41 -0
  186. package/dist/tasks/shared.js.map +1 -0
  187. package/dist/testing/connection.d.ts +7 -0
  188. package/dist/testing/connection.d.ts.map +1 -0
  189. package/dist/testing/connection.js +38 -0
  190. package/dist/testing/connection.js.map +1 -0
  191. package/dist/types/config.d.ts +44 -0
  192. package/dist/types/config.d.ts.map +1 -0
  193. package/dist/types/config.js +3 -0
  194. package/dist/types/config.js.map +1 -0
  195. package/dist/types/context.d.ts +18 -0
  196. package/dist/types/context.d.ts.map +1 -0
  197. package/dist/types/context.js +4 -0
  198. package/dist/types/context.js.map +1 -0
  199. package/dist/types/events.d.ts +43 -0
  200. package/dist/types/events.d.ts.map +1 -0
  201. package/dist/types/events.js +3 -0
  202. package/dist/types/events.js.map +1 -0
  203. package/dist/types/index.d.ts +6 -0
  204. package/dist/types/index.d.ts.map +1 -0
  205. package/dist/types/index.js +3 -0
  206. package/dist/types/index.js.map +1 -0
  207. package/dist/types/task-items.d.ts +12 -0
  208. package/dist/types/task-items.d.ts.map +1 -0
  209. package/dist/types/task-items.js +3 -0
  210. package/dist/types/task-items.js.map +1 -0
  211. package/dist/types/utils.d.ts +4 -0
  212. package/dist/types/utils.d.ts.map +1 -0
  213. package/dist/types/utils.js +8 -0
  214. package/dist/types/utils.js.map +1 -0
  215. package/dist/worker.d.ts +61 -0
  216. package/dist/worker.d.ts.map +1 -0
  217. package/dist/worker.js +206 -0
  218. package/dist/worker.js.map +1 -0
  219. package/dist/worker.test.d.ts +2 -0
  220. package/dist/worker.test.d.ts.map +1 -0
  221. package/dist/worker.test.js +1163 -0
  222. package/dist/worker.test.js.map +1 -0
  223. package/dist/workflow.d.ts +44 -0
  224. package/dist/workflow.d.ts.map +1 -0
  225. package/dist/workflow.js +21 -0
  226. package/dist/workflow.js.map +1 -0
  227. package/dist/workflow.test.d.ts +2 -0
  228. package/dist/workflow.test.d.ts.map +1 -0
  229. package/dist/workflow.test.js +73 -0
  230. package/dist/workflow.test.js.map +1 -0
  231. package/nodemon.json +6 -0
  232. package/package.json +63 -0
  233. package/scripts/migrate.ts +11 -0
  234. package/src/backend.ts +133 -0
  235. package/src/chaos.test.ts +108 -0
  236. package/src/client.test.ts +297 -0
  237. package/src/client.ts +331 -0
  238. package/src/config.test.ts +23 -0
  239. package/src/config.ts +35 -0
  240. package/src/core/duration.test.ts +326 -0
  241. package/src/core/duration.ts +86 -0
  242. package/src/core/error.test.ts +77 -0
  243. package/src/core/error.ts +30 -0
  244. package/src/core/json.ts +2 -0
  245. package/src/core/result.test.ts +13 -0
  246. package/src/core/result.ts +29 -0
  247. package/src/core/retry.test.ts +41 -0
  248. package/src/core/retry.ts +29 -0
  249. package/src/core/schema.ts +74 -0
  250. package/src/core/step.test.ts +362 -0
  251. package/src/core/step.ts +152 -0
  252. package/src/core/workflow.test.ts +184 -0
  253. package/src/core/workflow.ts +127 -0
  254. package/src/database/backend.test.ts +16 -0
  255. package/src/database/backend.testsuite.ts +1376 -0
  256. package/src/database/backend.ts +655 -0
  257. package/src/database/base.ts +23 -0
  258. package/src/database/migrations/20251212000000_0_init.ts +10 -0
  259. package/src/database/migrations/20251212000000_1_tables.ts +54 -0
  260. package/src/database/migrations/20251212000000_2_fk.ts +46 -0
  261. package/src/database/migrations/20251212000000_3_indexes.ts +82 -0
  262. package/src/database/pubsub.test.ts +92 -0
  263. package/src/database/pubsub.ts +92 -0
  264. package/src/execution.test.ts +508 -0
  265. package/src/execution.ts +291 -0
  266. package/src/index.ts +7 -0
  267. package/src/internal.ts +11 -0
  268. package/src/practices/01-remote-workflow.ts +61 -0
  269. package/src/registry.test.ts +122 -0
  270. package/src/registry.ts +65 -0
  271. package/src/testing/connection.ts +44 -0
  272. package/src/worker.test.ts +1138 -0
  273. package/src/worker.ts +281 -0
  274. package/src/workflow.test.ts +68 -0
  275. package/src/workflow.ts +84 -0
  276. package/table_ddl.sql +60 -0
  277. package/templates/openworkflow.config.ts +22 -0
  278. package/tsconfig.json +40 -0
  279. package/tsconfig.test.json +4 -0
  280. package/vite.config.ts +13 -0
@@ -0,0 +1 @@
1
+ {"version":3,"sources":["../../src/database/backend.ts"],"sourcesContent":["import { camelize } from \"inflection\";\nimport knex, { type Knex } from \"knex\";\nimport {\n type Backend,\n type CancelWorkflowRunParams,\n type ClaimWorkflowRunParams,\n type CompleteStepAttemptParams,\n type CompleteWorkflowRunParams,\n type CreateStepAttemptParams,\n type CreateWorkflowRunParams,\n DEFAULT_NAMESPACE_ID,\n type ExtendWorkflowRunLeaseParams,\n type FailStepAttemptParams,\n type FailWorkflowRunParams,\n type GetStepAttemptParams,\n type GetWorkflowRunParams,\n type ListStepAttemptsParams,\n type ListWorkflowRunsParams,\n type PaginatedResponse,\n type SleepWorkflowRunParams,\n} from \"../backend\";\nimport { DEFAULT_RETRY_POLICY } from \"../core/retry\";\nimport type { StepAttempt } from \"../core/step\";\nimport type { WorkflowRun } from \"../core/workflow\";\nimport { DEFAULT_SCHEMA, migrate } from \"./base\";\nimport { type OnSubscribed, PostgresPubSub } from \"./pubsub\";\n\nexport const DEFAULT_LISTEN_CHANNEL = \"new_tasks\" as const;\nconst DEFAULT_PAGINATION_PAGE_SIZE = 100 as const;\n\ninterface BackendPostgresOptions {\n namespaceId?: string;\n runMigrations?: boolean;\n\n // default: true\n usePubSub?: boolean;\n}\n\n/**\n * Manages a connection to a Postgres database for workflow operations.\n */\nexport class BackendPostgres implements Backend {\n private knex: Knex;\n private namespaceId: string;\n private usePubSub: boolean;\n private pubsub: PostgresPubSub | null = null;\n\n private constructor(knex: Knex, namespaceId: string, usePubSub: boolean) {\n this.knex = knex;\n this.namespaceId = namespaceId;\n this.usePubSub = usePubSub;\n }\n\n async subscribe(callback: OnSubscribed) {\n if (!this.usePubSub) {\n return;\n }\n\n if (!this.pubsub) {\n this.pubsub = await PostgresPubSub.create(this.knex);\n }\n\n this.pubsub.listenEvent(DEFAULT_LISTEN_CHANNEL, callback);\n }\n\n async publish(payload?: string): Promise<void> {\n if (!this.usePubSub) {\n return;\n }\n\n await this.knex.raw(\n payload\n ? `NOTIFY ${DEFAULT_LISTEN_CHANNEL}, '${payload}'`\n : `NOTIFY ${DEFAULT_LISTEN_CHANNEL}`,\n );\n }\n\n /**\n * Create and initialize a new BackendPostgres instance. This will\n * automatically run migrations on startup unless `runMigrations` is set to\n * false.\n */\n static async connect(\n dbConf: Knex.Config,\n options?: BackendPostgresOptions,\n ): Promise<BackendPostgres> {\n const postProcessResponse: Knex.Config[\"postProcessResponse\"] = (result, _queryContext) => {\n if (result === null || result === undefined) {\n return result;\n }\n\n if (dbConf?.postProcessResponse) {\n result = dbConf.postProcessResponse(result, _queryContext);\n }\n\n const camelizeRow = (row: Record<string, unknown>) =>\n Object.fromEntries(Object.entries(row).map(([key, value]) => [camelize(key, true), value]));\n\n if (Array.isArray(result)) {\n return result.map(camelizeRow);\n }\n\n return camelizeRow(result);\n };\n\n const { namespaceId, runMigrations, usePubSub } = {\n namespaceId: DEFAULT_NAMESPACE_ID,\n runMigrations: true,\n usePubSub: true,\n ...options,\n };\n\n const knexInstance = knex({ ...dbConf, postProcessResponse });\n if (runMigrations) {\n await migrate(knexInstance, DEFAULT_SCHEMA);\n }\n\n return new BackendPostgres(knexInstance, namespaceId, usePubSub);\n }\n\n async stop(): Promise<void> {\n await this.pubsub?.destroy();\n this.pubsub = null;\n await this.knex.destroy();\n }\n\n async createWorkflowRun(params: CreateWorkflowRunParams): Promise<WorkflowRun> {\n const qb = this.knex\n .withSchema(DEFAULT_SCHEMA)\n .table(\"workflow_runs\")\n .insert({\n namespace_id: this.namespaceId,\n id: crypto.randomUUID(),\n workflow_name: params.workflowName,\n version: params.version,\n status: \"pending\",\n idempotency_key: params.idempotencyKey,\n config: params.config,\n context: params.context,\n input: params.input,\n attempts: 0,\n available_at: params.availableAt ?? this.knex.fn.now(),\n deadline_at: params.deadlineAt,\n created_at: this.knex.fn.now(),\n updated_at: this.knex.fn.now(),\n })\n .returning(\"*\");\n\n const workflowRun = await qb;\n if (!workflowRun[0]) {\n throw new Error(\"Failed to create workflow run\");\n }\n\n return workflowRun[0];\n }\n\n async getWorkflowRun(params: GetWorkflowRunParams): Promise<WorkflowRun | null> {\n const workflowRun = await this.knex\n .withSchema(DEFAULT_SCHEMA)\n .table(\"workflow_runs\")\n .where(\"namespace_id\", this.namespaceId)\n .where(\"id\", params.workflowRunId)\n .select(\n \"namespace_id\",\n \"id\",\n \"workflow_name\",\n \"version\",\n \"status\",\n \"idempotency_key\",\n \"config\",\n \"context\",\n \"input\",\n \"output\",\n \"error\",\n \"attempts\",\n \"parent_step_attempt_namespace_id\",\n \"parent_step_attempt_id\",\n \"worker_id\",\n \"available_at\",\n \"deadline_at\",\n \"started_at\",\n \"finished_at\",\n \"created_at\",\n \"updated_at\",\n )\n .first();\n\n return workflowRun ?? null;\n }\n\n async listWorkflowRuns(params: ListWorkflowRunsParams): Promise<PaginatedResponse<WorkflowRun>> {\n const limit = params.limit ?? DEFAULT_PAGINATION_PAGE_SIZE;\n const { after, before } = params;\n\n let cursor: Cursor | null = null;\n if (after) {\n cursor = decodeCursor(after);\n } else if (before) {\n cursor = decodeCursor(before);\n }\n\n const qb = this.buildListWorkflowRunsWhere(params, cursor);\n const rows = await qb\n .orderBy(\"created_at\", before ? \"desc\" : \"asc\")\n .orderBy(\"id\", before ? \"desc\" : \"asc\")\n .limit(limit + 1);\n\n return this.processPaginationResults(\n rows,\n limit,\n typeof after === \"string\",\n typeof before === \"string\",\n );\n }\n\n private buildListWorkflowRunsWhere(params: ListWorkflowRunsParams, cursor: Cursor | null) {\n const { after } = params;\n const qb = this.knex\n .withSchema(DEFAULT_SCHEMA)\n .table(\"workflow_runs\")\n .where(\"namespace_id\", this.namespaceId);\n\n if (cursor) {\n const operator = after ? \">\" : \"<\";\n return qb.whereRaw(`(\"created_at\", \"id\") ${operator} (?, ?)`, [\n cursor.createdAt.toISOString(),\n cursor.id,\n ]);\n }\n\n return qb;\n }\n\n async claimWorkflowRun(params: ClaimWorkflowRunParams): Promise<WorkflowRun | null> {\n const claimed = await this.knex\n .with(\"expired\", (qb) =>\n qb\n .withSchema(DEFAULT_SCHEMA)\n .table(\"workflow_runs\")\n .update({\n status: \"failed\",\n error: JSON.stringify({ message: \"Workflow run deadline exceeded\" }),\n worker_id: null,\n available_at: null,\n finished_at: this.knex.raw(\"NOW()\"),\n updated_at: this.knex.raw(\"NOW()\"),\n })\n .where(\"namespace_id\", this.namespaceId)\n .whereIn(\"status\", [\"pending\", \"running\", \"sleeping\"])\n .whereNotNull(\"deadline_at\")\n .where(\"deadline_at\", \"<=\", this.knex.raw(\"NOW()\"))\n .returning(\"id\"),\n )\n .with(\"candidate\", (qb) =>\n qb\n .withSchema(DEFAULT_SCHEMA)\n .select(\"id\")\n .from(\"workflow_runs\")\n .where(\"namespace_id\", this.namespaceId)\n .whereIn(\"status\", [\"pending\", \"running\", \"sleeping\"])\n .where(\"available_at\", \"<=\", this.knex.raw(\"NOW()\"))\n .where((qb2) => {\n qb2.whereNull(\"deadline_at\").orWhere(\"deadline_at\", \">\", this.knex.raw(\"NOW()\"));\n })\n .orderByRaw(\"CASE WHEN status = 'pending' THEN 0 ELSE 1 END\")\n .orderBy(\"available_at\", \"asc\")\n .orderBy(\"created_at\", \"asc\")\n .limit(1)\n .forUpdate()\n .skipLocked(),\n )\n .withSchema(DEFAULT_SCHEMA)\n .table(\"workflow_runs as wr\")\n .where(\"wr.namespace_id\", this.namespaceId)\n .where(\"wr.id\", this.knex.ref(\"candidate.id\"))\n .update({\n status: \"running\",\n attempts: this.knex.raw(\"wr.attempts + 1\"),\n worker_id: params.workerId,\n available_at: this.knex.raw(`NOW() + ${params.leaseDurationMs} * INTERVAL '1 millisecond'`),\n started_at: this.knex.raw(\"COALESCE(wr.started_at, NOW())\"),\n updated_at: this.knex.raw(\"NOW()\"),\n })\n .updateFrom(\"candidate\")\n .returning(\"wr.*\");\n\n return claimed[0] ?? null;\n }\n\n async extendWorkflowRunLease(params: ExtendWorkflowRunLeaseParams): Promise<WorkflowRun> {\n const [updated] = await this.knex\n .withSchema(DEFAULT_SCHEMA)\n .table(\"workflow_runs\")\n .where(\"namespace_id\", this.namespaceId)\n .where(\"id\", params.workflowRunId)\n .where(\"status\", \"running\")\n .where(\"worker_id\", params.workerId)\n .update({\n available_at: this.knex.raw(`NOW() + ${params.leaseDurationMs} * INTERVAL '1 millisecond'`),\n updated_at: this.knex.fn.now(),\n })\n .returning(\"*\");\n\n if (!updated) {\n throw new Error(\"Failed to extend lease for workflow run\");\n }\n\n return updated;\n }\n\n async sleepWorkflowRun(params: SleepWorkflowRunParams): Promise<WorkflowRun> {\n // 'succeeded' status is deprecated\n const [updated] = await this.knex\n .withSchema(DEFAULT_SCHEMA)\n .table(\"workflow_runs\")\n .where(\"namespace_id\", this.namespaceId)\n .where(\"id\", params.workflowRunId)\n .whereNotIn(\"status\", [\"succeeded\", \"completed\", \"failed\", \"canceled\"])\n .where(\"worker_id\", params.workerId)\n .update({\n status: \"sleeping\",\n available_at: params.availableAt,\n worker_id: null,\n updated_at: this.knex.fn.now(),\n })\n .returning(\"*\");\n\n if (!updated) {\n throw new Error(\"Failed to sleep workflow run\");\n }\n\n return updated;\n }\n\n async completeWorkflowRun(params: CompleteWorkflowRunParams): Promise<WorkflowRun> {\n const [updated] = await this.knex\n .withSchema(DEFAULT_SCHEMA)\n .table(\"workflow_runs\")\n .where(\"namespace_id\", this.namespaceId)\n .where(\"id\", params.workflowRunId)\n .where(\"status\", \"running\")\n .where(\"worker_id\", params.workerId)\n .update({\n status: \"completed\",\n output: JSON.stringify(params.output),\n error: null,\n worker_id: params.workerId,\n available_at: null,\n finished_at: this.knex.fn.now(),\n updated_at: this.knex.fn.now(),\n })\n .returning(\"*\");\n\n if (!updated) {\n throw new Error(\"Failed to complete workflow run\");\n }\n\n return updated;\n }\n\n async failWorkflowRun(params: FailWorkflowRunParams): Promise<WorkflowRun> {\n const { workflowRunId, error } = params;\n const { initialIntervalMs, backoffCoefficient, maximumIntervalMs } = DEFAULT_RETRY_POLICY;\n\n // this beefy query updates a workflow's status, available_at, and\n // finished_at based on the workflow's deadline and retry policy\n //\n // if the next retry would exceed the deadline, the run is marked as\n // 'failed' and finalized, otherwise, the run is rescheduled with an updated\n // 'available_at' timestamp for the next retry\n const retryIntervalExpr = `LEAST(${initialIntervalMs} * POWER(${backoffCoefficient}, \"attempts\" - 1), ${maximumIntervalMs}) * INTERVAL '1 millisecond'`;\n const deadlineExceededCondition = `\"deadline_at\" IS NOT NULL AND NOW() + (${retryIntervalExpr}) >= \"deadline_at\"`;\n\n const [updated] = await this.knex\n .withSchema(DEFAULT_SCHEMA)\n .table(\"workflow_runs\")\n .where(\"namespace_id\", this.namespaceId)\n .where(\"id\", workflowRunId)\n .where(\"status\", \"running\")\n .where(\"worker_id\", params.workerId)\n .update({\n status: this.knex.raw(\n `CASE WHEN ${deadlineExceededCondition} THEN 'failed' ELSE 'pending' END`,\n ),\n available_at: this.knex.raw(\n `CASE WHEN ${deadlineExceededCondition} THEN NULL ELSE NOW() + (${retryIntervalExpr}) END`,\n ),\n finished_at: this.knex.raw(\n `CASE WHEN ${deadlineExceededCondition} THEN NOW() ELSE NULL END`,\n ),\n error: JSON.stringify(error),\n worker_id: null,\n started_at: null,\n updated_at: this.knex.fn.now(),\n })\n .returning(\"*\");\n\n if (!updated) {\n throw new Error(\"Failed to mark workflow run failed\");\n }\n\n return updated;\n }\n\n async cancelWorkflowRun(params: CancelWorkflowRunParams): Promise<WorkflowRun> {\n const [updated] = await this.knex\n .withSchema(DEFAULT_SCHEMA)\n .table(\"workflow_runs\")\n .where(\"namespace_id\", this.namespaceId)\n .where(\"id\", params.workflowRunId)\n .whereIn(\"status\", [\"pending\", \"running\", \"sleeping\"])\n .update({\n status: \"canceled\",\n worker_id: null,\n available_at: null,\n finished_at: this.knex.fn.now(),\n updated_at: this.knex.fn.now(),\n })\n .returning(\"*\");\n\n if (!updated) {\n // workflow may already be in a terminal state\n const existing = await this.getWorkflowRun({\n workflowRunId: params.workflowRunId,\n });\n if (!existing) {\n throw new Error(`Workflow run ${params.workflowRunId} does not exist`);\n }\n\n // if already canceled, just return it\n if (existing.status === \"canceled\") {\n return existing;\n }\n\n // throw error for completed/failed workflows\n // 'succeeded' status is deprecated\n if ([\"succeeded\", \"completed\", \"failed\"].includes(existing.status)) {\n throw new Error(\n `Cannot cancel workflow run ${params.workflowRunId} with status ${existing.status}`,\n );\n }\n\n throw new Error(\"Failed to cancel workflow run\");\n }\n\n return updated;\n }\n\n async createStepAttempt(params: CreateStepAttemptParams): Promise<StepAttempt> {\n const [stepAttempt] = await this.knex\n .withSchema(DEFAULT_SCHEMA)\n .table(\"step_attempts\")\n .insert({\n namespace_id: this.namespaceId,\n id: crypto.randomUUID(),\n workflow_run_id: params.workflowRunId,\n step_name: params.stepName,\n kind: params.kind,\n status: \"running\",\n config: JSON.stringify(params.config),\n context: JSON.stringify(params.context),\n started_at: this.knex.fn.now(),\n created_at: this.knex.raw(\"date_trunc('milliseconds', NOW())\"),\n updated_at: this.knex.fn.now(),\n })\n .returning(\"*\");\n\n if (!stepAttempt) {\n throw new Error(\"Failed to create step attempt\");\n }\n\n return stepAttempt;\n }\n\n async getStepAttempt(params: GetStepAttemptParams): Promise<StepAttempt | null> {\n const stepAttempt = await this.knex\n .withSchema(DEFAULT_SCHEMA)\n .table(\"step_attempts\")\n .where(\"namespace_id\", this.namespaceId)\n .where(\"id\", params.stepAttemptId)\n .first();\n\n return stepAttempt ?? null;\n }\n\n async listStepAttempts(params: ListStepAttemptsParams): Promise<PaginatedResponse<StepAttempt>> {\n const limit = params.limit ?? DEFAULT_PAGINATION_PAGE_SIZE;\n const { after, before } = params;\n\n let cursor: Cursor | null = null;\n if (after) {\n cursor = decodeCursor(after);\n } else if (before) {\n cursor = decodeCursor(before);\n }\n\n const qb = this.buildListStepAttemptsWhere(params, cursor);\n const rows = await qb\n .orderBy(\"created_at\", before ? \"desc\" : \"asc\")\n .orderBy(\"id\", before ? \"desc\" : \"asc\")\n .limit(limit + 1);\n\n return this.processPaginationResults(\n rows,\n limit,\n typeof after === \"string\",\n typeof before === \"string\",\n );\n }\n\n private buildListStepAttemptsWhere(params: ListStepAttemptsParams, cursor: Cursor | null) {\n const { after } = params;\n const qb = this.knex\n .withSchema(DEFAULT_SCHEMA)\n .table(\"step_attempts\")\n .where(\"namespace_id\", this.namespaceId)\n .where(\"workflow_run_id\", params.workflowRunId);\n\n if (cursor) {\n const operator = after ? \">\" : \"<\";\n return qb.whereRaw(`(\"created_at\", \"id\") ${operator} (?, ?)`, [\n cursor.createdAt.toISOString(),\n cursor.id,\n ]);\n }\n\n return qb;\n }\n\n private processPaginationResults<T extends Cursor>(\n rows: T[],\n limit: number,\n hasAfter: boolean,\n hasBefore: boolean,\n ): PaginatedResponse<T> {\n const data = rows;\n let hasNext = false;\n let hasPrev = false;\n\n if (hasBefore) {\n data.reverse();\n if (data.length > limit) {\n hasPrev = true;\n data.shift();\n }\n hasNext = true;\n } else {\n if (data.length > limit) {\n hasNext = true;\n data.pop();\n }\n if (hasAfter) {\n hasPrev = true;\n }\n }\n\n const lastItem = data.at(-1);\n const nextCursor = hasNext && lastItem ? encodeCursor(lastItem) : null;\n const firstItem = data[0];\n const prevCursor = hasPrev && firstItem ? encodeCursor(firstItem) : null;\n\n return {\n data,\n pagination: {\n next: nextCursor,\n prev: prevCursor,\n },\n };\n }\n\n async completeStepAttempt(params: CompleteStepAttemptParams): Promise<StepAttempt> {\n const [updated] = await this.knex\n .withSchema(DEFAULT_SCHEMA)\n .table(\"step_attempts as sa\")\n .update({\n status: \"completed\",\n output: JSON.stringify(params.output),\n error: null,\n finished_at: this.knex.fn.now(),\n updated_at: this.knex.fn.now(),\n })\n .updateFrom(`${DEFAULT_SCHEMA}.workflow_runs as wr`)\n .where(\"sa.namespace_id\", this.namespaceId)\n .where(\"sa.workflow_run_id\", params.workflowRunId)\n .where(\"sa.id\", params.stepAttemptId)\n .where(\"sa.status\", \"running\")\n .where(\"wr.namespace_id\", this.knex.ref(\"sa.namespace_id\"))\n .where(\"wr.id\", this.knex.ref(\"sa.workflow_run_id\"))\n .where(\"wr.status\", \"running\")\n .where(\"wr.worker_id\", params.workerId)\n .returning(\"sa.*\");\n\n if (!updated) {\n throw new Error(\"Failed to mark step attempt completed\");\n }\n\n return updated;\n }\n\n async failStepAttempt(params: FailStepAttemptParams): Promise<StepAttempt> {\n const [updated] = await this.knex\n .withSchema(DEFAULT_SCHEMA)\n .table(\"step_attempts as sa\")\n .update({\n status: \"failed\",\n output: null,\n error: JSON.stringify(params.error),\n finished_at: this.knex.fn.now(),\n updated_at: this.knex.fn.now(),\n })\n .updateFrom(`${DEFAULT_SCHEMA}.workflow_runs as wr`)\n .where(\"sa.namespace_id\", this.namespaceId)\n .where(\"sa.workflow_run_id\", params.workflowRunId)\n .where(\"sa.id\", params.stepAttemptId)\n .where(\"sa.status\", \"running\")\n .where(\"wr.namespace_id\", this.knex.ref(\"sa.namespace_id\"))\n .where(\"wr.id\", this.knex.ref(\"sa.workflow_run_id\"))\n .where(\"wr.status\", \"running\")\n .where(\"wr.worker_id\", params.workerId)\n .returning(\"sa.*\");\n\n if (!updated) {\n throw new Error(\"Failed to mark step attempt failed\");\n }\n\n return updated;\n }\n}\n\n/**\n * Cursor used for pagination. Requires created_at and id fields. Because JS\n * Date does not natively support microsecond precision dates, created_at should\n * be stored with millisecond precision in paginated tables to avoid issues with\n * cursor comparisons.\n */\ninterface Cursor {\n createdAt: Date;\n id: string;\n}\n\nfunction encodeCursor(item: Cursor): string {\n const encoded = Buffer.from(\n JSON.stringify({ createdAt: item.createdAt.toISOString(), id: item.id }),\n ).toString(\"base64\");\n return encoded;\n}\n\nexport function decodeCursor(cursor: string): Cursor {\n const decoded = Buffer.from(cursor, \"base64\").toString(\"utf8\");\n const parsed = JSON.parse(decoded) as { createdAt: string; id: string };\n return {\n createdAt: new Date(parsed.createdAt),\n id: parsed.id,\n };\n}\n"],"names":["camelize","knex","DEFAULT_NAMESPACE_ID","DEFAULT_RETRY_POLICY","DEFAULT_SCHEMA","migrate","PostgresPubSub","DEFAULT_LISTEN_CHANNEL","DEFAULT_PAGINATION_PAGE_SIZE","BackendPostgres","namespaceId","usePubSub","pubsub","subscribe","callback","create","listenEvent","publish","payload","raw","connect","dbConf","options","postProcessResponse","result","_queryContext","undefined","camelizeRow","row","Object","fromEntries","entries","map","key","value","Array","isArray","runMigrations","knexInstance","stop","destroy","createWorkflowRun","params","qb","withSchema","table","insert","namespace_id","id","crypto","randomUUID","workflow_name","workflowName","version","status","idempotency_key","idempotencyKey","config","context","input","attempts","available_at","availableAt","fn","now","deadline_at","deadlineAt","created_at","updated_at","returning","workflowRun","Error","getWorkflowRun","where","workflowRunId","select","first","listWorkflowRuns","limit","after","before","cursor","decodeCursor","buildListWorkflowRunsWhere","rows","orderBy","processPaginationResults","operator","whereRaw","createdAt","toISOString","claimWorkflowRun","claimed","with","update","error","JSON","stringify","message","worker_id","finished_at","whereIn","whereNotNull","from","qb2","whereNull","orWhere","orderByRaw","forUpdate","skipLocked","ref","workerId","leaseDurationMs","started_at","updateFrom","extendWorkflowRunLease","updated","sleepWorkflowRun","whereNotIn","completeWorkflowRun","output","failWorkflowRun","initialIntervalMs","backoffCoefficient","maximumIntervalMs","retryIntervalExpr","deadlineExceededCondition","cancelWorkflowRun","existing","includes","createStepAttempt","stepAttempt","workflow_run_id","step_name","stepName","kind","getStepAttempt","stepAttemptId","listStepAttempts","buildListStepAttemptsWhere","hasAfter","hasBefore","data","hasNext","hasPrev","reverse","length","shift","pop","lastItem","at","nextCursor","encodeCursor","firstItem","prevCursor","pagination","next","prev","completeStepAttempt","failStepAttempt","item","encoded","Buffer","toString","decoded","parsed","parse","Date"],"mappings":"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"}
@@ -0,0 +1,2 @@
1
+ export {};
2
+ //# sourceMappingURL=backend.test.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"backend.test.d.ts","sourceRoot":"","sources":["../../src/database/backend.test.ts"],"names":[],"mappings":""}
@@ -0,0 +1,17 @@
1
+ import { randomUUID } from "node:crypto";
2
+ import { KNEX_GLOBAL_CONFIG } from "../testing/connection.js";
3
+ import { BackendPostgres } from "./backend.js";
4
+ import { testBackend } from "./backend.testsuite.js";
5
+ testBackend({
6
+ setup: async ()=>{
7
+ return await BackendPostgres.connect(KNEX_GLOBAL_CONFIG, {
8
+ namespaceId: randomUUID(),
9
+ runMigrations: false
10
+ });
11
+ },
12
+ teardown: async (backend)=>{
13
+ await backend.stop();
14
+ }
15
+ });
16
+
17
+ //# sourceMappingURL=backend.test.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"sources":["../../src/database/backend.test.ts"],"sourcesContent":["import { randomUUID } from \"node:crypto\";\nimport { KNEX_GLOBAL_CONFIG } from \"../testing/connection\";\nimport { BackendPostgres } from \"./backend\";\nimport { testBackend } from \"./backend.testsuite\";\n\ntestBackend({\n setup: async () => {\n return await BackendPostgres.connect(KNEX_GLOBAL_CONFIG, {\n namespaceId: randomUUID(),\n runMigrations: false,\n });\n },\n teardown: async (backend) => {\n await (backend as BackendPostgres).stop();\n },\n});\n"],"names":["randomUUID","KNEX_GLOBAL_CONFIG","BackendPostgres","testBackend","setup","connect","namespaceId","runMigrations","teardown","backend","stop"],"mappings":"AAAA,SAASA,UAAU,QAAQ,cAAc;AACzC,SAASC,kBAAkB,QAAQ,2BAAwB;AAC3D,SAASC,eAAe,QAAQ,eAAY;AAC5C,SAASC,WAAW,QAAQ,yBAAsB;AAElDA,YAAY;IACVC,OAAO;QACL,OAAO,MAAMF,gBAAgBG,OAAO,CAACJ,oBAAoB;YACvDK,aAAaN;YACbO,eAAe;QACjB;IACF;IACAC,UAAU,OAAOC;QACf,MAAM,AAACA,QAA4BC,IAAI;IACzC;AACF"}
@@ -0,0 +1,20 @@
1
+ import type { Backend } from "..//backend";
2
+ /**
3
+ * Options for the Backend test suite.
4
+ */
5
+ export interface TestBackendOptions {
6
+ /**
7
+ * Creates a new isolated Backend instance.
8
+ */
9
+ setup: () => Promise<Backend>;
10
+ /**
11
+ * Cleans up a Backend instance.
12
+ */
13
+ teardown: (backend: Backend) => Promise<void>;
14
+ }
15
+ /**
16
+ * Runs the Backend test suite.
17
+ * @param options - Test suite options
18
+ */
19
+ export declare function testBackend(options: TestBackendOptions): void;
20
+ //# sourceMappingURL=backend.testsuite.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"backend.testsuite.d.ts","sourceRoot":"","sources":["../../src/database/backend.testsuite.ts"],"names":[],"mappings":"AAEA,OAAO,KAAK,EAAE,OAAO,EAAE,MAAM,aAAa,CAAC;AAI3C;;GAEG;AACH,MAAM,WAAW,kBAAkB;IACjC;;OAEG;IACH,KAAK,EAAE,MAAM,OAAO,CAAC,OAAO,CAAC,CAAC;IAC9B;;OAEG;IACH,QAAQ,EAAE,CAAC,OAAO,EAAE,OAAO,KAAK,OAAO,CAAC,IAAI,CAAC,CAAC;CAC/C;AAED;;;GAGG;AACH,wBAAgB,WAAW,CAAC,OAAO,EAAE,kBAAkB,GAAG,IAAI,CAswC7D"}