@kronos-ts/postgres 0.6.0 → 0.7.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
package/README.md CHANGED
@@ -94,9 +94,22 @@ import { pgAdapter } from "@kronos-ts/postgres/adapters/pg"
94
94
  const adapter = pgAdapter({
95
95
  connectionString: "postgresql://user:pass@host/db",
96
96
  poolConfig: { max: 10 }, // optional pg.Pool overrides
97
+ // Per-transaction safety timeouts, armed via SET LOCAL on every transaction
98
+ // this adapter opens. Defaults: 30s idle-in-transaction, statement off.
99
+ idleInTransactionTimeoutMs: 30_000, // 0 disables
100
+ statementTimeoutMs: 0, // opt in per deployment
97
101
  })
98
102
  ```
99
103
 
104
+ > **Safety timeouts live on the adapter.** Every transaction opened through the
105
+ > adapter (UoW-scoped commits, the event store's own-tx appends, the scheduler
106
+ > worker) is bounded, and each adapter instance is configured independently — so
107
+ > an event-store adapter and an event-processing adapter pointed at two
108
+ > different databases stay fully decoupled. `idleInTransactionTimeoutMs` is the
109
+ > important one: it stops a stalled transaction from pinning a connection (and
110
+ > `pg_snapshot_xmin`, which gates the tailing query) open indefinitely. The same
111
+ > two options are available on `postgresAdapter` and `bunSqlAdapter`.
112
+
100
113
  ### postgresAdapter
101
114
 
102
115
  ```typescript
@@ -16,7 +16,8 @@
16
16
  * a clear runtime error from the connect() call.
17
17
  */
18
18
  import type { PostgresAdapter } from "../adapter.js";
