@sanoma-ai/workflows 0.11.12 → 0.11.13

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 (142) hide show
  1. package/CLOUD-IDENTITY.md +12 -4
  2. package/KMS-SECRETS.md +3 -1
  3. package/README.md +4 -2
  4. package/dist/bundled.d.ts +2 -2
  5. package/dist/chats.d.ts +3 -3
  6. package/dist/chats.js +34 -20
  7. package/dist/chats.js.map +1 -1
  8. package/dist/client.d.ts +17 -4
  9. package/dist/client.js +74 -63
  10. package/dist/client.js.map +1 -1
  11. package/dist/cloud-identity.js +14 -12
  12. package/dist/cloud-identity.js.map +1 -1
  13. package/dist/collection.d.ts +2 -2
  14. package/dist/collection.js +53 -42
  15. package/dist/collection.js.map +1 -1
  16. package/dist/config.d.ts +11 -6
  17. package/dist/config.js +15 -13
  18. package/dist/config.js.map +1 -1
  19. package/dist/connection.d.ts +2 -0
  20. package/dist/connection.js +112 -40
  21. package/dist/connection.js.map +1 -1
  22. package/dist/credentials.d.ts +1 -1
  23. package/dist/credentials.js +33 -29
  24. package/dist/credentials.js.map +1 -1
  25. package/dist/db/company.d.ts +1152 -0
  26. package/dist/db/company.js +118 -0
  27. package/dist/db/company.js.map +1 -0
  28. package/dist/db/dbos.d.ts +111 -0
  29. package/dist/db/dbos.js +15 -0
  30. package/dist/db/dbos.js.map +1 -0
  31. package/dist/db/identity.d.ts +367 -0
  32. package/dist/db/identity.js +48 -0
  33. package/dist/db/identity.js.map +1 -0
  34. package/dist/db/index.d.ts +6 -0
  35. package/dist/db/index.js +10 -0
  36. package/dist/db/index.js.map +1 -0
  37. package/dist/db/kms.d.ts +224 -0
  38. package/dist/db/kms.js +29 -0
  39. package/dist/db/kms.js.map +1 -0
  40. package/dist/db/migrate.d.ts +63 -0
  41. package/dist/db/migrate.js +41 -0
  42. package/dist/db/migrate.js.map +1 -0
  43. package/dist/db/wakeup.d.ts +271 -0
  44. package/dist/db/wakeup.js +34 -0
  45. package/dist/db/wakeup.js.map +1 -0
  46. package/dist/db.d.ts +42 -39
  47. package/dist/db.js +129 -169
  48. package/dist/db.js.map +1 -1
  49. package/dist/deadlines.js +8 -4
  50. package/dist/deadlines.js.map +1 -1
  51. package/dist/deployment-key.d.ts +4 -1
  52. package/dist/deployment-key.js +10 -3
  53. package/dist/deployment-key.js.map +1 -1
  54. package/dist/host-derive.d.ts +12 -3
  55. package/dist/host-derive.js +21 -8
  56. package/dist/host-derive.js.map +1 -1
  57. package/dist/identity-provisioning.d.ts +2 -2
  58. package/dist/identity-provisioning.js +75 -42
  59. package/dist/identity-provisioning.js.map +1 -1
  60. package/dist/identity-service.js +18 -15
  61. package/dist/identity-service.js.map +1 -1
  62. package/dist/index.d.ts +2 -2
  63. package/dist/index.js +1 -1
  64. package/dist/index.js.map +1 -1
  65. package/dist/kms-secrets.d.ts +9 -0
  66. package/dist/kms-secrets.js +59 -27
  67. package/dist/kms-secrets.js.map +1 -1
  68. package/dist/ledger.d.ts +1 -1
  69. package/dist/ledger.js +22 -14
  70. package/dist/ledger.js.map +1 -1
  71. package/dist/op.d.ts +27 -6
  72. package/dist/op.js.map +1 -1
  73. package/dist/run-status.js +7 -3
  74. package/dist/run-status.js.map +1 -1
  75. package/dist/schedules.d.ts +1 -1
  76. package/dist/schedules.js +5 -7
  77. package/dist/schedules.js.map +1 -1
  78. package/dist/schema.d.ts +6 -5
  79. package/dist/schema.js +11 -7
  80. package/dist/schema.js.map +1 -1
  81. package/dist/shared.d.ts +6 -23
  82. package/dist/shared.js +6 -5
  83. package/dist/shared.js.map +1 -1
  84. package/dist/storage-provisioning.d.ts +2 -0
  85. package/dist/storage-provisioning.js +51 -50
  86. package/dist/storage-provisioning.js.map +1 -1
  87. package/dist/tokens.d.ts +2 -2
  88. package/dist/tokens.js +31 -20
  89. package/dist/tokens.js.map +1 -1
  90. package/dist/version.d.ts +4 -4
  91. package/dist/version.js +5 -5
  92. package/dist/version.js.map +1 -1
  93. package/dist/wakeup-service.d.ts +0 -4
  94. package/dist/wakeup-service.js +102 -93
  95. package/dist/wakeup-service.js.map +1 -1
  96. package/dist/worker.d.ts +7 -0
  97. package/dist/worker.js +26 -21
  98. package/dist/worker.js.map +1 -1
  99. package/drizzle/company/0000_tables.sql +104 -0
  100. package/drizzle/company/0001_wakeup_row.sql +2 -0
  101. package/drizzle/company/meta/0000_snapshot.json +652 -0
  102. package/drizzle/company/meta/0001_snapshot.json +652 -0
  103. package/drizzle/company/meta/_journal.json +20 -0
  104. package/drizzle/wakeup/0000_tables.sql +26 -0
  105. package/drizzle/wakeup/meta/0000_snapshot.json +200 -0
  106. package/drizzle/wakeup/meta/_journal.json +13 -0
  107. package/oxlint.json +2 -1
  108. package/package.json +11 -2
  109. package/src/bundled.ts +2 -2
  110. package/src/chats.ts +41 -42
  111. package/src/client.ts +81 -64
  112. package/src/cloud-identity.ts +23 -24
  113. package/src/collection.ts +58 -50
  114. package/src/config.ts +29 -19
  115. package/src/connection.ts +132 -102
  116. package/src/credentials.ts +37 -33
  117. package/src/db/company.ts +173 -0
  118. package/src/db/dbos.ts +17 -0
  119. package/src/db/identity.ts +61 -0
  120. package/src/db/index.ts +10 -0
  121. package/src/db/kms.ts +41 -0
  122. package/src/db/migrate.ts +70 -0
  123. package/src/db/wakeup.ts +41 -0
  124. package/src/db.ts +151 -182
  125. package/src/deadlines.ts +10 -4
  126. package/src/deployment-key.ts +11 -3
  127. package/src/host-derive.ts +26 -9
  128. package/src/identity-provisioning.ts +85 -57
  129. package/src/identity-service.ts +19 -19
  130. package/src/index.ts +3 -0
  131. package/src/kms-secrets.ts +64 -56
  132. package/src/ledger.ts +23 -18
  133. package/src/op.ts +28 -6
  134. package/src/run-status.ts +7 -6
  135. package/src/schedules.ts +6 -8
  136. package/src/schema.ts +11 -8
  137. package/src/shared.ts +6 -17
  138. package/src/storage-provisioning.ts +47 -52
  139. package/src/tokens.ts +43 -33
  140. package/src/version.ts +5 -5
  141. package/src/wakeup-service.ts +117 -131
  142. package/src/worker.ts +38 -21
