arrowbase 0.1.1
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/CHANGELOG.md +27 -0
- package/COMPATIBILITY.md +398 -0
- package/LICENSE +21 -0
- package/MIGRATING.md +238 -0
- package/README.md +897 -0
- package/RELEASE_NOTES.md +68 -0
- package/dist/arrow.d.ts +93 -0
- package/dist/arrow.js +5366 -0
- package/dist/arrow.js.map +1 -0
- package/dist/broadcast.d.ts +173 -0
- package/dist/broadcast.js +319 -0
- package/dist/broadcast.js.map +1 -0
- package/dist/collection-DGlKgOGi.d.ts +1932 -0
- package/dist/idb.d.ts +146 -0
- package/dist/idb.js +6193 -0
- package/dist/idb.js.map +1 -0
- package/dist/index.d.ts +1802 -0
- package/dist/index.js +13924 -0
- package/dist/index.js.map +1 -0
- package/dist/query-CzV9E57Y.d.ts +279 -0
- package/dist/react.d.ts +51 -0
- package/dist/react.js +1633 -0
- package/dist/react.js.map +1 -0
- package/dist/tanstack.d.ts +51 -0
- package/dist/tanstack.js +191 -0
- package/dist/tanstack.js.map +1 -0
- package/dist/types-CSoU6uED.d.ts +50 -0
- package/package.json +139 -0
package/MIGRATING.md
ADDED
|
@@ -0,0 +1,238 @@
|
|
|
1
|
+
# MIGRATING.md — from @tanstack/db to ArrowBase
|
|
2
|
+
|
|
3
|
+
ArrowBase targets the same public API shape as `@tanstack/db`, but stores rows in
|
|
4
|
+
Arrow-style column buffers. Most app code can switch imports first, then opt into
|
|
5
|
+
columnar-specific persistence, IPC, and indexing features later.
|
|
6
|
+
|
|
7
|
+
## Quick migration checklist
|
|
8
|
+
|
|
9
|
+
1. Change imports from `@tanstack/db` to `arrowbase`.
|
|
10
|
+
2. Add an ArrowBase schema and `capacity` for every root collection.
|
|
11
|
+
3. Keep `getKey`, mutation handlers, transactions, optimistic actions, live query
|
|
12
|
+
builders, local-only helpers, and local-storage helpers the same shape.
|
|
13
|
+
4. Run the parity gates: `pnpm typecheck`, `pnpm test`, `pnpm test:differential`,
|
|
14
|
+
`pnpm test:golden`, and `pnpm bench:vs-tanstack`.
|
|
15
|
+
5. Check [COMPATIBILITY.md](./COMPATIBILITY.md) if an import touches a less common
|
|
16
|
+
helper or type alias.
|
|
17
|
+
|
|
18
|
+
## Side-by-side snippets
|
|
19
|
+
|
|
20
|
+
### 1. Local-only collection
|
|
21
|
+
|
|
22
|
+
TanStack DB:
|
|
23
|
+
|
|
24
|
+
```ts
|
|
25
|
+
import { createCollection, localOnlyCollectionOptions } from '@tanstack/db';
|
|
26
|
+
|
|
27
|
+
type Todo = {
|
|
28
|
+
id: number;
|
|
29
|
+
title: string;
|
|
30
|
+
done: boolean;
|
|
31
|
+
};
|
|
32
|
+
|
|
33
|
+
const todos = createCollection(
|
|
34
|
+
localOnlyCollectionOptions<Todo, number>({
|
|
35
|
+
id: 'todos',
|
|
36
|
+
getKey: (todo) => todo.id,
|
|
37
|
+
initialData: [{ id: 1, title: 'ship', done: false }],
|
|
38
|
+
}),
|
|
39
|
+
);
|
|
40
|
+
|
|
41
|
+
await todos.preload();
|
|
42
|
+
```
|
|
43
|
+
|
|
44
|
+
ArrowBase:
|
|
45
|
+
|
|
46
|
+
```ts
|
|
47
|
+
import { createCollection, defineSchema, localOnlyCollectionOptions } from 'arrowbase';
|
|
48
|
+
|
|
49
|
+
type Todo = {
|
|
50
|
+
__id: number;
|
|
51
|
+
title: string;
|
|
52
|
+
done: boolean;
|
|
53
|
+
};
|
|
54
|
+
|
|
55
|
+
const todoSchema = defineSchema({
|
|
56
|
+
name: 'todos',
|
|
57
|
+
columns: {
|
|
58
|
+
__id: { type: 'uint32' },
|
|
59
|
+
title: { type: 'utf8' },
|
|
60
|
+
done: { type: 'bool' },
|
|
61
|
+
},
|
|
62
|
+
});
|
|
63
|
+
|
|
64
|
+
const todos = createCollection(
|
|
65
|
+
localOnlyCollectionOptions<Todo, number>({
|
|
66
|
+
id: 'todos',
|
|
67
|
+
schema: todoSchema,
|
|
68
|
+
capacity: 10_000,
|
|
69
|
+
getKey: (todo) => todo.__id,
|
|
70
|
+
initialData: [{ __id: 1, title: 'ship', done: false }],
|
|
71
|
+
}),
|
|
72
|
+
);
|
|
73
|
+
|
|
74
|
+
await todos.preload();
|
|
75
|
+
```
|
|
76
|
+
|
|
77
|
+
Key difference: ArrowBase needs a compiled column schema and fixed `capacity`.
|
|
78
|
+
Use `__id` when you want the native primary-key fast path; custom keys still work
|
|
79
|
+
through `getKey` for TanStack-shaped APIs.
|
|
80
|
+
|
|
81
|
+
### 2. Mutations and transactions
|
|
82
|
+
|
|
83
|
+
TanStack DB:
|
|
84
|
+
|
|
85
|
+
```ts
|
|
86
|
+
import { createTransaction } from '@tanstack/db';
|
|
87
|
+
|
|
88
|
+
const tx = createTransaction({
|
|
89
|
+
mutationFn: async ({ transaction }) => {
|
|
90
|
+
await api.save(transaction.mutations);
|
|
91
|
+
},
|
|
92
|
+
});
|
|
93
|
+
|
|
94
|
+
tx.mutate(() => {
|
|
95
|
+
todos.insert({ id: 2, title: 'docs', done: false });
|
|
96
|
+
todos.update(1, (draft) => {
|
|
97
|
+
draft.done = true;
|
|
98
|
+
});
|
|
99
|
+
});
|
|
100
|
+
|
|
101
|
+
await tx.isPersisted.promise;
|
|
102
|
+
```
|
|
103
|
+
|
|
104
|
+
ArrowBase:
|
|
105
|
+
|
|
106
|
+
```ts
|
|
107
|
+
import { createTransaction } from 'arrowbase';
|
|
108
|
+
|
|
109
|
+
const tx = createTransaction({
|
|
110
|
+
mutationFn: async ({ transaction }) => {
|
|
111
|
+
await api.save(transaction.mutations);
|
|
112
|
+
},
|
|
113
|
+
});
|
|
114
|
+
|
|
115
|
+
tx.mutate(() => {
|
|
116
|
+
todos.insert({ __id: 2, title: 'docs', done: false });
|
|
117
|
+
todos.update(1, (draft) => {
|
|
118
|
+
draft.done = true;
|
|
119
|
+
});
|
|
120
|
+
});
|
|
121
|
+
|
|
122
|
+
await tx.isPersisted.promise;
|
|
123
|
+
```
|
|
124
|
+
|
|
125
|
+
`ChangeMessage`, `PendingMutation`, rollback, optimistic mutation, and ambient
|
|
126
|
+
transaction shapes match the reference implementation. ArrowBase keeps the same
|
|
127
|
+
callback contracts but writes into column buffers.
|
|
128
|
+
|
|
129
|
+
### 3. Query builder and aggregates
|
|
130
|
+
|
|
131
|
+
TanStack DB:
|
|
132
|
+
|
|
133
|
+
```ts
|
|
134
|
+
import { Query, count, gt, sum } from '@tanstack/db';
|
|
135
|
+
|
|
136
|
+
const byDone = new Query()
|
|
137
|
+
.from({ todos })
|
|
138
|
+
.select(({ todos }) => ({
|
|
139
|
+
done: todos.done,
|
|
140
|
+
n: count(todos.id),
|
|
141
|
+
total: sum(todos.id),
|
|
142
|
+
}))
|
|
143
|
+
.where(({ todos }) => gt(todos.id, 0))
|
|
144
|
+
.groupBy(({ todos }) => todos.done);
|
|
145
|
+
```
|
|
146
|
+
|
|
147
|
+
ArrowBase:
|
|
148
|
+
|
|
149
|
+
```ts
|
|
150
|
+
import { Query, count, gt, sum } from 'arrowbase';
|
|
151
|
+
|
|
152
|
+
const byDone = new Query()
|
|
153
|
+
.from({ todos })
|
|
154
|
+
.select(({ todos }) => ({
|
|
155
|
+
done: todos.done,
|
|
156
|
+
n: count(todos.__id),
|
|
157
|
+
total: sum(todos.__id),
|
|
158
|
+
}))
|
|
159
|
+
.where(({ todos }) => gt(todos.__id, 0))
|
|
160
|
+
.groupBy(({ todos }) => todos.done);
|
|
161
|
+
```
|
|
162
|
+
|
|
163
|
+
The builder surface is compatible. ArrowBase also keeps its native `query()` /
|
|
164
|
+
`run()` API and vectorized `filter()` DSL for hot columnar paths.
|
|
165
|
+
|
|
166
|
+
### 4. Local storage
|
|
167
|
+
|
|
168
|
+
TanStack DB:
|
|
169
|
+
|
|
170
|
+
```ts
|
|
171
|
+
import { createCollection, localStorageCollectionOptions } from '@tanstack/db';
|
|
172
|
+
|
|
173
|
+
const prefs = createCollection(
|
|
174
|
+
localStorageCollectionOptions({
|
|
175
|
+
id: 'prefs',
|
|
176
|
+
storageKey: 'app:prefs',
|
|
177
|
+
getKey: (row) => row.id,
|
|
178
|
+
}),
|
|
179
|
+
);
|
|
180
|
+
```
|
|
181
|
+
|
|
182
|
+
ArrowBase:
|
|
183
|
+
|
|
184
|
+
```ts
|
|
185
|
+
import { createCollection, defineSchema, localStorageCollectionOptions } from 'arrowbase';
|
|
186
|
+
|
|
187
|
+
const prefsSchema = defineSchema({
|
|
188
|
+
name: 'prefs',
|
|
189
|
+
columns: {
|
|
190
|
+
__id: { type: 'uint32' },
|
|
191
|
+
name: { type: 'utf8' },
|
|
192
|
+
value: { type: 'utf8' },
|
|
193
|
+
},
|
|
194
|
+
});
|
|
195
|
+
|
|
196
|
+
const prefs = createCollection(
|
|
197
|
+
localStorageCollectionOptions({
|
|
198
|
+
id: 'prefs',
|
|
199
|
+
schema: prefsSchema,
|
|
200
|
+
capacity: 1_000,
|
|
201
|
+
storageKey: 'app:prefs',
|
|
202
|
+
getKey: (row) => row.__id,
|
|
203
|
+
}),
|
|
204
|
+
);
|
|
205
|
+
```
|
|
206
|
+
|
|
207
|
+
ArrowBase local storage persists the same logical collection state and exposes
|
|
208
|
+
`clearStorage`, `getStorageSize`, and `acceptMutations` utilities. The storage
|
|
209
|
+
record is columnar snapshot data rather than plain row JSON unless you provide a
|
|
210
|
+
custom parser.
|
|
211
|
+
|
|
212
|
+
## Common pitfalls
|
|
213
|
+
|
|
214
|
+
- **Capacity is explicit.** ArrowBase collections allocate typed column buffers
|
|
215
|
+
up front. Pick a headroom value and add app-level rollover/compaction if the
|
|
216
|
+
collection can exceed it.
|
|
217
|
+
- **Schema first.** You must map row fields to ArrowBase column types. `utf8`,
|
|
218
|
+
`dict_utf8`, `binary`, `list`, and `struct` are available for richer rows.
|
|
219
|
+
- **Primary-key naming.** Native examples use `__id`. If an existing app uses
|
|
220
|
+
`id`, either rename during migration or keep `getKey: (row) => row.id` and add
|
|
221
|
+
a numeric `__id` for columnar PK storage.
|
|
222
|
+
- **BigInt ↔ Number.** Safe-range numeric join keys are normalized so `int64` and
|
|
223
|
+
`uint32` keys can match. Outside the safe integer range, keep both sides as
|
|
224
|
+
`bigint` to avoid precision loss.
|
|
225
|
+
- **floating-point aggregate tolerance.** ArrowBase uses stable summation for
|
|
226
|
+
`sum`/`avg`. Results can differ from the reference in the last few bits; compare
|
|
227
|
+
with a tolerance rather than strict stringified floats.
|
|
228
|
+
- **Soft deletes.** ArrowBase can preserve tombstones internally and omit them
|
|
229
|
+
from public rows. Use `includeSoftDeleted` only when the app intentionally
|
|
230
|
+
renders tombstones.
|
|
231
|
+
- **Browser SharedArrayBuffer.** Browser use needs COOP/COEP headers. Node and
|
|
232
|
+
worker-thread usage do not need extra headers.
|
|
233
|
+
|
|
234
|
+
## Compatibility source of truth
|
|
235
|
+
|
|
236
|
+
[COMPATIBILITY.md](./COMPATIBILITY.md) is generated from the enumerated
|
|
237
|
+
`@tanstack/db@0.6.5` export list. For this parity release it is all green:
|
|
238
|
+
289/289 exports reviewed and accepted under the tolerances above.
|