@vibeorm/runtime 2.6.0 → 3.0.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/LICENSE +21 -0
- package/README.md +3 -1
- package/dist/adapter-kit/adapter-lifecycle.d.ts +79 -0
- package/dist/adapter-kit/deferred-control.d.ts +58 -0
- package/dist/adapter-kit/index.d.ts +10 -3
- package/dist/adapter-kit/index.js +317 -24
- package/dist/adapter-kit/index.js.map +10 -7
- package/dist/adapter-kit/nested-options.d.ts +16 -2
- package/dist/adapter-kit/row-changes.d.ts +15 -1
- package/dist/adapter-kit/savepoint-gate.d.ts +17 -3
- package/dist/adapter-kit/transaction-budget.d.ts +23 -13
- package/dist/adapter-kit/transaction-outcome.d.ts +167 -0
- package/dist/adapter.d.ts +103 -11
- package/dist/client.d.ts +7 -0
- package/dist/codecs.d.ts +35 -0
- package/dist/config.d.ts +15 -0
- package/dist/extensions.d.ts +10 -0
- package/dist/find-page.d.ts +9 -2
- package/dist/index.d.ts +8 -4
- package/dist/index.js +4086 -1295
- package/dist/index.js.map +40 -28
- package/dist/keyset-iterator.d.ts +12 -2
- package/dist/keyset.d.ts +65 -10
- package/dist/lateral-projection.d.ts +31 -1
- package/dist/model-meta.d.ts +12 -0
- package/dist/nested-fold.d.ts +98 -0
- package/dist/nested-update-data.d.ts +11 -0
- package/dist/nested-writes.d.ts +38 -1
- package/dist/query-builder.d.ts +78 -19
- package/dist/read-only.d.ts +5 -0
- package/dist/relation-key.d.ts +50 -0
- package/dist/relation-loader.d.ts +13 -1
- package/dist/relation-plan.d.ts +16 -0
- package/dist/strict-args.d.ts +1 -0
- package/dist/upsert-fold.d.ts +77 -0
- package/dist/write-scope.d.ts +9 -0
- package/package.json +7 -5
- package/dist/adapter-kit/index.d.ts.map +0 -1
- package/dist/adapter-kit/nested-options.d.ts.map +0 -1
- package/dist/adapter-kit/row-changes.d.ts.map +0 -1
- package/dist/adapter-kit/savepoint-gate.d.ts.map +0 -1
- package/dist/adapter-kit/savepoints.d.ts.map +0 -1
- package/dist/adapter-kit/session.d.ts.map +0 -1
- package/dist/adapter-kit/sqlite-session.d.ts.map +0 -1
- package/dist/adapter-kit/transaction-budget.d.ts.map +0 -1
- package/dist/adapter.d.ts.map +0 -1
- package/dist/advisory-key.d.ts.map +0 -1
- package/dist/advisory-lock.d.ts.map +0 -1
- package/dist/bulk-upsert.d.ts.map +0 -1
- package/dist/client-types.d.ts.map +0 -1
- package/dist/client.d.ts.map +0 -1
- package/dist/codecs.d.ts.map +0 -1
- package/dist/computed.d.ts.map +0 -1
- package/dist/database-module.d.ts.map +0 -1
- package/dist/db-now.d.ts.map +0 -1
- package/dist/diagnostics/index.d.ts.map +0 -1
- package/dist/diagnostics/insight.d.ts.map +0 -1
- package/dist/diagnostics/plan.d.ts.map +0 -1
- package/dist/diagnostics/preview.d.ts.map +0 -1
- package/dist/diagnostics/statement-diagnostics.d.ts.map +0 -1
- package/dist/diagnostics/types.d.ts.map +0 -1
- package/dist/diagnostics/workload.d.ts.map +0 -1
- package/dist/extensions.d.ts.map +0 -1
- package/dist/find-page.d.ts.map +0 -1
- package/dist/index.d.ts.map +0 -1
- package/dist/keyset-iterator.d.ts.map +0 -1
- package/dist/keyset-projection.d.ts.map +0 -1
- package/dist/keyset.d.ts.map +0 -1
- package/dist/lateral-projection.d.ts.map +0 -1
- package/dist/model-meta.d.ts.map +0 -1
- package/dist/module-context.d.ts.map +0 -1
- package/dist/nested-writes.d.ts.map +0 -1
- package/dist/policy-operation.d.ts.map +0 -1
- package/dist/policy.d.ts.map +0 -1
- package/dist/query-builder.d.ts.map +0 -1
- package/dist/read-only.d.ts.map +0 -1
- package/dist/relation-key.d.ts.map +0 -1
- package/dist/relation-loader.d.ts.map +0 -1
- package/dist/relation-plan.d.ts.map +0 -1
- package/dist/render-cache.d.ts.map +0 -1
- package/dist/rls-context.d.ts.map +0 -1
- package/dist/rls-readiness.d.ts.map +0 -1
- package/dist/scoped.d.ts.map +0 -1
- package/dist/sql-access.d.ts.map +0 -1
- package/dist/sql.d.ts.map +0 -1
- package/dist/strict-args.d.ts.map +0 -1
- package/dist/telemetry/collector.d.ts.map +0 -1
- package/dist/telemetry/config.d.ts.map +0 -1
- package/dist/telemetry/fingerprint.d.ts.map +0 -1
- package/dist/telemetry/index.d.ts.map +0 -1
- package/dist/telemetry/recorder.d.ts.map +0 -1
- package/dist/telemetry/statement.d.ts.map +0 -1
- package/dist/telemetry/types.d.ts.map +0 -1
- package/dist/transaction-row-changes.d.ts.map +0 -1
- package/dist/validators.d.ts.map +0 -1
- package/dist/views.d.ts.map +0 -1
- package/dist/write-scope.d.ts.map +0 -1
package/LICENSE
ADDED
|
@@ -0,0 +1,21 @@
|
|
|
1
|
+
MIT License
|
|
2
|
+
|
|
3
|
+
Copyright (c) 2026 VibeORM contributors
|
|
4
|
+
|
|
5
|
+
Permission is hereby granted, free of charge, to any person obtaining a copy
|
|
6
|
+
of this software and associated documentation files (the "Software"), to deal
|
|
7
|
+
in the Software without restriction, including without limitation the rights
|
|
8
|
+
to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
|
|
9
|
+
copies of the Software, and to permit persons to whom the Software is
|
|
10
|
+
furnished to do so, subject to the following conditions:
|
|
11
|
+
|
|
12
|
+
The above copyright notice and this permission notice shall be included in all
|
|
13
|
+
copies or substantial portions of the Software.
|
|
14
|
+
|
|
15
|
+
THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
|
|
16
|
+
IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
|
|
17
|
+
FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
|
|
18
|
+
AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
|
|
19
|
+
LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
|
|
20
|
+
OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
|
|
21
|
+
SOFTWARE.
|
package/README.md
CHANGED
|
@@ -26,7 +26,7 @@ Each `ModelDelegate` implements 16 methods:
|
|
|
26
26
|
| Delete | `delete` · `deleteMany` |
|
|
27
27
|
| Aggregate | `count` · `aggregate` · `groupBy` |
|
|
28
28
|
|
|
29
|
-
The statement-building pieces are exported too, for tooling that needs SQL without executing it: `buildQuery`, `compileWhere`, `compileSelect`, `compileOrderBy`, `resolveResultShape`, and the runtime metadata builders `buildRuntimeMeta`, `getModelMeta`, `getFieldMeta`.
|
|
29
|
+
The statement-building pieces are exported too, for tooling that needs SQL without executing it: `buildQuery`, `compileWhere`, `compileSelect`, `compileOrderBy`, `compileProjection`, `resolveResultShape`, and the runtime metadata builders `buildRuntimeMeta`, `getModelMeta`, `getFieldMeta`.
|
|
30
30
|
|
|
31
31
|
## The adapter contract
|
|
32
32
|
|
|
@@ -53,6 +53,7 @@ const adapter: DatabaseAdapter = {
|
|
|
53
53
|
- `formatArrayParam` converts a JS array into the driver's preferred scalar-array representation; the ORM path binds arrays through it, the raw path does not.
|
|
54
54
|
- The optional `wire` declaration (`WireFidelity`) tells the runtime what the driver already delivers for non-list scalars, so provably no-op decoders can be skipped.
|
|
55
55
|
- The optional `rowChanges()` member reports the surviving direct row changes of the adapter's active transaction as a number or `"unknown"`; it backs `transactionRowChanges`. An adapter without it reports `"unknown"`. The kit's `statementRowChanges`, `observeRowChanges` and `readRowChanges` implement it for the shipped adapters.
|
|
56
|
+
- The optional `transactionOutcome: "reported"` declaration says that a failed top-level `transaction()` records what happened beside the value it throws (commit outcome, whether `COMMIT` was sent, the cleanup `ROLLBACK`, the connection). An adapter reports through the kit's `settleFailedTransaction`, which applies the one commit-outcome rule; undeclared means no reports.
|
|
56
57
|
|
|
57
58
|
`toSqlExecutor({ adapter })` bridges an adapter to the `SqlExecutor` shape `@vibeorm/migrate` runs on.
|
|
58
59
|
|
|
@@ -60,6 +61,7 @@ const adapter: DatabaseAdapter = {
|
|
|
60
61
|
|
|
61
62
|
## Helpers for frameworks
|
|
62
63
|
|
|
64
|
+
- `transactionOutcomeOf({ error })` returns the facts of the failed top-level transaction that threw `error` (`commit`: `"not-committed"` or `"unknown"`, `commitSent`, `rollback`, `connection`), or `undefined` when there are none. The error itself is unchanged; branch on `adapter.transactionOutcome === "reported"`, never on an adapter name ([queries.md](https://github.com/vibeorm/vibeorm/blob/master/docs/queries.md#when-a-transaction-fails-transactionoutcomeof)).
|
|
63
65
|
- `transactionRowChanges({ db })` returns the direct row changes that survive in the transaction behind a handle, or `"unknown"` when some statement could not be observed ([queries.md](https://github.com/vibeorm/vibeorm/blob/master/docs/queries.md#rows-changed-so-far-transactionrowchanges)).
|
|
64
66
|
- `createDelegateMethodClassifier({ db })` returns `({ method, model? }) => "read" | "write" | undefined` for that handle's core and configured extension methods; `undefined` means denied ([queries.md](https://github.com/vibeorm/vibeorm/blob/master/docs/queries.md#read-only-clients-readonly)).
|
|
65
67
|
- `advisoryKeyOf({ text })` maps a string to a signed 64-bit `bigint` advisory-lock key (SHA-256 of the UTF-8 bytes, first eight bytes, big-endian). Different strings can map to the same key ([queries.md](https://github.com/vibeorm/vibeorm/blob/master/docs/queries.md#advisory-locks-advisorylock-tryadvisorylock)).
|
|
@@ -0,0 +1,79 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* The terminal lifetime of a root adapter (EPIC A2): `disconnect()` ends an
|
|
3
|
+
* adapter for good. ONE copy, shared by all six first-party adapters.
|
|
4
|
+
*
|
|
5
|
+
* - `admit` registers a root operation (statement, transaction, session,
|
|
6
|
+
* connect) synchronously, BEFORE it reaches its first await, and refuses
|
|
7
|
+
* with `VIBE_ADAPTER_CLOSED` once `disconnect()` was called. Admitted
|
|
8
|
+
* operations run independently: this is lifecycle accounting, not a queue —
|
|
9
|
+
* server statements stay concurrent.
|
|
10
|
+
* - `inCallback` marks a transaction/session callback as running, so the
|
|
11
|
+
* callback's own call of the root `disconnect()` refuses instead of waiting
|
|
12
|
+
* for itself to finish.
|
|
13
|
+
* - `disconnect` seals admission synchronously, waits until every admitted
|
|
14
|
+
* operation has settled (their callbacks may still issue child statements),
|
|
15
|
+
* then runs the adapter's cleanup once. Every later or concurrent call gets
|
|
16
|
+
* the same completion — success or failure — and admission never reopens.
|
|
17
|
+
*
|
|
18
|
+
* There is no timer, no cancellation and no scheduler: an unfinished admitted
|
|
19
|
+
* callback keeps `disconnect()` waiting. Stop producers and await pending work
|
|
20
|
+
* before closing.
|
|
21
|
+
*/
|
|
22
|
+
import { VibeError } from "@vibeorm/schema";
|
|
23
|
+
/** The adapter a lifecycle gate belongs to; carried as `meta.driver` by its refusals. */
|
|
24
|
+
export type AdapterLifecycleDriver = "pg" | "bun" | "mysql" | "pglite" | "sqlite" | "better-sqlite3";
|
|
25
|
+
/** One root adapter's terminal lifetime. */
|
|
26
|
+
export type AdapterLifecycleGate = {
|
|
27
|
+
/** Run a root operation, or refuse it with `VIBE_ADAPTER_CLOSED` once `disconnect()` was called. */
|
|
28
|
+
readonly admit: <T>(params: {
|
|
29
|
+
readonly run: () => Promise<T>;
|
|
30
|
+
}) => Promise<T>;
|
|
31
|
+
/** Run a transaction/session callback with this gate's active-callback marker set. */
|
|
32
|
+
readonly inCallback: <T>(params: {
|
|
33
|
+
readonly run: () => Promise<T>;
|
|
34
|
+
}) => Promise<T>;
|
|
35
|
+
/** Seal, drain admitted work, clean up once; every call shares the one completion. */
|
|
36
|
+
readonly disconnect: () => Promise<void>;
|
|
37
|
+
};
|
|
38
|
+
/** New root work on an adapter whose `disconnect()` was called. Fixed meta, never an address. */
|
|
39
|
+
export declare function adapterClosedError(params: {
|
|
40
|
+
readonly driver: AdapterLifecycleDriver;
|
|
41
|
+
readonly state: "closing" | "closed";
|
|
42
|
+
}): VibeError;
|
|
43
|
+
/** The root `disconnect()` called from inside one of its own running callbacks. */
|
|
44
|
+
export declare function disconnectInActiveCallbackError(params: {
|
|
45
|
+
readonly driver: AdapterLifecycleDriver;
|
|
46
|
+
}): VibeError;
|
|
47
|
+
/**
|
|
48
|
+
* `connect` / `disconnect` on a transaction handle (or `$connect` /
|
|
49
|
+
* `$disconnect` on a transaction client). The connection belongs to the
|
|
50
|
+
* transaction for its whole lifetime: reconnecting mid-transaction is
|
|
51
|
+
* meaningless and disconnecting would tear down an open transaction's own
|
|
52
|
+
* connection. The generated transaction type omits both; this refusal is the
|
|
53
|
+
* authority, because a type cannot stop a JavaScript caller.
|
|
54
|
+
*/
|
|
55
|
+
export declare function transactionLifecycleRefusal(params: {
|
|
56
|
+
readonly method: string;
|
|
57
|
+
}): VibeError;
|
|
58
|
+
/**
|
|
59
|
+
* Create the lifecycle gate of ONE root adapter. `cleanup` closes what the
|
|
60
|
+
* adapter owns (raw session, owned pool/instance/database) and is called at
|
|
61
|
+
* most once, after admitted work drained. `isConnectionReentrant` lets an
|
|
62
|
+
* embedded adapter report a running callback of the connection it shares with
|
|
63
|
+
* other wrappers; that callback's `disconnect()` refuses too.
|
|
64
|
+
*/
|
|
65
|
+
export declare function createAdapterLifecycleGate(params: {
|
|
66
|
+
readonly driver: AdapterLifecycleDriver;
|
|
67
|
+
readonly cleanup: () => Promise<void>;
|
|
68
|
+
readonly isConnectionReentrant?: () => boolean;
|
|
69
|
+
}): AdapterLifecycleGate;
|
|
70
|
+
/**
|
|
71
|
+
* The named shutdown-cleanup boundary of the adapters' `disconnect()`: run
|
|
72
|
+
* every step in order even when an earlier one failed (a failed raw-session
|
|
73
|
+
* rollback must still let the owned pool close), then reject with the FIRST
|
|
74
|
+
* failure, later failures attached as `meta.cleanupCause` evidence.
|
|
75
|
+
*/
|
|
76
|
+
export declare function runShutdownCleanup(params: {
|
|
77
|
+
readonly steps: readonly (() => Promise<void>)[];
|
|
78
|
+
}): Promise<void>;
|
|
79
|
+
//# sourceMappingURL=adapter-lifecycle.d.ts.map
|
|
@@ -0,0 +1,58 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Deferred transaction control (round-trip EPIC 6, pipelining).
|
|
3
|
+
*
|
|
4
|
+
* The opening of a transaction (`BEGIN …`, the `timeout` option's `SET LOCAL`)
|
|
5
|
+
* and every `SAVEPOINT` need no answer before the next statement may be sent:
|
|
6
|
+
* nothing in JavaScript reads their replies except error handling. An adapter
|
|
7
|
+
* that can put several statements on the wire at once (adapter-pg's one-Sync
|
|
8
|
+
* batch, adapter-bun's pipelined extended queries) therefore keeps them here
|
|
9
|
+
* and sends them AHEAD OF the next statement, in the same burst.
|
|
10
|
+
*
|
|
11
|
+
* Bookkeeping only — this module sends nothing and knows no driver:
|
|
12
|
+
* - {@link DeferredControl.take} hands the pending texts to the statement that
|
|
13
|
+
* is about to be sent; that statement carries them.
|
|
14
|
+
* - A transaction whose callback sends nothing never takes the opening, so the
|
|
15
|
+
* adapter sends neither `BEGIN` nor `COMMIT`/`ROLLBACK`
|
|
16
|
+
* ({@link DeferredControl.opened}).
|
|
17
|
+
* - A nested transaction whose body sends nothing never takes its `SAVEPOINT`,
|
|
18
|
+
* so its `RELEASE SAVEPOINT` / `ROLLBACK TO SAVEPOINT` are elided as well
|
|
19
|
+
* ({@link DeferredControl.routeSavepoint}). The savepoint gate's admission,
|
|
20
|
+
* sibling order and abort tracking are untouched: only WHEN the text leaves
|
|
21
|
+
* the client moves.
|
|
22
|
+
*
|
|
23
|
+
* ONE copy, shared by the postgres server adapters (constitution: adapter-kit).
|
|
24
|
+
*/
|
|
25
|
+
/** What the adapter does with one savepoint control text from the gate. */
|
|
26
|
+
export type SavepointControlRoute =
|
|
27
|
+
/** `SAVEPOINT x` queued: it rides with the next statement. */
|
|
28
|
+
"deferred"
|
|
29
|
+
/** The matching `SAVEPOINT` never left the client: send nothing. */
|
|
30
|
+
| "elided"
|
|
31
|
+
/** Send it now, as today. */
|
|
32
|
+
| "send";
|
|
33
|
+
/** Pending control texts of ONE top-level transaction (one connection). */
|
|
34
|
+
export type DeferredControl = {
|
|
35
|
+
/** True once the opening texts were handed out: the server has (or failed to open) the transaction. */
|
|
36
|
+
readonly opened: () => boolean;
|
|
37
|
+
/** Whether a control text waits to ride with the next statement. */
|
|
38
|
+
readonly hasPending: () => boolean;
|
|
39
|
+
/** Hand out every pending text in send order and empty the queue. */
|
|
40
|
+
readonly take: () => readonly string[];
|
|
41
|
+
/**
|
|
42
|
+
* Route a savepoint control text produced by `runNestedSavepoint`
|
|
43
|
+
* (`SAVEPOINT x`, `RELEASE SAVEPOINT x`, `ROLLBACK TO SAVEPOINT x`).
|
|
44
|
+
* Any other text routes to `"send"`.
|
|
45
|
+
*/
|
|
46
|
+
readonly routeSavepoint: (params: {
|
|
47
|
+
readonly text: string;
|
|
48
|
+
}) => SavepointControlRoute;
|
|
49
|
+
};
|
|
50
|
+
/**
|
|
51
|
+
* Start the bookkeeping for one top-level transaction. `opening` holds the
|
|
52
|
+
* texts that open it, in order (for example `["BEGIN", "SET LOCAL
|
|
53
|
+
* statement_timeout = 5000"]`); they stay pending until the first statement.
|
|
54
|
+
*/
|
|
55
|
+
export declare function createDeferredControl(params: {
|
|
56
|
+
readonly opening: readonly string[];
|
|
57
|
+
}): DeferredControl;
|
|
58
|
+
//# sourceMappingURL=deferred-control.d.ts.map
|
|
@@ -1,7 +1,8 @@
|
|
|
1
1
|
/**
|
|
2
2
|
* @vibeorm/runtime/adapter-kit — the transaction-safety helpers every driver
|
|
3
3
|
* adapter shares: savepoint naming, the savepoint lifetime gate (F14), the
|
|
4
|
-
* transaction budget (EPIC 6)
|
|
4
|
+
* transaction budget (EPIC 6), the nested-option refusal and the terminal
|
|
5
|
+
* adapter lifetime (EPIC A2: `disconnect()` ends an adapter for good).
|
|
5
6
|
*
|
|
6
7
|
* ONE copy. Each adapter imports from this subpath and re-exports the helpers
|
|
7
8
|
* it always offered, so a fix to the gate or the budget reaches every engine
|
|
@@ -15,10 +16,16 @@ export { createSavepointCounter, nextSavepointName } from "./savepoints.ts";
|
|
|
15
16
|
export type { SavepointCounter } from "./savepoints.ts";
|
|
16
17
|
export { abortTransactionOnServerFailure, createSavepointScope, isSavepointRollbackFailedError, isTransactionAbortedError, markTransactionAborted, markSavepointOpened, runNestedSavepoint, runRootScope, savepointRollbackFailedError, scopeTurn, transactionAbortedError, } from "./savepoint-gate.ts";
|
|
17
18
|
export type { AbortedTransaction, SavepointScope, SavepointState } from "./savepoint-gate.ts";
|
|
18
|
-
export { refuseNestedTransactionOptions } from "./nested-options.ts";
|
|
19
|
+
export { readOnlyRequested, refuseNestedTransactionOptions } from "./nested-options.ts";
|
|
20
|
+
export { createDeferredControl } from "./deferred-control.ts";
|
|
21
|
+
export type { DeferredControl, SavepointControlRoute } from "./deferred-control.ts";
|
|
19
22
|
export { DEFAULT_DEADLINE_CLOCK, engineStatementBudgetMs, isTransactionDeadlineError, startTransactionBudget, transactionClosedError, transactionDeadlineError, transactionOutcomeUnknownError, validateTransactionDeadline, } from "./transaction-budget.ts";
|
|
20
23
|
export type { BudgetStage, DeadlineClock, TransactionBudget, TransactionOutcome } from "./transaction-budget.ts";
|
|
21
|
-
export {
|
|
24
|
+
export { closeFailedTransactionBudget, failedCommitOutcome, recordTransactionOutcome, settleFailedTransaction, transactionOutcomeOf, } from "./transaction-outcome.ts";
|
|
25
|
+
export type { CommitProgress, ConnectionOutcome, RollbackOutcome, FailedCommitOutcome, TransactionOutcomeReport, } from "./transaction-outcome.ts";
|
|
26
|
+
export { ROW_CHANGES_COLUMN, dispatchSynchronousRowChanges, observeRowChanges, readRowChanges, statementRowChanges } from "./row-changes.ts";
|
|
22
27
|
export { runPinnedSession } from "./session.ts";
|
|
28
|
+
export { createAdapterLifecycleGate, runShutdownCleanup, transactionLifecycleRefusal } from "./adapter-lifecycle.ts";
|
|
29
|
+
export type { AdapterLifecycleDriver, AdapterLifecycleGate } from "./adapter-lifecycle.ts";
|
|
23
30
|
export { runSqliteSession } from "./sqlite-session.ts";
|
|
24
31
|
//# sourceMappingURL=index.d.ts.map
|