sorodb 0.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/CONTRIBUTING.md +33 -0
- package/LICENSE +21 -0
- package/README.md +126 -0
- package/docs/explanation/architecture.md +34 -0
- package/docs/getting-started.md +68 -0
- package/docs/guides/indexes-and-sorting.md +70 -0
- package/docs/guides/pagination.md +47 -0
- package/docs/guides/schema-upgrades.md +67 -0
- package/docs/guides/transactions.md +38 -0
- package/docs/reference/api.md +90 -0
- package/docs/reference/schema-and-query.md +87 -0
- package/examples/basic.js +26 -0
- package/package.json +45 -0
- package/src/collection.js +90 -0
- package/src/encoding.js +200 -0
- package/src/errors.js +43 -0
- package/src/index-methods.js +131 -0
- package/src/index.js +16 -0
- package/src/indexes.js +32 -0
- package/src/query.js +493 -0
- package/src/schema.js +247 -0
- package/src/storage.js +334 -0
- package/src/types.js +29 -0
- package/types/collection.d.ts +20 -0
- package/types/encoding.d.ts +32 -0
- package/types/errors.d.ts +26 -0
- package/types/index-methods.d.ts +16 -0
- package/types/index.d.ts +6 -0
- package/types/indexes.d.ts +4 -0
- package/types/query.d.ts +49 -0
- package/types/schema.d.ts +8 -0
- package/types/storage.d.ts +58 -0
- package/types/types.d.ts +160 -0
|
@@ -0,0 +1,16 @@
|
|
|
1
|
+
/** @param {unknown} value */
|
|
2
|
+
declare function supportsBtreeValue(value: unknown): boolean;
|
|
3
|
+
/** @param {unknown} value @param {import("./types.js").Direction} [direction] */
|
|
4
|
+
declare function btreeScalar(value: unknown, direction?: import("./types.js").Direction): Buffer<ArrayBuffer>;
|
|
5
|
+
/** @param {string} name */
|
|
6
|
+
export declare function indexMethod(name: string): {
|
|
7
|
+
supportsValue: typeof supportsBtreeValue;
|
|
8
|
+
encodeValue: typeof btreeScalar;
|
|
9
|
+
/** @param {import("./types.js").Index} index @param {import("./types.js").IndexField[]} order */
|
|
10
|
+
supportsOrder: (index: import("./types.js").Index, order: import("./types.js").IndexField[]) => boolean;
|
|
11
|
+
/** @param {string} table @param {import("./types.js").Index} index @param {string} path @param {unknown} value */
|
|
12
|
+
equalityPrefix(table: string, index: import("./types.js").Index, path: string, value: unknown): Buffer<ArrayBuffer> | null;
|
|
13
|
+
};
|
|
14
|
+
/** @param {string} table @param {import("./types.js").Index} index @param {import("./types.js").Document} doc */
|
|
15
|
+
export declare function indexKey(table: string, index: import("./types.js").Index, doc: import("./types.js").Document): Buffer<ArrayBuffer> | null;
|
|
16
|
+
export {};
|
package/types/index.d.ts
ADDED
|
@@ -0,0 +1,6 @@
|
|
|
1
|
+
/// <reference types="node" />
|
|
2
|
+
import { Database } from "./storage.js";
|
|
3
|
+
/** @param {import("./types.js").DatabaseConfig} config */
|
|
4
|
+
export default function SoroDB(config: import("./types.js").DatabaseConfig): Database;
|
|
5
|
+
export { SoroDB };
|
|
6
|
+
export { SoroError, ValidationError, SchemaError, ConflictError, QueryError, CursorError, } from "./errors.js";
|
|
@@ -0,0 +1,4 @@
|
|
|
1
|
+
/** @param {import("@slatedb/uniffi").DbTransaction} tx @param {import("./types.js").Table} table @param {import("./types.js").Document} document @param {import("./types.js").Index[]} [indexes] */
|
|
2
|
+
export declare function removeIndexes(tx: import("@slatedb/uniffi").DbTransaction, table: import("./types.js").Table, document: import("./types.js").Document, indexes?: import("./types.js").Index[]): Promise<void>;
|
|
3
|
+
/** @param {import("@slatedb/uniffi").DbTransaction} tx @param {import("./types.js").Table} table @param {import("./types.js").Document} document @param {import("./types.js").Index[]} [indexes] */
|
|
4
|
+
export declare function addIndexes(tx: import("@slatedb/uniffi").DbTransaction, table: import("./types.js").Table, document: import("./types.js").Document, indexes?: import("./types.js").Index[]): Promise<void>;
|
package/types/query.d.ts
ADDED
|
@@ -0,0 +1,49 @@
|
|
|
1
|
+
export declare class Query {
|
|
2
|
+
collection: import("./collection.js").Collection;
|
|
3
|
+
ast: import("./types.js").WhereNode | null;
|
|
4
|
+
order: import("./types.js").IndexField[];
|
|
5
|
+
select: string[] | undefined;
|
|
6
|
+
limit: number | undefined;
|
|
7
|
+
cursor: string | undefined;
|
|
8
|
+
fingerprint: string;
|
|
9
|
+
plan: {
|
|
10
|
+
prefix: Buffer<ArrayBuffer>;
|
|
11
|
+
index: null;
|
|
12
|
+
key?: undefined;
|
|
13
|
+
} | {
|
|
14
|
+
prefix: Buffer<ArrayBuffer>;
|
|
15
|
+
index: import("./types.js").Index;
|
|
16
|
+
key?: undefined;
|
|
17
|
+
} | {
|
|
18
|
+
prefix?: undefined;
|
|
19
|
+
key: Buffer<ArrayBuffer>;
|
|
20
|
+
index: null;
|
|
21
|
+
};
|
|
22
|
+
sessionId: string | null;
|
|
23
|
+
/** @param {import("./collection.js").Collection} collection @param {import("./types.js").QueryOptions} options */
|
|
24
|
+
constructor(collection: import("./collection.js").Collection, options: import("./types.js").QueryOptions);
|
|
25
|
+
_plan(): {
|
|
26
|
+
prefix: Buffer<ArrayBuffer>;
|
|
27
|
+
index: null;
|
|
28
|
+
key?: undefined;
|
|
29
|
+
} | {
|
|
30
|
+
prefix: Buffer<ArrayBuffer>;
|
|
31
|
+
index: import("./types.js").Index;
|
|
32
|
+
key?: undefined;
|
|
33
|
+
} | {
|
|
34
|
+
prefix?: undefined;
|
|
35
|
+
key: Buffer<ArrayBuffer>;
|
|
36
|
+
index: null;
|
|
37
|
+
};
|
|
38
|
+
/** @param {import("./types.js").Reader} reader @param {Uint8Array} [after] */
|
|
39
|
+
_rows(reader: import("./types.js").Reader, after?: Uint8Array): AsyncGenerator<{
|
|
40
|
+
key: Buffer<ArrayBuffer>;
|
|
41
|
+
value: import("./types.js").Document;
|
|
42
|
+
}, void, unknown>;
|
|
43
|
+
page(): Promise<{
|
|
44
|
+
items: import("./types.js").Document[];
|
|
45
|
+
nextCursor: string | null;
|
|
46
|
+
}>;
|
|
47
|
+
[Symbol.asyncIterator](): AsyncGenerator<import("./types.js").Document, void, unknown>;
|
|
48
|
+
close(): void;
|
|
49
|
+
}
|
|
@@ -0,0 +1,8 @@
|
|
|
1
|
+
/** @param {{ version: number }} config @param {import("./types.js").TableDefinition[]} definitions @returns {import("./types.js").CompiledSchema} */
|
|
2
|
+
export declare function compileSchema(config: {
|
|
3
|
+
version: number;
|
|
4
|
+
}, definitions: import("./types.js").TableDefinition[]): import("./types.js").CompiledSchema;
|
|
5
|
+
/** @param {import("./types.js").Table} table @param {unknown} document @param {boolean} [applyDefaults] @returns {import("./types.js").Document} */
|
|
6
|
+
export declare function validateDocument(table: import("./types.js").Table, document: unknown, applyDefaults?: boolean): import("./types.js").Document;
|
|
7
|
+
/** @param {import("./types.js").StoredSchema} previous @param {import("./types.js").StoredSchema} next @returns {import("./types.js").SchemaDiff} */
|
|
8
|
+
export declare function schemaDiff(previous: import("./types.js").StoredSchema, next: import("./types.js").StoredSchema): import("./types.js").SchemaDiff;
|
|
@@ -0,0 +1,58 @@
|
|
|
1
|
+
import { ObjectStore } from "@slatedb/uniffi";
|
|
2
|
+
import { Collection } from "./collection.js";
|
|
3
|
+
/** @param {import("./types.js").Reader} reader @param {Uint8Array} prefix @param {Uint8Array} [after] */
|
|
4
|
+
export declare function scan(reader: import("./types.js").Reader, prefix: Uint8Array, after?: Uint8Array): AsyncGenerator<{
|
|
5
|
+
key: Buffer<ArrayBuffer>;
|
|
6
|
+
value: Buffer<ArrayBuffer>;
|
|
7
|
+
}, void, unknown>;
|
|
8
|
+
export declare class Database {
|
|
9
|
+
config: import("./types.js").DatabaseConfig;
|
|
10
|
+
cursorTtlMs: number;
|
|
11
|
+
definition: import("./types.js").CompiledSchema | null;
|
|
12
|
+
native: import("@slatedb/uniffi").Db | null;
|
|
13
|
+
store: ObjectStore | null;
|
|
14
|
+
opening: Promise<void> | null;
|
|
15
|
+
closed: boolean;
|
|
16
|
+
/** @type {Map<string, import("./types.js").Session>} */
|
|
17
|
+
sessions: Map<string, import("./types.js").Session>;
|
|
18
|
+
/** @param {import("./types.js").DatabaseConfig} config */
|
|
19
|
+
constructor(config: import("./types.js").DatabaseConfig);
|
|
20
|
+
/** @param {{ version: number }} config @param {import("./types.js").TableDefinition[]} definitions */
|
|
21
|
+
schema(config: {
|
|
22
|
+
version: number;
|
|
23
|
+
}, definitions: import("./types.js").TableDefinition[]): this;
|
|
24
|
+
_ready(): Promise<void>;
|
|
25
|
+
_open(): Promise<void>;
|
|
26
|
+
/** @param {import("./types.js").SchemaDiff} diff */
|
|
27
|
+
_migrate(diff: import("./types.js").SchemaDiff): Promise<void>;
|
|
28
|
+
/** @param {string} name */
|
|
29
|
+
collection(name: string): Promise<Collection>;
|
|
30
|
+
/** @template T @param {(tx: import("@slatedb/uniffi").DbTransaction) => Promise<T>} fn @returns {Promise<T>} */
|
|
31
|
+
_atomic<T>(fn: (tx: import("@slatedb/uniffi").DbTransaction) => Promise<T>): Promise<T>;
|
|
32
|
+
/** @template T @param {(tx: { collection: (name: string) => Promise<Collection> }) => Promise<T>} callback @returns {Promise<T>} */
|
|
33
|
+
transaction<T>(callback: (tx: {
|
|
34
|
+
collection: (name: string) => Promise<Collection>;
|
|
35
|
+
}) => Promise<T>): Promise<T>;
|
|
36
|
+
_session(): void;
|
|
37
|
+
/** @param {string} fingerprint */
|
|
38
|
+
_newSession(fingerprint: string): Promise<{
|
|
39
|
+
id: `${string}-${string}-${string}-${string}-${string}`;
|
|
40
|
+
session: {
|
|
41
|
+
snapshot: import("@slatedb/uniffi").DbSnapshot;
|
|
42
|
+
fingerprint: string;
|
|
43
|
+
lastUsed: number;
|
|
44
|
+
active: number;
|
|
45
|
+
};
|
|
46
|
+
}>;
|
|
47
|
+
/** @param {string} id @param {import("./types.js").Session} session */
|
|
48
|
+
_armSession(id: string, session: import("./types.js").Session): void;
|
|
49
|
+
/** @param {import("./types.js").Session} session */
|
|
50
|
+
_holdSession(session: import("./types.js").Session): void;
|
|
51
|
+
/** @param {string} id */
|
|
52
|
+
_idleSession(id: string): void;
|
|
53
|
+
/** @param {string} id @param {string} fingerprint */
|
|
54
|
+
_getSession(id: string, fingerprint: string): import("./types.js").Session;
|
|
55
|
+
/** @param {string} id */
|
|
56
|
+
_releaseSession(id: string): void;
|
|
57
|
+
close(): Promise<void>;
|
|
58
|
+
}
|
package/types/types.d.ts
ADDED
|
@@ -0,0 +1,160 @@
|
|
|
1
|
+
export type Direction = "asc" | "desc";
|
|
2
|
+
export type Document = Record<string, unknown> & {
|
|
3
|
+
id: string | number;
|
|
4
|
+
};
|
|
5
|
+
export type DatabaseConfig = {
|
|
6
|
+
store: string;
|
|
7
|
+
path: string;
|
|
8
|
+
cursorTtlMs?: number;
|
|
9
|
+
};
|
|
10
|
+
export type ArkTypeDefinition = string | import("arktype").Type<unknown> | readonly ArkTypeValue[] | {
|
|
11
|
+
[key: string]: ArkTypeValue;
|
|
12
|
+
};
|
|
13
|
+
export type ArkTypeValue = ArkTypeDefinition | null | boolean | number | bigint | Date | Uint8Array;
|
|
14
|
+
export type DataValue = null | boolean | number | string | bigint | Date | Uint8Array | readonly DataValue[] | {
|
|
15
|
+
[key: string]: DataValue;
|
|
16
|
+
};
|
|
17
|
+
export type ColumnDefinition = {
|
|
18
|
+
type: ArkTypeDefinition;
|
|
19
|
+
primary?: boolean;
|
|
20
|
+
default?: DataValue | (() => DataValue);
|
|
21
|
+
};
|
|
22
|
+
export type IndexDefinition = {
|
|
23
|
+
name: string;
|
|
24
|
+
method?: "btree";
|
|
25
|
+
columns: (string | {
|
|
26
|
+
field: string;
|
|
27
|
+
direction?: Direction;
|
|
28
|
+
})[];
|
|
29
|
+
unique?: boolean;
|
|
30
|
+
};
|
|
31
|
+
export type TableDefinition = {
|
|
32
|
+
table: string;
|
|
33
|
+
columns: Record<string, ColumnDefinition>;
|
|
34
|
+
indexes?: IndexDefinition[];
|
|
35
|
+
};
|
|
36
|
+
export type IndexField = {
|
|
37
|
+
name: string;
|
|
38
|
+
direction: Direction;
|
|
39
|
+
};
|
|
40
|
+
export type Index = {
|
|
41
|
+
name: string;
|
|
42
|
+
method: "btree";
|
|
43
|
+
fields: IndexField[];
|
|
44
|
+
unique: boolean;
|
|
45
|
+
};
|
|
46
|
+
export type Table = {
|
|
47
|
+
name: string;
|
|
48
|
+
columns: Record<string, ColumnDefinition>;
|
|
49
|
+
indexes: Index[];
|
|
50
|
+
validator: (document: unknown) => unknown;
|
|
51
|
+
};
|
|
52
|
+
export type StoredColumn = {
|
|
53
|
+
type: string;
|
|
54
|
+
primary: boolean;
|
|
55
|
+
optional: boolean;
|
|
56
|
+
default: null | {
|
|
57
|
+
kind: string;
|
|
58
|
+
value?: string;
|
|
59
|
+
};
|
|
60
|
+
};
|
|
61
|
+
export type StoredTable = {
|
|
62
|
+
columns: Record<string, StoredColumn>;
|
|
63
|
+
indexes: Index[];
|
|
64
|
+
};
|
|
65
|
+
export type StoredSchema = {
|
|
66
|
+
version: number;
|
|
67
|
+
tables: Record<string, StoredTable>;
|
|
68
|
+
};
|
|
69
|
+
export type CompiledSchema = {
|
|
70
|
+
version: number;
|
|
71
|
+
tables: Map<string, Table>;
|
|
72
|
+
stored: StoredSchema;
|
|
73
|
+
};
|
|
74
|
+
export type SchemaDiff = {
|
|
75
|
+
changed: boolean;
|
|
76
|
+
additions: Map<string, {
|
|
77
|
+
columns: string[];
|
|
78
|
+
indexes: Index[];
|
|
79
|
+
}>;
|
|
80
|
+
};
|
|
81
|
+
export type Reader = import("@slatedb/uniffi").Db | import("@slatedb/uniffi").DbSnapshot | import("@slatedb/uniffi").DbTransaction;
|
|
82
|
+
export type Session = {
|
|
83
|
+
snapshot: import("@slatedb/uniffi").DbSnapshot;
|
|
84
|
+
fingerprint: string;
|
|
85
|
+
lastUsed: number;
|
|
86
|
+
active: number;
|
|
87
|
+
timer?: NodeJS.Timeout;
|
|
88
|
+
};
|
|
89
|
+
export type Predicate = {
|
|
90
|
+
op: "eq" | "ne" | "gt" | "gte" | "lt" | "lte" | "in" | "contains" | "startsWith" | "exists";
|
|
91
|
+
path: string;
|
|
92
|
+
value: unknown;
|
|
93
|
+
};
|
|
94
|
+
export type WhereNode = {
|
|
95
|
+
op: "and";
|
|
96
|
+
conditions: WhereNode[];
|
|
97
|
+
} | {
|
|
98
|
+
op: "or";
|
|
99
|
+
conditions: WhereNode[];
|
|
100
|
+
} | {
|
|
101
|
+
op: "not";
|
|
102
|
+
condition: WhereNode;
|
|
103
|
+
} | Predicate;
|
|
104
|
+
export type WhereBuilder = {
|
|
105
|
+
eq: (path: string, value: unknown) => WhereNode;
|
|
106
|
+
ne: (path: string, value: unknown) => WhereNode;
|
|
107
|
+
gt: (path: string, value: unknown) => WhereNode;
|
|
108
|
+
gte: (path: string, value: unknown) => WhereNode;
|
|
109
|
+
lt: (path: string, value: unknown) => WhereNode;
|
|
110
|
+
lte: (path: string, value: unknown) => WhereNode;
|
|
111
|
+
in: (path: string, value: unknown[]) => WhereNode;
|
|
112
|
+
contains: (path: string, value: unknown) => WhereNode;
|
|
113
|
+
startsWith: (path: string, value: string) => WhereNode;
|
|
114
|
+
exists: (path: string, value?: boolean) => WhereNode;
|
|
115
|
+
and: (...conditions: WhereNode[]) => WhereNode;
|
|
116
|
+
or: (...conditions: WhereNode[]) => WhereNode;
|
|
117
|
+
not: (condition: WhereNode) => WhereNode;
|
|
118
|
+
};
|
|
119
|
+
export type OrderBuilder = {
|
|
120
|
+
asc: (path: string) => OrderBuilder;
|
|
121
|
+
desc: (path: string) => OrderBuilder;
|
|
122
|
+
};
|
|
123
|
+
export type QueryOptions = {
|
|
124
|
+
where?: (builder: WhereBuilder) => WhereNode;
|
|
125
|
+
orderBy?: (builder: OrderBuilder) => unknown;
|
|
126
|
+
select?: string[];
|
|
127
|
+
limit?: number;
|
|
128
|
+
cursor?: string;
|
|
129
|
+
};
|
|
130
|
+
export type Cursor = {
|
|
131
|
+
id: string;
|
|
132
|
+
last: Buffer;
|
|
133
|
+
fingerprint: string;
|
|
134
|
+
};
|
|
135
|
+
/** @typedef {"asc" | "desc"} Direction */
|
|
136
|
+
/** @typedef {Record<string, unknown> & { id: string | number }} Document */
|
|
137
|
+
/** @typedef {{ store: string, path: string, cursorTtlMs?: number }} DatabaseConfig */
|
|
138
|
+
/** @typedef {string | import("arktype").Type<unknown> | readonly ArkTypeValue[] | { [key: string]: ArkTypeValue }} ArkTypeDefinition */
|
|
139
|
+
/** @typedef {ArkTypeDefinition | null | boolean | number | bigint | Date | Uint8Array} ArkTypeValue */
|
|
140
|
+
/** @typedef {null | boolean | number | string | bigint | Date | Uint8Array | readonly DataValue[] | { [key: string]: DataValue }} DataValue */
|
|
141
|
+
/** @typedef {{ type: ArkTypeDefinition, primary?: boolean, default?: DataValue | (() => DataValue) }} ColumnDefinition */
|
|
142
|
+
/** @typedef {{ name: string, method?: "btree", columns: (string | { field: string, direction?: Direction })[], unique?: boolean }} IndexDefinition */
|
|
143
|
+
/** @typedef {{ table: string, columns: Record<string, ColumnDefinition>, indexes?: IndexDefinition[] }} TableDefinition */
|
|
144
|
+
/** @typedef {{ name: string, direction: Direction }} IndexField */
|
|
145
|
+
/** @typedef {{ name: string, method: "btree", fields: IndexField[], unique: boolean }} Index */
|
|
146
|
+
/** @typedef {{ name: string, columns: Record<string, ColumnDefinition>, indexes: Index[], validator: (document: unknown) => unknown }} Table */
|
|
147
|
+
/** @typedef {{ type: string, primary: boolean, optional: boolean, default: null | { kind: string, value?: string } }} StoredColumn */
|
|
148
|
+
/** @typedef {{ columns: Record<string, StoredColumn>, indexes: Index[] }} StoredTable */
|
|
149
|
+
/** @typedef {{ version: number, tables: Record<string, StoredTable> }} StoredSchema */
|
|
150
|
+
/** @typedef {{ version: number, tables: Map<string, Table>, stored: StoredSchema }} CompiledSchema */
|
|
151
|
+
/** @typedef {{ changed: boolean, additions: Map<string, { columns: string[], indexes: Index[] }> }} SchemaDiff */
|
|
152
|
+
/** @typedef {import("@slatedb/uniffi").Db | import("@slatedb/uniffi").DbSnapshot | import("@slatedb/uniffi").DbTransaction} Reader */
|
|
153
|
+
/** @typedef {{ snapshot: import("@slatedb/uniffi").DbSnapshot, fingerprint: string, lastUsed: number, active: number, timer?: NodeJS.Timeout }} Session */
|
|
154
|
+
/** @typedef {{ op: "eq" | "ne" | "gt" | "gte" | "lt" | "lte" | "in" | "contains" | "startsWith" | "exists", path: string, value: unknown }} Predicate */
|
|
155
|
+
/** @typedef {{ op: "and", conditions: WhereNode[] } | { op: "or", conditions: WhereNode[] } | { op: "not", condition: WhereNode } | Predicate} WhereNode */
|
|
156
|
+
/** @typedef {{ eq: (path: string, value: unknown) => WhereNode, ne: (path: string, value: unknown) => WhereNode, gt: (path: string, value: unknown) => WhereNode, gte: (path: string, value: unknown) => WhereNode, lt: (path: string, value: unknown) => WhereNode, lte: (path: string, value: unknown) => WhereNode, in: (path: string, value: unknown[]) => WhereNode, contains: (path: string, value: unknown) => WhereNode, startsWith: (path: string, value: string) => WhereNode, exists: (path: string, value?: boolean) => WhereNode, and: (...conditions: WhereNode[]) => WhereNode, or: (...conditions: WhereNode[]) => WhereNode, not: (condition: WhereNode) => WhereNode }} WhereBuilder */
|
|
157
|
+
/** @typedef {{ asc: (path: string) => OrderBuilder, desc: (path: string) => OrderBuilder }} OrderBuilder */
|
|
158
|
+
/** @typedef {{ where?: (builder: WhereBuilder) => WhereNode, orderBy?: (builder: OrderBuilder) => unknown, select?: string[], limit?: number, cursor?: string }} QueryOptions */
|
|
159
|
+
/** @typedef {{ id: string, last: Buffer, fingerprint: string }} Cursor */
|
|
160
|
+
export {};
|