19
- export interface BunSqlAdapterConfig {
19
+ import { type SessionTimeoutOptions } from "../session-timeouts.js";
20
+ export interface BunSqlAdapterConfig extends SessionTimeoutOptions {
20
21
  readonly connectionString: string;
21
22
  }
22
23
  export declare function bunSqlAdapter(config: BunSqlAdapterConfig): PostgresAdapter;
@@ -1 +1 @@
1
- {"version":3,"file":"bun-sql.d.ts","sourceRoot":"","sources":["../../src/adapters/bun-sql.ts"],"names":[],"mappings":"AAAA;;;;;;;;;;;;;;;;GAgBG;AAEH,OAAO,KAAK,EACV,eAAe,EAIhB,MAAM,eAAe,CAAA;AAGtB,MAAM,WAAW,mBAAmB;IAClC,QAAQ,CAAC,gBAAgB,EAAE,MAAM,CAAA;CAClC;AA6ED,wBAAgB,aAAa,CAAC,MAAM,EAAE,mBAAmB,GAAG,eAAe,CA6H1E"}
1
+ {"version":3,"file":"bun-sql.d.ts","sourceRoot":"","sources":["../../src/adapters/bun-sql.ts"],"names":[],"mappings":"AAAA;;;;;;;;;;;;;;;;GAgBG;AAEH,OAAO,KAAK,EACV,eAAe,EAIhB,MAAM,eAAe,CAAA;AAEtB,OAAO,EACL,KAAK,qBAAqB,EAG3B,MAAM,wBAAwB,CAAA;AAE/B,MAAM,WAAW,mBAAoB,SAAQ,qBAAqB;IAChE,QAAQ,CAAC,gBAAgB,EAAE,MAAM,CAAA;CAClC;AA6ED,wBAAgB,aAAa,CAAC,MAAM,EAAE,mBAAmB,GAAG,eAAe,CAiI1E"}
@@ -16,6 +16,7 @@
16
16
  * a clear runtime error from the connect() call.
17
17
  */
18
18
  import { IsolationLevel } from "../adapter.js";
19
+ import { applySessionTimeouts, resolveSessionTimeouts, } from "../session-timeouts.js";
19
20
  /**
20
21
  * Bun.SQL surfaces SQLSTATE in `err.errno` (not `err.code`). The adapter
21
22
  * contract (D-12.12) requires SQLSTATE on `.code` so that `isDcbViolation(err)`
@@ -71,6 +72,7 @@ function getBunSql() {
71
72
  export function bunSqlAdapter(config) {
72
73
  let sql;
73
74
  let disconnected = false;
75
+ const timeouts = resolveSessionTimeouts(config);
74
76
  function getInstance() {
75
77
  if (!sql) {
76
78
  const SQL = getBunSql();
@@ -135,6 +137,9 @@ export function bunSqlAdapter(config) {
135
137
  return txSql.unsafe(text, normalizeParams(params)).catch(normalizeBunSqlError);
136
138
  },
137
139
  };
140
+ // Arm the per-transaction safety timeouts before handing the tx to the
141
+ // caller, so even the very first awaited statement is bounded.
142
+ await applySessionTimeouts(tx, timeouts);
138
143
  return fn(tx);
139
144
  }).catch(normalizeBunSqlError);
140
145
  },
@@ -1 +1 @@
1
- {"version":3,"file":"bun-sql.js","sourceRoot":"","sources":["../../src/adapters/bun-sql.ts"],"names":[],"mappings":"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"}
1
+ {"version":3,"file":"bun-sql.js","sourceRoot":"","sources":["../../src/adapters/bun-sql.ts"],"names":[],"mappings":"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"}
@@ -14,7 +14,8 @@
14
14
  */
15
15
  import { type PoolConfig } from "pg";
16
16
  import type { PostgresAdapter } from "../adapter.js";
17
- export interface PgAdapterConfig {
17
+ import { type SessionTimeoutOptions } from "../session-timeouts.js";
18
+ export interface PgAdapterConfig extends SessionTimeoutOptions {
18
19
  /** Standard libpq URI: postgresql://user:pass@host:port/db */
19
20
  readonly connectionString: string;
20
21
  /** Optional pg.Pool config overrides (max connections, idleTimeoutMillis, etc.). */
@@ -1 +1 @@
1
- {"version":3,"file":"pg.d.ts","sourceRoot":"","sources":["../../src/adapters/pg.ts"],"names":[],"mappings":"AAAA;;;;;;;;;;;;;GAaG;AAEH,OAAO,EAAyB,KAAK,UAAU,EAAE,MAAM,IAAI,CAAA;AAC3D,OAAO,KAAK,EACV,eAAe,EAIhB,MAAM,eAAe,CAAA;AAGtB,MAAM,WAAW,eAAe;IAC9B,8DAA8D;IAC9D,QAAQ,CAAC,gBAAgB,EAAE,MAAM,CAAA;IACjC,oFAAoF;IACpF,QAAQ,CAAC,UAAU,CAAC,EAAE,IAAI,CAAC,UAAU,EAAE,kBAAkB,CAAC,CAAA;CAC3D;AAOD,wBAAgB,SAAS,CAAC,MAAM,EAAE,eAAe,GAAG,eAAe,CA2JlE"}
1
+ {"version":3,"file":"pg.d.ts","sourceRoot":"","sources":["../../src/adapters/pg.ts"],"names":[],"mappings":"AAAA;;;;;;;;;;;;;GAaG;AAEH,OAAO,EAAyB,KAAK,UAAU,EAAE,MAAM,IAAI,CAAA;AAC3D,OAAO,KAAK,EACV,eAAe,EAIhB,MAAM,eAAe,CAAA;AAEtB,OAAO,EACL,KAAK,qBAAqB,EAG3B,MAAM,wBAAwB,CAAA;AAE/B,MAAM,WAAW,eAAgB,SAAQ,qBAAqB;IAC5D,8DAA8D;IAC9D,QAAQ,CAAC,gBAAgB,EAAE,MAAM,CAAA;IACjC,oFAAoF;IACpF,QAAQ,CAAC,UAAU,CAAC,EAAE,IAAI,CAAC,UAAU,EAAE,kBAAkB,CAAC,CAAA;CAC3D;AAOD,wBAAgB,SAAS,CAAC,MAAM,EAAE,eAAe,GAAG,eAAe,CA+JlE"}
@@ -14,11 +14,13 @@
14
14
  */
15
15
  import { Pool } from "pg";
16
16
  import { IsolationLevel } from "../adapter.js";
17
+ import { applySessionTimeouts, resolveSessionTimeouts, } from "../session-timeouts.js";
17
18
  export function pgAdapter(config) {
18
19
  let pool;
19
20
  let listenClient;
20
21
  const listenSlots = new Map();
21
22
  let disconnected = false;
23
+ const timeouts = resolveSessionTimeouts(config);
22
24
  function getPool() {
23
25
  if (!pool) {
24
26
  pool = new Pool({ connectionString: config.connectionString, ...config.poolConfig });
@@ -100,6 +102,9 @@ export function pgAdapter(config) {
100
102
  };
101
103
  let result;
102
104
  try {
105
+ // Arm the per-transaction safety timeouts before handing the tx to
106
+ // the caller, so even the very first awaited statement is bounded.
107
+ await applySessionTimeouts(tx, timeouts);
103
108
  result = await fn(tx);
104
109
  }
105
110
  catch (err) {
@@ -1 +1 @@
1
- {"version":3,"file":"pg.js","sourceRoot":"","sources":["../../src/adapters/pg.ts"],"names":[],"mappings":"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"}
1
+ {"version":3,"file":"pg.js","sourceRoot":"","sources":["../../src/adapters/pg.ts"],"names":[],"mappings":"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"}
@@ -18,7 +18,8 @@
18
18
  */
19
19
  import postgresClient from "postgres";
20
20
  import type { PostgresAdapter } from "../adapter.js";
21
- export interface PostgresAdapterConfig {
21
+ import { type SessionTimeoutOptions } from "../session-timeouts.js";
22
+ export interface PostgresAdapterConfig extends SessionTimeoutOptions {
22
23
  readonly connectionString: string;
23
24
  /** Additional postgres.js options. `transform.column.from` is forced off regardless. */
24
25
  readonly clientOptions?: Parameters<typeof postgresClient>[1];
@@ -1 +1 @@
1
- {"version":3,"file":"postgres.d.ts","sourceRoot":"","sources":["../../src/adapters/postgres.ts"],"names":[],"mappings":"AAAA;;;;;;;;;;;;;;;;;GAiBG;AAEH,OAAO,cAAc,MAAM,UAAU,CAAA;AAErC,OAAO,KAAK,EACV,eAAe,EAIhB,MAAM,eAAe,CAAA;AAGtB,MAAM,WAAW,qBAAqB;IACpC,QAAQ,CAAC,gBAAgB,EAAE,MAAM,CAAA;IACjC,wFAAwF;IACxF,QAAQ,CAAC,aAAa,CAAC,EAAE,UAAU,CAAC,OAAO,cAAc,CAAC,CAAC,CAAC,CAAC,CAAA;CAC9D;AAED,wBAAgB,eAAe,CAAC,MAAM,EAAE,qBAAqB,GAAG,eAAe,CAqG9E"}
1
+ {"version":3,"file":"postgres.d.ts","sourceRoot":"","sources":["../../src/adapters/postgres.ts"],"names":[],"mappings":"AAAA;;;;;;;;;;;;;;;;;GAiBG;AAEH,OAAO,cAAc,MAAM,UAAU,CAAA;AAErC,OAAO,KAAK,EACV,eAAe,EAIhB,MAAM,eAAe,CAAA;AAEtB,OAAO,EACL,KAAK,qBAAqB,EAG3B,MAAM,wBAAwB,CAAA;AAE/B,MAAM,WAAW,qBAAsB,SAAQ,qBAAqB;IAClE,QAAQ,CAAC,gBAAgB,EAAE,MAAM,CAAA;IACjC,wFAAwF;IACxF,QAAQ,CAAC,aAAa,CAAC,EAAE,UAAU,CAAC,OAAO,cAAc,CAAC,CAAC,CAAC,CAAC,CAAA;CAC9D;AAED,wBAAgB,eAAe,CAAC,MAAM,EAAE,qBAAqB,GAAG,eAAe,CAyG9E"}
@@ -18,9 +18,11 @@
18
18
  */
19
19
  import postgresClient from "postgres";
20
20
  import { IsolationLevel } from "../adapter.js";
21
+ import { applySessionTimeouts, resolveSessionTimeouts, } from "../session-timeouts.js";
21
22
  export function postgresAdapter(config) {
22
23
  let sql;
23
24
  let disconnected = false;
25
+ const timeouts = resolveSessionTimeouts(config);
24
26
  function getSql() {
25
27
  if (!sql) {
26
28
  sql = postgresClient(config.connectionString, {
@@ -82,6 +84,9 @@ export function postgresAdapter(config) {
82
84
  return rows;
83
85
  },
84
86
  };
87
+ // Arm the per-transaction safety timeouts before handing the tx to the
88
+ // caller, so even the very first awaited statement is bounded.
89
+ await applySessionTimeouts(tx, timeouts);
85
90
  return fn(tx);
86
91
  }));
87
92
  },
@@ -1 +1 @@
1
- {"version":3,"file":"postgres.js","sourceRoot":"","sources":["../../src/adapters/postgres.ts"],"names":[],"mappings":"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"}
1
+ {"version":3,"file":"postgres.js","sourceRoot":"","sources":["../../src/adapters/postgres.ts"],"names":[],"mappings":"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"}
package/dist/index.d.ts CHANGED
@@ -4,6 +4,7 @@ export { createPostgresEventStore, type PostgresEventStoreConfig, type Serialize
4
4
  export { createPostgresSnapshotStore, type PostgresSnapshotStoreConfig, } from "./postgres-snapshot-store.js";
5
5
  export { postgres, type PostgresConfig } from "./postgres.js";
6
6
  export { postgresTransactionManager } from "./postgres-transaction-manager.js";
7
+ export { type SessionTimeoutOptions, type ResolvedSessionTimeouts, resolveSessionTimeouts, applySessionTimeouts, } from "./session-timeouts.js";
7
8
  export { createPostgresEventScheduler, type PostgresEventScheduler, type PostgresEventSchedulerConfig, } from "./postgres-event-scheduler.js";
8
9
  export { bootstrapSchema, buildEventsTableDDL, buildEventsIndexesDDL, buildSnapshotsTableDDL, buildScheduledEventsTableDDL, buildScheduledEventsIndexesDDL, DEFAULT_TABLE_NAMES, type TableNames, } from "./schema.js";
9
10
  //# sourceMappingURL=index.d.ts.map
@@ -1 +1 @@
1
- {"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../src/index.ts"],"names":[],"mappings":"AAWA,OAAO,EACL,oBAAoB,EACpB,6BAA6B,EAC7B,cAAc,GACf,MAAM,aAAa,CAAA;AAKpB,OAAO,EACL,cAAc,EACd,KAAK,eAAe,EACpB,KAAK,0BAA0B,EAC/B,KAAK,kBAAkB,EACvB,KAAK,QAAQ,GACd,MAAM,cAAc,CAAA;AAGrB,OAAO,EACL,wBAAwB,EACxB,KAAK,wBAAwB,EAC7B,KAAK,UAAU,EACf,KAAK,WAAW,GACjB,MAAM,2BAA2B,CAAA;AAGlC,OAAO,EACL,2BAA2B,EAC3B,KAAK,2BAA2B,GACjC,MAAM,8BAA8B,CAAA;AAGrC,OAAO,EAAE,QAAQ,EAAE,KAAK,cAAc,EAAE,MAAM,eAAe,CAAA;AAM7D,OAAO,EAAE,0BAA0B,EAAE,MAAM,mCAAmC,CAAA;AAM9E,OAAO,EACL,4BAA4B,EAC5B,KAAK,sBAAsB,EAC3B,KAAK,4BAA4B,GAClC,MAAM,+BAA+B,CAAA;AAKtC,OAAO,EACL,eAAe,EACf,mBAAmB,EACnB,qBAAqB,EACrB,sBAAsB,EACtB,4BAA4B,EAC5B,8BAA8B,EAC9B,mBAAmB,EACnB,KAAK,UAAU,GAChB,MAAM,aAAa,CAAA"}
1
+ {"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../src/index.ts"],"names":[],"mappings":"AAWA,OAAO,EACL,oBAAoB,EACpB,6BAA6B,EAC7B,cAAc,GACf,MAAM,aAAa,CAAA;AAKpB,OAAO,EACL,cAAc,EACd,KAAK,eAAe,EACpB,KAAK,0BAA0B,EAC/B,KAAK,kBAAkB,EACvB,KAAK,QAAQ,GACd,MAAM,cAAc,CAAA;AAGrB,OAAO,EACL,wBAAwB,EACxB,KAAK,wBAAwB,EAC7B,KAAK,UAAU,EACf,KAAK,WAAW,GACjB,MAAM,2BAA2B,CAAA;AAGlC,OAAO,EACL,2BAA2B,EAC3B,KAAK,2BAA2B,GACjC,MAAM,8BAA8B,CAAA;AAGrC,OAAO,EAAE,QAAQ,EAAE,KAAK,cAAc,EAAE,MAAM,eAAe,CAAA;AAM7D,OAAO,EAAE,0BAA0B,EAAE,MAAM,mCAAmC,CAAA;AAK9E,OAAO,EACL,KAAK,qBAAqB,EAC1B,KAAK,uBAAuB,EAC5B,sBAAsB,EACtB,oBAAoB,GACrB,MAAM,uBAAuB,CAAA;AAM9B,OAAO,EACL,4BAA4B,EAC5B,KAAK,sBAAsB,EAC3B,KAAK,4BAA4B,GAClC,MAAM,+BAA+B,CAAA;AAKtC,OAAO,EACL,eAAe,EACf,mBAAmB,EACnB,qBAAqB,EACrB,sBAAsB,EACtB,4BAA4B,EAC5B,8BAA8B,EAC9B,mBAAmB,EACnB,KAAK,UAAU,GAChB,MAAM,aAAa,CAAA"}
package/dist/index.js CHANGED
@@ -24,6 +24,10 @@ export { postgres } from "./postgres.js";
24
24
  // `postgres(config)`; exported for direct use when composing UoW runners by
25
25
  // hand.
26
26
  export { postgresTransactionManager } from "./postgres-transaction-manager.js";
27
+ // Per-transaction safety timeouts (idle-in-transaction / statement), armed by
28
+ // each adapter's transaction() at BEGIN. The options are spread onto every
29
+ // adapter config; the helpers are exported for authors of custom adapters.
30
+ export { resolveSessionTimeouts, applySessionTimeouts, } from "./session-timeouts.js";
27
31
  // Postgres event scheduler — durable schedule() + cancel() + polling worker
28
32
  // that fires due schedules into the event store. Wired into postgres()
29
33
  // automatically when a uowFactory with the lazy postgres tx is in place;
package/dist/index.js.map CHANGED
@@ -1 +1 @@
1
- {"version":3,"file":"index.js","sourceRoot":"","sources":["../src/index.ts"],"names":[],"mappings":"AAAA,8CAA8C;AAC9C,EAAE;AACF,oEAAoE;AACpE,6EAA6E;AAC7E,mEAAmE;AACnE,yEAAyE;AACzE,EAAE;AACF,2EAA2E;AAC3E,0DAA0D;AAC1D,gEAAgE;AAEhE,OAAO,EACL,oBAAoB,EACpB,6BAA6B,EAC7B,cAAc,GACf,MAAM,aAAa,CAAA;AAEpB,uDAAuD;AACvD,uEAAuE;AACvE,8CAA8C;AAC9C,OAAO,EACL,cAAc,GAKf,MAAM,cAAc,CAAA;AAErB,iDAAiD;AACjD,OAAO,EACL,wBAAwB,GAIzB,MAAM,2BAA2B,CAAA;AAElC,mCAAmC;AACnC,OAAO,EACL,2BAA2B,GAE5B,MAAM,8BAA8B,CAAA;AAErC,8BAA8B;AAC9B,OAAO,EAAE,QAAQ,EAAuB,MAAM,eAAe,CAAA;AAE7D,6EAA6E;AAC7E,6EAA6E;AAC7E,4EAA4E;AAC5E,QAAQ;AACR,OAAO,EAAE,0BAA0B,EAAE,MAAM,mCAAmC,CAAA;AAE9E,4EAA4E;AAC5E,uEAAuE;AACvE,yEAAyE;AACzE,yEAAyE;AACzE,OAAO,EACL,4BAA4B,GAG7B,MAAM,+BAA+B,CAAA;AAEtC,4EAA4E;AAC5E,2EAA2E;AAC3E,wDAAwD;AACxD,OAAO,EACL,eAAe,EACf,mBAAmB,EACnB,qBAAqB,EACrB,sBAAsB,EACtB,4BAA4B,EAC5B,8BAA8B,EAC9B,mBAAmB,GAEpB,MAAM,aAAa,CAAA"}
1
+ {"version":3,"file":"index.js","sourceRoot":"","sources":["../src/index.ts"],"names":[],"mappings":"AAAA,8CAA8C;AAC9C,EAAE;AACF,oEAAoE;AACpE,6EAA6E;AAC7E,mEAAmE;AACnE,yEAAyE;AACzE,EAAE;AACF,2EAA2E;AAC3E,0DAA0D;AAC1D,gEAAgE;AAEhE,OAAO,EACL,oBAAoB,EACpB,6BAA6B,EAC7B,cAAc,GACf,MAAM,aAAa,CAAA;AAEpB,uDAAuD;AACvD,uEAAuE;AACvE,8CAA8C;AAC9C,OAAO,EACL,cAAc,GAKf,MAAM,cAAc,CAAA;AAErB,iDAAiD;AACjD,OAAO,EACL,wBAAwB,GAIzB,MAAM,2BAA2B,CAAA;AAElC,mCAAmC;AACnC,OAAO,EACL,2BAA2B,GAE5B,MAAM,8BAA8B,CAAA;AAErC,8BAA8B;AAC9B,OAAO,EAAE,QAAQ,EAAuB,MAAM,eAAe,CAAA;AAE7D,6EAA6E;AAC7E,6EAA6E;AAC7E,4EAA4E;AAC5E,QAAQ;AACR,OAAO,EAAE,0BAA0B,EAAE,MAAM,mCAAmC,CAAA;AAE9E,8EAA8E;AAC9E,2EAA2E;AAC3E,2EAA2E;AAC3E,OAAO,EAGL,sBAAsB,EACtB,oBAAoB,GACrB,MAAM,uBAAuB,CAAA;AAE9B,4EAA4E;AAC5E,uEAAuE;AACvE,yEAAyE;AACzE,yEAAyE;AACzE,OAAO,EACL,4BAA4B,GAG7B,MAAM,+BAA+B,CAAA;AAEtC,4EAA4E;AAC5E,2EAA2E;AAC3E,wDAAwD;AACxD,OAAO,EACL,eAAe,EACf,mBAAmB,EACnB,qBAAqB,EACrB,sBAAsB,EACtB,4BAA4B,EAC5B,8BAA8B,EAC9B,mBAAmB,GAEpB,MAAM,aAAa,CAAA"}
@@ -14,26 +14,7 @@
14
14
  import { type TransactionManager } from "@kronos-ts/messaging";
15
15
  import type { PostgresAdapter, PostgresAdapterTransaction } from "./adapter.js";
16
16
  import { IsolationLevel } from "./adapter.js";
17
- /** Tuning for the safety timeouts applied to every UoW-scoped transaction. */
18
- export interface PostgresTransactionManagerOptions {
19
- /**
20
- * `idle_in_transaction_session_timeout` (ms) applied via `SET LOCAL` on every
21
- * transaction. A UoW that begins a tx but stalls before commit/rollback would
22
- * otherwise hold its connection — and pin `pg_snapshot_xmin`, which gates the
23
- * gap-free tailing query in the event store — open indefinitely, stalling all
24
- * streaming processors until the process restarts. This bounds that window:
25
- * postgres aborts the idle transaction and the connection (and xmin) is freed.
26
- * Default 30000 (30s). Set 0 to disable (postgres default — no timeout).
27
- */
28
- readonly idleInTransactionTimeoutMs?: number;
29
- /**
30
- * `statement_timeout` (ms) applied via `SET LOCAL` on every transaction.
31
- * Bounds a single hung statement inside the tx. Default 0 (disabled) — large
32
- * appends / replays can legitimately run long, so opt in per deployment.
33
- */
34
- readonly statementTimeoutMs?: number;
35
- }
36
- export declare function postgresTransactionManager(adapter: PostgresAdapter, isolationLevel?: IsolationLevel, options?: PostgresTransactionManagerOptions): TransactionManager<PostgresAdapterTransaction>;
17
+ export declare function postgresTransactionManager(adapter: PostgresAdapter, isolationLevel?: IsolationLevel): TransactionManager<PostgresAdapterTransaction>;
37
18
  /**
38
19
  * Run `fn` inside a postgres tx, joining a UoW-scoped tx if one is active
39
20
  * (or installed lazily), otherwise opening an ad-hoc tx via `adapter.transaction`.
@@ -1 +1 @@
1
- {"version":3,"file":"postgres-transaction-manager.d.ts","sourceRoot":"","sources":["../src/postgres-transaction-manager.ts"],"names":[],"mappings":"AAAA;;;;;;;;;;;;GAYG;AAEH,OAAO,EAA+B,KAAK,kBAAkB,EAAE,MAAM,sBAAsB,CAAA;AAC3F,OAAO,KAAK,EAAE,eAAe,EAAE,0BAA0B,EAAE,MAAM,cAAc,CAAA;AAC/E,OAAO,EAAE,cAAc,EAAE,MAAM,cAAc,CAAA;AAsB7C,8EAA8E;AAC9E,MAAM,WAAW,iCAAiC;IAChD;;;;;;;;OAQG;IACH,QAAQ,CAAC,0BAA0B,CAAC,EAAE,MAAM,CAAA;IAC5C;;;;OAIG;IACH,QAAQ,CAAC,kBAAkB,CAAC,EAAE,MAAM,CAAA;CACrC;AAID,wBAAgB,0BAA0B,CACxC,OAAO,EAAE,eAAe,EACxB,cAAc,GAAE,cAA8C,EAC9D,OAAO,GAAE,iCAAsC,GAC9C,kBAAkB,CAAC,0BAA0B,CAAC,CAyFhD;AASD;;;;;;;;;;;;;GAaG;AACH,wBAAsB,iBAAiB,CAAC,CAAC,EACvC,OAAO,EAAE,eAAe,EACxB,EAAE,EAAE,CAAC,EAAE,EAAE,0BAA0B,KAAK,OAAO,CAAC,CAAC,CAAC,EAClD,cAAc,GAAE,cAA8C,GAC7D,OAAO,CAAC,CAAC,CAAC,CAIZ"}
1
+ {"version":3,"file":"postgres-transaction-manager.d.ts","sourceRoot":"","sources":["../src/postgres-transaction-manager.ts"],"names":[],"mappings":"AAAA;;;;;;;;;;;;GAYG;AAEH,OAAO,EAA+B,KAAK,kBAAkB,EAAE,MAAM,sBAAsB,CAAA;AAC3F,OAAO,KAAK,EAAE,eAAe,EAAE,0BAA0B,EAAE,MAAM,cAAc,CAAA;AAC/E,OAAO,EAAE,cAAc,EAAE,MAAM,cAAc,CAAA;AAsB7C,wBAAgB,0BAA0B,CACxC,OAAO,EAAE,eAAe,EACxB,cAAc,GAAE,cAA8C,GAC7D,kBAAkB,CAAC,0BAA0B,CAAC,CAuEhD;AAED;;;;;;;;;;;;;GAaG;AACH,wBAAsB,iBAAiB,CAAC,CAAC,EACvC,OAAO,EAAE,eAAe,EACxB,EAAE,EAAE,CAAC,EAAE,EAAE,0BAA0B,KAAK,OAAO,CAAC,CAAC,CAAC,EAClD,cAAc,GAAE,cAA8C,GAC7D,OAAO,CAAC,CAAC,CAAC,CAIZ"}
@@ -21,22 +21,7 @@ import { IsolationLevel } from "./adapter.js";
21
21
  const TX_CONTROL = Symbol("kronos.postgresTxControl");
22
22
  /** Marker error: signals an intentional rollback so the .catch can suppress it. */
23
23
  const ROLLBACK_MARKER = "__kronos_postgres_tx_rollback__";
24
- const DEFAULT_IDLE_IN_TRANSACTION_TIMEOUT_MS = 30_000;
25
- export function postgresTransactionManager(adapter, isolationLevel = IsolationLevel.READ_COMMITTED, options = {}) {
26
- const idleTimeoutMs = normalizeTimeoutMs(options.idleInTransactionTimeoutMs ?? DEFAULT_IDLE_IN_TRANSACTION_TIMEOUT_MS);
27
- const statementTimeoutMs = normalizeTimeoutMs(options.statementTimeoutMs ?? 0);
28
- // GUCs cannot be parameterized ($1) — the value is a config-supplied integer,
29
- // normalized to a non-negative whole number, so inlining is injection-safe.
30
- // SET LOCAL auto-resets at COMMIT/ROLLBACK, so it never leaks onto pooled
31
- // connections.
32
- async function applyTimeouts(tx) {
33
- if (idleTimeoutMs > 0) {
34
- await tx.query(`SET LOCAL idle_in_transaction_session_timeout = ${idleTimeoutMs}`);
35
- }
36
- if (statementTimeoutMs > 0) {
37
- await tx.query(`SET LOCAL statement_timeout = ${statementTimeoutMs}`);
38
- }
39
- }
24
+ export function postgresTransactionManager(adapter, isolationLevel = IsolationLevel.READ_COMMITTED) {
40
25
  return {
41
26
  async begin() {
42
27
  let captureTx;
@@ -51,9 +36,9 @@ export function postgresTransactionManager(adapter, isolationLevel = IsolationLe
51
36
  });
52
37
  const txPromise = adapter
53
38
  .transaction(isolationLevel, async (tx) => {
54
- // Arm the per-transaction safety timeouts before handing the tx to
55
- // the UoW, so even the very first awaited statement is bounded.
56
- await applyTimeouts(tx);
39
+ // Per-transaction safety timeouts are armed by the adapter's
40
+ // transaction() at BEGIN (see session-timeouts.ts), so they cover
41
+ // this UoW-scoped tx and every ad-hoc adapter.transaction() alike.
57
42
  captureTx(tx);
58
43
  await completion;
59
44
  })
@@ -98,13 +83,6 @@ export function postgresTransactionManager(adapter, isolationLevel = IsolationLe
98
83
  },
99
84
  };
100
85
  }
101
- /** Coerce a config timeout to a non-negative whole number of milliseconds.
102
- * Non-finite or negative values disable the timeout (treated as 0). */
103
- function normalizeTimeoutMs(value) {
104
- if (!Number.isFinite(value) || value <= 0)
105
- return 0;
106
- return Math.floor(value);
107
- }
108
86
  /**
109
87
  * Run `fn` inside a postgres tx, joining a UoW-scoped tx if one is active
110
88
  * (or installed lazily), otherwise opening an ad-hoc tx via `adapter.transaction`.
@@ -1 +1 @@
1
- {"version":3,"file":"postgres-transaction-manager.js","sourceRoot":"","sources":["../src/postgres-transaction-manager.ts"],"names":[],"mappings":"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"}
1
+ {"version":3,"file":"postgres-transaction-manager.js","sourceRoot":"","sources":["../src/postgres-transaction-manager.ts"],"names":[],"mappings":"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"}
@@ -46,14 +46,6 @@ export interface PostgresConfig {
46
46
  readonly pollIntervalMs?: number;
47
47
  readonly batchSize?: number;
48
48
  };
49
- /** Safety timeouts applied via `SET LOCAL` to every UoW-scoped transaction.
50
- * Guards against a stalled UoW holding a connection — and pinning
51
- * `pg_snapshot_xmin`, which would stall all streaming tailing — open until
52
- * restart. Defaults: 30s idle-in-transaction, statement timeout disabled. */
53
- readonly transaction?: {
54
- readonly idleInTransactionTimeoutMs?: number;
55
- readonly statementTimeoutMs?: number;
56
- };
57
49
  }
58
50
  export declare function postgres(config: PostgresConfig): (app: App) => void;
59
51
  //# sourceMappingURL=postgres.d.ts.map
@@ -1 +1 @@
1
- {"version":3,"file":"postgres.d.ts","sourceRoot":"","sources":["../src/postgres.ts"],"names":[],"mappings":"AAAA;;;;;;;;;;;;;;;;;;;;;;;;;;;GA2BG;AAEH,OAAO,KAAK,EAAE,GAAG,EAAE,MAAM,gBAAgB,CAAA;AACzC,OAAO,KAAK,EAAE,gBAAgB,EAAE,MAAM,mBAAmB,CAAA;AAMzD,OAAO,KAAK,EAAE,eAAe,EAAE,MAAM,cAAc,CAAA;AAQnD,OAAO,EAAwC,KAAK,UAAU,EAAE,MAAM,aAAa,CAAA;AAEnF,MAAM,WAAW,cAAc;IAC7B,8EAA8E;IAC9E,QAAQ,CAAC,OAAO,EAAE,eAAe,CAAA;IACjC;uCACmC;IACnC,QAAQ,CAAC,SAAS,CAAC,EAAE,OAAO,CAAA;IAC5B,uEAAuE;IACvE,QAAQ,CAAC,UAAU,CAAC,EAAE,UAAU,CAAA;IAChC;4CACwC;IACxC,QAAQ,CAAC,UAAU,CAAC,EAAE,OAAO,CAAC,gBAAgB,CAAC,CAAA;IAC/C,yDAAyD;IACzD,QAAQ,CAAC,SAAS,CAAC,EAAE;QACnB,QAAQ,CAAC,cAAc,CAAC,EAAE,MAAM,CAAA;QAChC,QAAQ,CAAC,SAAS,CAAC,EAAE,MAAM,CAAA;KAC5B,CAAA;IACD;;;kFAG8E;IAC9E,QAAQ,CAAC,WAAW,CAAC,EAAE;QACrB,QAAQ,CAAC,0BAA0B,CAAC,EAAE,MAAM,CAAA;QAC5C,QAAQ,CAAC,kBAAkB,CAAC,EAAE,MAAM,CAAA;KACrC,CAAA;CACF;AAED,wBAAgB,QAAQ,CAAC,MAAM,EAAE,cAAc,GAAG,CAAC,GAAG,EAAE,GAAG,KAAK,IAAI,CAgEnE"}
1
+ {"version":3,"file":"postgres.d.ts","sourceRoot":"","sources":["../src/postgres.ts"],"names":[],"mappings":"AAAA;;;;;;;;;;;;;;;;;;;;;;;;;;;GA2BG;AAEH,OAAO,KAAK,EAAE,GAAG,EAAE,MAAM,gBAAgB,CAAA;AACzC,OAAO,KAAK,EAAE,gBAAgB,EAAE,MAAM,mBAAmB,CAAA;AAMzD,OAAO,KAAK,EAAE,eAAe,EAAE,MAAM,cAAc,CAAA;AAQnD,OAAO,EAAwC,KAAK,UAAU,EAAE,MAAM,aAAa,CAAA;AAEnF,MAAM,WAAW,cAAc;IAC7B,8EAA8E;IAC9E,QAAQ,CAAC,OAAO,EAAE,eAAe,CAAA;IACjC;uCACmC;IACnC,QAAQ,CAAC,SAAS,CAAC,EAAE,OAAO,CAAA;IAC5B,uEAAuE;IACvE,QAAQ,CAAC,UAAU,CAAC,EAAE,UAAU,CAAA;IAChC;4CACwC;IACxC,QAAQ,CAAC,UAAU,CAAC,EAAE,OAAO,CAAC,gBAAgB,CAAC,CAAA;IAC/C,yDAAyD;IACzD,QAAQ,CAAC,SAAS,CAAC,EAAE;QACnB,QAAQ,CAAC,cAAc,CAAC,EAAE,MAAM,CAAA;QAChC,QAAQ,CAAC,SAAS,CAAC,EAAE,MAAM,CAAA;KAC5B,CAAA;CACF;AAED,wBAAgB,QAAQ,CAAC,MAAM,EAAE,cAAc,GAAG,CAAC,GAAG,EAAE,GAAG,KAAK,IAAI,CAoEnE"}
package/dist/postgres.js CHANGED
@@ -37,7 +37,11 @@ export function postgres(config) {
37
37
  const { adapter, resilience } = config;
38
38
  const bootstrap = config.bootstrap ?? true;
39
39
  const tables = config.tableNames ?? DEFAULT_TABLE_NAMES;
40
- const txManager = postgresTransactionManager(adapter, undefined, config.transaction);
40
+ // Safety timeouts (idle-in-transaction / statement) are armed by the adapter
41
+ // itself — configure them on the adapter (e.g. `pgAdapter({ connectionString,
42
+ // idleInTransactionTimeoutMs })`), so every transaction through it is bounded
43
+ // and two adapters on two databases stay independently configured.
44
+ const txManager = postgresTransactionManager(adapter);
41
45
  return (app) => {
42
46
  app.set("eventStore", ({ serializer, tagResolver }) => createPostgresEventStore({ adapter, serializer, tagResolver, tableNames: tables }));
43
47
  app.set("snapshotStore", ({ serializer }) => createPostgresSnapshotStore({ adapter, serializer, tableNames: tables }));
@@ -1 +1 @@
1
- {"version":3,"file":"postgres.js","sourceRoot":"","sources":["../src/postgres.ts"],"names":[],"mappings":"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"}
1
+ {"version":3,"file":"postgres.js","sourceRoot":"","sources":["../src/postgres.ts"],"names":[],"mappings":"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"}
@@ -0,0 +1,47 @@
1
+ /**
2
+ * Per-transaction safety timeouts, armed via `SET LOCAL` by each adapter's
3
+ * `transaction()` at BEGIN. Living on the adapter (not the transaction
4
+ * manager) means EVERY postgres transaction is bounded — UoW-scoped commits,
5
+ * the event store's own-tx append/publish, and the scheduler worker tick alike
6
+ * — and each adapter instance carries its own settings, so two adapters
7
+ * pointed at two different databases stay fully decoupled.
8
+ *
9
+ * A non-postgres adapter (e.g. a future sqlite one) arms its own
10
+ * dialect-appropriate settings, or none.
11
+ */
12
+ import type { PostgresAdapterTransaction } from "./adapter.js";
13
+ export interface SessionTimeoutOptions {
14
+ /**
15
+ * `idle_in_transaction_session_timeout` (ms) applied via `SET LOCAL` on every
16
+ * transaction. A transaction that begins but stalls before commit/rollback
17
+ * would otherwise hold its connection — and pin `pg_snapshot_xmin`, which
18
+ * gates the gap-free tailing query in the event store — open indefinitely,
19
+ * stalling all streaming processors until the process restarts. This bounds
20
+ * that window: postgres aborts the idle transaction and the connection (and
21
+ * xmin) is freed. Default 30000 (30s). Set 0 to disable (postgres default).
22
+ */
23
+ readonly idleInTransactionTimeoutMs?: number;
24
+ /**
25
+ * `statement_timeout` (ms) applied via `SET LOCAL` on every transaction.
26
+ * Bounds a single hung statement inside the tx. Default 0 (disabled) — large
27
+ * appends / replays can legitimately run long, so opt in per deployment.
28
+ */
29
+ readonly statementTimeoutMs?: number;
30
+ }
31
+ export interface ResolvedSessionTimeouts {
32
+ readonly idleInTransactionTimeoutMs: number;
33
+ readonly statementTimeoutMs: number;
34
+ }
35
+ /** Resolve config to concrete, normalized timeouts (applying defaults). */
36
+ export declare function resolveSessionTimeouts(opts?: SessionTimeoutOptions): ResolvedSessionTimeouts;
37
+ /**
38
+ * Arm the resolved timeouts on a freshly-opened transaction. No-op for any
39
+ * timeout resolved to 0.
40
+ *
41
+ * GUCs cannot be parameterized ($1) — the value is a config-supplied integer,
42
+ * normalized to a non-negative whole number, so inlining is injection-safe.
43
+ * `SET LOCAL` auto-resets at COMMIT/ROLLBACK, so it never leaks onto pooled
44
+ * connections.
45
+ */
46
+ export declare function applySessionTimeouts(tx: PostgresAdapterTransaction, timeouts: ResolvedSessionTimeouts): Promise<void>;
47
+ //# sourceMappingURL=session-timeouts.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"session-timeouts.d.ts","sourceRoot":"","sources":["../src/session-timeouts.ts"],"names":[],"mappings":"AAAA;;;;;;;;;;GAUG;AAEH,OAAO,KAAK,EAAE,0BAA0B,EAAE,MAAM,cAAc,CAAA;AAE9D,MAAM,WAAW,qBAAqB;IACpC;;;;;;;;OAQG;IACH,QAAQ,CAAC,0BAA0B,CAAC,EAAE,MAAM,CAAA;IAC5C;;;;OAIG;IACH,QAAQ,CAAC,kBAAkB,CAAC,EAAE,MAAM,CAAA;CACrC;AAED,MAAM,WAAW,uBAAuB;IACtC,QAAQ,CAAC,0BAA0B,EAAE,MAAM,CAAA;IAC3C,QAAQ,CAAC,kBAAkB,EAAE,MAAM,CAAA;CACpC;AAID,2EAA2E;AAC3E,wBAAgB,sBAAsB,CAAC,IAAI,CAAC,EAAE,qBAAqB,GAAG,uBAAuB,CAO5F;AAED;;;;;;;;GAQG;AACH,wBAAsB,oBAAoB,CACxC,EAAE,EAAE,0BAA0B,EAC9B,QAAQ,EAAE,uBAAuB,GAChC,OAAO,CAAC,IAAI,CAAC,CAOf"}
@@ -0,0 +1,44 @@
1
+ /**
2
+ * Per-transaction safety timeouts, armed via `SET LOCAL` by each adapter's
3
+ * `transaction()` at BEGIN. Living on the adapter (not the transaction
4
+ * manager) means EVERY postgres transaction is bounded — UoW-scoped commits,
5
+ * the event store's own-tx append/publish, and the scheduler worker tick alike
6
+ * — and each adapter instance carries its own settings, so two adapters
7
+ * pointed at two different databases stay fully decoupled.
8
+ *
9
+ * A non-postgres adapter (e.g. a future sqlite one) arms its own
10
+ * dialect-appropriate settings, or none.
11
+ */
12
+ const DEFAULT_IDLE_IN_TRANSACTION_TIMEOUT_MS = 30_000;
13
+ /** Resolve config to concrete, normalized timeouts (applying defaults). */
14
+ export function resolveSessionTimeouts(opts) {
15
+ return {
16
+ idleInTransactionTimeoutMs: normalizeTimeoutMs(opts?.idleInTransactionTimeoutMs ?? DEFAULT_IDLE_IN_TRANSACTION_TIMEOUT_MS),
17
+ statementTimeoutMs: normalizeTimeoutMs(opts?.statementTimeoutMs ?? 0),
18
+ };
19
+ }
20
+ /**
21
+ * Arm the resolved timeouts on a freshly-opened transaction. No-op for any
22
+ * timeout resolved to 0.
23
+ *
24
+ * GUCs cannot be parameterized ($1) — the value is a config-supplied integer,
25
+ * normalized to a non-negative whole number, so inlining is injection-safe.
26
+ * `SET LOCAL` auto-resets at COMMIT/ROLLBACK, so it never leaks onto pooled
27
+ * connections.
28
+ */
29
+ export async function applySessionTimeouts(tx, timeouts) {
30
+ if (timeouts.idleInTransactionTimeoutMs > 0) {
31
+ await tx.query(`SET LOCAL idle_in_transaction_session_timeout = ${timeouts.idleInTransactionTimeoutMs}`);
32
+ }
33
+ if (timeouts.statementTimeoutMs > 0) {
34
+ await tx.query(`SET LOCAL statement_timeout = ${timeouts.statementTimeoutMs}`);
35
+ }
36
+ }
37
+ /** Coerce a config timeout to a non-negative whole number of milliseconds.
38
+ * Non-finite or negative values disable the timeout (treated as 0). */
39
+ function normalizeTimeoutMs(value) {
40
+ if (!Number.isFinite(value) || value <= 0)
41
+ return 0;
42
+ return Math.floor(value);
43
+ }
44
+ //# sourceMappingURL=session-timeouts.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"session-timeouts.js","sourceRoot":"","sources":["../src/session-timeouts.ts"],"names":[],"mappings":"AAAA;;;;;;;;;;GAUG;AA4BH,MAAM,sCAAsC,GAAG,MAAM,CAAA;AAErD,2EAA2E;AAC3E,MAAM,UAAU,sBAAsB,CAAC,IAA4B;IACjE,OAAO;QACL,0BAA0B,EAAE,kBAAkB,CAC5C,IAAI,EAAE,0BAA0B,IAAI,sCAAsC,CAC3E;QACD,kBAAkB,EAAE,kBAAkB,CAAC,IAAI,EAAE,kBAAkB,IAAI,CAAC,CAAC;KACtE,CAAA;AACH,CAAC;AAED;;;;;;;;GAQG;AACH,MAAM,CAAC,KAAK,UAAU,oBAAoB,CACxC,EAA8B,EAC9B,QAAiC;IAEjC,IAAI,QAAQ,CAAC,0BAA0B,GAAG,CAAC,EAAE,CAAC;QAC5C,MAAM,EAAE,CAAC,KAAK,CAAC,mDAAmD,QAAQ,CAAC,0BAA0B,EAAE,CAAC,CAAA;IAC1G,CAAC;IACD,IAAI,QAAQ,CAAC,kBAAkB,GAAG,CAAC,EAAE,CAAC;QACpC,MAAM,EAAE,CAAC,KAAK,CAAC,iCAAiC,QAAQ,CAAC,kBAAkB,EAAE,CAAC,CAAA;IAChF,CAAC;AACH,CAAC;AAED;wEACwE;AACxE,SAAS,kBAAkB,CAAC,KAAa;IACvC,IAAI,CAAC,MAAM,CAAC,QAAQ,CAAC,KAAK,CAAC,IAAI,KAAK,IAAI,CAAC;QAAE,OAAO,CAAC,CAAA;IACnD,OAAO,IAAI,CAAC,KAAK,CAAC,KAAK,CAAC,CAAA;AAC1B,CAAC"}
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@kronos-ts/postgres",
3
- "version": "0.6.0",
3
+ "version": "0.7.0",
4
4
  "description": "PostgreSQL extension for Kronos — event store and snapshot store adapters.",
5
5
  "license": "Apache-2.0",
6
6
  "type": "module",
@@ -68,9 +68,9 @@
68
68
  },
69
69
  "dependencies": {
70
70
  "@kronos-ts/common": "0.1.1",
71
- "@kronos-ts/app": "0.4.1",
72
- "@kronos-ts/eventsourcing": "0.2.3",
73
- "@kronos-ts/messaging": "0.7.0"
71
+ "@kronos-ts/app": "0.5.0",
72
+ "@kronos-ts/eventsourcing": "0.3.0",
73
+ "@kronos-ts/messaging": "0.8.0"
74
74
  },
75
75
  "peerDependencies": {
76
76
  "pg": ">=8.0.0",
@@ -23,8 +23,13 @@ import type {
23
23
  QueryRow,
24
24
  } from "../adapter.js"
25
25
  import { IsolationLevel } from "../adapter.js"
26
+ import {
27
+ type SessionTimeoutOptions,
28
+ applySessionTimeouts,
29
+ resolveSessionTimeouts,
30
+ } from "../session-timeouts.js"
26
31
 
27
- export interface BunSqlAdapterConfig {
32
+ export interface BunSqlAdapterConfig extends SessionTimeoutOptions {
28
33
  readonly connectionString: string
29
34
  }
30
35
 
@@ -106,6 +111,7 @@ function getBunSql(): BunSqlConstructor {
106
111
  export function bunSqlAdapter(config: BunSqlAdapterConfig): PostgresAdapter {
107
112
  let sql: BunSqlInstance | undefined
108
113
  let disconnected = false
114
+ const timeouts = resolveSessionTimeouts(config)
109
115
 
110
116
  function getInstance(): BunSqlInstance {
111
117
  if (!sql) {
@@ -183,6 +189,9 @@ export function bunSqlAdapter(config: BunSqlAdapterConfig): PostgresAdapter {
183
189
  return txSql.unsafe(text, normalizeParams(params)).catch(normalizeBunSqlError) as Promise<R[]>
184
190
  },
185
191
  }
192
+ // Arm the per-transaction safety timeouts before handing the tx to the
193
+ // caller, so even the very first awaited statement is bounded.
194
+ await applySessionTimeouts(tx, timeouts)
186
195
  return fn(tx)
187
196
  }).catch(normalizeBunSqlError)
188
197
  },
@@ -21,8 +21,13 @@ import type {
21
21
  QueryRow,
22
22
  } from "../adapter.js"
23
23
  import { IsolationLevel } from "../adapter.js"
24
+ import {
25
+ type SessionTimeoutOptions,
26
+ applySessionTimeouts,
27
+ resolveSessionTimeouts,
28
+ } from "../session-timeouts.js"
24
29
 
25
- export interface PgAdapterConfig {
30
+ export interface PgAdapterConfig extends SessionTimeoutOptions {
26
31
  /** Standard libpq URI: postgresql://user:pass@host:port/db */
27
32
  readonly connectionString: string
28
33
  /** Optional pg.Pool config overrides (max connections, idleTimeoutMillis, etc.). */
@@ -39,6 +44,7 @@ export function pgAdapter(config: PgAdapterConfig): PostgresAdapter {
39
44
  let listenClient: PoolClient | undefined
40
45
  const listenSlots = new Map<string, Set<ListenerSlot>>()
41
46
  let disconnected = false
47
+ const timeouts = resolveSessionTimeouts(config)
42
48
 
43
49
  function getPool(): Pool {
44
50
  if (!pool) {
@@ -132,6 +138,9 @@ export function pgAdapter(config: PgAdapterConfig): PostgresAdapter {
132
138
  }
133
139
  let result: T
134
140
  try {
141
+ // Arm the per-transaction safety timeouts before handing the tx to
142
+ // the caller, so even the very first awaited statement is bounded.
143
+ await applySessionTimeouts(tx, timeouts)
135
144
  result = await fn(tx)
136
145
  } catch (err) {
137
146
  // ROLLBACK best-effort; preserve the ORIGINAL error.
@@ -26,8 +26,13 @@ import type {
26
26
  QueryRow,
27
27
  } from "../adapter.js"
28
28
  import { IsolationLevel } from "../adapter.js"
29
+ import {
30
+ type SessionTimeoutOptions,
31
+ applySessionTimeouts,
32
+ resolveSessionTimeouts,
33
+ } from "../session-timeouts.js"
29
34
 
30
- export interface PostgresAdapterConfig {
35
+ export interface PostgresAdapterConfig extends SessionTimeoutOptions {
31
36
  readonly connectionString: string
32
37
  /** Additional postgres.js options. `transform.column.from` is forced off regardless. */
33
38
  readonly clientOptions?: Parameters<typeof postgresClient>[1]
@@ -36,6 +41,7 @@ export interface PostgresAdapterConfig {
36
41
  export function postgresAdapter(config: PostgresAdapterConfig): PostgresAdapter {
37
42
  let sql: Sql | undefined
38
43
  let disconnected = false
44
+ const timeouts = resolveSessionTimeouts(config)
39
45
 
40
46
  function getSql(): Sql {
41
47
  if (!sql) {
@@ -112,6 +118,9 @@ export function postgresAdapter(config: PostgresAdapterConfig): PostgresAdapter
112
118
  return rows
113
119
  },
114
120
  }
121
+ // Arm the per-transaction safety timeouts before handing the tx to the
122
+ // caller, so even the very first awaited statement is bounded.
123
+ await applySessionTimeouts(tx, timeouts)
115
124
  return fn(tx)
116
125
  })) as T
117
126
  },
package/src/index.ts CHANGED
@@ -49,6 +49,16 @@ export { postgres, type PostgresConfig } from "./postgres.js"
49
49
  // hand.
50
50
  export { postgresTransactionManager } from "./postgres-transaction-manager.js"
51
51
 
52
+ // Per-transaction safety timeouts (idle-in-transaction / statement), armed by
53
+ // each adapter's transaction() at BEGIN. The options are spread onto every
54
+ // adapter config; the helpers are exported for authors of custom adapters.
55
+ export {
56
+ type SessionTimeoutOptions,
57
+ type ResolvedSessionTimeouts,
58
+ resolveSessionTimeouts,
59
+ applySessionTimeouts,
60
+ } from "./session-timeouts.js"
61
+
52
62
  // Postgres event scheduler — durable schedule() + cancel() + polling worker
53
63
  // that fires due schedules into the event store. Wired into postgres()
54
64
  // automatically when a uowFactory with the lazy postgres tx is in place;
@@ -36,51 +36,10 @@ interface ManagedPostgresTransaction extends PostgresAdapterTransaction {
36
36
  /** Marker error: signals an intentional rollback so the .catch can suppress it. */
37
37
  const ROLLBACK_MARKER = "__kronos_postgres_tx_rollback__"
38
38
 
39
- /** Tuning for the safety timeouts applied to every UoW-scoped transaction. */
40
- export interface PostgresTransactionManagerOptions {
41
- /**
42
- * `idle_in_transaction_session_timeout` (ms) applied via `SET LOCAL` on every
43
- * transaction. A UoW that begins a tx but stalls before commit/rollback would
44
- * otherwise hold its connection — and pin `pg_snapshot_xmin`, which gates the
45
- * gap-free tailing query in the event store — open indefinitely, stalling all
46
- * streaming processors until the process restarts. This bounds that window:
47
- * postgres aborts the idle transaction and the connection (and xmin) is freed.
48
- * Default 30000 (30s). Set 0 to disable (postgres default — no timeout).
49
- */
50
- readonly idleInTransactionTimeoutMs?: number
51
- /**
52
- * `statement_timeout` (ms) applied via `SET LOCAL` on every transaction.
53
- * Bounds a single hung statement inside the tx. Default 0 (disabled) — large
54
- * appends / replays can legitimately run long, so opt in per deployment.
55
- */
56
- readonly statementTimeoutMs?: number
57
- }
58
-
59
- const DEFAULT_IDLE_IN_TRANSACTION_TIMEOUT_MS = 30_000
60
-
61
39
  export function postgresTransactionManager(
62
40
  adapter: PostgresAdapter,
63
41
  isolationLevel: IsolationLevel = IsolationLevel.READ_COMMITTED,
64
- options: PostgresTransactionManagerOptions = {},
65
42
  ): TransactionManager<PostgresAdapterTransaction> {
66
- const idleTimeoutMs = normalizeTimeoutMs(
67
- options.idleInTransactionTimeoutMs ?? DEFAULT_IDLE_IN_TRANSACTION_TIMEOUT_MS,
68
- )
69
- const statementTimeoutMs = normalizeTimeoutMs(options.statementTimeoutMs ?? 0)
70
-
71
- // GUCs cannot be parameterized ($1) — the value is a config-supplied integer,
72
- // normalized to a non-negative whole number, so inlining is injection-safe.
73
- // SET LOCAL auto-resets at COMMIT/ROLLBACK, so it never leaks onto pooled
74
- // connections.
75
- async function applyTimeouts(tx: PostgresAdapterTransaction): Promise<void> {
76
- if (idleTimeoutMs > 0) {
77
- await tx.query(`SET LOCAL idle_in_transaction_session_timeout = ${idleTimeoutMs}`)
78
- }
79
- if (statementTimeoutMs > 0) {
80
- await tx.query(`SET LOCAL statement_timeout = ${statementTimeoutMs}`)
81
- }
82
- }
83
-
84
43
  return {
85
44
  async begin(): Promise<PostgresAdapterTransaction> {
86
45
  let captureTx!: (tx: PostgresAdapterTransaction) => void
@@ -97,9 +56,9 @@ export function postgresTransactionManager(
97
56
 
98
57
  const txPromise = adapter
99
58
  .transaction(isolationLevel, async (tx) => {
100
- // Arm the per-transaction safety timeouts before handing the tx to
101
- // the UoW, so even the very first awaited statement is bounded.
102
- await applyTimeouts(tx)
59
+ // Per-transaction safety timeouts are armed by the adapter's
60
+ // transaction() at BEGIN (see session-timeouts.ts), so they cover
61
+ // this UoW-scoped tx and every ad-hoc adapter.transaction() alike.
103
62
  captureTx(tx)
104
63
  await completion
105
64
  })
@@ -153,13 +112,6 @@ export function postgresTransactionManager(
153
112
  }
154
113
  }
155
114
 
156
- /** Coerce a config timeout to a non-negative whole number of milliseconds.
157
- * Non-finite or negative values disable the timeout (treated as 0). */
158
- function normalizeTimeoutMs(value: number): number {
159
- if (!Number.isFinite(value) || value <= 0) return 0
160
- return Math.floor(value)
161
- }
162
-
163
115
  /**
164
116
  * Run `fn` inside a postgres tx, joining a UoW-scoped tx if one is active
165
117
  * (or installed lazily), otherwise opening an ad-hoc tx via `adapter.transaction`.
package/src/postgres.ts CHANGED
@@ -60,14 +60,6 @@ export interface PostgresConfig {
60
60
  readonly pollIntervalMs?: number
61
61
  readonly batchSize?: number
62
62
  }
63
- /** Safety timeouts applied via `SET LOCAL` to every UoW-scoped transaction.
64
- * Guards against a stalled UoW holding a connection — and pinning
65
- * `pg_snapshot_xmin`, which would stall all streaming tailing — open until
66
- * restart. Defaults: 30s idle-in-transaction, statement timeout disabled. */
67
- readonly transaction?: {
68
- readonly idleInTransactionTimeoutMs?: number
69
- readonly statementTimeoutMs?: number
70
- }
71
63
  }
72
64
 
73
65
  export function postgres(config: PostgresConfig): (app: App) => void {
@@ -75,7 +67,11 @@ export function postgres(config: PostgresConfig): (app: App) => void {
75
67
  const bootstrap = config.bootstrap ?? true
76
68
  const tables = config.tableNames ?? DEFAULT_TABLE_NAMES
77
69
 
78
- const txManager = postgresTransactionManager(adapter, undefined, config.transaction)
70
+ // Safety timeouts (idle-in-transaction / statement) are armed by the adapter
71
+ // itself — configure them on the adapter (e.g. `pgAdapter({ connectionString,
72
+ // idleInTransactionTimeoutMs })`), so every transaction through it is bounded
73
+ // and two adapters on two databases stay independently configured.
74
+ const txManager = postgresTransactionManager(adapter)
79
75
 
80
76
  return (app: App) => {
81
77
  app.set("eventStore", ({ serializer, tagResolver }) =>
@@ -0,0 +1,77 @@
1
+ /**
2
+ * Per-transaction safety timeouts, armed via `SET LOCAL` by each adapter's
3
+ * `transaction()` at BEGIN. Living on the adapter (not the transaction
4
+ * manager) means EVERY postgres transaction is bounded — UoW-scoped commits,
5
+ * the event store's own-tx append/publish, and the scheduler worker tick alike
6
+ * — and each adapter instance carries its own settings, so two adapters
7
+ * pointed at two different databases stay fully decoupled.
8
+ *
9
+ * A non-postgres adapter (e.g. a future sqlite one) arms its own
10
+ * dialect-appropriate settings, or none.
11
+ */
12
+
13
+ import type { PostgresAdapterTransaction } from "./adapter.js"
14
+
15
+ export interface SessionTimeoutOptions {
16
+ /**
17
+ * `idle_in_transaction_session_timeout` (ms) applied via `SET LOCAL` on every
18
+ * transaction. A transaction that begins but stalls before commit/rollback
19
+ * would otherwise hold its connection — and pin `pg_snapshot_xmin`, which
20
+ * gates the gap-free tailing query in the event store — open indefinitely,
21
+ * stalling all streaming processors until the process restarts. This bounds
22
+ * that window: postgres aborts the idle transaction and the connection (and
23
+ * xmin) is freed. Default 30000 (30s). Set 0 to disable (postgres default).
24
+ */
25
+ readonly idleInTransactionTimeoutMs?: number
26
+ /**
27
+ * `statement_timeout` (ms) applied via `SET LOCAL` on every transaction.
28
+ * Bounds a single hung statement inside the tx. Default 0 (disabled) — large
29
+ * appends / replays can legitimately run long, so opt in per deployment.
30
+ */
31
+ readonly statementTimeoutMs?: number
32
+ }
33
+
34
+ export interface ResolvedSessionTimeouts {
35
+ readonly idleInTransactionTimeoutMs: number
36
+ readonly statementTimeoutMs: number
37
+ }
38
+
39
+ const DEFAULT_IDLE_IN_TRANSACTION_TIMEOUT_MS = 30_000
40
+
41
+ /** Resolve config to concrete, normalized timeouts (applying defaults). */
42
+ export function resolveSessionTimeouts(opts?: SessionTimeoutOptions): ResolvedSessionTimeouts {
43
+ return {
44
+ idleInTransactionTimeoutMs: normalizeTimeoutMs(
45
+ opts?.idleInTransactionTimeoutMs ?? DEFAULT_IDLE_IN_TRANSACTION_TIMEOUT_MS,
46
+ ),
47
+ statementTimeoutMs: normalizeTimeoutMs(opts?.statementTimeoutMs ?? 0),
48
+ }
49
+ }
50
+
51
+ /**
52
+ * Arm the resolved timeouts on a freshly-opened transaction. No-op for any
53
+ * timeout resolved to 0.
54
+ *
55
+ * GUCs cannot be parameterized ($1) — the value is a config-supplied integer,
56
+ * normalized to a non-negative whole number, so inlining is injection-safe.
57
+ * `SET LOCAL` auto-resets at COMMIT/ROLLBACK, so it never leaks onto pooled
58
+ * connections.
59
+ */
60
+ export async function applySessionTimeouts(
61
+ tx: PostgresAdapterTransaction,
62
+ timeouts: ResolvedSessionTimeouts,
63
+ ): Promise<void> {
64
+ if (timeouts.idleInTransactionTimeoutMs > 0) {
65
+ await tx.query(`SET LOCAL idle_in_transaction_session_timeout = ${timeouts.idleInTransactionTimeoutMs}`)
66
+ }
67
+ if (timeouts.statementTimeoutMs > 0) {
68
+ await tx.query(`SET LOCAL statement_timeout = ${timeouts.statementTimeoutMs}`)
69
+ }
70
+ }
71
+
72
+ /** Coerce a config timeout to a non-negative whole number of milliseconds.
73
+ * Non-finite or negative values disable the timeout (treated as 0). */
74
+ function normalizeTimeoutMs(value: number): number {
75
+ if (!Number.isFinite(value) || value <= 0) return 0
76
+ return Math.floor(value)
77
+ }