rado 1.0.5 → 1.0.7
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/dist/core/Database.d.ts +8 -4
- package/dist/core/Database.js +8 -4
- package/dist/core/Driver.d.ts +3 -2
- package/dist/core/Query.d.ts +1 -1
- package/dist/core/Query.js +2 -2
- package/dist/core/Sql.d.ts +2 -1
- package/dist/core/Sql.js +8 -1
- package/dist/core/expr/Conditions.js +9 -7
- package/dist/driver/better-sqlite3.js +11 -7
- package/dist/driver/bun-sqlite.js +11 -7
- package/dist/driver/sql.js.js +8 -10
- package/dist/sqlite/functions.d.ts +1 -5
- package/dist/sqlite/functions.js +0 -2
- package/dist/sqlite/transactions.d.ts +3 -0
- package/dist/sqlite/transactions.js +35 -0
- package/dist/universal/functions.d.ts +1 -1
- package/dist/universal/functions.js +9 -5
- package/package.json +1 -1
package/dist/core/Database.d.ts
CHANGED
|
@@ -8,6 +8,7 @@ import { QueryBatch } from './Query.js';
|
|
|
8
8
|
import { Resolver } from './Resolver.js';
|
|
9
9
|
import type { Table } from './Table.js';
|
|
10
10
|
export declare class Database<Meta extends QueryMeta = Either> extends Builder<Meta> implements HasResolver<Meta> {
|
|
11
|
+
#private;
|
|
11
12
|
driver: Driver;
|
|
12
13
|
dialect: Dialect;
|
|
13
14
|
diff: Diff;
|
|
@@ -26,17 +27,20 @@ export declare class Database<Meta extends QueryMeta = Either> extends Builder<M
|
|
|
26
27
|
transaction<T>(this: Database<Async>, run: (tx: Transaction<Meta>) => Promise<T>, options?: TransactionOptions[Meta['dialect']]): Promise<T>;
|
|
27
28
|
transaction<T>(run: (tx: Transaction<Meta>) => T | Promise<T>, options?: TransactionOptions[Meta['dialect']]): Deliver<Meta, T>;
|
|
28
29
|
}
|
|
30
|
+
export interface TransactionUniversalOptions {
|
|
31
|
+
async?: boolean;
|
|
32
|
+
}
|
|
29
33
|
export interface TransactionOptions {
|
|
30
|
-
universal:
|
|
31
|
-
sqlite: {
|
|
34
|
+
universal: TransactionUniversalOptions;
|
|
35
|
+
sqlite: TransactionUniversalOptions & {
|
|
32
36
|
behavior?: 'deferred' | 'immediate' | 'exclusive';
|
|
33
37
|
};
|
|
34
|
-
postgres: {
|
|
38
|
+
postgres: TransactionUniversalOptions & {
|
|
35
39
|
isolationLevel?: 'read uncommitted' | 'read committed' | 'repeatable read' | 'serializable';
|
|
36
40
|
accessMode?: 'read only' | 'read write';
|
|
37
41
|
deferrable?: boolean;
|
|
38
42
|
};
|
|
39
|
-
mysql: {
|
|
43
|
+
mysql: TransactionUniversalOptions & {
|
|
40
44
|
isolationLevel?: 'read uncommitted' | 'read committed' | 'repeatable read' | 'serializable';
|
|
41
45
|
accessMode?: 'read only' | 'read write';
|
|
42
46
|
withConsistentSnapshot?: boolean;
|
package/dist/core/Database.js
CHANGED
|
@@ -64,11 +64,15 @@ var Database = class extends Builder {
|
|
|
64
64
|
throw new Error("Query has parameters");
|
|
65
65
|
return this.driver.exec(emitter.sql);
|
|
66
66
|
}
|
|
67
|
+
#transactionLock;
|
|
67
68
|
transaction(run, options = {}) {
|
|
68
|
-
return this.driver.transaction(
|
|
69
|
-
|
|
70
|
-
|
|
71
|
-
|
|
69
|
+
return this.driver.transaction(
|
|
70
|
+
(inner) => {
|
|
71
|
+
const tx = new Transaction(inner, this.dialect, this.diff);
|
|
72
|
+
return run(tx);
|
|
73
|
+
},
|
|
74
|
+
{ async: run.constructor.name === "AsyncFunction", ...options }
|
|
75
|
+
);
|
|
72
76
|
}
|
|
73
77
|
};
|
|
74
78
|
var Rollback = class extends Error {
|
package/dist/core/Driver.d.ts
CHANGED
|
@@ -1,3 +1,4 @@
|
|
|
1
|
+
import type { TransactionUniversalOptions } from './Database.js';
|
|
1
2
|
export type Driver = SyncDriver | AsyncDriver;
|
|
2
3
|
export type Statement = SyncStatement | AsyncStatement;
|
|
3
4
|
export interface BatchQuery {
|
|
@@ -16,7 +17,7 @@ export interface SyncDriver extends DriverSpecs {
|
|
|
16
17
|
close(): void;
|
|
17
18
|
exec(query: string): void;
|
|
18
19
|
prepare(query: string, options?: PrepareOptions): SyncStatement;
|
|
19
|
-
transaction<T>(run: (inner: SyncDriver) => T, options:
|
|
20
|
+
transaction<T>(run: (inner: SyncDriver) => T, options: TransactionUniversalOptions): T;
|
|
20
21
|
batch(queries: Array<BatchQuery>): Array<Array<unknown>>;
|
|
21
22
|
}
|
|
22
23
|
export interface SyncStatement {
|
|
@@ -30,7 +31,7 @@ export interface AsyncDriver extends DriverSpecs {
|
|
|
30
31
|
close(): Promise<void>;
|
|
31
32
|
exec(query: string): Promise<void>;
|
|
32
33
|
prepare(query: string, options?: PrepareOptions): AsyncStatement;
|
|
33
|
-
transaction<T>(run: (inner: AsyncDriver) => Promise<T>, options:
|
|
34
|
+
transaction<T>(run: (inner: AsyncDriver) => Promise<T>, options: TransactionUniversalOptions): Promise<T>;
|
|
34
35
|
batch(queries: Array<BatchQuery>): Promise<Array<Array<unknown>>>;
|
|
35
36
|
}
|
|
36
37
|
export interface AsyncStatement {
|
package/dist/core/Query.d.ts
CHANGED
|
@@ -32,7 +32,7 @@ export declare abstract class Query<Result, Meta extends QueryMeta> extends Exec
|
|
|
32
32
|
get(db?: HasResolver): Deliver<Meta, Result | null>;
|
|
33
33
|
run(db?: HasResolver): Deliver<Meta, void>;
|
|
34
34
|
prepare<Inputs extends Record<string, unknown>>(name?: string): PreparedQuery<Result, Inputs, Meta>;
|
|
35
|
-
toSQL(): {
|
|
35
|
+
toSQL(db?: HasResolver): {
|
|
36
36
|
sql: string;
|
|
37
37
|
params: Array<unknown>;
|
|
38
38
|
};
|
package/dist/core/Query.js
CHANGED
|
@@ -80,8 +80,8 @@ var Query = class extends Executable {
|
|
|
80
80
|
prepare(name) {
|
|
81
81
|
return getData(this).resolver.prepare(this, name);
|
|
82
82
|
}
|
|
83
|
-
toSQL() {
|
|
84
|
-
const
|
|
83
|
+
toSQL(db) {
|
|
84
|
+
const resolver = db ? getResolver(db) : getData(this).resolver;
|
|
85
85
|
if (!resolver)
|
|
86
86
|
throw new Error("Query has no resolver");
|
|
87
87
|
return resolver.toSQL(this);
|
package/dist/core/Sql.d.ts
CHANGED
|
@@ -29,6 +29,7 @@ export declare class Sql<Value = unknown> implements HasSql<Value> {
|
|
|
29
29
|
field(field: FieldData): Sql<Value>;
|
|
30
30
|
add(sql: HasSql): Sql<Value>;
|
|
31
31
|
value(value: unknown): Sql<Value>;
|
|
32
|
+
getValue(): Value | undefined;
|
|
32
33
|
inline(value: unknown): Sql<Value>;
|
|
33
34
|
jsonPath(path: Array<string | number>): Sql<Value>;
|
|
34
35
|
placeholder(name: string): Sql<Value>;
|
|
@@ -48,7 +49,7 @@ export declare namespace sql {
|
|
|
48
49
|
export function identifier<T>(identifier: string): Sql<T>;
|
|
49
50
|
export function field<T>(field: FieldData): Sql<T>;
|
|
50
51
|
export function chunk<Type extends keyof EmitMethods>(type: Type, inner: Parameters<EmitMethods[Type]>[0]): Sql;
|
|
51
|
-
export function universal(runtimes: Partial<Record<Runtime | 'default', Sql
|
|
52
|
+
export function universal<T>(runtimes: Partial<Record<Runtime | 'default', Sql<T>>>): Sql<T>;
|
|
52
53
|
type QueryChunk = HasSql | undefined;
|
|
53
54
|
export function query(ast: Record<string, boolean | QueryChunk | Array<QueryChunk>>): Sql;
|
|
54
55
|
export function join<T>(items: Array<Sql | HasSql | undefined | false>, separator?: Sql): Sql<T>;
|
package/dist/core/Sql.js
CHANGED
|
@@ -46,6 +46,13 @@ var Sql = class _Sql {
|
|
|
46
46
|
value(value) {
|
|
47
47
|
return this.chunk("emitValue", value);
|
|
48
48
|
}
|
|
49
|
+
getValue() {
|
|
50
|
+
if (this.#chunks.length !== 1)
|
|
51
|
+
return;
|
|
52
|
+
const chunk = this.#chunks[0];
|
|
53
|
+
if (chunk?.type === "emitValue")
|
|
54
|
+
return chunk.inner;
|
|
55
|
+
}
|
|
49
56
|
inline(value) {
|
|
50
57
|
return this.chunk("emitInline", value);
|
|
51
58
|
}
|
|
@@ -141,7 +148,7 @@ function sql(strings, ...inner) {
|
|
|
141
148
|
}
|
|
142
149
|
sql2.chunk = chunk;
|
|
143
150
|
function universal(runtimes) {
|
|
144
|
-
return chunk("emitUniversal", runtimes);
|
|
151
|
+
return empty().chunk("emitUniversal", runtimes);
|
|
145
152
|
}
|
|
146
153
|
sql2.universal = universal;
|
|
147
154
|
function query(ast) {
|
|
@@ -1,5 +1,5 @@
|
|
|
1
1
|
// src/core/expr/Conditions.ts
|
|
2
|
-
import { getQuery } from "../Internal.js";
|
|
2
|
+
import { getQuery, getSql, hasSql } from "../Internal.js";
|
|
3
3
|
import { sql } from "../Sql.js";
|
|
4
4
|
import { input } from "./Input.js";
|
|
5
5
|
function bool(impl) {
|
|
@@ -41,19 +41,21 @@ function not(condition) {
|
|
|
41
41
|
return bool(sql`not ${input(condition)}`);
|
|
42
42
|
}
|
|
43
43
|
function inArray(left, right) {
|
|
44
|
-
|
|
45
|
-
|
|
44
|
+
const value = (hasSql(right) ? getSql(right).getValue() : void 0) ?? right;
|
|
45
|
+
if (Array.isArray(value)) {
|
|
46
|
+
if (value.length === 0)
|
|
46
47
|
return sql`false`;
|
|
47
|
-
return bool(sql`${input(left)} in (${sql.join(
|
|
48
|
+
return bool(sql`${input(left)} in (${sql.join(value.map(input), sql`, `)})`);
|
|
48
49
|
}
|
|
49
50
|
return bool(sql`${input(left)} in ${input(right)}`);
|
|
50
51
|
}
|
|
51
52
|
function notInArray(left, right) {
|
|
52
|
-
|
|
53
|
-
|
|
53
|
+
const value = (hasSql(right) ? getSql(right).getValue() : void 0) ?? right;
|
|
54
|
+
if (Array.isArray(value)) {
|
|
55
|
+
if (value.length === 0)
|
|
54
56
|
return sql`true`;
|
|
55
57
|
return bool(
|
|
56
|
-
sql`${input(left)} not in (${sql.join(
|
|
58
|
+
sql`${input(left)} not in (${sql.join(value.map(input), sql`, `)})`
|
|
57
59
|
);
|
|
58
60
|
}
|
|
59
61
|
return bool(sql`${input(left)} not in ${input(right)}`);
|
|
@@ -2,6 +2,7 @@
|
|
|
2
2
|
import { SyncDatabase } from "../core/Database.js";
|
|
3
3
|
import { sqliteDialect } from "../sqlite.js";
|
|
4
4
|
import { sqliteDiff } from "../sqlite/diff.js";
|
|
5
|
+
import { execTransaction } from "../sqlite/transactions.js";
|
|
5
6
|
var PreparedStatement = class {
|
|
6
7
|
constructor(stmt, isSelection) {
|
|
7
8
|
this.stmt = stmt;
|
|
@@ -25,9 +26,10 @@ var PreparedStatement = class {
|
|
|
25
26
|
free() {
|
|
26
27
|
}
|
|
27
28
|
};
|
|
28
|
-
var BetterSqlite3Driver = class {
|
|
29
|
-
constructor(client) {
|
|
29
|
+
var BetterSqlite3Driver = class _BetterSqlite3Driver {
|
|
30
|
+
constructor(client, depth = 0) {
|
|
30
31
|
this.client = client;
|
|
32
|
+
this.depth = depth;
|
|
31
33
|
}
|
|
32
34
|
parsesJson = false;
|
|
33
35
|
exec(query) {
|
|
@@ -48,11 +50,13 @@ var BetterSqlite3Driver = class {
|
|
|
48
50
|
);
|
|
49
51
|
}
|
|
50
52
|
transaction(run, options) {
|
|
51
|
-
|
|
52
|
-
|
|
53
|
-
|
|
54
|
-
|
|
55
|
-
|
|
53
|
+
return execTransaction(
|
|
54
|
+
this,
|
|
55
|
+
this.depth,
|
|
56
|
+
(depth) => new _BetterSqlite3Driver(this.client, depth),
|
|
57
|
+
run,
|
|
58
|
+
options
|
|
59
|
+
);
|
|
56
60
|
}
|
|
57
61
|
};
|
|
58
62
|
function connect(db) {
|
|
@@ -2,6 +2,7 @@
|
|
|
2
2
|
import { SyncDatabase } from "../core/Database.js";
|
|
3
3
|
import { sqliteDialect } from "../sqlite.js";
|
|
4
4
|
import { sqliteDiff } from "../sqlite/diff.js";
|
|
5
|
+
import { execTransaction } from "../sqlite/transactions.js";
|
|
5
6
|
var PreparedStatement = class {
|
|
6
7
|
constructor(stmt) {
|
|
7
8
|
this.stmt = stmt;
|
|
@@ -22,9 +23,10 @@ var PreparedStatement = class {
|
|
|
22
23
|
this.stmt.finalize();
|
|
23
24
|
}
|
|
24
25
|
};
|
|
25
|
-
var BunSqliteDriver = class {
|
|
26
|
-
constructor(client) {
|
|
26
|
+
var BunSqliteDriver = class _BunSqliteDriver {
|
|
27
|
+
constructor(client, depth = 0) {
|
|
27
28
|
this.client = client;
|
|
29
|
+
this.depth = depth;
|
|
28
30
|
}
|
|
29
31
|
parsesJson = false;
|
|
30
32
|
exec(query) {
|
|
@@ -42,11 +44,13 @@ var BunSqliteDriver = class {
|
|
|
42
44
|
}, {});
|
|
43
45
|
}
|
|
44
46
|
transaction(run, options) {
|
|
45
|
-
|
|
46
|
-
|
|
47
|
-
|
|
48
|
-
|
|
49
|
-
|
|
47
|
+
return execTransaction(
|
|
48
|
+
this,
|
|
49
|
+
this.depth,
|
|
50
|
+
(depth) => new _BunSqliteDriver(this.client, depth),
|
|
51
|
+
run,
|
|
52
|
+
options
|
|
53
|
+
);
|
|
50
54
|
}
|
|
51
55
|
};
|
|
52
56
|
function connect(db) {
|
package/dist/driver/sql.js.js
CHANGED
|
@@ -2,6 +2,7 @@
|
|
|
2
2
|
import { SyncDatabase } from "../core/Database.js";
|
|
3
3
|
import { sqliteDialect } from "../sqlite.js";
|
|
4
4
|
import { sqliteDiff } from "../sqlite/diff.js";
|
|
5
|
+
import { execTransaction } from "../sqlite/transactions.js";
|
|
5
6
|
var PreparedStatement = class {
|
|
6
7
|
constructor(client, stmt) {
|
|
7
8
|
this.client = client;
|
|
@@ -59,16 +60,13 @@ var SqlJsDriver = class _SqlJsDriver {
|
|
|
59
60
|
);
|
|
60
61
|
}
|
|
61
62
|
transaction(run, options) {
|
|
62
|
-
|
|
63
|
-
|
|
64
|
-
|
|
65
|
-
|
|
66
|
-
|
|
67
|
-
|
|
68
|
-
|
|
69
|
-
this.exec(this.depth > 0 ? `rollback to d${this.depth}` : "rollback");
|
|
70
|
-
throw error;
|
|
71
|
-
}
|
|
63
|
+
return execTransaction(
|
|
64
|
+
this,
|
|
65
|
+
this.depth,
|
|
66
|
+
(depth) => new _SqlJsDriver(this.client, depth),
|
|
67
|
+
run,
|
|
68
|
+
options
|
|
69
|
+
);
|
|
72
70
|
}
|
|
73
71
|
};
|
|
74
72
|
function connect(db) {
|
|
@@ -1,14 +1,10 @@
|
|
|
1
|
-
import type {
|
|
1
|
+
import type { HasSql, HasTable } from '../core/Internal.js';
|
|
2
2
|
import { type Sql } from '../core/Sql.js';
|
|
3
3
|
import { type Input } from '../core/expr/Input.js';
|
|
4
4
|
/**: The count(X) function returns a count of the number of times that X is not NULL in a group. The count(*) function (with no arguments) returns the total number of rows in the group. */
|
|
5
5
|
export declare const count: (x?: HasSql) => Sql<number>;
|
|
6
6
|
/** The iif(X,Y,Z) function returns the value Y if X is true, and Z otherwise. The iif(X,Y,Z) function is logically equivalent to and generates the same bytecode as the CASE HasSql "CASE WHEN X THEN Y ELSE Z END".*/
|
|
7
7
|
export declare const iif: <T>(x: Input<boolean>, y: Input<T>, z: Input<T>) => Sql<T>;
|
|
8
|
-
/**
|
|
9
|
-
* The EXISTS operator always evaluates to one of the integer values 0 and 1. If executing the SELECT statement specified as the right-hand operand of the EXISTS operator would return one or more rows, then the EXISTS operator evaluates to 1. If executing the SELECT would return no rows at all, then the EXISTS operator evaluates to 0.
|
|
10
|
-
*/
|
|
11
|
-
export declare const exists: (cursor: HasQuery) => Sql<boolean>;
|
|
12
8
|
/** Use the match operator for the FTS5 module */
|
|
13
9
|
export declare const match: (table: HasTable, searchTerm: Input<string>) => Sql<boolean>;
|
|
14
10
|
/** Returns a real value reflecting the accuracy of the current match */
|
package/dist/sqlite/functions.js
CHANGED
|
@@ -4,7 +4,6 @@ import { Functions } from "../core/expr/Functions.js";
|
|
|
4
4
|
import { input } from "../core/expr/Input.js";
|
|
5
5
|
var count = Functions.count;
|
|
6
6
|
var iif = Functions.iif;
|
|
7
|
-
var exists = Functions.exists;
|
|
8
7
|
var match = Functions.match;
|
|
9
8
|
var bm25 = Functions.bm25;
|
|
10
9
|
var highlight = Functions.highlight;
|
|
@@ -101,7 +100,6 @@ export {
|
|
|
101
100
|
date,
|
|
102
101
|
datetime,
|
|
103
102
|
degrees,
|
|
104
|
-
exists,
|
|
105
103
|
exp,
|
|
106
104
|
floor,
|
|
107
105
|
group_concat,
|
|
@@ -0,0 +1,3 @@
|
|
|
1
|
+
import type { TransactionOptions } from '../core/Database.js';
|
|
2
|
+
import type { SyncDriver } from '../core/Driver.js';
|
|
3
|
+
export declare function execTransaction<T>(driver: SyncDriver, depth: number, wrap: (depth: number) => SyncDriver, run: (inner: SyncDriver) => T, options: TransactionOptions['sqlite']): T;
|
|
@@ -0,0 +1,35 @@
|
|
|
1
|
+
// src/sqlite/transactions.ts
|
|
2
|
+
var locks = /* @__PURE__ */ new WeakMap();
|
|
3
|
+
function execTransaction(driver, depth, wrap, run, options) {
|
|
4
|
+
const needsLock = options.async;
|
|
5
|
+
const behavior = options.behavior ?? "deferred";
|
|
6
|
+
if (!needsLock)
|
|
7
|
+
return transact();
|
|
8
|
+
let trigger;
|
|
9
|
+
const lock = new Promise((resolve) => trigger = resolve);
|
|
10
|
+
const current = Promise.resolve(locks.get(driver));
|
|
11
|
+
locks.set(driver, lock);
|
|
12
|
+
return current.then(transact).finally(trigger);
|
|
13
|
+
function transact() {
|
|
14
|
+
try {
|
|
15
|
+
driver.exec(depth > 0 ? `savepoint d${depth}` : `begin ${behavior}`);
|
|
16
|
+
const result = run(wrap(depth + 1));
|
|
17
|
+
if (result instanceof Promise)
|
|
18
|
+
return result.then(release, rollback);
|
|
19
|
+
return release(result);
|
|
20
|
+
} catch (error) {
|
|
21
|
+
return rollback(error);
|
|
22
|
+
}
|
|
23
|
+
}
|
|
24
|
+
function release(result) {
|
|
25
|
+
driver.exec(depth > 0 ? `release d${depth}` : "commit");
|
|
26
|
+
return result;
|
|
27
|
+
}
|
|
28
|
+
function rollback(error) {
|
|
29
|
+
driver.exec(depth > 0 ? `rollback to d${depth}` : "rollback");
|
|
30
|
+
throw error;
|
|
31
|
+
}
|
|
32
|
+
}
|
|
33
|
+
export {
|
|
34
|
+
execTransaction
|
|
35
|
+
};
|
|
@@ -1,4 +1,4 @@
|
|
|
1
1
|
import { type Sql } from '../core/Sql.js';
|
|
2
|
-
import type
|
|
2
|
+
import { type Input } from '../core/expr/Input.js';
|
|
3
3
|
export declare function lastInsertId(): Sql<number>;
|
|
4
4
|
export declare function concat(...slices: Array<Input<string | null>>): Sql<string>;
|
|
@@ -1,16 +1,20 @@
|
|
|
1
1
|
// src/universal/functions.ts
|
|
2
2
|
import { sql } from "../core/Sql.js";
|
|
3
|
-
import {
|
|
3
|
+
import { Functions } from "../core/expr/Functions.js";
|
|
4
|
+
import { input } from "../core/expr/Input.js";
|
|
4
5
|
var insertId = sql.universal({
|
|
5
|
-
sqlite:
|
|
6
|
-
postgres:
|
|
7
|
-
mysql:
|
|
6
|
+
sqlite: Functions.last_insert_rowid(),
|
|
7
|
+
postgres: Functions.lastval(),
|
|
8
|
+
mysql: Functions.last_insert_id()
|
|
8
9
|
}).mapWith(Number);
|
|
9
10
|
function lastInsertId() {
|
|
10
11
|
return insertId;
|
|
11
12
|
}
|
|
12
13
|
function concat(...slices) {
|
|
13
|
-
return
|
|
14
|
+
return sql.universal({
|
|
15
|
+
mysql: Functions.concat(...slices),
|
|
16
|
+
default: sql.join(slices.map(input), sql` || `)
|
|
17
|
+
});
|
|
14
18
|
}
|
|
15
19
|
export {
|
|
16
20
|
concat,
|