@evolu/common 5.4.8 → 6.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/README.md +30 -34
- package/dist/src/Array.d.ts +17 -0
- package/dist/src/Array.d.ts.map +1 -0
- package/dist/src/Array.js +12 -0
- package/dist/src/Assert.d.ts +68 -0
- package/dist/src/Assert.d.ts.map +1 -0
- package/dist/src/Assert.js +77 -0
- package/dist/src/BigInt.d.ts +20 -0
- package/dist/src/BigInt.d.ts.map +1 -0
- package/dist/src/BigInt.js +18 -0
- package/dist/src/Buffer.d.ts +92 -0
- package/dist/src/Buffer.d.ts.map +1 -0
- package/dist/src/Buffer.js +62 -0
- package/dist/src/Callbacks.d.ts +20 -0
- package/dist/src/Callbacks.d.ts.map +1 -0
- package/dist/src/Callbacks.js +18 -0
- package/dist/src/Console.d.ts +78 -0
- package/dist/src/Console.d.ts.map +1 -0
- package/dist/src/Console.js +103 -0
- package/dist/src/Crypto.d.ts +72 -39
- package/dist/src/Crypto.d.ts.map +1 -1
- package/dist/src/Crypto.js +89 -54
- package/dist/src/Eq.d.ts +97 -0
- package/dist/src/Eq.d.ts.map +1 -0
- package/dist/src/Eq.js +167 -0
- package/dist/src/Error.d.ts +14 -10
- package/dist/src/Error.d.ts.map +1 -1
- package/dist/src/Error.js +43 -11
- package/dist/src/Evolu/Config.d.ts +69 -0
- package/dist/src/Evolu/Config.d.ts.map +1 -0
- package/dist/src/Evolu/Config.js +9 -0
- package/dist/src/Evolu/Db.d.ts +126 -0
- package/dist/src/Evolu/Db.d.ts.map +1 -0
- package/dist/src/Evolu/Db.js +774 -0
- package/dist/src/Evolu/Diff.d.ts +43 -0
- package/dist/src/Evolu/Diff.d.ts.map +1 -0
- package/dist/src/Evolu/Diff.js +95 -0
- package/dist/src/Evolu/Evolu.d.ts +334 -0
- package/dist/src/Evolu/Evolu.d.ts.map +1 -0
- package/dist/src/Evolu/Evolu.js +434 -0
- package/dist/src/Evolu/Internal.d.ts +26 -0
- package/dist/src/Evolu/Internal.d.ts.map +1 -0
- package/dist/src/Evolu/Internal.js +25 -0
- package/dist/src/Evolu/Kysely.d.ts +6 -0
- package/dist/src/Evolu/Kysely.d.ts.map +1 -0
- package/dist/src/Evolu/Kysely.js +21 -0
- package/dist/src/Evolu/Owner.d.ts +155 -0
- package/dist/src/Evolu/Owner.d.ts.map +1 -0
- package/dist/src/Evolu/Owner.js +126 -0
- package/dist/src/Evolu/Platform.d.ts +23 -0
- package/dist/src/Evolu/Platform.d.ts.map +1 -0
- package/dist/src/Evolu/Platform.js +1 -0
- package/dist/src/Evolu/Protocol.d.ts +401 -0
- package/dist/src/Evolu/Protocol.d.ts.map +1 -0
- package/dist/src/Evolu/Protocol.js +1151 -0
- package/dist/src/Evolu/Public.d.ts +18 -0
- package/dist/src/Evolu/Public.d.ts.map +1 -0
- package/dist/src/Evolu/Public.js +11 -0
- package/dist/src/Evolu/PublicKysely.d.ts +148 -0
- package/dist/src/Evolu/PublicKysely.d.ts.map +1 -0
- package/dist/src/Evolu/PublicKysely.js +185 -0
- package/dist/src/Evolu/Query.d.ts +63 -0
- package/dist/src/Evolu/Query.d.ts.map +1 -0
- package/dist/src/Evolu/Query.js +61 -0
- package/dist/src/Evolu/Relay.d.ts +13 -0
- package/dist/src/Evolu/Relay.d.ts.map +1 -0
- package/dist/src/Evolu/Relay.js +109 -0
- package/dist/src/Evolu/Schema.d.ts +201 -0
- package/dist/src/Evolu/Schema.d.ts.map +1 -0
- package/dist/src/Evolu/Schema.js +150 -0
- package/dist/src/Evolu/Storage.d.ts +49 -0
- package/dist/src/Evolu/Storage.d.ts.map +1 -0
- package/dist/src/Evolu/Storage.js +1111 -0
- package/dist/src/Evolu/Sync.d.ts +59 -0
- package/dist/src/Evolu/Sync.d.ts.map +1 -0
- package/dist/src/Evolu/Sync.js +29 -0
- package/dist/src/Evolu/Timestamp.d.ts +106 -0
- package/dist/src/Evolu/Timestamp.d.ts.map +1 -0
- package/dist/src/Evolu/Timestamp.js +179 -0
- package/dist/src/Function.d.ts +54 -0
- package/dist/src/Function.d.ts.map +1 -0
- package/dist/src/Function.js +38 -0
- package/dist/src/ManyToManyMap.d.ts +26 -0
- package/dist/src/ManyToManyMap.d.ts.map +1 -0
- package/dist/src/ManyToManyMap.js +92 -0
- package/dist/src/NanoId.d.ts +27 -0
- package/dist/src/NanoId.d.ts.map +1 -0
- package/dist/src/NanoId.js +6 -0
- package/dist/src/Number.d.ts +42 -0
- package/dist/src/Number.d.ts.map +1 -0
- package/dist/src/Number.js +55 -0
- package/dist/src/Object.d.ts +35 -0
- package/dist/src/Object.d.ts.map +1 -0
- package/dist/src/Object.js +36 -0
- package/dist/src/Order.d.ts +90 -0
- package/dist/src/Order.d.ts.map +1 -0
- package/dist/src/Order.js +85 -0
- package/dist/src/Promise.d.ts +180 -0
- package/dist/src/Promise.d.ts.map +1 -0
- package/dist/src/Promise.js +176 -0
- package/dist/src/Random.d.ts +52 -0
- package/dist/src/Random.d.ts.map +1 -0
- package/dist/src/Random.js +29 -0
- package/dist/src/Ref.d.ts +40 -0
- package/dist/src/Ref.d.ts.map +1 -0
- package/dist/src/Ref.js +13 -0
- package/dist/src/Result.d.ts +421 -0
- package/dist/src/Result.d.ts.map +1 -0
- package/dist/src/Result.js +357 -0
- package/dist/src/Skiplist.d.ts +23 -0
- package/dist/src/Skiplist.d.ts.map +1 -0
- package/dist/src/Skiplist.js +58 -0
- package/dist/src/Sqlite.d.ts +116 -52
- package/dist/src/Sqlite.d.ts.map +1 -1
- package/dist/src/Sqlite.js +183 -67
- package/dist/src/Store.d.ts +45 -8
- package/dist/src/Store.d.ts.map +1 -1
- package/dist/src/Store.js +33 -17
- package/dist/src/String.d.ts +2 -0
- package/dist/src/String.d.ts.map +1 -0
- package/dist/src/String.js +14 -0
- package/dist/src/Time.d.ts +20 -0
- package/dist/src/Time.d.ts.map +1 -0
- package/dist/src/Time.js +25 -0
- package/dist/src/Type.d.ts +1937 -0
- package/dist/src/Type.d.ts.map +1 -0
- package/dist/src/Type.js +2002 -0
- package/dist/src/Types.d.ts +188 -0
- package/dist/src/Types.d.ts.map +1 -0
- package/dist/src/Types.js +6 -0
- package/dist/src/WebSocket.d.ts +112 -0
- package/dist/src/WebSocket.d.ts.map +1 -0
- package/dist/src/WebSocket.js +139 -0
- package/dist/src/Worker.d.ts +44 -0
- package/dist/src/Worker.d.ts.map +1 -0
- package/dist/src/Worker.js +66 -0
- package/dist/src/index.d.ts +24 -11
- package/dist/src/index.d.ts.map +1 -1
- package/dist/src/index.js +24 -11
- package/package.json +29 -38
- package/src/Array.ts +39 -0
- package/src/Assert.ts +116 -0
- package/src/BigInt.ts +29 -0
- package/src/Buffer.ts +175 -0
- package/src/Callbacks.ts +43 -0
- package/src/Console.ts +159 -0
- package/src/Crypto.ts +169 -115
- package/src/Eq.ts +204 -0
- package/src/Error.ts +57 -20
- package/src/Evolu/Config.ts +83 -0
- package/src/Evolu/Db.ts +1275 -0
- package/src/Evolu/Diff.ts +142 -0
- package/src/Evolu/Evolu.ts +947 -0
- package/src/Evolu/Internal.ts +26 -0
- package/src/Evolu/Kysely.ts +38 -0
- package/src/Evolu/Owner.ts +296 -0
- package/src/Evolu/Platform.ts +27 -0
- package/src/Evolu/Protocol.ts +1857 -0
- package/src/Evolu/Public.ts +43 -0
- package/src/Evolu/PublicKysely.ts +240 -0
- package/src/Evolu/Query.ts +167 -0
- package/src/Evolu/Relay.ts +142 -0
- package/src/Evolu/Schema.ts +417 -0
- package/src/Evolu/Storage.ts +1281 -0
- package/src/Evolu/Sync.ts +105 -0
- package/src/Evolu/Timestamp.ts +311 -0
- package/src/Function.ts +58 -0
- package/src/ManyToManyMap.ts +140 -0
- package/src/NanoId.ts +39 -0
- package/src/Number.ts +90 -0
- package/src/Object.ts +64 -0
- package/src/Order.ts +113 -0
- package/src/Promise.ts +295 -0
- package/src/Random.ts +68 -0
- package/src/Ref.ts +63 -0
- package/src/Result.ts +453 -0
- package/src/Skiplist.ts +102 -0
- package/src/Sqlite.ts +366 -153
- package/src/Store.ts +79 -36
- package/src/String.ts +10 -0
- package/src/Time.ts +36 -0
- package/src/Type.ts +3978 -0
- package/src/Types.ts +209 -0
- package/src/WebSocket.ts +273 -0
- package/src/Worker.ts +129 -0
- package/src/index.ts +24 -11
- package/dist/src/Config.d.ts +0 -56
- package/dist/src/Config.d.ts.map +0 -1
- package/dist/src/Config.js +0 -39
- package/dist/src/Crdt.d.ts +0 -89
- package/dist/src/Crdt.d.ts.map +0 -1
- package/dist/src/Crdt.js +0 -181
- package/dist/src/Db.d.ts +0 -107
- package/dist/src/Db.d.ts.map +0 -1
- package/dist/src/Db.js +0 -443
- package/dist/src/Diff.d.ts +0 -27
- package/dist/src/Diff.d.ts.map +0 -1
- package/dist/src/Diff.js +0 -84
- package/dist/src/Evolu.d.ts +0 -426
- package/dist/src/Evolu.d.ts.map +0 -1
- package/dist/src/Evolu.js +0 -333
- package/dist/src/Model.d.ts +0 -141
- package/dist/src/Model.d.ts.map +0 -1
- package/dist/src/Model.js +0 -125
- package/dist/src/Murmurhash.d.ts +0 -2
- package/dist/src/Murmurhash.d.ts.map +0 -1
- package/dist/src/Murmurhash.js +0 -60
- package/dist/src/Owner.d.ts +0 -33
- package/dist/src/Owner.d.ts.map +0 -1
- package/dist/src/Owner.js +0 -26
- package/dist/src/Platform.d.ts +0 -37
- package/dist/src/Platform.d.ts.map +0 -1
- package/dist/src/Platform.js +0 -11
- package/dist/src/Protobuf.d.ts +0 -81
- package/dist/src/Protobuf.d.ts.map +0 -1
- package/dist/src/Protobuf.js +0 -92
- package/dist/src/Public.d.ts +0 -13
- package/dist/src/Public.d.ts.map +0 -1
- package/dist/src/Public.js +0 -6
- package/dist/src/Socket.d.ts +0 -8
- package/dist/src/Socket.d.ts.map +0 -1
- package/dist/src/Socket.js +0 -51
- package/dist/src/Sql.d.ts +0 -12
- package/dist/src/Sql.d.ts.map +0 -1
- package/dist/src/Sql.js +0 -30
- package/dist/src/Sync.d.ts +0 -70
- package/dist/src/Sync.d.ts.map +0 -1
- package/dist/src/Sync.js +0 -127
- package/src/Config.ts +0 -119
- package/src/Crdt.ts +0 -361
- package/src/Db.ts +0 -955
- package/src/Diff.ts +0 -114
- package/src/Evolu.ts +0 -1016
- package/src/Model.ts +0 -233
- package/src/Murmurhash.ts +0 -70
- package/src/Owner.ts +0 -69
- package/src/Platform.ts +0 -47
- package/src/Protobuf.ts +0 -155
- package/src/Public.ts +0 -12
- package/src/Socket.ts +0 -83
- package/src/Sql.ts +0 -41
- package/src/Sync.ts +0 -315
package/dist/src/Sqlite.js
CHANGED
|
@@ -1,68 +1,163 @@
|
|
|
1
|
-
import
|
|
2
|
-
import
|
|
3
|
-
import
|
|
4
|
-
|
|
5
|
-
|
|
6
|
-
|
|
7
|
-
|
|
8
|
-
|
|
9
|
-
|
|
10
|
-
|
|
11
|
-
|
|
12
|
-
|
|
13
|
-
|
|
14
|
-
|
|
15
|
-
|
|
16
|
-
|
|
17
|
-
|
|
18
|
-
|
|
19
|
-
|
|
20
|
-
|
|
21
|
-
|
|
22
|
-
|
|
23
|
-
|
|
24
|
-
|
|
1
|
+
import { createTransferableError } from "./Error.js";
|
|
2
|
+
import { err, ok, tryAsync, trySync } from "./Result.js";
|
|
3
|
+
import { Boolean, Null, Number, String, transform, Uint8Array, union, } from "./Type.js";
|
|
4
|
+
/**
|
|
5
|
+
* A value that can be stored in Sqlite.
|
|
6
|
+
*
|
|
7
|
+
* Note that Evolu can't support Int64 because expo-sqlite (and some others) do
|
|
8
|
+
* not support it.
|
|
9
|
+
*/
|
|
10
|
+
export const SqliteValue = union(Null, String, Number, Uint8Array);
|
|
11
|
+
/**
|
|
12
|
+
* Creates a fully featured {@link Sqlite} instance from a {@link SqliteDriver}
|
|
13
|
+
* implementation.
|
|
14
|
+
*/
|
|
15
|
+
export const createSqlite = (deps) => async (name, options) => tryAsync(async () => {
|
|
16
|
+
const driver = await deps.createSqliteDriver(name, options);
|
|
17
|
+
let isDisposed = false;
|
|
18
|
+
const doRollback = () => trySync(() => {
|
|
19
|
+
deps.console?.log("[sql] rollback");
|
|
20
|
+
driver.exec(sql `rollback;`, true);
|
|
21
|
+
}, createSqliteError);
|
|
22
|
+
const sqlite = {
|
|
23
|
+
exec: (query) => trySync(() => {
|
|
24
|
+
deps.console?.log("[sql]", query);
|
|
25
|
+
const result = maybeLogSqliteQueryExecutionTime(query, () => driver.exec(query, isSqlMutation(query.sql)));
|
|
26
|
+
deps.console?.log("[sql]", result);
|
|
27
|
+
return result;
|
|
28
|
+
}, (error) => ({
|
|
29
|
+
type: "SqliteError",
|
|
30
|
+
error: createTransferableError(error),
|
|
31
|
+
})),
|
|
32
|
+
transaction: (callback) => {
|
|
33
|
+
const transactionResult = trySync(() => {
|
|
34
|
+
deps.console?.log("[sql] begin");
|
|
35
|
+
driver.exec(sql `begin;`, true);
|
|
36
|
+
const result = callback();
|
|
37
|
+
if (!result.ok)
|
|
38
|
+
return result;
|
|
39
|
+
deps.console?.log("[sql] commit");
|
|
40
|
+
driver.exec(sql `commit;`, true);
|
|
41
|
+
return result;
|
|
42
|
+
}, createSqliteError);
|
|
43
|
+
// There was an SqliteError during begin, callback, or commit
|
|
44
|
+
if (!transactionResult.ok) {
|
|
45
|
+
const rollback = doRollback();
|
|
46
|
+
if (!rollback.ok) {
|
|
47
|
+
deps.console?.log("[sql] rollback failed", rollback.error);
|
|
48
|
+
return err({
|
|
49
|
+
type: "SqliteError",
|
|
50
|
+
error: transactionResult.error.error,
|
|
51
|
+
rollbackError: rollback.error.error,
|
|
52
|
+
});
|
|
53
|
+
}
|
|
54
|
+
return transactionResult;
|
|
55
|
+
}
|
|
56
|
+
// Callback returned an error
|
|
57
|
+
if (!transactionResult.value.ok) {
|
|
58
|
+
const rollback = doRollback();
|
|
59
|
+
if (!rollback.ok) {
|
|
60
|
+
deps.console?.log("[sql] rollback failed", rollback.error);
|
|
61
|
+
return err({
|
|
62
|
+
type: "SqliteError",
|
|
63
|
+
error: createTransferableError(transactionResult.value.error),
|
|
64
|
+
rollbackError: rollback.error.error,
|
|
65
|
+
});
|
|
66
|
+
}
|
|
67
|
+
return transactionResult.value;
|
|
68
|
+
}
|
|
69
|
+
return ok(transactionResult.value.value);
|
|
25
70
|
},
|
|
26
|
-
|
|
27
|
-
|
|
28
|
-
|
|
29
|
-
|
|
30
|
-
|
|
31
|
-
|
|
32
|
-
|
|
33
|
-
|
|
34
|
-
|
|
35
|
-
|
|
36
|
-
|
|
37
|
-
|
|
71
|
+
export: () => trySync(() => {
|
|
72
|
+
return driver.export();
|
|
73
|
+
}, (error) => ({
|
|
74
|
+
type: "SqliteError",
|
|
75
|
+
error: createTransferableError(error),
|
|
76
|
+
})),
|
|
77
|
+
[Symbol.dispose]: () => {
|
|
78
|
+
if (isDisposed)
|
|
79
|
+
return;
|
|
80
|
+
isDisposed = true;
|
|
81
|
+
driver[Symbol.dispose]();
|
|
82
|
+
},
|
|
83
|
+
};
|
|
84
|
+
return sqlite;
|
|
85
|
+
}, createSqliteError);
|
|
86
|
+
const createSqliteError = (error) => ({
|
|
87
|
+
type: "SqliteError",
|
|
88
|
+
error: createTransferableError(error),
|
|
89
|
+
});
|
|
90
|
+
const maybeLogSqliteQueryExecutionTime = (query, callback) => {
|
|
91
|
+
if (!query.options?.logQueryExecutionTime) {
|
|
92
|
+
return callback();
|
|
93
|
+
}
|
|
94
|
+
const start = performance.now();
|
|
95
|
+
const result = callback();
|
|
96
|
+
const elapsed = performance.now() - start;
|
|
97
|
+
// eslint-disable-next-line no-console
|
|
98
|
+
console.log(`SqliteQueryExecutionTime: ${elapsed.toString()}ms`, query);
|
|
99
|
+
return result;
|
|
38
100
|
};
|
|
39
|
-
const
|
|
40
|
-
|
|
41
|
-
|
|
42
|
-
|
|
43
|
-
|
|
44
|
-
|
|
45
|
-
|
|
46
|
-
|
|
47
|
-
|
|
101
|
+
export const createPreparedStatementsCache = (factory, disposeFn) => {
|
|
102
|
+
let isDisposed = false;
|
|
103
|
+
const cache = new Map();
|
|
104
|
+
return {
|
|
105
|
+
get: (query, alwaysPrepare) => {
|
|
106
|
+
if (alwaysPrepare !== true && !query.options?.prepare)
|
|
107
|
+
return null;
|
|
108
|
+
let statement = cache.get(query.sql);
|
|
109
|
+
if (!statement) {
|
|
110
|
+
statement = factory(query.sql);
|
|
111
|
+
cache.set(query.sql, statement);
|
|
112
|
+
}
|
|
113
|
+
return statement;
|
|
114
|
+
},
|
|
115
|
+
[Symbol.dispose]: () => {
|
|
116
|
+
if (isDisposed)
|
|
117
|
+
return;
|
|
118
|
+
isDisposed = true;
|
|
119
|
+
cache.forEach(disposeFn);
|
|
120
|
+
cache.clear();
|
|
121
|
+
},
|
|
122
|
+
};
|
|
48
123
|
};
|
|
49
|
-
|
|
50
|
-
|
|
51
|
-
|
|
52
|
-
|
|
53
|
-
|
|
54
|
-
|
|
55
|
-
|
|
124
|
+
/** TODO: Docs. */
|
|
125
|
+
export const sql = (strings, ...parameters) => {
|
|
126
|
+
let sql = "";
|
|
127
|
+
const values = [];
|
|
128
|
+
for (let i = 0; i < strings.length; i++) {
|
|
129
|
+
sql += strings[i];
|
|
130
|
+
if (i < parameters.length) {
|
|
131
|
+
const param = parameters[i];
|
|
132
|
+
if (typeof param === "object" && param != null && "type" in param) {
|
|
133
|
+
sql += param.sql;
|
|
134
|
+
}
|
|
135
|
+
else {
|
|
136
|
+
sql += "?";
|
|
137
|
+
values.push(param);
|
|
138
|
+
}
|
|
56
139
|
}
|
|
57
|
-
|
|
140
|
+
}
|
|
141
|
+
return { sql: sql, parameters: values };
|
|
58
142
|
};
|
|
59
|
-
|
|
60
|
-
|
|
61
|
-
|
|
62
|
-
|
|
63
|
-
|
|
143
|
+
sql.identifier = (identifier) => ({
|
|
144
|
+
type: "SqlIdentifier",
|
|
145
|
+
// From Kysely
|
|
146
|
+
sql: `"${identifier.replace(/"/g, '""')}"`,
|
|
147
|
+
});
|
|
148
|
+
/**
|
|
149
|
+
* Insert any string.
|
|
150
|
+
*
|
|
151
|
+
* Sql.raw sometimes breaks auto-formatting because the parser does not consider
|
|
152
|
+
* it valid SQL. A workaround is to remove it, format it, and put it back.
|
|
153
|
+
*
|
|
154
|
+
* **Warning**: This is not escaped.
|
|
155
|
+
*/
|
|
156
|
+
sql.raw = (raw) => ({ type: "RawSql", sql: raw });
|
|
157
|
+
sql.prepared = (strings, ...parameters) => {
|
|
158
|
+
const query = sql(strings, ...parameters);
|
|
159
|
+
return { ...query, options: { prepare: true } };
|
|
64
160
|
};
|
|
65
|
-
/** This is good enough detection because SQL strings in Evolu are predictable. */
|
|
66
161
|
const isSqlMutationRegEx = new RegExp(`\\b(${[
|
|
67
162
|
"alter",
|
|
68
163
|
"create",
|
|
@@ -71,14 +166,27 @@ const isSqlMutationRegEx = new RegExp(`\\b(${[
|
|
|
71
166
|
"insert",
|
|
72
167
|
"replace",
|
|
73
168
|
"update",
|
|
74
|
-
|
|
75
|
-
|
|
76
|
-
|
|
77
|
-
|
|
78
|
-
|
|
79
|
-
|
|
169
|
+
"begin",
|
|
170
|
+
"commit",
|
|
171
|
+
"rollback",
|
|
172
|
+
"pragma",
|
|
173
|
+
"vacuum",
|
|
174
|
+
].join("|")})\\b`, "i");
|
|
175
|
+
export const isSqlMutation = (sql) => isSqlMutationRegEx.test(sql.replace(/--.*$/gm, ""));
|
|
176
|
+
export const explainSqliteQueryPlan = (deps) => (query) => {
|
|
177
|
+
const result = deps.sqlite.exec({
|
|
178
|
+
...query,
|
|
179
|
+
sql: `EXPLAIN QUERY PLAN ${query.sql}`,
|
|
180
|
+
});
|
|
181
|
+
if (!result.ok)
|
|
182
|
+
return result;
|
|
183
|
+
// eslint-disable-next-line no-console
|
|
184
|
+
console.log("ExplainQueryPlan", query);
|
|
185
|
+
// eslint-disable-next-line no-console
|
|
186
|
+
console.log(drawSqliteQueryPlan(result.value.rows));
|
|
187
|
+
return ok();
|
|
80
188
|
};
|
|
81
|
-
|
|
189
|
+
const drawSqliteQueryPlan = (rows) => rows
|
|
82
190
|
.map((row) => {
|
|
83
191
|
let parentId = row.parent;
|
|
84
192
|
let indent = 0;
|
|
@@ -88,8 +196,16 @@ export const drawSqliteQueryPlan = (rows) => rows
|
|
|
88
196
|
break;
|
|
89
197
|
parentId = parent.parent;
|
|
90
198
|
indent++;
|
|
91
|
-
// eslint-disable-next-line no-constant-condition
|
|
199
|
+
// eslint-disable-next-line @typescript-eslint/no-unnecessary-condition, no-constant-condition
|
|
92
200
|
} while (true);
|
|
93
201
|
return `${" ".repeat(indent)}${row.detail}`;
|
|
94
202
|
})
|
|
95
203
|
.join("\n");
|
|
204
|
+
/**
|
|
205
|
+
* SQLite represents boolean values using `0` (false) and `1` (true) instead of
|
|
206
|
+
* a dedicated boolean type. This transform Type ensures that values conform to
|
|
207
|
+
* SQLite's boolean representation.
|
|
208
|
+
*
|
|
209
|
+
* See: https://www.sqlite.org/quirks.html#no_separate_boolean_datatype
|
|
210
|
+
*/
|
|
211
|
+
export const SqliteBoolean = transform(Boolean, union(0, 1), (value) => ok(value ? 1 : 0), (value) => value === 1);
|
package/dist/src/Store.d.ts
CHANGED
|
@@ -1,10 +1,47 @@
|
|
|
1
|
-
|
|
2
|
-
|
|
3
|
-
|
|
4
|
-
|
|
5
|
-
|
|
6
|
-
|
|
7
|
-
|
|
1
|
+
/**
|
|
2
|
+
* A mutable reference for managing state with change notifications
|
|
3
|
+
*
|
|
4
|
+
* @module
|
|
5
|
+
*/
|
|
6
|
+
import { Eq } from "./Eq.js";
|
|
7
|
+
import { Ref } from "./Ref.js";
|
|
8
|
+
/**
|
|
9
|
+
* A store for managing state with change notifications. Extends {@link Ref} with
|
|
10
|
+
* subscriptions. Provides methods to get, set, and modify state, and to notify
|
|
11
|
+
* listeners when the state changes.
|
|
12
|
+
*/
|
|
13
|
+
export interface Store<T> extends Ref<T> {
|
|
14
|
+
/**
|
|
15
|
+
* Registers a listener to be called on state changes and returns a function
|
|
16
|
+
* to unsubscribe.
|
|
17
|
+
*/
|
|
18
|
+
readonly subscribe: StoreSubscribe;
|
|
19
|
+
/** Returns the current state of the store. */
|
|
20
|
+
readonly get: () => T;
|
|
21
|
+
/**
|
|
22
|
+
* Updates the store's state and notifies all subscribed listeners if the new
|
|
23
|
+
* state differs from the current one.
|
|
24
|
+
*/
|
|
25
|
+
readonly set: (state: T) => void;
|
|
26
|
+
/**
|
|
27
|
+
* Modifies the store's state by applying a callback function to the current
|
|
28
|
+
* state and notifies listeners if the state changes.
|
|
29
|
+
*/
|
|
30
|
+
readonly modify: (updater: (current: T) => T) => void;
|
|
8
31
|
}
|
|
9
|
-
|
|
32
|
+
/** Registers a listener for state changes, returning an unsubscribe function. */
|
|
33
|
+
export type StoreSubscribe = (listener: StoreListener) => StoreUnsubscribe;
|
|
34
|
+
/** A callback invoked whenever the store's state updates. */
|
|
35
|
+
export type StoreListener = () => void;
|
|
36
|
+
/** A function to remove a previously added listener. */
|
|
37
|
+
export type StoreUnsubscribe = () => void;
|
|
38
|
+
/**
|
|
39
|
+
* Creates a store with the given initial state. The store encapsulates its
|
|
40
|
+
* state, which can be read with `get` and updated with `set` or `modify`. All
|
|
41
|
+
* changes are broadcast to subscribers.
|
|
42
|
+
*
|
|
43
|
+
* By default, state changes are detected using `===` (shallow equality). You
|
|
44
|
+
* can provide a custom equality function as the second argument.
|
|
45
|
+
*/
|
|
46
|
+
export declare const createStore: <T>(initialState: T, eq?: Eq<T>) => Store<T>;
|
|
10
47
|
//# sourceMappingURL=Store.d.ts.map
|
package/dist/src/Store.d.ts.map
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"Store.d.ts","sourceRoot":"","sources":["../../src/Store.ts"],"names":[],"mappings":"AAAA,OAAO,
|
|
1
|
+
{"version":3,"file":"Store.d.ts","sourceRoot":"","sources":["../../src/Store.ts"],"names":[],"mappings":"AAAA;;;;GAIG;AACH,OAAO,EAAE,EAAE,EAAY,MAAM,SAAS,CAAC;AACvC,OAAO,EAAE,GAAG,EAAE,MAAM,UAAU,CAAC;AAE/B;;;;GAIG;AACH,MAAM,WAAW,KAAK,CAAC,CAAC,CAAE,SAAQ,GAAG,CAAC,CAAC,CAAC;IACtC;;;OAGG;IACH,QAAQ,CAAC,SAAS,EAAE,cAAc,CAAC;IAEnC,8CAA8C;IAC9C,QAAQ,CAAC,GAAG,EAAE,MAAM,CAAC,CAAC;IAEtB;;;OAGG;IACH,QAAQ,CAAC,GAAG,EAAE,CAAC,KAAK,EAAE,CAAC,KAAK,IAAI,CAAC;IAEjC;;;OAGG;IACH,QAAQ,CAAC,MAAM,EAAE,CAAC,OAAO,EAAE,CAAC,OAAO,EAAE,CAAC,KAAK,CAAC,KAAK,IAAI,CAAC;CACvD;AAED,iFAAiF;AACjF,MAAM,MAAM,cAAc,GAAG,CAAC,QAAQ,EAAE,aAAa,KAAK,gBAAgB,CAAC;AAE3E,6DAA6D;AAC7D,MAAM,MAAM,aAAa,GAAG,MAAM,IAAI,CAAC;AAEvC,wDAAwD;AACxD,MAAM,MAAM,gBAAgB,GAAG,MAAM,IAAI,CAAC;AAE1C;;;;;;;GAOG;AACH,eAAO,MAAM,WAAW,GAAI,CAAC,EAC3B,cAAc,CAAC,EACf,KAAI,EAAE,CAAC,CAAC,CAAY,KACnB,KAAK,CAAC,CAAC,CA4BT,CAAC"}
|
package/dist/src/Store.js
CHANGED
|
@@ -1,23 +1,39 @@
|
|
|
1
|
-
|
|
2
|
-
|
|
1
|
+
/**
|
|
2
|
+
* A mutable reference for managing state with change notifications
|
|
3
|
+
*
|
|
4
|
+
* @module
|
|
5
|
+
*/
|
|
6
|
+
import { eqStrict } from "./Eq.js";
|
|
7
|
+
/**
|
|
8
|
+
* Creates a store with the given initial state. The store encapsulates its
|
|
9
|
+
* state, which can be read with `get` and updated with `set` or `modify`. All
|
|
10
|
+
* changes are broadcast to subscribers.
|
|
11
|
+
*
|
|
12
|
+
* By default, state changes are detected using `===` (shallow equality). You
|
|
13
|
+
* can provide a custom equality function as the second argument.
|
|
14
|
+
*/
|
|
15
|
+
export const createStore = (initialState, eq = eqStrict) => {
|
|
3
16
|
const listeners = new Set();
|
|
4
17
|
let currentState = initialState;
|
|
5
|
-
const
|
|
6
|
-
|
|
18
|
+
const updateState = (newState) => {
|
|
19
|
+
if (eq(newState, currentState))
|
|
20
|
+
return;
|
|
21
|
+
currentState = newState;
|
|
22
|
+
listeners.forEach((listener) => {
|
|
23
|
+
listener();
|
|
24
|
+
});
|
|
25
|
+
};
|
|
26
|
+
return {
|
|
27
|
+
subscribe: (listener) => {
|
|
7
28
|
listeners.add(listener);
|
|
8
|
-
return () =>
|
|
9
|
-
|
|
10
|
-
|
|
29
|
+
return () => listeners.delete(listener);
|
|
30
|
+
},
|
|
31
|
+
get: () => currentState,
|
|
32
|
+
set: (state) => {
|
|
33
|
+
updateState(state);
|
|
11
34
|
},
|
|
12
|
-
|
|
13
|
-
|
|
35
|
+
modify: (updater) => {
|
|
36
|
+
updateState(updater(currentState));
|
|
14
37
|
},
|
|
15
|
-
setState: (state) => Effect.sync(() => {
|
|
16
|
-
if (state === currentState)
|
|
17
|
-
return;
|
|
18
|
-
currentState = state;
|
|
19
|
-
listeners.forEach((listener) => listener());
|
|
20
|
-
}),
|
|
21
38
|
};
|
|
22
|
-
|
|
23
|
-
});
|
|
39
|
+
};
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"String.d.ts","sourceRoot":"","sources":["../../src/String.ts"],"names":[],"mappings":"AAAA,eAAO,MAAM,2BAA2B,GAAI,OAAO,OAAO,KAAG,MAS5D,CAAC"}
|
|
@@ -0,0 +1,14 @@
|
|
|
1
|
+
export const safelyStringifyUnknownValue = (value) => {
|
|
2
|
+
if (value === null)
|
|
3
|
+
return "null";
|
|
4
|
+
if (value === undefined)
|
|
5
|
+
return "undefined";
|
|
6
|
+
if (typeof value === "string")
|
|
7
|
+
return `"${value}"`;
|
|
8
|
+
try {
|
|
9
|
+
return JSON.stringify(value);
|
|
10
|
+
}
|
|
11
|
+
catch {
|
|
12
|
+
return globalThis.String(value);
|
|
13
|
+
}
|
|
14
|
+
};
|
|
@@ -0,0 +1,20 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* ⏳
|
|
3
|
+
*
|
|
4
|
+
* @module
|
|
5
|
+
*/
|
|
6
|
+
/** Retrieves the current time in milliseconds, similar to `Date.now()`. */
|
|
7
|
+
export interface Time {
|
|
8
|
+
readonly now: () => number;
|
|
9
|
+
}
|
|
10
|
+
export interface TimeDep {
|
|
11
|
+
readonly time: Time;
|
|
12
|
+
}
|
|
13
|
+
/** Creates a {@link Time} using Date.now(). */
|
|
14
|
+
export declare const createTime: () => Time;
|
|
15
|
+
/**
|
|
16
|
+
* Creates a {@link Time} that returns a monotonically increasing number based on
|
|
17
|
+
* a queueMicrotask.
|
|
18
|
+
*/
|
|
19
|
+
export declare const createTestTime: () => Time;
|
|
20
|
+
//# sourceMappingURL=Time.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"Time.d.ts","sourceRoot":"","sources":["../../src/Time.ts"],"names":[],"mappings":"AAAA;;;;GAIG;AAEH,2EAA2E;AAC3E,MAAM,WAAW,IAAI;IACnB,QAAQ,CAAC,GAAG,EAAE,MAAM,MAAM,CAAC;CAC5B;AAED,MAAM,WAAW,OAAO;IACtB,QAAQ,CAAC,IAAI,EAAE,IAAI,CAAC;CACrB;AAED,+CAA+C;AAC/C,eAAO,MAAM,UAAU,QAAO,IAE5B,CAAC;AAEH;;;GAGG;AACH,eAAO,MAAM,cAAc,QAAO,IAWjC,CAAC"}
|
package/dist/src/Time.js
ADDED
|
@@ -0,0 +1,25 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* ⏳
|
|
3
|
+
*
|
|
4
|
+
* @module
|
|
5
|
+
*/
|
|
6
|
+
/** Creates a {@link Time} using Date.now(). */
|
|
7
|
+
export const createTime = () => ({
|
|
8
|
+
now: () => Date.now(),
|
|
9
|
+
});
|
|
10
|
+
/**
|
|
11
|
+
* Creates a {@link Time} that returns a monotonically increasing number based on
|
|
12
|
+
* a queueMicrotask.
|
|
13
|
+
*/
|
|
14
|
+
export const createTestTime = () => {
|
|
15
|
+
let now = 0;
|
|
16
|
+
return {
|
|
17
|
+
now: () => {
|
|
18
|
+
const current = now;
|
|
19
|
+
queueMicrotask(() => {
|
|
20
|
+
now++;
|
|
21
|
+
});
|
|
22
|
+
return current;
|
|
23
|
+
},
|
|
24
|
+
};
|
|
25
|
+
};
|