@@ -0,0 +1,34 @@
1
+ import { sql } from "drizzle-orm";
2
+ import { index, integer, pgTable, text, timestamp, uuid } from "drizzle-orm/pg-core";
3
+ // The wakeup service's tables (`wakeup-service.ts`), in the service's own database: never a
4
+ // company's, which every company database gets. Migrations under `drizzle/wakeup/`.
5
+ const when = () => timestamp({ withTimezone: true });
6
+ /** One account per party that registers instances, its token's hash alone. */
7
+ export const wakeupAccounts = pgTable("sanoma_wakeup_accounts", {
8
+ id: uuid().primaryKey(),
9
+ tokenHash: text().notNull().unique(),
10
+ label: text().notNull(),
11
+ createdAt: when().notNull().defaultNow(),
12
+ revokedAt: when(),
13
+ });
14
+ /** Each registered instance: its URL, its token's hash and its registered wake. */
15
+ export const wakeupInstances = pgTable("sanoma_wakeup_instances", {
16
+ id: uuid().primaryKey(),
17
+ accountId: uuid()
18
+ .notNull()
19
+ .references(() => wakeupAccounts.id),
20
+ url: text().notNull(),
21
+ tokenHash: text().notNull().unique(),
22
+ at: when(),
23
+ calledAt: when(),
24
+ attempts: integer().notNull().default(0),
25
+ nextAttemptAt: when(),
26
+ lastError: text(),
27
+ createdAt: when().notNull().defaultNow(),
28
+ }, (t) => [
29
+ index("sanoma_wakeup_instances_at")
30
+ .on(t.at)
31
+ .where(sql `${t.at} IS NOT NULL`),
32
+ index("sanoma_wakeup_instances_account").on(t.accountId),
33
+ ]);
34
+ //# sourceMappingURL=wakeup.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"wakeup.js","sourceRoot":"","sources":["../../src/db/wakeup.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,GAAG,EAAE,MAAM,aAAa,CAAC;AAClC,OAAO,EAAE,KAAK,EAAE,OAAO,EAAE,OAAO,EAAE,IAAI,EAAE,SAAS,EAAE,IAAI,EAAE,MAAM,qBAAqB,CAAC;AAErF,4FAA4F;AAC5F,oFAAoF;AAEpF,MAAM,IAAI,GAAG,GAAG,EAAE,CAAC,SAAS,CAAC,EAAE,YAAY,EAAE,IAAI,EAAE,CAAC,CAAC;AAErD,8EAA8E;AAC9E,MAAM,CAAC,MAAM,cAAc,GAAG,OAAO,CAAC,wBAAwB,EAAE;IAC9D,EAAE,EAAE,IAAI,EAAE,CAAC,UAAU,EAAE;IACvB,SAAS,EAAE,IAAI,EAAE,CAAC,OAAO,EAAE,CAAC,MAAM,EAAE;IACpC,KAAK,EAAE,IAAI,EAAE,CAAC,OAAO,EAAE;IACvB,SAAS,EAAE,IAAI,EAAE,CAAC,OAAO,EAAE,CAAC,UAAU,EAAE;IACxC,SAAS,EAAE,IAAI,EAAE;CAClB,CAAC,CAAC;AAEH,mFAAmF;AACnF,MAAM,CAAC,MAAM,eAAe,GAAG,OAAO,CACpC,yBAAyB,EACzB;IACE,EAAE,EAAE,IAAI,EAAE,CAAC,UAAU,EAAE;IACvB,SAAS,EAAE,IAAI,EAAE;SACd,OAAO,EAAE;SACT,UAAU,CAAC,GAAG,EAAE,CAAC,cAAc,CAAC,EAAE,CAAC;IACtC,GAAG,EAAE,IAAI,EAAE,CAAC,OAAO,EAAE;IACrB,SAAS,EAAE,IAAI,EAAE,CAAC,OAAO,EAAE,CAAC,MAAM,EAAE;IACpC,EAAE,EAAE,IAAI,EAAE;IACV,QAAQ,EAAE,IAAI,EAAE;IAChB,QAAQ,EAAE,OAAO,EAAE,CAAC,OAAO,EAAE,CAAC,OAAO,CAAC,CAAC,CAAC;IACxC,aAAa,EAAE,IAAI,EAAE;IACrB,SAAS,EAAE,IAAI,EAAE;IACjB,SAAS,EAAE,IAAI,EAAE,CAAC,OAAO,EAAE,CAAC,UAAU,EAAE;CACzC,EACD,CAAC,CAAC,EAAE,EAAE,CAAC;IACL,KAAK,CAAC,4BAA4B,CAAC;SAChC,EAAE,CAAC,CAAC,CAAC,EAAE,CAAC;SACR,KAAK,CAAC,GAAG,CAAA,GAAG,CAAC,CAAC,EAAE,cAAc,CAAC;IAClC,KAAK,CAAC,iCAAiC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,SAAS,CAAC;CACzD,CACF,CAAC"}
package/dist/db.d.ts CHANGED
@@ -1,25 +1,24 @@
1
1
  import { DBOSClient } from "@dbos-inc/dbos-sdk";
