@powersync/web 0.0.0-dev-20241119081147 → 0.0.0-dev-20250127153955
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 +33 -0
- package/dist/3cb48be086dd9edd02ff.wasm +0 -0
- package/dist/_journeyapps_wa-sqlite-_journeyapps_wa-sqlite_src_examples_IDBBatchAtomicVFS_js-_powersync_co-780aa20.index.umd.js +335 -0
- package/dist/_journeyapps_wa-sqlite-_journeyapps_wa-sqlite_src_examples_IDBBatchAtomicVFS_js-_powersync_co-780aa20.index.umd.js.map +1 -0
- package/dist/_journeyapps_wa-sqlite-_journeyapps_wa-sqlite_src_examples_IDBBatchAtomicVFS_js-_powersync_co-780aa21.index.umd.js +335 -0
- package/dist/_journeyapps_wa-sqlite-_journeyapps_wa-sqlite_src_examples_IDBBatchAtomicVFS_js-_powersync_co-780aa21.index.umd.js.map +1 -0
- package/dist/df958358cadf945bd0fe.wasm +0 -0
- package/dist/f9c8ada26c59f5bf4339.wasm +0 -0
- package/dist/fe5693c7678cf12e05ac.wasm +0 -0
- package/dist/index.umd.js +3716 -626
- package/dist/index.umd.js.map +1 -1
- package/dist/worker/SharedSyncImplementation.umd.js +275 -2200
- package/dist/worker/SharedSyncImplementation.umd.js.map +1 -1
- package/dist/worker/WASQLiteDB.umd.js +956 -395
- package/dist/worker/WASQLiteDB.umd.js.map +1 -1
- package/dist/worker/node_modules_journeyapps_wa-sqlite_dist_mc-wa-sqlite-async_mjs.umd.js +45 -0
- package/dist/worker/node_modules_journeyapps_wa-sqlite_dist_mc-wa-sqlite-async_mjs.umd.js.map +1 -0
- package/dist/worker/node_modules_journeyapps_wa-sqlite_dist_mc-wa-sqlite_mjs.umd.js +45 -0
- package/dist/worker/node_modules_journeyapps_wa-sqlite_dist_mc-wa-sqlite_mjs.umd.js.map +1 -0
- package/dist/worker/node_modules_journeyapps_wa-sqlite_dist_wa-sqlite-async_mjs.umd.js +2 -132
- package/dist/worker/node_modules_journeyapps_wa-sqlite_dist_wa-sqlite-async_mjs.umd.js.map +1 -1
- package/dist/worker/node_modules_journeyapps_wa-sqlite_dist_wa-sqlite_mjs.umd.js +45 -0
- package/dist/worker/node_modules_journeyapps_wa-sqlite_dist_wa-sqlite_mjs.umd.js.map +1 -0
- package/dist/worker/node_modules_journeyapps_wa-sqlite_src_examples_AccessHandlePoolVFS_js.umd.js +1509 -0
- package/dist/worker/node_modules_journeyapps_wa-sqlite_src_examples_AccessHandlePoolVFS_js.umd.js.map +1 -0
- package/dist/worker/node_modules_journeyapps_wa-sqlite_src_examples_IDBBatchAtomicVFS_js.umd.js +1746 -1372
- package/dist/worker/node_modules_journeyapps_wa-sqlite_src_examples_IDBBatchAtomicVFS_js.umd.js.map +1 -1
- package/dist/worker/node_modules_journeyapps_wa-sqlite_src_examples_OPFSCoopSyncVFS_js.umd.js +1641 -0
- package/dist/worker/node_modules_journeyapps_wa-sqlite_src_examples_OPFSCoopSyncVFS_js.umd.js.map +1 -0
- package/lib/package.json +6 -6
- package/lib/src/db/PowerSyncDatabase.d.ts +10 -2
- package/lib/src/db/PowerSyncDatabase.js +20 -4
- package/lib/src/db/adapters/AbstractWebSQLOpenFactory.d.ts +2 -0
- package/lib/src/db/adapters/AbstractWebSQLOpenFactory.js +3 -0
- package/lib/src/db/adapters/AsyncDatabaseConnection.d.ts +26 -0
- package/lib/src/db/adapters/LockedAsyncDatabaseAdapter.d.ts +82 -0
- package/lib/src/db/adapters/LockedAsyncDatabaseAdapter.js +239 -0
- package/lib/src/db/adapters/WebDBAdapter.d.ts +17 -0
- package/lib/src/db/adapters/WebDBAdapter.js +1 -0
- package/lib/src/db/adapters/WorkerWrappedAsyncDatabaseConnection.d.ts +39 -0
- package/lib/src/db/adapters/WorkerWrappedAsyncDatabaseConnection.js +46 -0
- package/lib/src/db/adapters/wa-sqlite/WASQLiteConnection.d.ts +127 -0
- package/lib/src/db/adapters/wa-sqlite/WASQLiteConnection.js +343 -0
- package/lib/src/db/adapters/wa-sqlite/WASQLiteDBAdapter.d.ts +12 -43
- package/lib/src/db/adapters/wa-sqlite/WASQLiteDBAdapter.js +36 -209
- package/lib/src/db/adapters/wa-sqlite/WASQLiteOpenFactory.d.ts +12 -0
- package/lib/src/db/adapters/wa-sqlite/WASQLiteOpenFactory.js +81 -4
- package/lib/src/db/adapters/web-sql-flags.d.ts +26 -0
- package/lib/src/db/adapters/web-sql-flags.js +5 -0
- package/lib/src/db/sync/SharedWebStreamingSyncImplementation.d.ts +9 -2
- package/lib/src/db/sync/SharedWebStreamingSyncImplementation.js +17 -12
- package/lib/src/db/sync/WebStreamingSyncImplementation.d.ts +0 -5
- package/lib/src/index.d.ts +8 -7
- package/lib/src/index.js +8 -7
- package/lib/src/worker/db/WASQLiteDB.worker.js +38 -20
- package/lib/src/worker/db/open-worker-database.d.ts +5 -4
- package/lib/src/worker/db/open-worker-database.js +5 -3
- package/lib/src/worker/sync/AbstractSharedSyncClientProvider.d.ts +1 -0
- package/lib/src/worker/sync/SharedSyncImplementation.d.ts +20 -3
- package/lib/src/worker/sync/SharedSyncImplementation.js +40 -11
- package/lib/tsconfig.tsbuildinfo +1 -1
- package/package.json +7 -7
- package/dist/5fe5ed837a91c836c24f.wasm +0 -0
- package/lib/src/shared/open-db.d.ts +0 -5
- package/lib/src/shared/open-db.js +0 -192
- package/lib/src/shared/types.d.ts +0 -22
- /package/lib/src/{shared/types.js → db/adapters/AsyncDatabaseConnection.js} +0 -0
|
@@ -1,219 +1,46 @@
|
|
|
1
|
-
import { BaseObserver } from '@powersync/common';
|
|
2
1
|
import * as Comlink from 'comlink';
|
|
3
|
-
import
|
|
4
|
-
import {
|
|
5
|
-
import {
|
|
6
|
-
import {
|
|
7
|
-
import {
|
|
2
|
+
import { resolveWebPowerSyncFlags } from '../../PowerSyncDatabase';
|
|
3
|
+
import { LockedAsyncDatabaseAdapter } from '../LockedAsyncDatabaseAdapter';
|
|
4
|
+
import { TemporaryStorageOption } from '../web-sql-flags';
|
|
5
|
+
import { WorkerWrappedAsyncDatabaseConnection } from '../WorkerWrappedAsyncDatabaseConnection';
|
|
6
|
+
import { WASQLiteOpenFactory } from './WASQLiteOpenFactory';
|
|
8
7
|
/**
|
|
9
8
|
* Adapter for WA-SQLite SQLite connections.
|
|
10
9
|
*/
|
|
11
|
-
export class WASQLiteDBAdapter extends
|
|
12
|
-
options;
|
|
13
|
-
initialized;
|
|
14
|
-
logger;
|
|
15
|
-
dbGetHelpers;
|
|
16
|
-
methods;
|
|
17
|
-
debugMode;
|
|
10
|
+
export class WASQLiteDBAdapter extends LockedAsyncDatabaseAdapter {
|
|
18
11
|
constructor(options) {
|
|
19
|
-
super(
|
|
20
|
-
|
|
21
|
-
|
|
22
|
-
|
|
23
|
-
|
|
24
|
-
|
|
25
|
-
|
|
26
|
-
|
|
27
|
-
|
|
28
|
-
|
|
29
|
-
|
|
30
|
-
|
|
31
|
-
|
|
32
|
-
|
|
12
|
+
super({
|
|
13
|
+
name: options.dbFilename,
|
|
14
|
+
openConnection: async () => {
|
|
15
|
+
const { workerPort, temporaryStorage } = options;
|
|
16
|
+
if (workerPort) {
|
|
17
|
+
const remote = Comlink.wrap(workerPort);
|
|
18
|
+
return new WorkerWrappedAsyncDatabaseConnection({
|
|
19
|
+
remote,
|
|
20
|
+
identifier: options.dbFilename,
|
|
21
|
+
baseConnection: await remote({
|
|
22
|
+
...options,
|
|
23
|
+
temporaryStorage: temporaryStorage ?? TemporaryStorageOption.MEMORY,
|
|
24
|
+
flags: resolveWebPowerSyncFlags(options.flags),
|
|
25
|
+
encryptionKey: options.encryptionKey
|
|
26
|
+
})
|
|
27
|
+
});
|
|
33
28
|
}
|
|
34
|
-
|
|
35
|
-
|
|
36
|
-
|
|
37
|
-
|
|
38
|
-
|
|
39
|
-
|
|
40
|
-
|
|
41
|
-
|
|
42
|
-
|
|
43
|
-
|
|
44
|
-
}
|
|
45
|
-
get name() {
|
|
46
|
-
return this.options.dbFilename;
|
|
47
|
-
}
|
|
48
|
-
get flags() {
|
|
49
|
-
return resolveWebSQLFlags(this.options.flags ?? {});
|
|
50
|
-
}
|
|
51
|
-
getWorker() { }
|
|
52
|
-
async init() {
|
|
53
|
-
const { enableMultiTabs, useWebWorker } = this.flags;
|
|
54
|
-
if (!enableMultiTabs) {
|
|
55
|
-
this.logger.warn('Multiple tabs are not enabled in this browser');
|
|
56
|
-
}
|
|
57
|
-
if (useWebWorker) {
|
|
58
|
-
const optionsDbWorker = this.options.worker;
|
|
59
|
-
const dbOpener = this.options.workerPort
|
|
60
|
-
? Comlink.wrap(this.options.workerPort)
|
|
61
|
-
: typeof optionsDbWorker === 'function'
|
|
62
|
-
? Comlink.wrap(resolveWorkerDatabasePortFactory(() => optionsDbWorker({
|
|
63
|
-
...this.options,
|
|
64
|
-
flags: this.flags
|
|
65
|
-
})))
|
|
66
|
-
: getWorkerDatabaseOpener(this.options.dbFilename, enableMultiTabs, optionsDbWorker);
|
|
67
|
-
this.methods = await dbOpener(this.options.dbFilename);
|
|
68
|
-
this.methods.registerOnTableChange(Comlink.proxy((event) => {
|
|
69
|
-
this.iterateListeners((cb) => cb.tablesUpdated?.(event));
|
|
70
|
-
}));
|
|
71
|
-
return;
|
|
72
|
-
}
|
|
73
|
-
this.methods = await _openDB(this.options.dbFilename, { useWebWorker: false });
|
|
74
|
-
this.methods.registerOnTableChange((event) => {
|
|
75
|
-
this.iterateListeners((cb) => cb.tablesUpdated?.(event));
|
|
76
|
-
});
|
|
77
|
-
}
|
|
78
|
-
async execute(query, params) {
|
|
79
|
-
return this.writeLock((ctx) => ctx.execute(query, params));
|
|
80
|
-
}
|
|
81
|
-
async executeBatch(query, params) {
|
|
82
|
-
return this.writeLock((ctx) => this._executeBatch(query, params));
|
|
83
|
-
}
|
|
84
|
-
/**
|
|
85
|
-
* Wraps the worker execute function, awaiting for it to be available
|
|
86
|
-
*/
|
|
87
|
-
_execute = async (sql, bindings) => {
|
|
88
|
-
await this.initialized;
|
|
89
|
-
const result = await this.methods.execute(sql, bindings);
|
|
90
|
-
return {
|
|
91
|
-
...result,
|
|
92
|
-
rows: {
|
|
93
|
-
...result.rows,
|
|
94
|
-
item: (idx) => result.rows._array[idx]
|
|
95
|
-
}
|
|
96
|
-
};
|
|
97
|
-
};
|
|
98
|
-
/**
|
|
99
|
-
* Wraps the worker executeBatch function, awaiting for it to be available
|
|
100
|
-
*/
|
|
101
|
-
_executeBatch = async (query, params) => {
|
|
102
|
-
await this.initialized;
|
|
103
|
-
const result = await this.methods.executeBatch(query, params);
|
|
104
|
-
return {
|
|
105
|
-
...result,
|
|
106
|
-
rows: undefined
|
|
107
|
-
};
|
|
108
|
-
};
|
|
109
|
-
/**
|
|
110
|
-
* Attempts to close the connection.
|
|
111
|
-
* Shared workers might not actually close the connection if other
|
|
112
|
-
* tabs are still using it.
|
|
113
|
-
*/
|
|
114
|
-
close() {
|
|
115
|
-
this.methods?.close?.();
|
|
116
|
-
}
|
|
117
|
-
async getAll(sql, parameters) {
|
|
118
|
-
await this.initialized;
|
|
119
|
-
return this.dbGetHelpers.getAll(sql, parameters);
|
|
120
|
-
}
|
|
121
|
-
async getOptional(sql, parameters) {
|
|
122
|
-
await this.initialized;
|
|
123
|
-
return this.dbGetHelpers.getOptional(sql, parameters);
|
|
124
|
-
}
|
|
125
|
-
async get(sql, parameters) {
|
|
126
|
-
await this.initialized;
|
|
127
|
-
return this.dbGetHelpers.get(sql, parameters);
|
|
128
|
-
}
|
|
129
|
-
async readLock(fn, options) {
|
|
130
|
-
await this.initialized;
|
|
131
|
-
return this.acquireLock(async () => fn(this.generateDBHelpers({ execute: this._execute })));
|
|
132
|
-
}
|
|
133
|
-
async writeLock(fn, options) {
|
|
134
|
-
await this.initialized;
|
|
135
|
-
return this.acquireLock(async () => fn(this.generateDBHelpers({ execute: this._execute })));
|
|
136
|
-
}
|
|
137
|
-
acquireLock(callback) {
|
|
138
|
-
return getNavigatorLocks().request(`db-lock-${this.options.dbFilename}`, callback);
|
|
139
|
-
}
|
|
140
|
-
async readTransaction(fn, options) {
|
|
141
|
-
return this.readLock(this.wrapTransaction(fn));
|
|
142
|
-
}
|
|
143
|
-
writeTransaction(fn, options) {
|
|
144
|
-
return this.writeLock(this.wrapTransaction(fn));
|
|
145
|
-
}
|
|
146
|
-
/**
|
|
147
|
-
* Wraps a lock context into a transaction context
|
|
148
|
-
*/
|
|
149
|
-
wrapTransaction(cb) {
|
|
150
|
-
return async (tx) => {
|
|
151
|
-
await this._execute('BEGIN TRANSACTION');
|
|
152
|
-
let finalized = false;
|
|
153
|
-
const commit = async () => {
|
|
154
|
-
if (finalized) {
|
|
155
|
-
return { rowsAffected: 0 };
|
|
156
|
-
}
|
|
157
|
-
finalized = true;
|
|
158
|
-
return this._execute('COMMIT');
|
|
159
|
-
};
|
|
160
|
-
const rollback = () => {
|
|
161
|
-
finalized = true;
|
|
162
|
-
return this._execute('ROLLBACK');
|
|
163
|
-
};
|
|
164
|
-
try {
|
|
165
|
-
const result = await cb({
|
|
166
|
-
...tx,
|
|
167
|
-
commit,
|
|
168
|
-
rollback
|
|
29
|
+
const openFactory = new WASQLiteOpenFactory({
|
|
30
|
+
dbFilename: options.dbFilename,
|
|
31
|
+
dbLocation: options.dbLocation,
|
|
32
|
+
debugMode: options.debugMode,
|
|
33
|
+
flags: options.flags,
|
|
34
|
+
temporaryStorage,
|
|
35
|
+
logger: options.logger,
|
|
36
|
+
vfs: options.vfs,
|
|
37
|
+
encryptionKey: options.encryptionKey,
|
|
38
|
+
worker: options.worker
|
|
169
39
|
});
|
|
170
|
-
|
|
171
|
-
await commit();
|
|
172
|
-
}
|
|
173
|
-
return result;
|
|
174
|
-
}
|
|
175
|
-
catch (ex) {
|
|
176
|
-
this.logger.debug('Caught ex in transaction', ex);
|
|
177
|
-
try {
|
|
178
|
-
await rollback();
|
|
179
|
-
}
|
|
180
|
-
catch (ex2) {
|
|
181
|
-
// In rare cases, a rollback may fail.
|
|
182
|
-
// Safe to ignore.
|
|
183
|
-
}
|
|
184
|
-
throw ex;
|
|
185
|
-
}
|
|
186
|
-
};
|
|
187
|
-
}
|
|
188
|
-
generateDBHelpers(tx) {
|
|
189
|
-
return {
|
|
190
|
-
...tx,
|
|
191
|
-
/**
|
|
192
|
-
* Execute a read-only query and return results
|
|
193
|
-
*/
|
|
194
|
-
async getAll(sql, parameters) {
|
|
195
|
-
const res = await tx.execute(sql, parameters);
|
|
196
|
-
return res.rows?._array ?? [];
|
|
40
|
+
return openFactory.openConnection();
|
|
197
41
|
},
|
|
198
|
-
|
|
199
|
-
|
|
200
|
-
|
|
201
|
-
async getOptional(sql, parameters) {
|
|
202
|
-
const res = await tx.execute(sql, parameters);
|
|
203
|
-
return res.rows?.item(0) ?? null;
|
|
204
|
-
},
|
|
205
|
-
/**
|
|
206
|
-
* Execute a read-only query and return the first result, error if the ResultSet is empty.
|
|
207
|
-
*/
|
|
208
|
-
async get(sql, parameters) {
|
|
209
|
-
const res = await tx.execute(sql, parameters);
|
|
210
|
-
const first = res.rows?.item(0);
|
|
211
|
-
if (!first) {
|
|
212
|
-
throw new Error('Result set is empty');
|
|
213
|
-
}
|
|
214
|
-
return first;
|
|
215
|
-
}
|
|
216
|
-
};
|
|
42
|
+
debugMode: options.debugMode,
|
|
43
|
+
logger: options.logger
|
|
44
|
+
});
|
|
217
45
|
}
|
|
218
|
-
async refreshSchema() { }
|
|
219
46
|
}
|
|
@@ -1,8 +1,20 @@
|
|
|
1
1
|
import { DBAdapter } from '@powersync/common';
|
|
2
2
|
import { AbstractWebSQLOpenFactory } from '../AbstractWebSQLOpenFactory';
|
|
3
|
+
import { AsyncDatabaseConnection } from '../AsyncDatabaseConnection';
|
|
4
|
+
import { ResolvedWebSQLOpenOptions, WebSQLOpenFactoryOptions } from '../web-sql-flags';
|
|
5
|
+
import { WASQLiteVFS } from './WASQLiteConnection';
|
|
6
|
+
export interface WASQLiteOpenFactoryOptions extends WebSQLOpenFactoryOptions {
|
|
7
|
+
vfs?: WASQLiteVFS;
|
|
8
|
+
}
|
|
9
|
+
export interface ResolvedWASQLiteOpenFactoryOptions extends ResolvedWebSQLOpenOptions {
|
|
10
|
+
vfs: WASQLiteVFS;
|
|
11
|
+
}
|
|
3
12
|
/**
|
|
4
13
|
* Opens a SQLite connection using WA-SQLite.
|
|
5
14
|
*/
|
|
6
15
|
export declare class WASQLiteOpenFactory extends AbstractWebSQLOpenFactory {
|
|
16
|
+
constructor(options: WASQLiteOpenFactoryOptions);
|
|
17
|
+
get waOptions(): WASQLiteOpenFactoryOptions;
|
|
7
18
|
protected openAdapter(): DBAdapter;
|
|
19
|
+
openConnection(): Promise<AsyncDatabaseConnection>;
|
|
8
20
|
}
|
|
@@ -1,13 +1,90 @@
|
|
|
1
|
-
import
|
|
1
|
+
import * as Comlink from 'comlink';
|
|
2
|
+
import { openWorkerDatabasePort, resolveWorkerDatabasePortFactory } from '../../../worker/db/open-worker-database';
|
|
2
3
|
import { AbstractWebSQLOpenFactory } from '../AbstractWebSQLOpenFactory';
|
|
4
|
+
import { LockedAsyncDatabaseAdapter } from '../LockedAsyncDatabaseAdapter';
|
|
5
|
+
import { TemporaryStorageOption } from '../web-sql-flags';
|
|
6
|
+
import { WorkerWrappedAsyncDatabaseConnection } from '../WorkerWrappedAsyncDatabaseConnection';
|
|
7
|
+
import { WASqliteConnection, WASQLiteVFS } from './WASQLiteConnection';
|
|
3
8
|
/**
|
|
4
9
|
* Opens a SQLite connection using WA-SQLite.
|
|
5
10
|
*/
|
|
6
11
|
export class WASQLiteOpenFactory extends AbstractWebSQLOpenFactory {
|
|
12
|
+
constructor(options) {
|
|
13
|
+
super(options);
|
|
14
|
+
assertValidWASQLiteOpenFactoryOptions(options);
|
|
15
|
+
}
|
|
16
|
+
get waOptions() {
|
|
17
|
+
// Cast to extended type
|
|
18
|
+
return this.options;
|
|
19
|
+
}
|
|
7
20
|
openAdapter() {
|
|
8
|
-
return new
|
|
9
|
-
|
|
10
|
-
|
|
21
|
+
return new LockedAsyncDatabaseAdapter({
|
|
22
|
+
name: this.options.dbFilename,
|
|
23
|
+
openConnection: () => this.openConnection(),
|
|
24
|
+
debugMode: this.options.debugMode,
|
|
25
|
+
logger: this.logger
|
|
11
26
|
});
|
|
12
27
|
}
|
|
28
|
+
async openConnection() {
|
|
29
|
+
const { enableMultiTabs, useWebWorker } = this.resolvedFlags;
|
|
30
|
+
const { vfs = WASQLiteVFS.IDBBatchAtomicVFS, temporaryStorage = TemporaryStorageOption.MEMORY, encryptionKey } = this.waOptions;
|
|
31
|
+
if (!enableMultiTabs) {
|
|
32
|
+
this.logger.warn('Multiple tabs are not enabled in this browser');
|
|
33
|
+
}
|
|
34
|
+
if (useWebWorker) {
|
|
35
|
+
const optionsDbWorker = this.options.worker;
|
|
36
|
+
const workerPort = typeof optionsDbWorker == 'function'
|
|
37
|
+
? resolveWorkerDatabasePortFactory(() => optionsDbWorker({
|
|
38
|
+
...this.options,
|
|
39
|
+
temporaryStorage,
|
|
40
|
+
flags: this.resolvedFlags,
|
|
41
|
+
encryptionKey
|
|
42
|
+
}))
|
|
43
|
+
: openWorkerDatabasePort(this.options.dbFilename, enableMultiTabs, optionsDbWorker, this.waOptions.vfs);
|
|
44
|
+
const workerDBOpener = Comlink.wrap(workerPort);
|
|
45
|
+
return new WorkerWrappedAsyncDatabaseConnection({
|
|
46
|
+
remote: workerDBOpener,
|
|
47
|
+
baseConnection: await workerDBOpener({
|
|
48
|
+
dbFilename: this.options.dbFilename,
|
|
49
|
+
vfs,
|
|
50
|
+
temporaryStorage,
|
|
51
|
+
flags: this.resolvedFlags,
|
|
52
|
+
encryptionKey: encryptionKey
|
|
53
|
+
}),
|
|
54
|
+
identifier: this.options.dbFilename,
|
|
55
|
+
onClose: () => {
|
|
56
|
+
if (workerPort instanceof Worker) {
|
|
57
|
+
workerPort.terminate();
|
|
58
|
+
}
|
|
59
|
+
else {
|
|
60
|
+
workerPort.close();
|
|
61
|
+
}
|
|
62
|
+
}
|
|
63
|
+
});
|
|
64
|
+
}
|
|
65
|
+
else {
|
|
66
|
+
// Don't use a web worker
|
|
67
|
+
return new WASqliteConnection({
|
|
68
|
+
dbFilename: this.options.dbFilename,
|
|
69
|
+
dbLocation: this.options.dbLocation,
|
|
70
|
+
debugMode: this.options.debugMode,
|
|
71
|
+
vfs,
|
|
72
|
+
temporaryStorage,
|
|
73
|
+
flags: this.resolvedFlags,
|
|
74
|
+
encryptionKey: encryptionKey
|
|
75
|
+
});
|
|
76
|
+
}
|
|
77
|
+
}
|
|
78
|
+
}
|
|
79
|
+
/**
|
|
80
|
+
* Asserts that the factory options are valid.
|
|
81
|
+
*/
|
|
82
|
+
function assertValidWASQLiteOpenFactoryOptions(options) {
|
|
83
|
+
// The OPFS VFS only works in dedicated web workers.
|
|
84
|
+
if ('vfs' in options && 'flags' in options) {
|
|
85
|
+
const { vfs, flags = {} } = options;
|
|
86
|
+
if (vfs !== WASQLiteVFS.IDBBatchAtomicVFS && 'useWebWorker' in flags && !flags.useWebWorker) {
|
|
87
|
+
throw new Error(`Invalid configuration: The 'useWebWorker' flag must be true when using an OPFS-based VFS (${vfs}).`);
|
|
88
|
+
}
|
|
89
|
+
}
|
|
13
90
|
}
|
|
@@ -1,4 +1,5 @@
|
|
|
1
1
|
import { SQLOpenOptions } from '@powersync/common';
|
|
2
|
+
import { ILogger } from 'js-logger';
|
|
2
3
|
/**
|
|
3
4
|
* Common settings used when creating SQL connections on web.
|
|
4
5
|
*/
|
|
@@ -33,6 +34,20 @@ export interface WebSQLFlags {
|
|
|
33
34
|
export type ResolvedWebSQLFlags = Required<WebSQLFlags>;
|
|
34
35
|
export interface ResolvedWebSQLOpenOptions extends SQLOpenOptions {
|
|
35
36
|
flags: ResolvedWebSQLFlags;
|
|
37
|
+
/**
|
|
38
|
+
* Where to store SQLite temporary files. Defaults to 'MEMORY'.
|
|
39
|
+
* Setting this to `FILESYSTEM` can cause issues with larger queries or datasets.
|
|
40
|
+
*/
|
|
41
|
+
temporaryStorage: TemporaryStorageOption;
|
|
42
|
+
/**
|
|
43
|
+
* Encryption key for the database.
|
|
44
|
+
* If set, the database will be encrypted using ChaCha20.
|
|
45
|
+
*/
|
|
46
|
+
encryptionKey?: string;
|
|
47
|
+
}
|
|
48
|
+
export declare enum TemporaryStorageOption {
|
|
49
|
+
MEMORY = "memory",
|
|
50
|
+
FILESYSTEM = "file"
|
|
36
51
|
}
|
|
37
52
|
/**
|
|
38
53
|
* Options for opening a Web SQL connection
|
|
@@ -46,6 +61,17 @@ export interface WebSQLOpenFactoryOptions extends SQLOpenOptions {
|
|
|
46
61
|
* or a factory method that returns a worker.
|
|
47
62
|
*/
|
|
48
63
|
worker?: string | URL | ((options: ResolvedWebSQLOpenOptions) => Worker | SharedWorker);
|
|
64
|
+
logger?: ILogger;
|
|
65
|
+
/**
|
|
66
|
+
* Where to store SQLite temporary files. Defaults to 'MEMORY'.
|
|
67
|
+
* Setting this to `FILESYSTEM` can cause issues with larger queries or datasets.
|
|
68
|
+
*/
|
|
69
|
+
temporaryStorage?: TemporaryStorageOption;
|
|
70
|
+
/**
|
|
71
|
+
* Encryption key for the database.
|
|
72
|
+
* If set, the database will be encrypted using ChaCha20.
|
|
73
|
+
*/
|
|
74
|
+
encryptionKey?: string;
|
|
49
75
|
}
|
|
50
76
|
export declare function isServerSide(): boolean;
|
|
51
77
|
export declare const DEFAULT_WEB_SQL_FLAGS: ResolvedWebSQLFlags;
|
|
@@ -1,3 +1,8 @@
|
|
|
1
|
+
export var TemporaryStorageOption;
|
|
2
|
+
(function (TemporaryStorageOption) {
|
|
3
|
+
TemporaryStorageOption["MEMORY"] = "memory";
|
|
4
|
+
TemporaryStorageOption["FILESYSTEM"] = "file";
|
|
5
|
+
})(TemporaryStorageOption || (TemporaryStorageOption = {}));
|
|
1
6
|
export function isServerSide() {
|
|
2
7
|
return typeof window == 'undefined';
|
|
3
8
|
}
|
|
@@ -2,6 +2,7 @@ import { PowerSyncConnectionOptions, PowerSyncCredentials, SyncStatusOptions } f
|
|
|
2
2
|
import * as Comlink from 'comlink';
|
|
3
3
|
import { AbstractSharedSyncClientProvider } from '../../worker/sync/AbstractSharedSyncClientProvider';
|
|
4
4
|
import { SharedSyncImplementation } from '../../worker/sync/SharedSyncImplementation';
|
|
5
|
+
import { WebDBAdapter } from '../adapters/WebDBAdapter';
|
|
5
6
|
import { WebStreamingSyncImplementation, WebStreamingSyncImplementationOptions } from './WebStreamingSyncImplementation';
|
|
6
7
|
/**
|
|
7
8
|
* The shared worker will trigger methods on this side of the message port
|
|
@@ -10,7 +11,9 @@ import { WebStreamingSyncImplementation, WebStreamingSyncImplementationOptions }
|
|
|
10
11
|
declare class SharedSyncClientProvider extends AbstractSharedSyncClientProvider {
|
|
11
12
|
protected options: WebStreamingSyncImplementationOptions;
|
|
12
13
|
statusChanged: (status: SyncStatusOptions) => void;
|
|
13
|
-
|
|
14
|
+
protected webDB: WebDBAdapter;
|
|
15
|
+
constructor(options: WebStreamingSyncImplementationOptions, statusChanged: (status: SyncStatusOptions) => void, webDB: WebDBAdapter);
|
|
16
|
+
getDBWorkerPort(): Promise<MessagePort>;
|
|
14
17
|
fetchCredentials(): Promise<PowerSyncCredentials | null>;
|
|
15
18
|
uploadCrud(): Promise<void>;
|
|
16
19
|
get logger(): import("js-logger").ILogger | undefined;
|
|
@@ -23,12 +26,16 @@ declare class SharedSyncClientProvider extends AbstractSharedSyncClientProvider
|
|
|
23
26
|
time(label: string): void;
|
|
24
27
|
timeEnd(label: string): void;
|
|
25
28
|
}
|
|
29
|
+
export interface SharedWebStreamingSyncImplementationOptions extends WebStreamingSyncImplementationOptions {
|
|
30
|
+
db: WebDBAdapter;
|
|
31
|
+
}
|
|
26
32
|
export declare class SharedWebStreamingSyncImplementation extends WebStreamingSyncImplementation {
|
|
27
33
|
protected syncManager: Comlink.Remote<SharedSyncImplementation>;
|
|
28
34
|
protected clientProvider: SharedSyncClientProvider;
|
|
29
35
|
protected messagePort: MessagePort;
|
|
30
36
|
protected isInitialized: Promise<void>;
|
|
31
|
-
|
|
37
|
+
protected dbAdapter: WebDBAdapter;
|
|
38
|
+
constructor(options: SharedWebStreamingSyncImplementationOptions);
|
|
32
39
|
/**
|
|
33
40
|
* Starts the sync process, this effectively acts as a call to
|
|
34
41
|
* `connect` if not yet connected.
|
|
@@ -1,9 +1,8 @@
|
|
|
1
1
|
import * as Comlink from 'comlink';
|
|
2
|
-
import { openWorkerDatabasePort, resolveWorkerDatabasePortFactory } from '../../worker/db/open-worker-database';
|
|
3
2
|
import { AbstractSharedSyncClientProvider } from '../../worker/sync/AbstractSharedSyncClientProvider';
|
|
4
3
|
import { SharedSyncClientEvent } from '../../worker/sync/SharedSyncImplementation';
|
|
4
|
+
import { resolveWebSQLFlags, TemporaryStorageOption } from '../adapters/web-sql-flags';
|
|
5
5
|
import { WebStreamingSyncImplementation } from './WebStreamingSyncImplementation';
|
|
6
|
-
import { resolveWebSQLFlags } from '../adapters/web-sql-flags';
|
|
7
6
|
/**
|
|
8
7
|
* The shared worker will trigger methods on this side of the message port
|
|
9
8
|
* via this client provider.
|
|
@@ -11,10 +10,16 @@ import { resolveWebSQLFlags } from '../adapters/web-sql-flags';
|
|
|
11
10
|
class SharedSyncClientProvider extends AbstractSharedSyncClientProvider {
|
|
12
11
|
options;
|
|
13
12
|
statusChanged;
|
|
14
|
-
|
|
13
|
+
webDB;
|
|
14
|
+
constructor(options, statusChanged, webDB) {
|
|
15
15
|
super();
|
|
16
16
|
this.options = options;
|
|
17
17
|
this.statusChanged = statusChanged;
|
|
18
|
+
this.webDB = webDB;
|
|
19
|
+
}
|
|
20
|
+
async getDBWorkerPort() {
|
|
21
|
+
const { port } = await this.webDB.shareConnection();
|
|
22
|
+
return Comlink.transfer(port, [port]);
|
|
18
23
|
}
|
|
19
24
|
async fetchCredentials() {
|
|
20
25
|
const credentials = await this.options.remote.getCredentials();
|
|
@@ -29,8 +34,7 @@ class SharedSyncClientProvider extends AbstractSharedSyncClientProvider {
|
|
|
29
34
|
*/
|
|
30
35
|
return {
|
|
31
36
|
endpoint: credentials.endpoint,
|
|
32
|
-
token: credentials.token
|
|
33
|
-
expiresAt: credentials.expiresAt
|
|
37
|
+
token: credentials.token
|
|
34
38
|
};
|
|
35
39
|
}
|
|
36
40
|
async uploadCrud() {
|
|
@@ -73,8 +77,10 @@ export class SharedWebStreamingSyncImplementation extends WebStreamingSyncImplem
|
|
|
73
77
|
clientProvider;
|
|
74
78
|
messagePort;
|
|
75
79
|
isInitialized;
|
|
80
|
+
dbAdapter;
|
|
76
81
|
constructor(options) {
|
|
77
82
|
super(options);
|
|
83
|
+
this.dbAdapter = options.db;
|
|
78
84
|
/**
|
|
79
85
|
* Configure or connect to the shared sync worker.
|
|
80
86
|
* This worker will manage all syncing operations remotely.
|
|
@@ -82,6 +88,8 @@ export class SharedWebStreamingSyncImplementation extends WebStreamingSyncImplem
|
|
|
82
88
|
const resolvedWorkerOptions = {
|
|
83
89
|
...options,
|
|
84
90
|
dbFilename: this.options.identifier,
|
|
91
|
+
// TODO
|
|
92
|
+
temporaryStorage: TemporaryStorageOption.MEMORY,
|
|
85
93
|
flags: resolveWebSQLFlags(options.flags)
|
|
86
94
|
};
|
|
87
95
|
const syncWorker = options.sync?.worker;
|
|
@@ -112,13 +120,9 @@ export class SharedWebStreamingSyncImplementation extends WebStreamingSyncImplem
|
|
|
112
120
|
* sync worker.
|
|
113
121
|
*/
|
|
114
122
|
const { crudUploadThrottleMs, identifier, retryDelayMs } = this.options;
|
|
115
|
-
const dbWorker = options.database?.options?.worker;
|
|
116
|
-
const dbOpenerPort = typeof dbWorker === 'function'
|
|
117
|
-
? resolveWorkerDatabasePortFactory(() => dbWorker(resolvedWorkerOptions))
|
|
118
|
-
: openWorkerDatabasePort(this.options.identifier, true, dbWorker);
|
|
119
123
|
const flags = { ...this.webOptions.flags, workers: undefined };
|
|
120
|
-
this.isInitialized = this.syncManager.
|
|
121
|
-
|
|
124
|
+
this.isInitialized = this.syncManager.setParams({
|
|
125
|
+
dbParams: this.dbAdapter.getConfiguration(),
|
|
122
126
|
streamOptions: {
|
|
123
127
|
crudUploadThrottleMs,
|
|
124
128
|
identifier,
|
|
@@ -131,7 +135,7 @@ export class SharedWebStreamingSyncImplementation extends WebStreamingSyncImplem
|
|
|
131
135
|
*/
|
|
132
136
|
this.clientProvider = new SharedSyncClientProvider(this.webOptions, (status) => {
|
|
133
137
|
this.iterateListeners((l) => this.updateSyncStatus(status));
|
|
134
|
-
});
|
|
138
|
+
}, options.db);
|
|
135
139
|
/**
|
|
136
140
|
* The sync worker will call this client provider when it needs
|
|
137
141
|
* to fetch credentials or upload data.
|
|
@@ -180,6 +184,7 @@ export class SharedWebStreamingSyncImplementation extends WebStreamingSyncImplem
|
|
|
180
184
|
* Used in tests to force a connection states
|
|
181
185
|
*/
|
|
182
186
|
async _testUpdateStatus(status) {
|
|
187
|
+
await this.isInitialized;
|
|
183
188
|
return this.syncManager['_testUpdateAllStatuses'](status.toJSON());
|
|
184
189
|
}
|
|
185
190
|
}
|
|
@@ -2,11 +2,6 @@ import { AbstractStreamingSyncImplementation, AbstractStreamingSyncImplementatio
|
|
|
2
2
|
import { ResolvedWebSQLOpenOptions, WebSQLFlags } from '../adapters/web-sql-flags';
|
|
3
3
|
export interface WebStreamingSyncImplementationOptions extends AbstractStreamingSyncImplementationOptions {
|
|
4
4
|
flags?: WebSQLFlags;
|
|
5
|
-
database?: {
|
|
6
|
-
options: {
|
|
7
|
-
worker?: string | URL | ((options: ResolvedWebSQLOpenOptions) => Worker | SharedWorker);
|
|
8
|
-
};
|
|
9
|
-
};
|
|
10
5
|
sync?: {
|
|
11
6
|
worker?: string | URL | ((options: ResolvedWebSQLOpenOptions) => SharedWorker);
|
|
12
7
|
};
|
package/lib/src/index.d.ts
CHANGED
|
@@ -1,11 +1,12 @@
|
|
|
1
1
|
export * from '@powersync/common';
|
|
2
|
-
export * from './db/PowerSyncDatabase';
|
|
3
|
-
export * from './db/sync/WebRemote';
|
|
4
|
-
export * from './db/sync/WebStreamingSyncImplementation';
|
|
5
|
-
export * from './db/sync/SharedWebStreamingSyncImplementation';
|
|
6
|
-
export * from './db/adapters/wa-sqlite/WASQLiteDBAdapter';
|
|
7
|
-
export * from './db/adapters/wa-sqlite/WASQLitePowerSyncDatabaseOpenFactory';
|
|
8
2
|
export * from './db/adapters/AbstractWebPowerSyncDatabaseOpenFactory';
|
|
9
|
-
export * from './db/adapters/web-sql-flags';
|
|
10
3
|
export * from './db/adapters/AbstractWebSQLOpenFactory';
|
|
4
|
+
export * from './db/adapters/wa-sqlite/WASQLiteConnection';
|
|
5
|
+
export * from './db/adapters/wa-sqlite/WASQLiteDBAdapter';
|
|
11
6
|
export * from './db/adapters/wa-sqlite/WASQLiteOpenFactory';
|
|
7
|
+
export * from './db/adapters/wa-sqlite/WASQLitePowerSyncDatabaseOpenFactory';
|
|
8
|
+
export * from './db/adapters/web-sql-flags';
|
|
9
|
+
export * from './db/PowerSyncDatabase';
|
|
10
|
+
export * from './db/sync/SharedWebStreamingSyncImplementation';
|
|
11
|
+
export * from './db/sync/WebRemote';
|
|
12
|
+
export * from './db/sync/WebStreamingSyncImplementation';
|
package/lib/src/index.js
CHANGED
|
@@ -1,11 +1,12 @@
|
|
|
1
1
|
export * from '@powersync/common';
|
|
2
|
-
export * from './db/PowerSyncDatabase';
|
|
3
|
-
export * from './db/sync/WebRemote';
|
|
4
|
-
export * from './db/sync/WebStreamingSyncImplementation';
|
|
5
|
-
export * from './db/sync/SharedWebStreamingSyncImplementation';
|
|
6
|
-
export * from './db/adapters/wa-sqlite/WASQLiteDBAdapter';
|
|
7
|
-
export * from './db/adapters/wa-sqlite/WASQLitePowerSyncDatabaseOpenFactory';
|
|
8
2
|
export * from './db/adapters/AbstractWebPowerSyncDatabaseOpenFactory';
|
|
9
|
-
export * from './db/adapters/web-sql-flags';
|
|
10
3
|
export * from './db/adapters/AbstractWebSQLOpenFactory';
|
|
4
|
+
export * from './db/adapters/wa-sqlite/WASQLiteConnection';
|
|
5
|
+
export * from './db/adapters/wa-sqlite/WASQLiteDBAdapter';
|
|
11
6
|
export * from './db/adapters/wa-sqlite/WASQLiteOpenFactory';
|
|
7
|
+
export * from './db/adapters/wa-sqlite/WASQLitePowerSyncDatabaseOpenFactory';
|
|
8
|
+
export * from './db/adapters/web-sql-flags';
|
|
9
|
+
export * from './db/PowerSyncDatabase';
|
|
10
|
+
export * from './db/sync/SharedWebStreamingSyncImplementation';
|
|
11
|
+
export * from './db/sync/WebRemote';
|
|
12
|
+
export * from './db/sync/WebStreamingSyncImplementation';
|