2
+ import { type NodePgClient, type NodePgQueryResultHKT } from "drizzle-orm/node-postgres";
3
+ import { type PgDatabase } from "drizzle-orm/pg-core";
2
4
  import { Client, Pool } from "pg";
3
- /** A connection or a pool: what the queries take. */
4
- export type Db = Pick<Pool | Client, "query">;
5
- /** Where the credentials set from the app live. */
6
- export declare const CREDENTIALS_TABLE = "sanoma_credentials";
7
- /** Where the Postgres ledger keeps its records. */
8
- export declare const LEDGER_TABLE = "sanoma_ledger";
9
- /** Where the collections keep their records (`collection.ts`): one row per collection and key, the record as JSON. */
10
- export declare const DATA_TABLE = "sanoma_data";
11
5
  /**
12
- * The instance's side of its wakeup: one row, made with the table. `at` is the deadline last
13
- * registered, `stopped_at` when the worker last stopped itself (the schedules backfill from it),
14
- * `last_error` why the last registration failed.
6
+ * A database, or a transaction on one (`db.transaction`): what every store takes, so a store runs
7
+ * inside a caller's transaction as it runs on its own. Made by `databaseOn`.
15
8
  */
16
- export declare const WAKEUP_TABLE = "sanoma_wakeup";
17
- /** The operator agent's chats (`chats.ts`): who each is for, its engine and its draft. */
18
- export declare const CHATS_TABLE = "sanoma_chats";
19
- /** Each chat's messages, the AI SDK's UI messages as JSON, in `seq` order. */
20
- export declare const CHAT_MESSAGES_TABLE = "sanoma_chat_messages";
21
- /** The api tokens (`tokens.ts`): each one's SHA-256, never the token, whom it acts for, its groups, and when it was revoked. */
22
- export declare const API_TOKENS_TABLE = "sanoma_api_tokens";
9
+ export type Db = PgDatabase<NodePgQueryResultHKT>;
10
+ /**
11
+ * Drizzle over `client`, a `pg` pool or connection the caller owns and ends (`db.$client`). Column
12
+ * names are the schema's properties in snake_case (`casing`), as the generated migrations write them.
13
+ *
14
+ * A statement that fails throws the `pg` error itself, as `client.query` would, not Drizzle's
15
+ * `DrizzleQueryError`, whose message carries the statement and its parameters (a credential's
16
+ * sealed value, a person's email, a record): `pgCode` reads the code, and no message or log
17
+ * repeats what was sent. `db.test.ts` holds Drizzle to this with a sentinel parameter.
18
+ */
19
+ export declare function databaseOn<C extends NodePgClient>(client: C): import("drizzle-orm/node-postgres").NodePgDatabase<Record<string, never>> & {
20
+ $client: NodePgClient extends C ? Pool : C;
21
+ };
23
22
  /** The Postgres error code of `err`, or an empty string when it has none. */
24
23
  export declare const pgCode: (err: unknown) => string;
25
24
  /** True for the failure of a create that another process won: what was to be made is there. */
@@ -45,8 +44,8 @@ export declare const DBOS_DATABASE_OPTIONS: {
45
44
  * `version`, so DBOS gives them to a worker of that version: those it stamped, each with its status
46
45
  * (a PENDING one is the caller's to queue again). DBOS has no call for it (a run's version is set at
47
46
  * its start, `forkWorkflow` makes a new id, `rewindWorkflow` takes only an ended run), so this is the
48
- * runtime's one write to DBOS's own tables, in its schema `dbos` (dbos-sdk 5.2.11). One statement:
49
- * of two workers stamping a run, one does.
47
+ * runtime's one write to DBOS's own tables (`db/dbos.ts`, dbos-sdk 5.2.11). One statement: of two
48
+ * workers stamping a run, one does.
50
49
  */
51
50
  export declare function stampVersion(db: Db, ids: readonly string[], version: string): Promise<{
52
51
  id: string;
@@ -57,17 +56,19 @@ export declare function stampVersion(db: Db, ids: readonly string[], version: st
57
56
  * the runtime, its tests and `@sanoma-ai/testing` make one (`DBOS_DATABASE_OPTIONS`).
58
57
  */
59
58
  export declare const dbosClient: (databaseUrl: string, applicationName?: string) => Promise<DBOSClient>;
60
- /** A pool opened on first use, once its database is prepared, and ended by `close`. */
61
- export interface LazyPool {
62
- db(): Promise<Pool>;
59
+ /** A database opened on first use, once prepared, and ended by `close`. */
60
+ export interface LazyDb {
61
+ db(): Promise<Db>;
62
+ /** The pool `db()` runs on, once the database is prepared. */
63
+ pool(): Promise<Pool>;
63
64
  close(): Promise<void>;
64
65
  }
65
66
  /**
66
- * A pool for `what` on the database at `databaseUrl`, opened on the first `db()` once the
67
- * database is prepared (`prepareDatabase`). A preparation that fails lets the pool go, so the
68
- * next `db()` tries again. `close` ends the pool, for good: a `db()` after it is refused.
67
+ * A database for `what` on a pool at `databaseUrl`, opened on the first `db()` (or `pool()`) once
68
+ * the database is prepared (`prepareDatabase`). A preparation that fails lets the pool go, so the
69
+ * next call tries again. `close` ends the pool, for good: a call after it is refused.
69
70
  */
70
- export declare function lazyPool(databaseUrl: string, what: string): LazyPool;
71
+ export declare function lazyDb(databaseUrl: string, what: string): LazyDb;
71
72
  /**
72
73
  * From now on, `prepareDatabase` makes nothing: it only checks that DBOS's tables and the
73
74
  * runtime's are there, and refuses, naming `by`, what prepares them, when they are not. For a
@@ -79,21 +80,23 @@ export declare function checkPreparedOnly(by: string): void;
79
80
  * Makes the database at `databaseUrl` ready for the runtime, once per process and URL: the
80
81
  * database itself and DBOS's tables when they are not there yet (as a worker's launch makes
81
82
  * them; credentials may be set, and a ledger read, before any worker has run), then the
82
- * credentials, ledger, data, wakeup and chat tables, and its idle-transaction timeout (`guardIdleTransactions`).
83
- * Two processes preparing one database both succeed: the second waits for the first
84
- * (`lockPreparation`). A preparation that fails is forgotten, so the next call tries again.
83
+ * runtime's tables, by the migrations the database has not had (`COMPANY_MIGRATIONS`), and its
84
+ * idle-transaction timeout (`guardIdleTransactions`). Two processes preparing one database both
85
+ * succeed: the second waits for the first (`lockPreparation`). A preparation that fails is
86
+ * forgotten, so the next call tries again.
85
87
  */
86
88
  export declare function prepareDatabase(databaseUrl: string): Promise<void>;
89
+ /**
90
+ * Runs `make` on a connection holding the preparation's session lock of the database at
91
+ * `databaseUrl` (made first when missing), so a second process waits, then finds everything made.
92
+ * For what makes a database's tables: `prepareDatabase`, and the wakeup service's own.
93
+ */
94
+ export declare function underPreparationLock<T>(databaseUrl: string, make: (db: Db) => Promise<T>): Promise<T>;
87
95
  /** A connection to the database at `databaseUrl`, made first when it is not there (`createDatabase`). */
88
96
  export declare function connectMaking(databaseUrl: string): Promise<Client>;
89
97
  /**
90
- * Runs `ddl` (`CREATE TABLE IF NOT EXISTS`, and the like) on `db`. Two processes racing to create
91
- * the same table both succeed; any other failure names the `what` table, with its cause.
98
+ * Marks a sealed invite request's `nonce` spent until `expiresAt`, when the row goes: true the
99
+ * first time, false for one spent already, whichever process asks. A row, not memory: the app
100
+ * keeps nothing across requests.
92
101
  */
93
- export declare function createTable(db: Db, ddl: string, what: string): Promise<void>;
94
- /** Records that the wakeup took `at`. */
95
- export declare function recordWakeupRegistration(db: Db, at: string): Promise<void>;
96
- /** Records why the last registration failed. */
97
- export declare function recordWakeupError(db: Db, error: string): Promise<void>;
98
- /** Records that the worker stops itself now. */
99
- export declare function recordWakeupStop(db: Db): Promise<void>;
102
+ export declare function spendInviteRequest(db: Db, nonce: string, expiresAt: Date): Promise<boolean>;
package/dist/db.js CHANGED
@@ -1,100 +1,49 @@
1
1
  import { DBOS, DBOSClient } from "@dbos-inc/dbos-sdk";
2
2
  import { setTimeout as delay } from "node:timers/promises";
3
- import { Client, escapeIdentifier, Pool } from "pg";
3
+ import { and, eq, inArray, lte, ne, sql } from "drizzle-orm";
4
+ import { DrizzleQueryError } from "drizzle-orm/errors";
5
+ import { drizzle } from "drizzle-orm/node-postgres";
6
+ import { PgPreparedQuery } from "drizzle-orm/pg-core";
7
+ import { Client, Pool } from "pg";
8
+ import { inviteRequests } from "./db/company.js";
9
+ import { workflowStatus } from "./db/dbos.js";
10
+ import { applyMigrations, COMPANY_MIGRATIONS, migrationsApplied } from "./db/migrate.js";
4
11
  import { warn } from "./log.js";
5
12
  import { errorMessage } from "./shared.js";
6
- /** Where the credentials set from the app live. */
7
- export const CREDENTIALS_TABLE = "sanoma_credentials";
8
- /** Where the Postgres ledger keeps its records. */
9
- export const LEDGER_TABLE = "sanoma_ledger";
10
- /** Where the collections keep their records (`collection.ts`): one row per collection and key, the record as JSON. */
11
- export const DATA_TABLE = "sanoma_data";
12
13
  /**
13
- * The instance's side of its wakeup: one row, made with the table. `at` is the deadline last
14
- * registered, `stopped_at` when the worker last stopped itself (the schedules backfill from it),
15
- * `last_error` why the last registration failed.
14
+ * Drizzle over `client`, a `pg` pool or connection the caller owns and ends (`db.$client`). Column
15
+ * names are the schema's properties in snake_case (`casing`), as the generated migrations write them.
16
+ *
17
+ * A statement that fails throws the `pg` error itself, as `client.query` would, not Drizzle's
18
+ * `DrizzleQueryError`, whose message carries the statement and its parameters (a credential's
19
+ * sealed value, a person's email, a record): `pgCode` reads the code, and no message or log
20
+ * repeats what was sent. `db.test.ts` holds Drizzle to this with a sentinel parameter.
16
21
  */
17
- export const WAKEUP_TABLE = "sanoma_wakeup";
18
- /** The operator agent's chats (`chats.ts`): who each is for, its engine and its draft. */
19
- export const CHATS_TABLE = "sanoma_chats";
20
- /** Each chat's messages, the AI SDK's UI messages as JSON, in `seq` order. */
21
- export const CHAT_MESSAGES_TABLE = "sanoma_chat_messages";
22
- /** The api tokens (`tokens.ts`): each one's SHA-256, never the token, whom it acts for, its groups, and when it was revoked. */
23
- export const API_TOKENS_TABLE = "sanoma_api_tokens";
24
- /** The runtime's tables, each with the word the messages name it by. */
25
- const TABLES = [
26
- [
27
- "connection health",
28
- `CREATE TABLE IF NOT EXISTS sanoma_connection_health (
29
- connection_id text PRIMARY KEY, revision text NOT NULL, health text NOT NULL,
30
- credential_version text, externally_renewed boolean NOT NULL, checked_at timestamptz NOT NULL DEFAULT now())`,
31
- ],
32
- [
33
- "connection setup receipts",
34
- `CREATE TABLE IF NOT EXISTS sanoma_connection_setups (
35
- connection_id text NOT NULL, revision text NOT NULL, credential_version text NOT NULL,
36
- PRIMARY KEY(connection_id, revision))`,
37
- ],
38
- [
39
- "connections",
40
- `CREATE TABLE IF NOT EXISTS sanoma_connections (
41
- id text PRIMARY KEY, vendor text NOT NULL, method text NOT NULL, owner text, rule text,
42
- account text NOT NULL, scopes jsonb NOT NULL, revision text NOT NULL, definition text NOT NULL,
43
- credential text, location jsonb, status text NOT NULL DEFAULT 'connected', updated_by text NOT NULL,
44
- updated_at timestamptz NOT NULL DEFAULT now());
45
- ALTER TABLE sanoma_connections ADD COLUMN IF NOT EXISTS location jsonb`,
46
- ],
47
- [
48
- "credentials",
49
- // A table from before 0.10.0 (one row per name, each value sealed to its name alone) holds
50
- // nothing 0.10.0 can read: it goes, and its credentials are set again.
51
- // One table for the look and the drop: the one the name resolves to.
52
- `DO $$ BEGIN
53
- IF to_regclass('${CREDENTIALS_TABLE}') IS NOT NULL AND NOT EXISTS (
54
- SELECT FROM pg_attribute
55
- WHERE attrelid = to_regclass('${CREDENTIALS_TABLE}') AND attname = 'namespace' AND NOT attisdropped
56
- ) THEN
57
- DROP TABLE ${CREDENTIALS_TABLE};
58
- END IF;
59
- END $$; ` +
60
- `CREATE TABLE IF NOT EXISTS ${CREDENTIALS_TABLE} (namespace text NOT NULL, name text NOT NULL, value text NOT NULL, ` +
61
- "version text NOT NULL, set_by text NOT NULL, set_at timestamptz NOT NULL DEFAULT now(), PRIMARY KEY(namespace, name))",
62
- ],
63
- [
64
- "ledger",
65
- // `n` is the write order, `id` the record's, which the first write of takes, and `seq` the
66
- // record's place in its run: a run reads in `seq` order, then write order.
67
- `CREATE TABLE IF NOT EXISTS ${LEDGER_TABLE} (n bigserial PRIMARY KEY, id text NOT NULL UNIQUE, ` +
68
- `run_id text NOT NULL, seq integer NOT NULL, record jsonb NOT NULL); ` +
69
- `CREATE INDEX IF NOT EXISTS ${LEDGER_TABLE}_run_seq ON ${LEDGER_TABLE} (run_id, seq, n)`,
70
- ],
71
- [
72
- "data",
73
- `CREATE TABLE IF NOT EXISTS ${DATA_TABLE} (collection text NOT NULL, key text NOT NULL, record jsonb NOT NULL, ` +
74
- "updated_at timestamptz NOT NULL DEFAULT now(), updated_by text NOT NULL, PRIMARY KEY (collection, key))",
75
- ],
76
- [
77
- "wakeup",
78
- `CREATE TABLE IF NOT EXISTS ${WAKEUP_TABLE} (id integer PRIMARY KEY CHECK (id = 1), at timestamptz, ` +
79
- `stopped_at timestamptz, last_error text); INSERT INTO ${WAKEUP_TABLE} (id) VALUES (1) ON CONFLICT (id) DO NOTHING`,
80
- ],
81
- [
82
- "chats",
83
- `CREATE TABLE IF NOT EXISTS ${CHATS_TABLE} (id text PRIMARY KEY, person text NOT NULL, engine text NOT NULL, ` +
84
- "draft_id text, title text NOT NULL, created_at timestamptz NOT NULL DEFAULT now()); " +
85
- `CREATE INDEX IF NOT EXISTS ${CHATS_TABLE}_person ON ${CHATS_TABLE} (person, created_at)`,
86
- ],
87
- [
88
- "chat messages",
89
- `CREATE TABLE IF NOT EXISTS ${CHAT_MESSAGES_TABLE} (chat_id text NOT NULL REFERENCES ${CHATS_TABLE} (id) ` +
90
- "ON DELETE CASCADE, id text NOT NULL, seq integer NOT NULL, message jsonb NOT NULL, PRIMARY KEY (chat_id, id))",
91
- ],
92
- [
93
- "api tokens",
94
- `CREATE TABLE IF NOT EXISTS ${API_TOKENS_TABLE} (id text PRIMARY KEY, hash text NOT NULL UNIQUE, ` +
95
- "subject text NOT NULL, groups jsonb NOT NULL, created_at timestamptz NOT NULL DEFAULT now(), revoked_at timestamptz)",
96
- ],
97
- ];
22
+ export function databaseOn(client) {
23
+ rethrowCause();
24
+ return drizzle(client, { casing: "snake_case" });
25
+ }
26
+ let rethrowing = false;
27
+ /**
28
+ * Makes every prepared query of this copy of Drizzle throw the driver's error in place of
29
+ * `DrizzleQueryError` (drizzle-orm 0.45.4 wraps in `PgPreparedQuery.queryWithCache`, the one
30
+ * place every query passes). Once per copy of the module.
31
+ */
32
+ function rethrowCause() {
33
+ if (rethrowing)
34
+ return;
35
+ rethrowing = true;
36
+ const prototype = PgPreparedQuery.prototype;
37
+ const wrapped = prototype.queryWithCache;
38
+ prototype.queryWithCache = async function (...args) {
39
+ try {
40
+ return await wrapped.apply(this, args);
41
+ }
42
+ catch (err) {
43
+ throw err instanceof DrizzleQueryError && err.cause !== undefined ? err.cause : err;
44
+ }
45
+ };
46
+ }
98
47
  /** The Postgres error code of `err`, or an empty string when it has none. */
99
48
  export const pgCode = (err) => err?.code?.toString() ?? "";
100
49
  /**
@@ -129,15 +78,16 @@ export const DBOS_DATABASE_OPTIONS = { systemDatabaseIdleTransactionTimeoutMs: 0
129
78
  * `version`, so DBOS gives them to a worker of that version: those it stamped, each with its status
130
79
  * (a PENDING one is the caller's to queue again). DBOS has no call for it (a run's version is set at
131
80
  * its start, `forkWorkflow` makes a new id, `rewindWorkflow` takes only an ended run), so this is the
132
- * runtime's one write to DBOS's own tables, in its schema `dbos` (dbos-sdk 5.2.11). One statement:
133
- * of two workers stamping a run, one does.
81
+ * runtime's one write to DBOS's own tables (`db/dbos.ts`, dbos-sdk 5.2.11). One statement: of two
82
+ * workers stamping a run, one does.
134
83
  */
135
84
  export async function stampVersion(db, ids, version) {
136
- const { rows } = await db.query(`UPDATE dbos.workflow_status SET application_version = $1
137
- WHERE workflow_uuid = ANY($2) AND name = 'change' AND status IN ('PENDING', 'ENQUEUED')
138
- AND application_version <> $1
139
- RETURNING workflow_uuid, status`, [version, ids]);
140
- return rows.map((r) => ({ id: r.workflow_uuid, pending: r.status === "PENDING" }));
85
+ const stamped = await db
86
+ .update(workflowStatus)
87
+ .set({ applicationVersion: version })
88
+ .where(and(inArray(workflowStatus.workflowUuid, [...ids]), eq(workflowStatus.name, "change"), inArray(workflowStatus.status, ["PENDING", "ENQUEUED"]), ne(workflowStatus.applicationVersion, version)))
89
+ .returning({ id: workflowStatus.workflowUuid, status: workflowStatus.status });
90
+ return stamped.map((r) => ({ id: r.id, pending: r.status === "PENDING" }));
141
91
  }
142
92
  /**
143
93
  * A DBOS client of the app `applicationName` on the database at `databaseUrl`, as every client of
@@ -159,33 +109,39 @@ const INSUFFICIENT_PRIVILEGE = "42501";
159
109
  /** Postgres's code for a database that is not there (`invalid_catalog_name`). */
160
110
  const NO_DATABASE = "3D000";
161
111
  /**
162
- * A pool for `what` on the database at `databaseUrl`, opened on the first `db()` once the
163
- * database is prepared (`prepareDatabase`). A preparation that fails lets the pool go, so the
164
- * next `db()` tries again. `close` ends the pool, for good: a `db()` after it is refused.
112
+ * A database for `what` on a pool at `databaseUrl`, opened on the first `db()` (or `pool()`) once
113
+ * the database is prepared (`prepareDatabase`). A preparation that fails lets the pool go, so the
114
+ * next call tries again. `close` ends the pool, for good: a call after it is refused.
165
115
  */
166
- export function lazyPool(databaseUrl, what) {
116
+ export function lazyDb(databaseUrl, what) {
167
117
  let pool;
118
+ let db;
168
119
  let closed = false;
120
+ async function opened() {
121
+ if (closed)
122
+ throw new Error(`the ${what} store is closed`);
123
+ const current = (pool ??= openPool(databaseUrl, what));
124
+ try {
125
+ await prepareDatabase(databaseUrl);
126
+ }
127
+ catch (err) {
128
+ if (pool === current)
129
+ pool = db = undefined;
130
+ await current.end().catch(() => undefined);
131
+ throw err;
132
+ }
133
+ return current;
134
+ }
169
135
  return {
170
136
  async db() {
171
- if (closed)
172
- throw new Error(`the ${what} store is closed`);
173
- const current = (pool ??= openPool(databaseUrl, what));
174
- try {
175
- await prepareDatabase(databaseUrl);
176
- }
177
- catch (err) {
178
- if (pool === current)
179
- pool = undefined;
180
- await current.end().catch(() => undefined);
181
- throw err;
182
- }
183
- return current;
137
+ const current = await opened();
138
+ return (db ??= databaseOn(current));
184
139
  },
140
+ pool: opened,
185
141
  async close() {
186
142
  closed = true;
187
143
  const current = pool;
188
- pool = undefined;
144
+ pool = db = undefined;
189
145
  await current?.end();
190
146
  },
191
147
  };
@@ -207,9 +163,10 @@ export function checkPreparedOnly(by) {
207
163
  * Makes the database at `databaseUrl` ready for the runtime, once per process and URL: the
208
164
  * database itself and DBOS's tables when they are not there yet (as a worker's launch makes
209
165
  * them; credentials may be set, and a ledger read, before any worker has run), then the
210
- * credentials, ledger, data, wakeup and chat tables, and its idle-transaction timeout (`guardIdleTransactions`).
211
- * Two processes preparing one database both succeed: the second waits for the first
212
- * (`lockPreparation`). A preparation that fails is forgotten, so the next call tries again.
166
+ * runtime's tables, by the migrations the database has not had (`COMPANY_MIGRATIONS`), and its
167
+ * idle-transaction timeout (`guardIdleTransactions`). Two processes preparing one database both
168
+ * succeed: the second waits for the first (`lockPreparation`). A preparation that fails is
169
+ * forgotten, so the next call tries again.
213
170
  */
214
171
  export function prepareDatabase(databaseUrl) {
215
172
  let preparing = prepared.get(databaseUrl);
@@ -227,32 +184,46 @@ export function prepareDatabase(databaseUrl) {
227
184
  /** The error a preparation fails with, its cause `err`. */
228
185
  const unprepared = (err) => new Error(`could not prepare the database: ${errorMessage(err)}`, { cause: err });
229
186
  async function prepare(databaseUrl) {
230
- const conn = await lockPreparation(databaseUrl).catch((err) => {
231
- throw unprepared(err);
232
- });
233
- try {
187
+ await underPreparationLock(databaseUrl, async (db) => {
234
188
  await DBOS.migrate(databaseUrl).catch((err) => {
235
189
  // A DBOS table made meanwhile by a release from before the lock, mid-upgrade: it is there.
236
190
  if (!madeAlready(err))
237
191
  throw unprepared(err);
238
192
  });
239
- for (const [what, ddl] of TABLES)
240
- await createTable(conn, ddl, what);
241
- await guardIdleTransactions(conn);
193
+ await applyMigrations(db, COMPANY_MIGRATIONS).catch((err) => {
194
+ throw unprepared(err);
195
+ });
196
+ await guardIdleTransactions(db);
197
+ });
198
+ }
199
+ /**
200
+ * Runs `make` on a connection holding the preparation's session lock of the database at
201
+ * `databaseUrl` (made first when missing), so a second process waits, then finds everything made.
202
+ * For what makes a database's tables: `prepareDatabase`, and the wakeup service's own.
203
+ */
204
+ export async function underPreparationLock(databaseUrl, make) {
205
+ const db = await lockPreparation(databaseUrl).catch((err) => {
206
+ throw unprepared(err);
207
+ });
208
+ try {
209
+ return await make(db);
242
210
  }
243
211
  finally {
244
212
  // Ending the session releases the lock; a failure to end it must not hide the preparation's.
245
- await conn.end().catch(() => undefined);
213
+ await db.$client.end().catch(() => undefined);
246
214
  }
247
215
  }
248
- /** The last of the runtime's tables a preparation makes (`TABLES`), so its being there says they all are. */
249
- const LAST_TABLE = API_TOKENS_TABLE;
250
- /** Refuses when the database at `databaseUrl` lacks DBOS's tables or the runtime's: `by` makes them, not this process. */
216
+ /**
217
+ * Refuses when the database at `databaseUrl` lacks DBOS's tables or the runtime's (every
218
+ * migration of `COMPANY_MIGRATIONS`, by its journal): `by` makes them, not this process.
219
+ */
251
220
  async function checkPrepared(databaseUrl, by) {
252
221
  const conn = await connect(databaseUrl);
253
222
  try {
254
- const { rows } = await conn.query(`SELECT to_regclass('dbos.workflow_status') IS NOT NULL AS dbos, to_regclass('${LAST_TABLE}') IS NOT NULL AS ours`);
255
- const { dbos, ours } = rows[0];
223
+ const db = databaseOn(conn);
224
+ const { rows } = await db.execute(sql `SELECT to_regclass('dbos.workflow_status') IS NOT NULL AS dbos`);
225
+ const dbos = rows[0]?.dbos === true;
226
+ const ours = await migrationsApplied(db, COMPANY_MIGRATIONS);
256
227
  if (!dbos || !ours) {
257
228
  const missing = [...(dbos ? [] : ["DBOS's"]), ...(ours ? [] : ["Sanoma's"])].join(" and ");
258
229
  throw new Error(`the database has no ${missing} tables yet: ${by} makes them, and this process never does`);
@@ -265,21 +236,22 @@ async function checkPrepared(databaseUrl, by) {
265
236
  /**
266
237
  * A connection to the database at `databaseUrl` (made first when missing) holding the
267
238
  * preparation's session lock until it ends, so a second process waits, then finds everything
268
- * made. Racing `DBOS.migrate`s lose to each other in many ways (40P01, XX000), so the race is
269
- * prevented rather than each loss forgiven. The lock is polled, never waited for by a blocked
270
- * statement: `CREATE INDEX CONCURRENTLY` waits on that statement's snapshot, a deadlock Postgres
271
- * cannot see (the lock's holder is this connection, not the migration's).
239
+ * made. Racing `DBOS.migrate`s lose to each other in many ways (40P01, XX000), and Drizzle's
240
+ * migrator takes no lock of its own, so the race is prevented rather than each loss forgiven.
241
+ * The lock is polled, never waited for by a blocked statement: `CREATE INDEX CONCURRENTLY` waits
242
+ * on that statement's snapshot, a deadlock Postgres cannot see (the lock's holder is this
243
+ * connection, not the migration's).
272
244
  */
273
245
  async function lockPreparation(databaseUrl) {
274
- const conn = await connectMaking(databaseUrl);
246
+ const db = databaseOn(await connectMaking(databaseUrl));
275
247
  try {
276
- const ask = "SELECT pg_try_advisory_lock(hashtext('sanoma.prepareDatabase')) AS locked";
277
- while (!(await conn.query(ask)).rows[0].locked)
248
+ const ask = sql `SELECT pg_try_advisory_lock(hashtext('sanoma.prepareDatabase')) AS locked`;
249
+ while ((await db.execute(ask)).rows[0]?.locked !== true)
278
250
  await delay(50);
279
- return conn;
251
+ return db;
280
252
  }
281
253
  catch (err) {
282
- await conn.end().catch(() => undefined);
254
+ await db.$client.end().catch(() => undefined);
283
255
  throw err;
284
256
  }
285
257
  }
@@ -309,7 +281,7 @@ async function createDatabase(databaseUrl) {
309
281
  url.pathname = "/postgres";
310
282
  const admin = await connect(url.toString());
311
283
  try {
312
- await admin.query(`CREATE DATABASE ${escapeIdentifier(name)}`);
284
+ await databaseOn(admin).execute(sql `CREATE DATABASE ${sql.identifier(name)}`);
313
285
  }
314
286
  catch (err) {
315
287
  if (!madeAlready(err))
@@ -327,13 +299,13 @@ async function createDatabase(databaseUrl) {
327
299
  */
328
300
  async function guardIdleTransactions(db) {
329
301
  try {
330
- await db.query(`DO $$ BEGIN
302
+ await db.execute(sql `DO $$ BEGIN
331
303
  IF current_setting('idle_in_transaction_session_timeout') = '0' AND NOT EXISTS (
332
304
  SELECT FROM pg_db_role_setting s JOIN pg_database d ON d.oid = s.setdatabase, unnest(s.setconfig) c
333
305
  WHERE d.datname = current_database() AND s.setrole = 0 AND c LIKE 'idle_in_transaction_session_timeout=%'
334
306
  ) THEN
335
307
  EXECUTE format('ALTER DATABASE %I SET idle_in_transaction_session_timeout = %L', current_database(),
336
- '${IDLE_IN_TRANSACTION_TIMEOUT}');
308
+ ${sql.raw(`'${IDLE_IN_TRANSACTION_TIMEOUT}'`)});
337
309
  END IF;
338
310
  END $$`);
339
311
  }
@@ -343,31 +315,19 @@ async function guardIdleTransactions(db) {
343
315
  }
344
316
  }
345
317
  /**
346
- * Runs `ddl` (`CREATE TABLE IF NOT EXISTS`, and the like) on `db`. Two processes racing to create
347
- * the same table both succeed; any other failure names the `what` table, with its cause.
318
+ * Marks a sealed invite request's `nonce` spent until `expiresAt`, when the row goes: true the
319
+ * first time, false for one spent already, whichever process asks. A row, not memory: the app
320
+ * keeps nothing across requests.
348
321
  */
349
- export async function createTable(db, ddl, what) {
350
- try {
351
- await db.query(ddl);
352
- }
353
- catch (err) {
354
- if (madeAlready(err))
355
- return;
356
- throw new Error(`could not prepare the ${what} table: ${errorMessage(err)}`, { cause: err });
357
- }
358
- }
359
- // The wakeup row's writes: one worker registers per instance (the supervisor runs one at a time,
360
- // and a deploy stops the old container before the new one starts), so none names a worker.
361
- /** Records that the wakeup took `at`. */
362
- export async function recordWakeupRegistration(db, at) {
363
- await db.query(`UPDATE ${WAKEUP_TABLE} SET at = $1, last_error = NULL WHERE id = 1`, [at]);
364
- }
365
- /** Records why the last registration failed. */
366
- export async function recordWakeupError(db, error) {
367
- await db.query(`UPDATE ${WAKEUP_TABLE} SET last_error = $1 WHERE id = 1`, [error]);
368
- }
369
- /** Records that the worker stops itself now. */
370
- export async function recordWakeupStop(db) {
371
- await db.query(`UPDATE ${WAKEUP_TABLE} SET stopped_at = now() WHERE id = 1`);
322
+ export async function spendInviteRequest(db, nonce, expiresAt) {
323
+ // Rows go an hour after they expire, not at it: the app's clock decides when a request is
324
+ // past, and a database clock ahead of it must not forget a nonce the app still accepts.
325
+ await db.delete(inviteRequests).where(lte(inviteRequests.expiresAt, sql `now() - interval '1 hour'`));
326
+ const spent = await db
327
+ .insert(inviteRequests)
328
+ .values({ nonce, expiresAt })
329
+ .onConflictDoNothing({ target: inviteRequests.nonce })
330
+ .returning({ nonce: inviteRequests.nonce });
331
+ return spent.length === 1;
372
332
  }
373
333
  //# sourceMappingURL=db.js.map
package/dist/db.js.map CHANGED
@@ -1 +1 @@
1
- {"version":3,"file":"db.js","sourceRoot":"","sources":["../src/db.ts"],"names":[],"mappings":"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"}
1
+ {"version":3,"file":"db.js","sourceRoot":"","sources":["../src/db.ts"],"names":[],"mappings":"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"}