syncorejs 0.2.1 → 0.2.2
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 +2 -1
- package/dist/_vendor/cli/app.d.mts.map +1 -1
- package/dist/_vendor/cli/app.mjs +323 -42
- package/dist/_vendor/cli/app.mjs.map +1 -1
- package/dist/_vendor/cli/context.mjs +27 -9
- package/dist/_vendor/cli/context.mjs.map +1 -1
- package/dist/_vendor/cli/doctor.mjs +513 -46
- package/dist/_vendor/cli/doctor.mjs.map +1 -1
- package/dist/_vendor/cli/messages.mjs +5 -4
- package/dist/_vendor/cli/messages.mjs.map +1 -1
- package/dist/_vendor/cli/project.mjs +110 -12
- package/dist/_vendor/cli/project.mjs.map +1 -1
- package/dist/_vendor/cli/render.mjs +57 -9
- package/dist/_vendor/cli/render.mjs.map +1 -1
- package/dist/_vendor/cli/targets.mjs +4 -3
- package/dist/_vendor/cli/targets.mjs.map +1 -1
- package/dist/_vendor/core/cli.d.mts +13 -3
- package/dist/_vendor/core/cli.d.mts.map +1 -1
- package/dist/_vendor/core/cli.mjs +242 -91
- package/dist/_vendor/core/cli.mjs.map +1 -1
- package/dist/_vendor/core/devtools-auth.mjs +60 -0
- package/dist/_vendor/core/devtools-auth.mjs.map +1 -0
- package/dist/_vendor/core/index.d.mts +5 -3
- package/dist/_vendor/core/index.mjs +22 -2
- package/dist/_vendor/core/index.mjs.map +1 -1
- package/dist/_vendor/core/runtime/components.d.mts +111 -0
- package/dist/_vendor/core/runtime/components.d.mts.map +1 -0
- package/dist/_vendor/core/runtime/components.mjs +186 -0
- package/dist/_vendor/core/runtime/components.mjs.map +1 -0
- package/dist/_vendor/core/runtime/devtools.d.mts +4 -4
- package/dist/_vendor/core/runtime/devtools.d.mts.map +1 -1
- package/dist/_vendor/core/runtime/devtools.mjs +52 -41
- package/dist/_vendor/core/runtime/devtools.mjs.map +1 -1
- package/dist/_vendor/core/runtime/functions.d.mts +10 -10
- package/dist/_vendor/core/runtime/functions.d.mts.map +1 -1
- package/dist/_vendor/core/runtime/functions.mjs +2 -2
- package/dist/_vendor/core/runtime/functions.mjs.map +1 -1
- package/dist/_vendor/core/runtime/internal/engines/devtoolsEngine.mjs +77 -0
- package/dist/_vendor/core/runtime/internal/engines/devtoolsEngine.mjs.map +1 -0
- package/dist/_vendor/core/runtime/internal/engines/executionEngine.mjs +617 -0
- package/dist/_vendor/core/runtime/internal/engines/executionEngine.mjs.map +1 -0
- package/dist/_vendor/core/runtime/internal/engines/reactivityEngine.mjs +186 -0
- package/dist/_vendor/core/runtime/internal/engines/reactivityEngine.mjs.map +1 -0
- package/dist/_vendor/core/runtime/internal/engines/schedulerEngine.mjs +220 -0
- package/dist/_vendor/core/runtime/internal/engines/schedulerEngine.mjs.map +1 -0
- package/dist/_vendor/core/runtime/internal/engines/schemaEngine.mjs +203 -0
- package/dist/_vendor/core/runtime/internal/engines/schemaEngine.mjs.map +1 -0
- package/dist/_vendor/core/runtime/internal/engines/shared.mjs +177 -0
- package/dist/_vendor/core/runtime/internal/engines/shared.mjs.map +1 -0
- package/dist/_vendor/core/runtime/internal/engines/storageEngine.mjs +144 -0
- package/dist/_vendor/core/runtime/internal/engines/storageEngine.mjs.map +1 -0
- package/dist/_vendor/core/runtime/internal/runtimeKernel.mjs +220 -0
- package/dist/_vendor/core/runtime/internal/runtimeKernel.mjs.map +1 -0
- package/dist/_vendor/core/runtime/internal/runtimeStatus.mjs +32 -0
- package/dist/_vendor/core/runtime/internal/runtimeStatus.mjs.map +1 -0
- package/dist/_vendor/core/runtime/internal/systemMeta.mjs +61 -0
- package/dist/_vendor/core/runtime/internal/systemMeta.mjs.map +1 -0
- package/dist/_vendor/core/runtime/internal/transactionCoordinator.mjs +37 -0
- package/dist/_vendor/core/runtime/internal/transactionCoordinator.mjs.map +1 -0
- package/dist/_vendor/core/runtime/runtime.d.mts +159 -205
- package/dist/_vendor/core/runtime/runtime.d.mts.map +1 -1
- package/dist/_vendor/core/runtime/runtime.mjs +16 -1371
- package/dist/_vendor/core/runtime/runtime.mjs.map +1 -1
- package/dist/_vendor/core/transport.d.mts +111 -0
- package/dist/_vendor/core/transport.d.mts.map +1 -0
- package/dist/_vendor/core/transport.mjs +419 -0
- package/dist/_vendor/core/transport.mjs.map +1 -0
- package/dist/_vendor/devtools-protocol/index.d.ts +39 -1
- package/dist/_vendor/devtools-protocol/index.d.ts.map +1 -1
- package/dist/_vendor/devtools-protocol/index.js +25 -9
- package/dist/_vendor/devtools-protocol/index.js.map +1 -1
- package/dist/_vendor/next/index.d.ts +1 -1
- package/dist/_vendor/next/index.d.ts.map +1 -1
- package/dist/_vendor/next/index.js +31 -13
- package/dist/_vendor/next/index.js.map +1 -1
- package/dist/_vendor/platform-expo/index.d.ts +12 -12
- package/dist/_vendor/platform-expo/index.d.ts.map +1 -1
- package/dist/_vendor/platform-expo/index.js +4 -2
- package/dist/_vendor/platform-expo/index.js.map +1 -1
- package/dist/_vendor/platform-expo/react.d.ts.map +1 -1
- package/dist/_vendor/platform-expo/react.js +11 -10
- package/dist/_vendor/platform-expo/react.js.map +1 -1
- package/dist/_vendor/platform-node/index.d.mts +23 -19
- package/dist/_vendor/platform-node/index.d.mts.map +1 -1
- package/dist/_vendor/platform-node/index.mjs +13 -5
- package/dist/_vendor/platform-node/index.mjs.map +1 -1
- package/dist/_vendor/platform-node/ipc-react.d.mts.map +1 -1
- package/dist/_vendor/platform-node/ipc-react.mjs +15 -2
- package/dist/_vendor/platform-node/ipc-react.mjs.map +1 -1
- package/dist/_vendor/platform-node/ipc.d.mts +11 -35
- package/dist/_vendor/platform-node/ipc.d.mts.map +1 -1
- package/dist/_vendor/platform-node/ipc.mjs +3 -273
- package/dist/_vendor/platform-node/ipc.mjs.map +1 -1
- package/dist/_vendor/platform-web/external-change.d.ts +2 -1
- package/dist/_vendor/platform-web/external-change.d.ts.map +1 -1
- package/dist/_vendor/platform-web/external-change.js +2 -1
- package/dist/_vendor/platform-web/external-change.js.map +1 -1
- package/dist/_vendor/platform-web/index.d.ts +21 -21
- package/dist/_vendor/platform-web/index.d.ts.map +1 -1
- package/dist/_vendor/platform-web/index.js +44 -7
- package/dist/_vendor/platform-web/index.js.map +1 -1
- package/dist/_vendor/platform-web/react.d.ts.map +1 -1
- package/dist/_vendor/platform-web/react.js +29 -13
- package/dist/_vendor/platform-web/react.js.map +1 -1
- package/dist/_vendor/platform-web/worker.d.ts +11 -35
- package/dist/_vendor/platform-web/worker.d.ts.map +1 -1
- package/dist/_vendor/platform-web/worker.js +3 -267
- package/dist/_vendor/platform-web/worker.js.map +1 -1
- package/dist/_vendor/react/index.d.ts +36 -20
- package/dist/_vendor/react/index.d.ts.map +1 -1
- package/dist/_vendor/react/index.js +279 -57
- package/dist/_vendor/react/index.js.map +1 -1
- package/dist/_vendor/schema/definition.d.ts +48 -63
- package/dist/_vendor/schema/definition.d.ts.map +1 -1
- package/dist/_vendor/schema/definition.js +22 -39
- package/dist/_vendor/schema/definition.js.map +1 -1
- package/dist/_vendor/schema/index.d.ts +4 -4
- package/dist/_vendor/schema/index.js +2 -2
- package/dist/_vendor/schema/planner.d.ts +19 -2
- package/dist/_vendor/schema/planner.d.ts.map +1 -1
- package/dist/_vendor/schema/planner.js +79 -3
- package/dist/_vendor/schema/planner.js.map +1 -1
- package/dist/_vendor/schema/validators.d.ts +141 -121
- package/dist/_vendor/schema/validators.d.ts.map +1 -1
- package/dist/_vendor/schema/validators.js +300 -42
- package/dist/_vendor/schema/validators.js.map +1 -1
- package/dist/_vendor/svelte/index.d.ts +47 -19
- package/dist/_vendor/svelte/index.d.ts.map +1 -1
- package/dist/_vendor/svelte/index.js +250 -20
- package/dist/_vendor/svelte/index.js.map +1 -1
- package/dist/components.d.ts +2 -0
- package/dist/components.js +2 -0
- package/dist/index.d.ts +3 -2
- package/dist/index.js +2 -1
- package/package.json +8 -3
|
@@ -4,8 +4,11 @@ import { createWebPersistence, isOpfsAvailable } from "./persistence.js";
|
|
|
4
4
|
import { BroadcastChannelExternalChangeSignal, SqlJsExternalChangeApplier, createDefaultSyncChannelName } from "./external-change.js";
|
|
5
5
|
import { SqlJsDriver } from "./sqljs.js";
|
|
6
6
|
import { SyncoreWebWorkerClient, attachWebWorkerRuntime, createManagedWebWorkerClient, createSyncoreWebWorkerClient, createWebWorkerClient } from "./worker.js";
|
|
7
|
-
import { SyncoreRuntime, createDevtoolsCommandHandler, createDevtoolsSubscriptionHost } from "../core/index.mjs";
|
|
7
|
+
import { SyncoreRuntime, createDevtoolsCommandHandler, createDevtoolsSubscriptionHost, generateId } from "../core/index.mjs";
|
|
8
|
+
import { SYNCORE_DEVTOOLS_MAX_SUPPORTED_PROTOCOL_VERSION, SYNCORE_DEVTOOLS_MIN_SUPPORTED_PROTOCOL_VERSION, SYNCORE_DEVTOOLS_PROTOCOL_VERSION } from "../devtools-protocol/index.js";
|
|
8
9
|
//#region src/index.ts
|
|
10
|
+
const DEVTOOLS_META_NAMESPACE = "__syncore_devtools_meta__";
|
|
11
|
+
const STORAGE_SCOPE_ID_PREFIX = "storage-scope";
|
|
9
12
|
/**
|
|
10
13
|
* Create a full Syncore runtime directly in the browser.
|
|
11
14
|
*
|
|
@@ -34,10 +37,12 @@ async function createWebSyncoreRuntime(options) {
|
|
|
34
37
|
const origin = resolveWebOrigin();
|
|
35
38
|
const sessionLabel = resolveWebSessionLabel();
|
|
36
39
|
const databaseLabel = options.databaseName ?? "syncore";
|
|
40
|
+
const storageScopeId = await resolvePersistedStorageScopeId(persistence, databaseLabel);
|
|
37
41
|
const storageIdentity = [
|
|
38
42
|
origin ?? "unknown-origin",
|
|
39
43
|
persistence.storageProtocol,
|
|
40
|
-
databaseLabel
|
|
44
|
+
databaseLabel,
|
|
45
|
+
storageScopeId
|
|
41
46
|
].join("::");
|
|
42
47
|
const autoDevtools = options.devtools === void 0 && shouldAutoConnectDevtools() ? (() => {
|
|
43
48
|
const sinkOptions = {
|
|
@@ -63,6 +68,7 @@ async function createWebSyncoreRuntime(options) {
|
|
|
63
68
|
const runtime = new SyncoreRuntime({
|
|
64
69
|
schema: options.schema,
|
|
65
70
|
functions: options.functions,
|
|
71
|
+
...options.components ? { components: options.components } : {},
|
|
66
72
|
driver,
|
|
67
73
|
storage,
|
|
68
74
|
externalChangeSignal: externalChangeSupport.signal,
|
|
@@ -70,7 +76,6 @@ async function createWebSyncoreRuntime(options) {
|
|
|
70
76
|
platform: options.platform ?? "browser",
|
|
71
77
|
...options.capabilities ? { capabilities: options.capabilities } : {},
|
|
72
78
|
...resolvedDevtools ? { devtools: resolvedDevtools } : {},
|
|
73
|
-
...options.experimentalPlugins ? { experimentalPlugins: options.experimentalPlugins } : {},
|
|
74
79
|
...options.scheduler ? { scheduler: options.scheduler } : {}
|
|
75
80
|
});
|
|
76
81
|
if (autoDevtools) {
|
|
@@ -79,13 +84,13 @@ async function createWebSyncoreRuntime(options) {
|
|
|
79
84
|
driver,
|
|
80
85
|
schema: options.schema,
|
|
81
86
|
functions: options.functions,
|
|
82
|
-
runtime
|
|
87
|
+
admin: runtime.getAdmin()
|
|
83
88
|
}));
|
|
84
89
|
autoDevtools.attachSubscriptionHost(createDevtoolsSubscriptionHost({
|
|
85
90
|
driver,
|
|
86
91
|
schema: options.schema,
|
|
87
92
|
functions: options.functions,
|
|
88
|
-
runtime
|
|
93
|
+
admin: runtime.getAdmin()
|
|
89
94
|
}));
|
|
90
95
|
}
|
|
91
96
|
return runtime;
|
|
@@ -172,6 +177,9 @@ function createBrowserWebSocketDevtoolsSink(options) {
|
|
|
172
177
|
socket.onopen = () => {
|
|
173
178
|
if (latestHello) sendNow({
|
|
174
179
|
type: "hello",
|
|
180
|
+
protocolVersion: SYNCORE_DEVTOOLS_PROTOCOL_VERSION,
|
|
181
|
+
minSupportedProtocolVersion: SYNCORE_DEVTOOLS_MIN_SUPPORTED_PROTOCOL_VERSION,
|
|
182
|
+
maxSupportedProtocolVersion: SYNCORE_DEVTOOLS_MAX_SUPPORTED_PROTOCOL_VERSION,
|
|
175
183
|
runtimeId: latestHello.runtimeId,
|
|
176
184
|
platform: latestHello.platform,
|
|
177
185
|
...options.appName ? { appName: options.appName } : {},
|
|
@@ -260,6 +268,9 @@ function createBrowserWebSocketDevtoolsSink(options) {
|
|
|
260
268
|
};
|
|
261
269
|
send({
|
|
262
270
|
type: "hello",
|
|
271
|
+
protocolVersion: SYNCORE_DEVTOOLS_PROTOCOL_VERSION,
|
|
272
|
+
minSupportedProtocolVersion: SYNCORE_DEVTOOLS_MIN_SUPPORTED_PROTOCOL_VERSION,
|
|
273
|
+
maxSupportedProtocolVersion: SYNCORE_DEVTOOLS_MAX_SUPPORTED_PROTOCOL_VERSION,
|
|
263
274
|
runtimeId: event.runtimeId,
|
|
264
275
|
platform: event.platform,
|
|
265
276
|
...options.appName ? { appName: options.appName } : {},
|
|
@@ -277,7 +288,7 @@ function createBrowserWebSocketDevtoolsSink(options) {
|
|
|
277
288
|
});
|
|
278
289
|
},
|
|
279
290
|
attachRuntime(runtime) {
|
|
280
|
-
getSummary = () => withRuntimeSummaryMeta(runtime.getRuntimeSummary(), options);
|
|
291
|
+
getSummary = () => withRuntimeSummaryMeta(runtime.getAdmin().getRuntimeSummary(), options);
|
|
281
292
|
},
|
|
282
293
|
attachCommandHandler(handler) {
|
|
283
294
|
onCommand = handler;
|
|
@@ -388,12 +399,38 @@ function resolveWebSessionLabel() {
|
|
|
388
399
|
globalThis.localStorage?.setItem(STORAGE_KEY, uniqueName);
|
|
389
400
|
} catch {}
|
|
390
401
|
}
|
|
391
|
-
const browser =
|
|
402
|
+
const browser = resolveBrowserName(navigator);
|
|
392
403
|
return `${uniqueName} (${browser})`;
|
|
393
404
|
} catch {
|
|
394
405
|
return;
|
|
395
406
|
}
|
|
396
407
|
}
|
|
408
|
+
function resolveBrowserName(nav) {
|
|
409
|
+
const brands = nav.userAgentData?.brands?.map((entry) => entry.brand) ?? [];
|
|
410
|
+
if (brands.some((brand) => /microsoft edge/i.test(brand))) return "Edge";
|
|
411
|
+
if (brands.some((brand) => /firefox/i.test(brand))) return "Firefox";
|
|
412
|
+
if (brands.some((brand) => /opera/i.test(brand))) return "Opera";
|
|
413
|
+
if (brands.some((brand) => /chrome|chromium/i.test(brand))) return "Chrome";
|
|
414
|
+
if (brands.some((brand) => /safari/i.test(brand))) return "Safari";
|
|
415
|
+
const userAgent = nav.userAgent;
|
|
416
|
+
if (/Firefox\//i.test(userAgent)) return "Firefox";
|
|
417
|
+
if (/Edg\//i.test(userAgent)) return "Edge";
|
|
418
|
+
if (/OPR\/|Opera/i.test(userAgent)) return "Opera";
|
|
419
|
+
if (/Chrome\/|CriOS\//i.test(userAgent)) return "Chrome";
|
|
420
|
+
if (/Safari\//i.test(userAgent)) return "Safari";
|
|
421
|
+
return "Browser";
|
|
422
|
+
}
|
|
423
|
+
async function resolvePersistedStorageScopeId(persistence, databaseLabel) {
|
|
424
|
+
const id = `${STORAGE_SCOPE_ID_PREFIX}:${databaseLabel}`;
|
|
425
|
+
const existing = await persistence.getFile(DEVTOOLS_META_NAMESPACE, id);
|
|
426
|
+
if (existing) {
|
|
427
|
+
const value = new TextDecoder().decode(existing.bytes).trim();
|
|
428
|
+
if (value.length > 0) return value;
|
|
429
|
+
}
|
|
430
|
+
const nextValue = generateId();
|
|
431
|
+
await persistence.putFile(DEVTOOLS_META_NAMESPACE, id, new TextEncoder().encode(nextValue), "text/plain");
|
|
432
|
+
return nextValue;
|
|
433
|
+
}
|
|
397
434
|
function announceBrowserSession(options) {
|
|
398
435
|
if (!options.enabled || !options.sessionLabel) return;
|
|
399
436
|
const announcedSessions = getAnnouncedBrowserSessions();
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"index.js","names":[],"sources":["../src/index.ts"],"sourcesContent":["import {\n type AnySyncoreSchema,\n createDevtoolsCommandHandler,\n createDevtoolsSubscriptionHost,\n type DevtoolsCommandHandler,\n type DevtoolsSink,\n type DevtoolsSubscriptionHost,\n SyncoreRuntime,\n type SchedulerOptions,\n type SyncoreCapabilities,\n type SyncoreExperimentalPlugin,\n type SyncoreRuntimeOptions,\n type SyncoreStorageAdapter,\n type StorageObject,\n type StorageWriteInput\n} from \"@syncore/core\";\nimport {\n type SyncoreDevtoolsClientMessage,\n type SyncoreDevtoolsMessage,\n type SyncoreRuntimeSummary\n} from \"@syncore/devtools-protocol\";\nimport {\n createWebPersistence,\n type SyncoreWebPersistence,\n type WebPersistenceMode\n} from \"./persistence.js\";\nimport {\n BroadcastChannelExternalChangeSignal,\n createDefaultSyncChannelName,\n SqlJsExternalChangeApplier\n} from \"./external-change.js\";\nimport { SqlJsDriver } from \"./sqljs.js\";\nimport {\n attachWebWorkerRuntime,\n type SyncoreWorkerMessageEndpoint\n} from \"./worker.js\";\nexport * from \"./worker.js\";\nexport * from \"./persistence.js\";\nexport * from \"./indexeddb.js\";\nexport * from \"./opfs.js\";\nexport * from \"./external-change.js\";\n\nexport type WebSyncoreSchema = AnySyncoreSchema;\nexport type BrowserSyncoreSchema = WebSyncoreSchema;\n\n/**\n * Options for constructing a browser Syncore runtime.\n *\n * Use this when you want to host the full runtime in a browser tab or worker.\n */\nexport interface CreateWebRuntimeOptions {\n /** The schema for the local Syncore app. */\n schema: WebSyncoreSchema;\n\n /** The generated function registry for the local Syncore app. */\n functions: SyncoreRuntimeOptions<WebSyncoreSchema>[\"functions\"];\n\n /** Optional platform capabilities exposed to function handlers. */\n capabilities?: SyncoreCapabilities;\n\n /** Optional custom SQL driver. Defaults to SQL.js with local persistence. */\n driver?: SyncoreRuntimeOptions<WebSyncoreSchema>[\"driver\"];\n\n /** Optional custom file/blob storage adapter. */\n storage?: SyncoreStorageAdapter;\n\n /** Optional experimental plugins for runtime hooks. */\n experimentalPlugins?: Array<SyncoreExperimentalPlugin<WebSyncoreSchema>>;\n\n /** Optional explicit persistence implementation. */\n persistence?: SyncoreWebPersistence;\n\n /** Which browser persistence mode to use when Syncore creates one for you. */\n persistenceMode?: WebPersistenceMode;\n\n /** Logical database name for SQL.js and local storage namespaces. */\n databaseName?: string;\n\n /** Optional IndexedDB database name for persistence metadata. */\n persistenceDatabaseName?: string;\n\n /** Optional OPFS directory name for persistent files. */\n opfsRootDirectoryName?: string;\n\n /** Optional namespace for file/blob storage. */\n storageNamespace?: string;\n\n /** Optional direct wasm URL for SQL.js. */\n wasmUrl?: string;\n\n /** Optional callback for resolving SQL.js support files. */\n locateFile?: (fileName: string) => string;\n\n /** Optional runtime platform label shown in devtools snapshots. */\n platform?: string;\n\n /** Optional devtools sink used during development. */\n devtools?: DevtoolsSink | false;\n\n /** Optional scheduler configuration for jobs and recurring work. */\n scheduler?: SchedulerOptions;\n}\n\n/**\n * Options for hosting a Syncore runtime inside a browser Worker.\n */\nexport interface CreateWebWorkerRuntimeOptions extends CreateWebRuntimeOptions {\n /** The message endpoint exposed by the current worker global. */\n endpoint: SyncoreWorkerMessageEndpoint;\n}\n\n/**\n * Options for constructing a browser Syncore runtime.\n */\nexport type CreateBrowserRuntimeOptions = CreateWebRuntimeOptions;\n\n/**\n * Options for hosting a Syncore runtime inside a browser Worker.\n */\nexport type CreateBrowserWorkerRuntimeOptions = CreateWebWorkerRuntimeOptions;\n\nexport interface WebExternalChangeSupport {\n signal: BroadcastChannelExternalChangeSignal;\n applier?: SqlJsExternalChangeApplier;\n}\n\n/**\n * Create a full Syncore runtime directly in the browser.\n *\n * Most React apps should use a worker runtime instead so queries and SQLite work\n * stay off the main thread.\n */\nexport async function createWebSyncoreRuntime(\n options: CreateWebRuntimeOptions\n): Promise<SyncoreRuntime<WebSyncoreSchema>> {\n const persistence =\n options.persistence ??\n (await createWebPersistence({\n ...(options.persistenceMode ? { mode: options.persistenceMode } : {}),\n ...(options.persistenceDatabaseName\n ? { indexedDbDatabaseName: options.persistenceDatabaseName }\n : {}),\n opfsRootDirectoryName:\n options.opfsRootDirectoryName ?? options.databaseName ?? \"syncore\"\n }));\n const driver =\n options.driver ??\n (await SqlJsDriver.create({\n databaseName: options.databaseName ?? \"syncore\",\n persistence,\n ...(options.wasmUrl ? { wasmUrl: options.wasmUrl } : {}),\n ...(options.locateFile ? { locateFile: options.locateFile } : {})\n }));\n const storage =\n options.storage ??\n new BrowserFileStorageAdapter(\n persistence,\n options.storageNamespace ?? options.databaseName ?? \"syncore\"\n );\n const externalChangeSupport = createWebExternalChangeSupport({\n databaseName: options.databaseName ?? \"syncore\",\n persistence,\n driver\n });\n const appName = resolveWebAppName();\n const origin = resolveWebOrigin();\n const sessionLabel = resolveWebSessionLabel();\n const databaseLabel = options.databaseName ?? \"syncore\";\n const storageIdentity = [\n origin ?? \"unknown-origin\",\n persistence.storageProtocol,\n databaseLabel\n ].join(\"::\");\n const autoDevtools =\n options.devtools === undefined && shouldAutoConnectDevtools()\n ? (() => {\n const sinkOptions: BrowserWebSocketDevtoolsSinkOptions = {\n url: resolveDefaultDevtoolsUrl(),\n targetKind: \"client\",\n storageProtocol: persistence.storageProtocol,\n databaseLabel,\n storageIdentity\n };\n if (appName) {\n sinkOptions.appName = appName;\n }\n if (origin) {\n sinkOptions.origin = origin;\n }\n if (sessionLabel) {\n sinkOptions.sessionLabel = sessionLabel;\n }\n return createBrowserWebSocketDevtoolsSink(sinkOptions);\n })()\n : undefined;\n const resolvedDevtools =\n options.devtools === false ? undefined : (options.devtools ?? autoDevtools);\n\n announceBrowserSession({\n enabled: resolvedDevtools !== undefined,\n sessionLabel,\n appName,\n origin,\n devtoolsUrl:\n options.devtools && typeof options.devtools === \"object\"\n ? undefined\n : resolveDefaultDevtoolsUrl()\n });\n\n const runtime = new SyncoreRuntime({\n schema: options.schema,\n functions: options.functions,\n driver,\n storage,\n externalChangeSignal: externalChangeSupport.signal,\n ...(externalChangeSupport.applier\n ? { externalChangeApplier: externalChangeSupport.applier }\n : {}),\n platform: options.platform ?? \"browser\",\n ...(options.capabilities ? { capabilities: options.capabilities } : {}),\n ...(resolvedDevtools ? { devtools: resolvedDevtools } : {}),\n ...(options.experimentalPlugins\n ? { experimentalPlugins: options.experimentalPlugins }\n : {}),\n ...(options.scheduler ? { scheduler: options.scheduler } : {})\n });\n\n if (autoDevtools) {\n autoDevtools.attachRuntime(runtime);\n autoDevtools.attachCommandHandler(\n createDevtoolsCommandHandler({\n driver,\n schema: options.schema,\n functions: options.functions,\n runtime\n })\n );\n autoDevtools.attachSubscriptionHost(\n createDevtoolsSubscriptionHost({\n driver,\n schema: options.schema,\n functions: options.functions,\n runtime\n })\n );\n }\n\n return runtime;\n}\n\nexport function createWebExternalChangeSupport(options: {\n databaseName: string;\n persistence: SyncoreWebPersistence;\n driver: CreateWebRuntimeOptions[\"driver\"] | undefined;\n}): WebExternalChangeSupport {\n const signal = new BroadcastChannelExternalChangeSignal({\n channelName: createDefaultSyncChannelName(options.databaseName)\n });\n const sqlDriver =\n options.driver instanceof SqlJsDriver ? options.driver : undefined;\n\n if (!sqlDriver) {\n return { signal };\n }\n\n return {\n signal,\n applier: new SqlJsExternalChangeApplier({\n databaseName: options.databaseName,\n persistence: options.persistence,\n createDatabase: (bytes) => sqlDriver.createDatabaseFromBytes(bytes),\n replaceDatabase: (database) => {\n sqlDriver.replaceDatabase(database);\n }\n })\n };\n}\n\nexport async function createExpoWebExternalChangeSupport(options: {\n databaseName: string;\n locateFile?: (fileName: string) => string;\n wasmUrl?: string;\n persistenceDatabaseName?: string;\n opfsRootDirectoryName?: string;\n persistenceMode?: WebPersistenceMode;\n}): Promise<WebExternalChangeSupport> {\n const persistence = await createWebPersistence({\n ...(options.persistenceMode ? { mode: options.persistenceMode } : {}),\n ...(options.persistenceDatabaseName\n ? { indexedDbDatabaseName: options.persistenceDatabaseName }\n : {}),\n opfsRootDirectoryName: options.opfsRootDirectoryName ?? options.databaseName\n });\n const driver = await SqlJsDriver.create({\n databaseName: options.databaseName,\n persistence,\n ...(options.wasmUrl ? { wasmUrl: options.wasmUrl } : {}),\n ...(options.locateFile ? { locateFile: options.locateFile } : {})\n });\n\n return createWebExternalChangeSupport({\n databaseName: options.databaseName,\n persistence,\n driver\n });\n}\n\n/**\n * Attach a Syncore runtime to a browser Worker endpoint.\n */\nexport function createWebWorkerRuntime(options: CreateWebWorkerRuntimeOptions) {\n return attachWebWorkerRuntime({\n endpoint: options.endpoint,\n createRuntime: () => createWebSyncoreRuntime(options)\n });\n}\n\n/**\n * Attach a Syncore runtime to a browser Worker endpoint.\n */\nexport function createBrowserWorkerRuntime(\n options: CreateBrowserWorkerRuntimeOptions\n) {\n return createWebWorkerRuntime(options);\n}\n\n/**\n * Create a client directly from a browser Syncore runtime.\n */\nexport function createWebSyncoreClient(\n runtime: SyncoreRuntime<WebSyncoreSchema>\n) {\n return runtime.createClient();\n}\n\n/**\n * Create a full Syncore runtime directly in the browser.\n */\nexport function createBrowserSyncoreRuntime(\n options: CreateBrowserRuntimeOptions\n) {\n return createWebSyncoreRuntime(options);\n}\n\n/**\n * Create a client directly from a browser Syncore runtime.\n */\nexport function createBrowserSyncoreClient(\n runtime: SyncoreRuntime<BrowserSyncoreSchema>\n) {\n return createWebSyncoreClient(runtime);\n}\n\nexport interface BrowserWebSocketDevtoolsSinkOptions {\n url: string;\n reconnectDelayMs?: number;\n appName?: string;\n origin?: string;\n sessionLabel?: string;\n targetKind?: \"client\";\n storageProtocol?: string;\n databaseLabel?: string;\n storageIdentity?: string;\n}\n\nexport interface BrowserWebSocketDevtoolsSink extends DevtoolsSink {\n attachRuntime(runtime: SyncoreRuntime<AnySyncoreSchema>): void;\n attachCommandHandler(handler: DevtoolsCommandHandler): void;\n attachSubscriptionHost(host: DevtoolsSubscriptionHost): void;\n dispose(): void;\n}\n\nexport function createBrowserWebSocketDevtoolsSink(\n options: BrowserWebSocketDevtoolsSinkOptions\n): BrowserWebSocketDevtoolsSink {\n let socket: WebSocket | undefined;\n let disposed = false;\n let connectTimer: ReturnType<typeof setTimeout> | undefined;\n let getSummary: (() => SyncoreRuntimeSummary) | undefined;\n let onCommand: DevtoolsCommandHandler | undefined;\n let subscriptionHost: DevtoolsSubscriptionHost | undefined;\n const pendingMessages: SyncoreDevtoolsMessage[] = [];\n let latestHello:\n | {\n runtimeId: string;\n platform: string;\n }\n | undefined;\n\n const connect = () => {\n if (disposed || typeof WebSocket === \"undefined\") {\n return;\n }\n socket = new WebSocket(options.url);\n socket.onopen = () => {\n if (latestHello) {\n sendNow({\n type: \"hello\",\n runtimeId: latestHello.runtimeId,\n platform: latestHello.platform,\n ...(options.appName ? { appName: options.appName } : {}),\n ...(options.origin ? { origin: options.origin } : {}),\n ...(options.sessionLabel\n ? { sessionLabel: options.sessionLabel }\n : {}),\n ...(options.targetKind ? { targetKind: options.targetKind } : {}),\n ...(options.storageProtocol\n ? { storageProtocol: options.storageProtocol }\n : {}),\n ...(options.databaseLabel ? { databaseLabel: options.databaseLabel } : {}),\n ...(options.storageIdentity\n ? { storageIdentity: options.storageIdentity }\n : {})\n });\n }\n flushPendingMessages();\n };\n socket.onmessage = (event) => {\n if (typeof event.data !== \"string\") {\n return;\n }\n const message = JSON.parse(event.data) as\n | SyncoreDevtoolsMessage\n | SyncoreDevtoolsClientMessage;\n if (message.type === \"ping\") {\n send({ type: \"pong\" });\n } else if (message.type === \"command\" && onCommand) {\n onCommand(message.payload)\n .then((responsePayload) => {\n const runtimeId =\n latestHello?.runtimeId ?? getSummary?.().runtimeId;\n if (!runtimeId) {\n return;\n }\n send({\n type: \"command.result\",\n commandId: message.commandId,\n runtimeId,\n payload: responsePayload\n });\n })\n .catch((err) => {\n const runtimeId =\n latestHello?.runtimeId ?? getSummary?.().runtimeId;\n if (!runtimeId) {\n return;\n }\n send({\n type: \"command.result\",\n commandId: message.commandId,\n runtimeId,\n payload: {\n kind: \"error\",\n message: err instanceof Error ? err.message : \"Unknown error\"\n }\n });\n });\n } else if (message.type === \"subscribe\" && subscriptionHost) {\n void subscriptionHost.subscribe(\n message.subscriptionId,\n message.payload,\n (payload) => {\n const runtimeId =\n latestHello?.runtimeId ?? getSummary?.().runtimeId;\n if (!runtimeId) {\n return;\n }\n send({\n type: \"subscription.data\",\n subscriptionId: message.subscriptionId,\n runtimeId,\n payload\n });\n }\n );\n } else if (message.type === \"unsubscribe\") {\n subscriptionHost?.unsubscribe(message.subscriptionId);\n }\n };\n socket.onclose = scheduleReconnect;\n socket.onerror = () => {\n socket?.close();\n };\n };\n\n const scheduleReconnect = () => {\n if (disposed || connectTimer) {\n return;\n }\n connectTimer = setTimeout(() => {\n connectTimer = undefined;\n connect();\n }, options.reconnectDelayMs ?? 1200);\n };\n\n const sendNow = (message: SyncoreDevtoolsMessage) => {\n if (socket?.readyState === WebSocket.OPEN) {\n socket.send(JSON.stringify(message));\n }\n };\n\n const flushPendingMessages = () => {\n while (pendingMessages.length > 0) {\n const nextMessage = pendingMessages.shift();\n if (nextMessage) {\n sendNow(nextMessage);\n }\n }\n };\n\n const send = (message: SyncoreDevtoolsMessage) => {\n if (socket?.readyState === WebSocket.OPEN) {\n sendNow(message);\n return;\n }\n pendingMessages.push(message);\n };\n\n connect();\n\n return {\n emit(event) {\n if (event.type === \"runtime.connected\") {\n latestHello = {\n runtimeId: event.runtimeId,\n platform: event.platform\n };\n send({\n type: \"hello\",\n runtimeId: event.runtimeId,\n platform: event.platform,\n ...(options.appName ? { appName: options.appName } : {}),\n ...(options.origin ? { origin: options.origin } : {}),\n ...(options.sessionLabel\n ? { sessionLabel: options.sessionLabel }\n : {}),\n ...(options.targetKind ? { targetKind: options.targetKind } : {}),\n ...(options.storageProtocol\n ? { storageProtocol: options.storageProtocol }\n : {}),\n ...(options.databaseLabel ? { databaseLabel: options.databaseLabel } : {}),\n ...(options.storageIdentity\n ? { storageIdentity: options.storageIdentity }\n : {})\n });\n }\n send({ type: \"event\", event });\n },\n attachRuntime(runtime) {\n getSummary = () =>\n withRuntimeSummaryMeta(runtime.getRuntimeSummary(), options);\n },\n attachCommandHandler(handler) {\n onCommand = handler;\n },\n attachSubscriptionHost(host) {\n subscriptionHost = host;\n },\n dispose() {\n disposed = true;\n if (connectTimer) {\n clearTimeout(connectTimer);\n }\n subscriptionHost?.dispose();\n socket?.close();\n }\n };\n}\n\nfunction withRuntimeSummaryMeta(\n summary: SyncoreRuntimeSummary,\n options: BrowserWebSocketDevtoolsSinkOptions\n): SyncoreRuntimeSummary {\n return {\n ...summary,\n ...(options.appName ? { appName: options.appName } : {}),\n ...(options.origin ? { origin: options.origin } : {}),\n ...(options.sessionLabel ? { sessionLabel: options.sessionLabel } : {}),\n ...(options.targetKind ? { targetKind: options.targetKind } : {}),\n ...(options.storageProtocol\n ? { storageProtocol: options.storageProtocol }\n : {}),\n ...(options.databaseLabel ? { databaseLabel: options.databaseLabel } : {}),\n ...(options.storageIdentity\n ? { storageIdentity: options.storageIdentity }\n : {})\n };\n}\n\nfunction shouldAutoConnectDevtools(): boolean {\n const hostname = resolveWebHostname();\n if (!hostname) {\n return false;\n }\n return (\n hostname === \"localhost\" ||\n isPrivateNetworkHostname(hostname) ||\n hostname.endsWith(\".local\")\n );\n}\n\nfunction resolveDefaultDevtoolsUrl(): string {\n return \"ws://127.0.0.1:4311\";\n}\n\nfunction resolveLocationString(\n key: \"href\" | \"origin\" | \"hostname\"\n): string | undefined {\n try {\n const value = globalThis.location?.[key];\n return typeof value === \"string\" && value.length > 0 ? value : undefined;\n } catch {\n return undefined;\n }\n}\n\nfunction resolveGlobalOrigin(): string | undefined {\n try {\n const value = (globalThis as { origin?: unknown }).origin;\n return typeof value === \"string\" && value.length > 0 ? value : undefined;\n } catch {\n return undefined;\n }\n}\n\nfunction parseUrlCandidate(candidate: string | undefined): URL | undefined {\n if (!candidate || candidate === \"null\") {\n return undefined;\n }\n try {\n const parsed = new URL(candidate);\n if (parsed.protocol === \"blob:\" && parsed.pathname.length > 0) {\n try {\n return new URL(parsed.pathname);\n } catch {\n return parsed;\n }\n }\n return parsed;\n } catch {\n return undefined;\n }\n}\n\nfunction resolveWebHostname(): string | undefined {\n const directHostname = resolveLocationString(\"hostname\");\n if (directHostname) {\n return directHostname;\n }\n return (\n parseUrlCandidate(resolveLocationString(\"href\"))?.hostname ||\n parseUrlCandidate(resolveLocationString(\"origin\"))?.hostname ||\n parseUrlCandidate(resolveGlobalOrigin())?.hostname ||\n undefined\n );\n}\n\nfunction isPrivateNetworkHostname(hostname: string): boolean {\n const normalized = hostname.toLowerCase().replace(/^\\[|\\]$/g, \"\");\n if (normalized === \"::1\") {\n return true;\n }\n if (normalized.startsWith(\"fc\") || normalized.startsWith(\"fd\")) {\n return true;\n }\n const match = /^(\\d{1,3})\\.(\\d{1,3})\\.(\\d{1,3})\\.(\\d{1,3})$/.exec(normalized);\n if (!match) {\n return false;\n }\n const octets = match.slice(1).map((part) => Number(part));\n if (octets.some((part) => Number.isNaN(part) || part < 0 || part > 255)) {\n return false;\n }\n const first = octets[0];\n const second = octets[1];\n if (first === undefined || second === undefined) {\n return false;\n }\n return (\n first === 10 ||\n first === 127 ||\n (first === 169 && second === 254) ||\n (first === 172 && second >= 16 && second <= 31) ||\n (first === 192 && second === 168)\n );\n}\n\nfunction resolveWebOrigin(): string | undefined {\n const directOrigin = resolveLocationString(\"origin\");\n if (directOrigin && directOrigin !== \"null\") {\n return directOrigin;\n }\n const parsedOrigin =\n parseUrlCandidate(resolveLocationString(\"href\"))?.origin ||\n parseUrlCandidate(resolveGlobalOrigin())?.origin;\n return parsedOrigin && parsedOrigin !== \"null\" ? parsedOrigin : undefined;\n}\n\nfunction resolveWebAppName(): string | undefined {\n try {\n return resolveWebHostname() ?? globalThis.document?.title ?? undefined;\n } catch {\n return undefined;\n }\n}\n\nfunction resolveWebSessionLabel(): string | undefined {\n try {\n if (typeof navigator === \"undefined\") {\n return undefined;\n }\n\n // Generate or retrieve a persistent unique name for this browser instance.\n // This makes it much easier to identify which browser tab/window you're\n // looking at in the devtools dashboard.\n const STORAGE_KEY = \"syncore-session-name\";\n let uniqueName: string | null = null;\n\n try {\n uniqueName = globalThis.localStorage?.getItem(STORAGE_KEY) ?? null;\n } catch {\n /* localStorage may not be available */\n }\n\n if (!uniqueName) {\n uniqueName = generateUniqueSessionName();\n\n try {\n globalThis.localStorage?.setItem(STORAGE_KEY, uniqueName);\n } catch {\n /* ignore storage errors */\n }\n }\n\n // Detect browser type for additional context\n const browser = navigator.userAgent.includes(\"Firefox\")\n ? \"Firefox\"\n : navigator.userAgent.includes(\"Chrome\")\n ? \"Chrome\"\n : navigator.userAgent.includes(\"Safari\")\n ? \"Safari\"\n : \"Browser\";\n\n return `${uniqueName} (${browser})`;\n } catch {\n return undefined;\n }\n}\n\nfunction announceBrowserSession(options: {\n enabled: boolean;\n sessionLabel?: string | undefined;\n appName?: string | undefined;\n origin?: string | undefined;\n devtoolsUrl?: string | undefined;\n}): void {\n if (!options.enabled || !options.sessionLabel) {\n return;\n }\n\n const announcedSessions = getAnnouncedBrowserSessions();\n if (announcedSessions.has(options.sessionLabel)) {\n return;\n }\n announcedSessions.add(options.sessionLabel);\n\n try {\n const details = [\n options.appName ? `app=${options.appName}` : undefined,\n options.origin ? `origin=${options.origin}` : undefined,\n options.devtoolsUrl ? `devtools=${options.devtoolsUrl}` : undefined\n ].filter((value): value is string => value !== undefined);\n\n console.info(\n `[syncore] Browser session: ${options.sessionLabel}${details.length > 0 ? ` (${details.join(\", \")})` : \"\"}`\n );\n } catch {\n /* ignore console failures */\n }\n}\n\nfunction getAnnouncedBrowserSessions(): Set<string> {\n const key = \"__syncoreAnnouncedBrowserSessions\";\n const scope = globalThis as typeof globalThis & {\n [key]?: Set<string>;\n };\n if (!scope[key]) {\n scope[key] = new Set<string>();\n }\n return scope[key];\n}\n\n/* ------------------------------------------------------------------ */\n/* Unique session name generator */\n/* ------------------------------------------------------------------ */\n\nconst SESSION_ADJECTIVES = [\n \"Acrobatic\",\n \"Bold\",\n \"Cosmic\",\n \"Daring\",\n \"Electric\",\n \"Fierce\",\n \"Golden\",\n \"Hidden\",\n \"Iron\",\n \"Jade\",\n \"Keen\",\n \"Lunar\",\n \"Mystic\",\n \"Noble\",\n \"Orbital\",\n \"Primal\",\n \"Quick\",\n \"Radiant\",\n \"Shadow\",\n \"Turbo\",\n \"Ultra\",\n \"Vivid\",\n \"Wicked\",\n \"Xenon\",\n \"Zen\",\n \"Arctic\",\n \"Binary\",\n \"Cyber\",\n \"Digital\",\n \"Ember\",\n \"Frozen\",\n \"Galactic\",\n \"Hyper\",\n \"Infra\",\n \"Jumbo\",\n \"Kinetic\",\n \"Liquid\",\n \"Magnetic\",\n \"Neon\",\n \"Onyx\",\n \"Phantom\",\n \"Quantum\",\n \"Rapid\",\n \"Sonic\",\n \"Titan\",\n \"Velvet\",\n \"Wild\",\n \"Blazing\",\n \"Crystal\",\n \"Dynamic\"\n] as const;\n\nconst SESSION_NOUNS = [\n \"Monkey\",\n \"Phoenix\",\n \"Tiger\",\n \"Dragon\",\n \"Falcon\",\n \"Panther\",\n \"Wolf\",\n \"Eagle\",\n \"Cobra\",\n \"Shark\",\n \"Raven\",\n \"Fox\",\n \"Lynx\",\n \"Hawk\",\n \"Bear\",\n \"Jaguar\",\n \"Viper\",\n \"Owl\",\n \"Stallion\",\n \"Dolphin\",\n \"Developer\",\n \"Hacker\",\n \"Wizard\",\n \"Ninja\",\n \"Pilot\",\n \"Pioneer\",\n \"Voyager\",\n \"Explorer\",\n \"Runner\",\n \"Ranger\",\n \"Maverick\",\n \"Spartan\",\n \"Viking\",\n \"Sentinel\",\n \"Guardian\",\n \"Nomad\",\n \"Cipher\",\n \"Vector\",\n \"Matrix\",\n \"Prism\",\n \"Nebula\",\n \"Comet\",\n \"Pulse\",\n \"Vertex\",\n \"Flux\",\n \"Storm\",\n \"Blaze\",\n \"Frost\",\n \"Thunder\",\n \"Drift\"\n] as const;\n\nfunction generateUniqueSessionName(): string {\n const adj =\n SESSION_ADJECTIVES[Math.floor(Math.random() * SESSION_ADJECTIVES.length)]!;\n const noun = SESSION_NOUNS[Math.floor(Math.random() * SESSION_NOUNS.length)]!;\n return `${adj} ${noun}`;\n}\n\n/**\n * Browser file/blob storage built on top of Syncore web persistence.\n */\nexport class BrowserFileStorageAdapter implements SyncoreStorageAdapter {\n constructor(\n private readonly persistence: SyncoreWebPersistence,\n private readonly namespace: string\n ) {}\n\n async put(id: string, input: StorageWriteInput): Promise<StorageObject> {\n const bytes = normalizeBinary(input.data);\n await this.persistence.putFile(\n this.namespace,\n id,\n bytes,\n input.contentType ?? null\n );\n return {\n id,\n path: `${this.persistence.storageProtocol}://${this.namespace}/${id}`,\n size: bytes.byteLength,\n contentType: input.contentType ?? null\n };\n }\n\n async get(id: string): Promise<StorageObject | null> {\n const file = await this.persistence.getFile(this.namespace, id);\n if (!file) {\n return null;\n }\n return {\n id,\n path: `${this.persistence.storageProtocol}://${this.namespace}/${id}`,\n size: file.size,\n contentType: file.contentType\n };\n }\n\n async read(id: string): Promise<Uint8Array | null> {\n const file = await this.persistence.getFile(this.namespace, id);\n return file?.bytes ?? null;\n }\n\n async delete(id: string): Promise<void> {\n await this.persistence.deleteFile(this.namespace, id);\n }\n\n async list(): Promise<StorageObject[]> {\n const files = await this.persistence.listFiles(this.namespace);\n return files.map((file) => ({\n id: file.id,\n path: `${this.persistence.storageProtocol}://${this.namespace}/${file.id}`,\n size: file.size,\n contentType: file.contentType\n }));\n }\n}\n\nfunction normalizeBinary(data: StorageWriteInput[\"data\"]): Uint8Array {\n if (typeof data === \"string\") {\n return new TextEncoder().encode(data);\n }\n if (data instanceof Uint8Array) {\n return data;\n }\n return new Uint8Array(data);\n}\n"],"mappings":"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"}
|
|
1
|
+
{"version":3,"file":"index.js","names":[],"sources":["../src/index.ts"],"sourcesContent":["import {\n createDevtoolsCommandHandler,\n createDevtoolsSubscriptionHost,\n type DevtoolsCommandHandler,\n type DevtoolsSink,\n type DevtoolsSubscriptionHost,\n type SyncoreDataModel,\n generateId,\n SyncoreRuntime,\n type SchedulerOptions,\n type SyncoreCapabilities,\n type SyncoreRuntimeOptions,\n type SyncoreStorageAdapter,\n type StorageObject,\n type StorageWriteInput\n} from \"@syncore/core\";\nimport {\n SYNCORE_DEVTOOLS_MAX_SUPPORTED_PROTOCOL_VERSION,\n SYNCORE_DEVTOOLS_MIN_SUPPORTED_PROTOCOL_VERSION,\n SYNCORE_DEVTOOLS_PROTOCOL_VERSION,\n type SyncoreDevtoolsClientMessage,\n type SyncoreDevtoolsMessage,\n type SyncoreRuntimeSummary\n} from \"@syncore/devtools-protocol\";\nimport {\n createWebPersistence,\n type SyncoreWebPersistence,\n type WebPersistenceMode\n} from \"./persistence.js\";\nimport {\n BroadcastChannelExternalChangeSignal,\n createDefaultSyncChannelName,\n SqlJsExternalChangeApplier\n} from \"./external-change.js\";\nimport { SqlJsDriver } from \"./sqljs.js\";\nimport {\n attachWebWorkerRuntime,\n type SyncoreWorkerMessageEndpoint\n} from \"./worker.js\";\nexport * from \"./worker.js\";\nexport * from \"./persistence.js\";\nexport * from \"./indexeddb.js\";\nexport * from \"./opfs.js\";\nexport * from \"./external-change.js\";\n\nexport type WebSyncoreSchema<\n TSchema extends SyncoreDataModel = SyncoreDataModel\n> = TSchema;\nexport type BrowserSyncoreSchema<\n TSchema extends SyncoreDataModel = SyncoreDataModel\n> = WebSyncoreSchema<TSchema>;\n\nconst DEVTOOLS_META_NAMESPACE = \"__syncore_devtools_meta__\";\nconst STORAGE_SCOPE_ID_PREFIX = \"storage-scope\";\n\n/**\n * Options for constructing a browser Syncore runtime.\n *\n * Use this when you want to host the full runtime in a browser tab or worker.\n */\nexport interface CreateWebRuntimeOptions<\n TSchema extends WebSyncoreSchema = WebSyncoreSchema\n> {\n /** The schema for the local Syncore app. */\n schema: TSchema;\n\n /** The generated function registry for the local Syncore app. */\n functions: SyncoreRuntimeOptions<TSchema>[\"functions\"];\n\n /** Optional resolved installed components for the local Syncore app. */\n components?: SyncoreRuntimeOptions<TSchema>[\"components\"];\n\n /** Optional platform capabilities exposed to function handlers. */\n capabilities?: SyncoreCapabilities;\n\n /** Optional custom SQL driver. Defaults to SQL.js with local persistence. */\n driver?: SyncoreRuntimeOptions<TSchema>[\"driver\"];\n\n /** Optional custom file/blob storage adapter. */\n storage?: SyncoreStorageAdapter;\n\n /** Optional explicit persistence implementation. */\n persistence?: SyncoreWebPersistence;\n\n /** Which browser persistence mode to use when Syncore creates one for you. */\n persistenceMode?: WebPersistenceMode;\n\n /** Logical database name for SQL.js and local storage namespaces. */\n databaseName?: string;\n\n /** Optional IndexedDB database name for persistence metadata. */\n persistenceDatabaseName?: string;\n\n /** Optional OPFS directory name for persistent files. */\n opfsRootDirectoryName?: string;\n\n /** Optional namespace for file/blob storage. */\n storageNamespace?: string;\n\n /** Optional direct wasm URL for SQL.js. */\n wasmUrl?: string;\n\n /** Optional callback for resolving SQL.js support files. */\n locateFile?: (fileName: string) => string;\n\n /** Optional runtime platform label shown in devtools snapshots. */\n platform?: string;\n\n /** Optional devtools sink used during development. */\n devtools?: DevtoolsSink | false;\n\n /** Optional scheduler configuration for jobs and recurring work. */\n scheduler?: SchedulerOptions;\n}\n\n/**\n * Options for hosting a Syncore runtime inside a browser Worker.\n */\nexport interface CreateWebWorkerRuntimeOptions<\n TSchema extends WebSyncoreSchema = WebSyncoreSchema\n> extends CreateWebRuntimeOptions<TSchema> {\n /** The message endpoint exposed by the current worker global. */\n endpoint: SyncoreWorkerMessageEndpoint;\n}\n\n/**\n * Options for constructing a browser Syncore runtime.\n */\nexport type CreateBrowserRuntimeOptions<\n TSchema extends BrowserSyncoreSchema = BrowserSyncoreSchema\n> = CreateWebRuntimeOptions<TSchema>;\n\n/**\n * Options for hosting a Syncore runtime inside a browser Worker.\n */\nexport type CreateBrowserWorkerRuntimeOptions<\n TSchema extends BrowserSyncoreSchema = BrowserSyncoreSchema\n> = CreateWebWorkerRuntimeOptions<TSchema>;\n\nexport interface WebExternalChangeSupport {\n signal: BroadcastChannelExternalChangeSignal;\n applier?: SqlJsExternalChangeApplier;\n}\n\n/**\n * Create a full Syncore runtime directly in the browser.\n *\n * Most React apps should use a worker runtime instead so queries and SQLite work\n * stay off the main thread.\n */\nexport async function createWebSyncoreRuntime<\n TSchema extends WebSyncoreSchema\n>(\n options: CreateWebRuntimeOptions<TSchema>\n): Promise<SyncoreRuntime<TSchema>> {\n const persistence =\n options.persistence ??\n (await createWebPersistence({\n ...(options.persistenceMode ? { mode: options.persistenceMode } : {}),\n ...(options.persistenceDatabaseName\n ? { indexedDbDatabaseName: options.persistenceDatabaseName }\n : {}),\n opfsRootDirectoryName:\n options.opfsRootDirectoryName ?? options.databaseName ?? \"syncore\"\n }));\n const driver =\n options.driver ??\n (await SqlJsDriver.create({\n databaseName: options.databaseName ?? \"syncore\",\n persistence,\n ...(options.wasmUrl ? { wasmUrl: options.wasmUrl } : {}),\n ...(options.locateFile ? { locateFile: options.locateFile } : {})\n }));\n const storage =\n options.storage ??\n new BrowserFileStorageAdapter(\n persistence,\n options.storageNamespace ?? options.databaseName ?? \"syncore\"\n );\n const externalChangeSupport = createWebExternalChangeSupport({\n databaseName: options.databaseName ?? \"syncore\",\n persistence,\n driver\n });\n const appName = resolveWebAppName();\n const origin = resolveWebOrigin();\n const sessionLabel = resolveWebSessionLabel();\n const databaseLabel = options.databaseName ?? \"syncore\";\n const storageScopeId = await resolvePersistedStorageScopeId(\n persistence,\n databaseLabel\n );\n const storageIdentity = [\n origin ?? \"unknown-origin\",\n persistence.storageProtocol,\n databaseLabel,\n storageScopeId\n ].join(\"::\");\n const autoDevtools =\n options.devtools === undefined && shouldAutoConnectDevtools()\n ? (() => {\n const sinkOptions: BrowserWebSocketDevtoolsSinkOptions = {\n url: resolveDefaultDevtoolsUrl(),\n targetKind: \"client\",\n storageProtocol: persistence.storageProtocol,\n databaseLabel,\n storageIdentity\n };\n if (appName) {\n sinkOptions.appName = appName;\n }\n if (origin) {\n sinkOptions.origin = origin;\n }\n if (sessionLabel) {\n sinkOptions.sessionLabel = sessionLabel;\n }\n return createBrowserWebSocketDevtoolsSink(sinkOptions);\n })()\n : undefined;\n const resolvedDevtools =\n options.devtools === false ? undefined : (options.devtools ?? autoDevtools);\n\n announceBrowserSession({\n enabled: resolvedDevtools !== undefined,\n sessionLabel,\n appName,\n origin,\n devtoolsUrl:\n options.devtools && typeof options.devtools === \"object\"\n ? undefined\n : resolveDefaultDevtoolsUrl()\n });\n\n const runtime = new SyncoreRuntime({\n schema: options.schema,\n functions: options.functions,\n ...(options.components ? { components: options.components } : {}),\n driver,\n storage,\n externalChangeSignal: externalChangeSupport.signal,\n ...(externalChangeSupport.applier\n ? { externalChangeApplier: externalChangeSupport.applier }\n : {}),\n platform: options.platform ?? \"browser\",\n ...(options.capabilities ? { capabilities: options.capabilities } : {}),\n ...(resolvedDevtools ? { devtools: resolvedDevtools } : {}),\n ...(options.scheduler ? { scheduler: options.scheduler } : {})\n });\n\n if (autoDevtools) {\n autoDevtools.attachRuntime(runtime);\n autoDevtools.attachCommandHandler(\n createDevtoolsCommandHandler({\n driver,\n schema: options.schema,\n functions: options.functions,\n admin: runtime.getAdmin()\n })\n );\n autoDevtools.attachSubscriptionHost(\n createDevtoolsSubscriptionHost({\n driver,\n schema: options.schema,\n functions: options.functions,\n admin: runtime.getAdmin()\n })\n );\n }\n\n return runtime;\n}\n\nexport function createWebExternalChangeSupport(options: {\n databaseName: string;\n persistence: SyncoreWebPersistence;\n driver: CreateWebRuntimeOptions<SyncoreDataModel>[\"driver\"] | undefined;\n}): WebExternalChangeSupport {\n const signal = new BroadcastChannelExternalChangeSignal({\n channelName: createDefaultSyncChannelName(options.databaseName)\n });\n const sqlDriver =\n options.driver instanceof SqlJsDriver ? options.driver : undefined;\n\n if (!sqlDriver) {\n return { signal };\n }\n\n return {\n signal,\n applier: new SqlJsExternalChangeApplier({\n databaseName: options.databaseName,\n persistence: options.persistence,\n createDatabase: (bytes) => sqlDriver.createDatabaseFromBytes(bytes),\n replaceDatabase: (database) => {\n sqlDriver.replaceDatabase(database);\n }\n })\n };\n}\n\nexport async function createExpoWebExternalChangeSupport(options: {\n databaseName: string;\n locateFile?: (fileName: string) => string;\n wasmUrl?: string;\n persistenceDatabaseName?: string;\n opfsRootDirectoryName?: string;\n persistenceMode?: WebPersistenceMode;\n}): Promise<WebExternalChangeSupport> {\n const persistence = await createWebPersistence({\n ...(options.persistenceMode ? { mode: options.persistenceMode } : {}),\n ...(options.persistenceDatabaseName\n ? { indexedDbDatabaseName: options.persistenceDatabaseName }\n : {}),\n opfsRootDirectoryName: options.opfsRootDirectoryName ?? options.databaseName\n });\n const driver = await SqlJsDriver.create({\n databaseName: options.databaseName,\n persistence,\n ...(options.wasmUrl ? { wasmUrl: options.wasmUrl } : {}),\n ...(options.locateFile ? { locateFile: options.locateFile } : {})\n });\n\n return createWebExternalChangeSupport({\n databaseName: options.databaseName,\n persistence,\n driver\n });\n}\n\n/**\n * Attach a Syncore runtime to a browser Worker endpoint.\n */\nexport function createWebWorkerRuntime<\n TSchema extends WebSyncoreSchema\n>(options: CreateWebWorkerRuntimeOptions<TSchema>) {\n return attachWebWorkerRuntime({\n endpoint: options.endpoint,\n createRuntime: () => createWebSyncoreRuntime(options)\n });\n}\n\n/**\n * Attach a Syncore runtime to a browser Worker endpoint.\n */\nexport function createBrowserWorkerRuntime(\n options: CreateBrowserWorkerRuntimeOptions\n) {\n return createWebWorkerRuntime(options);\n}\n\n/**\n * Create a client directly from a browser Syncore runtime.\n */\nexport function createWebSyncoreClient<\n TSchema extends WebSyncoreSchema\n>(runtime: SyncoreRuntime<TSchema>) {\n return runtime.createClient();\n}\n\n/**\n * Create a full Syncore runtime directly in the browser.\n */\nexport function createBrowserSyncoreRuntime<\n TSchema extends BrowserSyncoreSchema\n>(options: CreateBrowserRuntimeOptions<TSchema>) {\n return createWebSyncoreRuntime(options);\n}\n\n/**\n * Create a client directly from a browser Syncore runtime.\n */\nexport function createBrowserSyncoreClient<\n TSchema extends BrowserSyncoreSchema\n>(runtime: SyncoreRuntime<TSchema>) {\n return createWebSyncoreClient(runtime);\n}\n\nexport interface BrowserWebSocketDevtoolsSinkOptions {\n url: string;\n reconnectDelayMs?: number;\n appName?: string;\n origin?: string;\n sessionLabel?: string;\n targetKind?: \"client\";\n storageProtocol?: string;\n databaseLabel?: string;\n storageIdentity?: string;\n}\n\nexport interface BrowserWebSocketDevtoolsSink extends DevtoolsSink {\n attachRuntime(runtime: SyncoreRuntime<WebSyncoreSchema>): void;\n attachCommandHandler(handler: DevtoolsCommandHandler): void;\n attachSubscriptionHost(host: DevtoolsSubscriptionHost): void;\n dispose(): void;\n}\n\nexport function createBrowserWebSocketDevtoolsSink(\n options: BrowserWebSocketDevtoolsSinkOptions\n): BrowserWebSocketDevtoolsSink {\n let socket: WebSocket | undefined;\n let disposed = false;\n let connectTimer: ReturnType<typeof setTimeout> | undefined;\n let getSummary: (() => SyncoreRuntimeSummary) | undefined;\n let onCommand: DevtoolsCommandHandler | undefined;\n let subscriptionHost: DevtoolsSubscriptionHost | undefined;\n const pendingMessages: SyncoreDevtoolsMessage[] = [];\n let latestHello:\n | {\n runtimeId: string;\n platform: string;\n }\n | undefined;\n\n const connect = () => {\n if (disposed || typeof WebSocket === \"undefined\") {\n return;\n }\n socket = new WebSocket(options.url);\n socket.onopen = () => {\n if (latestHello) {\n sendNow({\n type: \"hello\",\n protocolVersion: SYNCORE_DEVTOOLS_PROTOCOL_VERSION,\n minSupportedProtocolVersion:\n SYNCORE_DEVTOOLS_MIN_SUPPORTED_PROTOCOL_VERSION,\n maxSupportedProtocolVersion:\n SYNCORE_DEVTOOLS_MAX_SUPPORTED_PROTOCOL_VERSION,\n runtimeId: latestHello.runtimeId,\n platform: latestHello.platform,\n ...(options.appName ? { appName: options.appName } : {}),\n ...(options.origin ? { origin: options.origin } : {}),\n ...(options.sessionLabel\n ? { sessionLabel: options.sessionLabel }\n : {}),\n ...(options.targetKind ? { targetKind: options.targetKind } : {}),\n ...(options.storageProtocol\n ? { storageProtocol: options.storageProtocol }\n : {}),\n ...(options.databaseLabel ? { databaseLabel: options.databaseLabel } : {}),\n ...(options.storageIdentity\n ? { storageIdentity: options.storageIdentity }\n : {})\n });\n }\n flushPendingMessages();\n };\n socket.onmessage = (event) => {\n if (typeof event.data !== \"string\") {\n return;\n }\n const message = JSON.parse(event.data) as\n | SyncoreDevtoolsMessage\n | SyncoreDevtoolsClientMessage;\n if (message.type === \"ping\") {\n send({ type: \"pong\" });\n } else if (message.type === \"command\" && onCommand) {\n onCommand(message.payload)\n .then((responsePayload) => {\n const runtimeId =\n latestHello?.runtimeId ?? getSummary?.().runtimeId;\n if (!runtimeId) {\n return;\n }\n send({\n type: \"command.result\",\n commandId: message.commandId,\n runtimeId,\n payload: responsePayload\n });\n })\n .catch((err) => {\n const runtimeId =\n latestHello?.runtimeId ?? getSummary?.().runtimeId;\n if (!runtimeId) {\n return;\n }\n send({\n type: \"command.result\",\n commandId: message.commandId,\n runtimeId,\n payload: {\n kind: \"error\",\n message: err instanceof Error ? err.message : \"Unknown error\"\n }\n });\n });\n } else if (message.type === \"subscribe\" && subscriptionHost) {\n void subscriptionHost.subscribe(\n message.subscriptionId,\n message.payload,\n (payload) => {\n const runtimeId =\n latestHello?.runtimeId ?? getSummary?.().runtimeId;\n if (!runtimeId) {\n return;\n }\n send({\n type: \"subscription.data\",\n subscriptionId: message.subscriptionId,\n runtimeId,\n payload\n });\n }\n );\n } else if (message.type === \"unsubscribe\") {\n subscriptionHost?.unsubscribe(message.subscriptionId);\n }\n };\n socket.onclose = scheduleReconnect;\n socket.onerror = () => {\n socket?.close();\n };\n };\n\n const scheduleReconnect = () => {\n if (disposed || connectTimer) {\n return;\n }\n connectTimer = setTimeout(() => {\n connectTimer = undefined;\n connect();\n }, options.reconnectDelayMs ?? 1200);\n };\n\n const sendNow = (message: SyncoreDevtoolsMessage) => {\n if (socket?.readyState === WebSocket.OPEN) {\n socket.send(JSON.stringify(message));\n }\n };\n\n const flushPendingMessages = () => {\n while (pendingMessages.length > 0) {\n const nextMessage = pendingMessages.shift();\n if (nextMessage) {\n sendNow(nextMessage);\n }\n }\n };\n\n const send = (message: SyncoreDevtoolsMessage) => {\n if (socket?.readyState === WebSocket.OPEN) {\n sendNow(message);\n return;\n }\n pendingMessages.push(message);\n };\n\n connect();\n\n return {\n emit(event) {\n if (event.type === \"runtime.connected\") {\n latestHello = {\n runtimeId: event.runtimeId,\n platform: event.platform\n };\n send({\n type: \"hello\",\n protocolVersion: SYNCORE_DEVTOOLS_PROTOCOL_VERSION,\n minSupportedProtocolVersion:\n SYNCORE_DEVTOOLS_MIN_SUPPORTED_PROTOCOL_VERSION,\n maxSupportedProtocolVersion:\n SYNCORE_DEVTOOLS_MAX_SUPPORTED_PROTOCOL_VERSION,\n runtimeId: event.runtimeId,\n platform: event.platform,\n ...(options.appName ? { appName: options.appName } : {}),\n ...(options.origin ? { origin: options.origin } : {}),\n ...(options.sessionLabel\n ? { sessionLabel: options.sessionLabel }\n : {}),\n ...(options.targetKind ? { targetKind: options.targetKind } : {}),\n ...(options.storageProtocol\n ? { storageProtocol: options.storageProtocol }\n : {}),\n ...(options.databaseLabel ? { databaseLabel: options.databaseLabel } : {}),\n ...(options.storageIdentity\n ? { storageIdentity: options.storageIdentity }\n : {})\n });\n }\n send({ type: \"event\", event });\n },\n attachRuntime(runtime) {\n getSummary = () =>\n withRuntimeSummaryMeta(runtime.getAdmin().getRuntimeSummary(), options);\n },\n attachCommandHandler(handler) {\n onCommand = handler;\n },\n attachSubscriptionHost(host) {\n subscriptionHost = host;\n },\n dispose() {\n disposed = true;\n if (connectTimer) {\n clearTimeout(connectTimer);\n }\n subscriptionHost?.dispose();\n socket?.close();\n }\n };\n}\n\nfunction withRuntimeSummaryMeta(\n summary: SyncoreRuntimeSummary,\n options: BrowserWebSocketDevtoolsSinkOptions\n): SyncoreRuntimeSummary {\n return {\n ...summary,\n ...(options.appName ? { appName: options.appName } : {}),\n ...(options.origin ? { origin: options.origin } : {}),\n ...(options.sessionLabel ? { sessionLabel: options.sessionLabel } : {}),\n ...(options.targetKind ? { targetKind: options.targetKind } : {}),\n ...(options.storageProtocol\n ? { storageProtocol: options.storageProtocol }\n : {}),\n ...(options.databaseLabel ? { databaseLabel: options.databaseLabel } : {}),\n ...(options.storageIdentity\n ? { storageIdentity: options.storageIdentity }\n : {})\n };\n}\n\nfunction shouldAutoConnectDevtools(): boolean {\n const hostname = resolveWebHostname();\n if (!hostname) {\n return false;\n }\n return (\n hostname === \"localhost\" ||\n isPrivateNetworkHostname(hostname) ||\n hostname.endsWith(\".local\")\n );\n}\n\nfunction resolveDefaultDevtoolsUrl(): string {\n return \"ws://127.0.0.1:4311\";\n}\n\nfunction resolveLocationString(\n key: \"href\" | \"origin\" | \"hostname\"\n): string | undefined {\n try {\n const value = globalThis.location?.[key];\n return typeof value === \"string\" && value.length > 0 ? value : undefined;\n } catch {\n return undefined;\n }\n}\n\nfunction resolveGlobalOrigin(): string | undefined {\n try {\n const value = (globalThis as { origin?: unknown }).origin;\n return typeof value === \"string\" && value.length > 0 ? value : undefined;\n } catch {\n return undefined;\n }\n}\n\nfunction parseUrlCandidate(candidate: string | undefined): URL | undefined {\n if (!candidate || candidate === \"null\") {\n return undefined;\n }\n try {\n const parsed = new URL(candidate);\n if (parsed.protocol === \"blob:\" && parsed.pathname.length > 0) {\n try {\n return new URL(parsed.pathname);\n } catch {\n return parsed;\n }\n }\n return parsed;\n } catch {\n return undefined;\n }\n}\n\nfunction resolveWebHostname(): string | undefined {\n const directHostname = resolveLocationString(\"hostname\");\n if (directHostname) {\n return directHostname;\n }\n return (\n parseUrlCandidate(resolveLocationString(\"href\"))?.hostname ||\n parseUrlCandidate(resolveLocationString(\"origin\"))?.hostname ||\n parseUrlCandidate(resolveGlobalOrigin())?.hostname ||\n undefined\n );\n}\n\nfunction isPrivateNetworkHostname(hostname: string): boolean {\n const normalized = hostname.toLowerCase().replace(/^\\[|\\]$/g, \"\");\n if (normalized === \"::1\") {\n return true;\n }\n if (normalized.startsWith(\"fc\") || normalized.startsWith(\"fd\")) {\n return true;\n }\n const match = /^(\\d{1,3})\\.(\\d{1,3})\\.(\\d{1,3})\\.(\\d{1,3})$/.exec(normalized);\n if (!match) {\n return false;\n }\n const octets = match.slice(1).map((part) => Number(part));\n if (octets.some((part) => Number.isNaN(part) || part < 0 || part > 255)) {\n return false;\n }\n const first = octets[0];\n const second = octets[1];\n if (first === undefined || second === undefined) {\n return false;\n }\n return (\n first === 10 ||\n first === 127 ||\n (first === 169 && second === 254) ||\n (first === 172 && second >= 16 && second <= 31) ||\n (first === 192 && second === 168)\n );\n}\n\nfunction resolveWebOrigin(): string | undefined {\n const directOrigin = resolveLocationString(\"origin\");\n if (directOrigin && directOrigin !== \"null\") {\n return directOrigin;\n }\n const parsedOrigin =\n parseUrlCandidate(resolveLocationString(\"href\"))?.origin ||\n parseUrlCandidate(resolveGlobalOrigin())?.origin;\n return parsedOrigin && parsedOrigin !== \"null\" ? parsedOrigin : undefined;\n}\n\nfunction resolveWebAppName(): string | undefined {\n try {\n return resolveWebHostname() ?? globalThis.document?.title ?? undefined;\n } catch {\n return undefined;\n }\n}\n\nfunction resolveWebSessionLabel(): string | undefined {\n try {\n if (typeof navigator === \"undefined\") {\n return undefined;\n }\n\n // Generate or retrieve a persistent unique name for this browser instance.\n // This makes it much easier to identify which browser tab/window you're\n // looking at in the devtools dashboard.\n const STORAGE_KEY = \"syncore-session-name\";\n let uniqueName: string | null = null;\n\n try {\n uniqueName = globalThis.localStorage?.getItem(STORAGE_KEY) ?? null;\n } catch {\n /* localStorage may not be available */\n }\n\n if (!uniqueName) {\n uniqueName = generateUniqueSessionName();\n\n try {\n globalThis.localStorage?.setItem(STORAGE_KEY, uniqueName);\n } catch {\n /* ignore storage errors */\n }\n }\n\n const browser = resolveBrowserName(navigator);\n\n return `${uniqueName} (${browser})`;\n } catch {\n return undefined;\n }\n}\n\nfunction resolveBrowserName(\n nav: Navigator & {\n userAgentData?: {\n brands?: Array<{\n brand: string;\n }>;\n };\n }\n): string {\n const brands = nav.userAgentData?.brands?.map((entry) => entry.brand) ?? [];\n\n if (brands.some((brand) => /microsoft edge/i.test(brand))) {\n return \"Edge\";\n }\n if (brands.some((brand) => /firefox/i.test(brand))) {\n return \"Firefox\";\n }\n if (brands.some((brand) => /opera/i.test(brand))) {\n return \"Opera\";\n }\n if (brands.some((brand) => /chrome|chromium/i.test(brand))) {\n return \"Chrome\";\n }\n if (brands.some((brand) => /safari/i.test(brand))) {\n return \"Safari\";\n }\n\n const userAgent = nav.userAgent;\n if (/Firefox\\//i.test(userAgent)) {\n return \"Firefox\";\n }\n if (/Edg\\//i.test(userAgent)) {\n return \"Edge\";\n }\n if (/OPR\\/|Opera/i.test(userAgent)) {\n return \"Opera\";\n }\n if (/Chrome\\/|CriOS\\//i.test(userAgent)) {\n return \"Chrome\";\n }\n if (/Safari\\//i.test(userAgent)) {\n return \"Safari\";\n }\n return \"Browser\";\n}\n\nasync function resolvePersistedStorageScopeId(\n persistence: SyncoreWebPersistence,\n databaseLabel: string\n): Promise<string> {\n const id = `${STORAGE_SCOPE_ID_PREFIX}:${databaseLabel}`;\n const existing = await persistence.getFile(DEVTOOLS_META_NAMESPACE, id);\n\n if (existing) {\n const value = new TextDecoder().decode(existing.bytes).trim();\n if (value.length > 0) {\n return value;\n }\n }\n\n const nextValue = generateId();\n await persistence.putFile(\n DEVTOOLS_META_NAMESPACE,\n id,\n new TextEncoder().encode(nextValue),\n \"text/plain\"\n );\n return nextValue;\n}\n\nfunction announceBrowserSession(options: {\n enabled: boolean;\n sessionLabel?: string | undefined;\n appName?: string | undefined;\n origin?: string | undefined;\n devtoolsUrl?: string | undefined;\n}): void {\n if (!options.enabled || !options.sessionLabel) {\n return;\n }\n\n const announcedSessions = getAnnouncedBrowserSessions();\n if (announcedSessions.has(options.sessionLabel)) {\n return;\n }\n announcedSessions.add(options.sessionLabel);\n\n try {\n const details = [\n options.appName ? `app=${options.appName}` : undefined,\n options.origin ? `origin=${options.origin}` : undefined,\n options.devtoolsUrl ? `devtools=${options.devtoolsUrl}` : undefined\n ].filter((value): value is string => value !== undefined);\n\n console.info(\n `[syncore] Browser session: ${options.sessionLabel}${details.length > 0 ? ` (${details.join(\", \")})` : \"\"}`\n );\n } catch {\n /* ignore console failures */\n }\n}\n\nfunction getAnnouncedBrowserSessions(): Set<string> {\n const key = \"__syncoreAnnouncedBrowserSessions\";\n const scope = globalThis as typeof globalThis & {\n [key]?: Set<string>;\n };\n if (!scope[key]) {\n scope[key] = new Set<string>();\n }\n return scope[key];\n}\n\n/* ------------------------------------------------------------------ */\n/* Unique session name generator */\n/* ------------------------------------------------------------------ */\n\nconst SESSION_ADJECTIVES = [\n \"Acrobatic\",\n \"Bold\",\n \"Cosmic\",\n \"Daring\",\n \"Electric\",\n \"Fierce\",\n \"Golden\",\n \"Hidden\",\n \"Iron\",\n \"Jade\",\n \"Keen\",\n \"Lunar\",\n \"Mystic\",\n \"Noble\",\n \"Orbital\",\n \"Primal\",\n \"Quick\",\n \"Radiant\",\n \"Shadow\",\n \"Turbo\",\n \"Ultra\",\n \"Vivid\",\n \"Wicked\",\n \"Xenon\",\n \"Zen\",\n \"Arctic\",\n \"Binary\",\n \"Cyber\",\n \"Digital\",\n \"Ember\",\n \"Frozen\",\n \"Galactic\",\n \"Hyper\",\n \"Infra\",\n \"Jumbo\",\n \"Kinetic\",\n \"Liquid\",\n \"Magnetic\",\n \"Neon\",\n \"Onyx\",\n \"Phantom\",\n \"Quantum\",\n \"Rapid\",\n \"Sonic\",\n \"Titan\",\n \"Velvet\",\n \"Wild\",\n \"Blazing\",\n \"Crystal\",\n \"Dynamic\"\n] as const;\n\nconst SESSION_NOUNS = [\n \"Monkey\",\n \"Phoenix\",\n \"Tiger\",\n \"Dragon\",\n \"Falcon\",\n \"Panther\",\n \"Wolf\",\n \"Eagle\",\n \"Cobra\",\n \"Shark\",\n \"Raven\",\n \"Fox\",\n \"Lynx\",\n \"Hawk\",\n \"Bear\",\n \"Jaguar\",\n \"Viper\",\n \"Owl\",\n \"Stallion\",\n \"Dolphin\",\n \"Developer\",\n \"Hacker\",\n \"Wizard\",\n \"Ninja\",\n \"Pilot\",\n \"Pioneer\",\n \"Voyager\",\n \"Explorer\",\n \"Runner\",\n \"Ranger\",\n \"Maverick\",\n \"Spartan\",\n \"Viking\",\n \"Sentinel\",\n \"Guardian\",\n \"Nomad\",\n \"Cipher\",\n \"Vector\",\n \"Matrix\",\n \"Prism\",\n \"Nebula\",\n \"Comet\",\n \"Pulse\",\n \"Vertex\",\n \"Flux\",\n \"Storm\",\n \"Blaze\",\n \"Frost\",\n \"Thunder\",\n \"Drift\"\n] as const;\n\nfunction generateUniqueSessionName(): string {\n const adj =\n SESSION_ADJECTIVES[Math.floor(Math.random() * SESSION_ADJECTIVES.length)]!;\n const noun = SESSION_NOUNS[Math.floor(Math.random() * SESSION_NOUNS.length)]!;\n return `${adj} ${noun}`;\n}\n\n/**\n * Browser file/blob storage built on top of Syncore web persistence.\n */\nexport class BrowserFileStorageAdapter implements SyncoreStorageAdapter {\n constructor(\n private readonly persistence: SyncoreWebPersistence,\n private readonly namespace: string\n ) {}\n\n async put(id: string, input: StorageWriteInput): Promise<StorageObject> {\n const bytes = normalizeBinary(input.data);\n await this.persistence.putFile(\n this.namespace,\n id,\n bytes,\n input.contentType ?? null\n );\n return {\n id,\n path: `${this.persistence.storageProtocol}://${this.namespace}/${id}`,\n size: bytes.byteLength,\n contentType: input.contentType ?? null\n };\n }\n\n async get(id: string): Promise<StorageObject | null> {\n const file = await this.persistence.getFile(this.namespace, id);\n if (!file) {\n return null;\n }\n return {\n id,\n path: `${this.persistence.storageProtocol}://${this.namespace}/${id}`,\n size: file.size,\n contentType: file.contentType\n };\n }\n\n async read(id: string): Promise<Uint8Array | null> {\n const file = await this.persistence.getFile(this.namespace, id);\n return file?.bytes ?? null;\n }\n\n async delete(id: string): Promise<void> {\n await this.persistence.deleteFile(this.namespace, id);\n }\n\n async list(): Promise<StorageObject[]> {\n const files = await this.persistence.listFiles(this.namespace);\n return files.map((file) => ({\n id: file.id,\n path: `${this.persistence.storageProtocol}://${this.namespace}/${file.id}`,\n size: file.size,\n contentType: file.contentType\n }));\n }\n}\n\nfunction normalizeBinary(data: StorageWriteInput[\"data\"]): Uint8Array {\n if (typeof data === \"string\") {\n return new TextEncoder().encode(data);\n }\n if (data instanceof Uint8Array) {\n return data;\n }\n return new Uint8Array(data);\n}\n"],"mappings":"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"}
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"react.d.ts","names":[],"sources":["../src/react.tsx"],"mappings":";;;;;;;;
|
|
1
|
+
{"version":3,"file":"react.d.ts","names":[],"sources":["../src/react.tsx"],"mappings":";;;;;;;;UAgBiB,uBAAA,SAAgC,oCAAA;EAAR;EAEvC,QAAA,EAAU,SAAA;EAAA;EAGV,QAAA,GAAW,SAAA;AAAA;;;;KAMD,2BAAA,GAA8B,uBAAA;;;;iBAK1B,kBAAA,CAAA;EACd,QAAA;EACA,SAAA;EACA,UAAA;EACA,UAAA;EACA;AAAA,GACC,uBAAA,GAA0B,SAAA;;AAX7B;;iBAiEgB,sBAAA,CAAuB,KAAA,EAAO,2BAAA,GAA2B,kBAAA,CAAA,GAAA,CAAA,OAAA"}
|
|
@@ -1,5 +1,6 @@
|
|
|
1
1
|
import { createSyncoreWebWorkerClient } from "./worker.js";
|
|
2
|
-
import {
|
|
2
|
+
import { createUnavailableSyncoreClient } from "../core/index.mjs";
|
|
3
|
+
import { useEffect, useMemo, useState } from "react";
|
|
3
4
|
import { SyncoreProvider } from "../react/index.js";
|
|
4
5
|
import { jsx } from "react/jsx-runtime";
|
|
5
6
|
//#region src/react.tsx
|
|
@@ -7,27 +8,42 @@ import { jsx } from "react/jsx-runtime";
|
|
|
7
8
|
* Start a worker-backed Syncore client and provide it to React descendants.
|
|
8
9
|
*/
|
|
9
10
|
function SyncoreWebProvider({ children, workerUrl, workerType, workerName, fallback = null }) {
|
|
10
|
-
const
|
|
11
|
+
const bootingClient = useMemo(() => createUnavailableSyncoreClient({
|
|
12
|
+
kind: "starting",
|
|
13
|
+
reason: "booting"
|
|
14
|
+
}), []);
|
|
15
|
+
const [client, setClient] = useState(bootingClient);
|
|
11
16
|
useEffect(() => {
|
|
12
|
-
|
|
13
|
-
|
|
14
|
-
|
|
15
|
-
|
|
16
|
-
|
|
17
|
-
|
|
17
|
+
let disposed = false;
|
|
18
|
+
let managedClient;
|
|
19
|
+
setClient(bootingClient);
|
|
20
|
+
try {
|
|
21
|
+
managedClient = createSyncoreWebWorkerClient({
|
|
22
|
+
workerUrl,
|
|
23
|
+
...workerType ? { workerType } : {},
|
|
24
|
+
...workerName ? { workerName } : {}
|
|
25
|
+
});
|
|
26
|
+
if (!disposed) setClient(managedClient.client);
|
|
27
|
+
} catch (error) {
|
|
28
|
+
if (!disposed) setClient(createUnavailableSyncoreClient({
|
|
29
|
+
kind: "unavailable",
|
|
30
|
+
reason: "worker-unavailable",
|
|
31
|
+
...error instanceof Error ? { error } : {}
|
|
32
|
+
}));
|
|
33
|
+
}
|
|
18
34
|
return () => {
|
|
19
|
-
|
|
20
|
-
|
|
35
|
+
disposed = true;
|
|
36
|
+
managedClient?.dispose();
|
|
21
37
|
};
|
|
22
38
|
}, [
|
|
39
|
+
bootingClient,
|
|
23
40
|
workerName,
|
|
24
41
|
workerType,
|
|
25
42
|
workerUrl
|
|
26
43
|
]);
|
|
27
|
-
if (!managedClient) return fallback;
|
|
28
44
|
return /* @__PURE__ */ jsx(SyncoreProvider, {
|
|
29
|
-
client
|
|
30
|
-
children
|
|
45
|
+
client,
|
|
46
|
+
children: children ?? fallback
|
|
31
47
|
});
|
|
32
48
|
}
|
|
33
49
|
/**
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"react.js","names":[],"sources":["../src/react.tsx"],"sourcesContent":["import { useEffect, useState } from \"react\";\nimport type { ReactNode } from \"react\";\nimport { SyncoreProvider } from \"@syncore/react\";\nimport {\n createSyncoreWebWorkerClient,\n type CreateWebWorkerClientProviderOptions,\n type ManagedWebWorkerClient\n} from \"./worker.js\";\n\n/**\n * Props for {@link SyncoreWebProvider}.\n */\nexport interface SyncoreWebProviderProps extends CreateWebWorkerClientProviderOptions {\n /** The React subtree that should receive the Syncore client. */\n children: ReactNode;\n\n /** Optional fallback content rendered before the worker client is ready. */\n fallback?: ReactNode;\n}\n\n/**\n * Props for {@link SyncoreBrowserProvider}.\n */\nexport type SyncoreBrowserProviderProps = SyncoreWebProviderProps;\n\n/**\n * Start a worker-backed Syncore client and provide it to React descendants.\n */\nexport function SyncoreWebProvider({\n children,\n workerUrl,\n workerType,\n workerName,\n fallback = null\n}: SyncoreWebProviderProps): ReactNode {\n const [
|
|
1
|
+
{"version":3,"file":"react.js","names":[],"sources":["../src/react.tsx"],"sourcesContent":["import {\n createUnavailableSyncoreClient,\n type SyncoreClient\n} from \"@syncore/core\";\nimport { useEffect, useMemo, useState } from \"react\";\nimport type { ReactNode } from \"react\";\nimport { SyncoreProvider } from \"@syncore/react\";\nimport {\n createSyncoreWebWorkerClient,\n type CreateWebWorkerClientProviderOptions,\n type ManagedWebWorkerClient\n} from \"./worker.js\";\n\n/**\n * Props for {@link SyncoreWebProvider}.\n */\nexport interface SyncoreWebProviderProps extends CreateWebWorkerClientProviderOptions {\n /** The React subtree that should receive the Syncore client. */\n children: ReactNode;\n\n /** Optional fallback content rendered before the worker client is ready. */\n fallback?: ReactNode;\n}\n\n/**\n * Props for {@link SyncoreBrowserProvider}.\n */\nexport type SyncoreBrowserProviderProps = SyncoreWebProviderProps;\n\n/**\n * Start a worker-backed Syncore client and provide it to React descendants.\n */\nexport function SyncoreWebProvider({\n children,\n workerUrl,\n workerType,\n workerName,\n fallback = null\n}: SyncoreWebProviderProps): ReactNode {\n const bootingClient = useMemo(\n () =>\n createUnavailableSyncoreClient({\n kind: \"starting\",\n reason: \"booting\"\n }),\n []\n );\n const [client, setClient] = useState<SyncoreClient>(bootingClient);\n\n useEffect(() => {\n let disposed = false;\n let managedClient: ManagedWebWorkerClient | undefined;\n\n setClient(bootingClient);\n\n try {\n managedClient = createSyncoreWebWorkerClient({\n workerUrl,\n ...(workerType ? { workerType } : {}),\n ...(workerName ? { workerName } : {})\n });\n if (!disposed) {\n setClient(managedClient.client);\n }\n } catch (error) {\n if (!disposed) {\n setClient(\n createUnavailableSyncoreClient({\n kind: \"unavailable\",\n reason: \"worker-unavailable\",\n ...(error instanceof Error ? { error } : {})\n })\n );\n }\n }\n\n return () => {\n disposed = true;\n managedClient?.dispose();\n };\n }, [bootingClient, workerName, workerType, workerUrl]);\n\n return (\n <SyncoreProvider client={client}>\n {children ?? fallback}\n </SyncoreProvider>\n );\n}\n\n/**\n * Start a worker-backed Syncore client and provide it to React descendants.\n */\nexport function SyncoreBrowserProvider(props: SyncoreBrowserProviderProps) {\n return <SyncoreWebProvider {...props} />;\n}\n"],"mappings":";;;;;;;;;AAgCA,SAAgB,mBAAmB,EACjC,UACA,WACA,YACA,YACA,WAAW,QAC0B;CACrC,MAAM,gBAAgB,cAElB,+BAA+B;EAC7B,MAAM;EACN,QAAQ;EACT,CAAC,EACJ,EAAE,CACH;CACD,MAAM,CAAC,QAAQ,aAAa,SAAwB,cAAc;AAElE,iBAAgB;EACd,IAAI,WAAW;EACf,IAAI;AAEJ,YAAU,cAAc;AAExB,MAAI;AACF,mBAAgB,6BAA6B;IAC3C;IACA,GAAI,aAAa,EAAE,YAAY,GAAG,EAAE;IACpC,GAAI,aAAa,EAAE,YAAY,GAAG,EAAE;IACrC,CAAC;AACF,OAAI,CAAC,SACH,WAAU,cAAc,OAAO;WAE1B,OAAO;AACd,OAAI,CAAC,SACH,WACE,+BAA+B;IAC7B,MAAM;IACN,QAAQ;IACR,GAAI,iBAAiB,QAAQ,EAAE,OAAO,GAAG,EAAE;IAC5C,CAAC,CACH;;AAIL,eAAa;AACX,cAAW;AACX,kBAAe,SAAS;;IAEzB;EAAC;EAAe;EAAY;EAAY;EAAU,CAAC;AAEtD,QACE,oBAAC,iBAAD;EAAyB;YACtB,YAAY;EACG,CAAA;;;;;AAOtB,SAAgB,uBAAuB,OAAoC;AACzE,QAAO,oBAAC,oBAAD,EAAoB,GAAI,OAAS,CAAA"}
|
|
@@ -1,41 +1,17 @@
|
|
|
1
|
-
import {
|
|
1
|
+
import { AttachRuntimeBridgeOptions, AttachedRuntimeBridge, BridgeQueryWatch, SyncoreBridgeClient, SyncoreBridgeMessageEndpoint, SyncoreDataModel } from "../core/index.d.mts";
|
|
2
2
|
|
|
3
3
|
//#region src/worker.d.ts
|
|
4
|
-
type WebWorkerSyncoreSchema =
|
|
5
|
-
|
|
6
|
-
|
|
7
|
-
|
|
8
|
-
|
|
9
|
-
|
|
10
|
-
|
|
11
|
-
|
|
12
|
-
};
|
|
13
|
-
type OptionalArgsTuple<TArgs> = Record<never, never> extends TArgs ? [args?: TArgs] : [args: TArgs];
|
|
14
|
-
declare class SyncoreWebWorkerClient implements SyncoreClient {
|
|
15
|
-
private readonly endpoint;
|
|
16
|
-
private readonly pendingRequests;
|
|
17
|
-
private readonly watchRecordsByKey;
|
|
18
|
-
private readonly watchKeyBySubscriptionId;
|
|
19
|
-
private disposed;
|
|
20
|
-
private readonly handleMessage;
|
|
21
|
-
constructor(endpoint: SyncoreWorkerMessageEndpoint);
|
|
22
|
-
query<TArgs, TResult>(reference: FunctionReference<"query", TArgs, TResult>, ...args: OptionalArgsTuple<TArgs>): Promise<TResult>;
|
|
23
|
-
mutation<TArgs, TResult>(reference: FunctionReference<"mutation", TArgs, TResult>, ...args: OptionalArgsTuple<TArgs>): Promise<TResult>;
|
|
24
|
-
action<TArgs, TResult>(reference: FunctionReference<"action", TArgs, TResult>, ...args: OptionalArgsTuple<TArgs>): Promise<TResult>;
|
|
25
|
-
watchQuery<TArgs, TResult>(reference: FunctionReference<"query", TArgs, TResult>, ...args: OptionalArgsTuple<TArgs>): WorkerQueryWatch<TResult>;
|
|
26
|
-
dispose(): void;
|
|
27
|
-
private invoke;
|
|
28
|
-
private rejectAllPending;
|
|
29
|
-
private ensureNotDisposed;
|
|
30
|
-
}
|
|
31
|
-
interface AttachWebWorkerRuntimeOptions {
|
|
32
|
-
endpoint: SyncoreWorkerMessageEndpoint;
|
|
33
|
-
createRuntime: (() => Promise<SyncoreRuntime<WebWorkerSyncoreSchema>>) | (() => SyncoreRuntime<WebWorkerSyncoreSchema>);
|
|
34
|
-
}
|
|
35
|
-
interface AttachedWebWorkerRuntime {
|
|
36
|
-
ready: Promise<void>;
|
|
37
|
-
dispose(): Promise<void>;
|
|
4
|
+
type WebWorkerSyncoreSchema<TSchema extends SyncoreDataModel = SyncoreDataModel> = TSchema;
|
|
5
|
+
type SyncoreWorkerMessageEndpoint = SyncoreBridgeMessageEndpoint;
|
|
6
|
+
type WorkerQueryWatch<TValue> = BridgeQueryWatch<TValue>;
|
|
7
|
+
declare class SyncoreWebWorkerClient extends SyncoreBridgeClient {
|
|
8
|
+
query: SyncoreBridgeClient["query"];
|
|
9
|
+
mutation: SyncoreBridgeClient["mutation"];
|
|
10
|
+
action: SyncoreBridgeClient["action"];
|
|
11
|
+
watchQuery: SyncoreBridgeClient["watchQuery"];
|
|
38
12
|
}
|
|
13
|
+
type AttachWebWorkerRuntimeOptions<TSchema extends WebWorkerSyncoreSchema = WebWorkerSyncoreSchema> = AttachRuntimeBridgeOptions<TSchema>;
|
|
14
|
+
type AttachedWebWorkerRuntime = AttachedRuntimeBridge;
|
|
39
15
|
/**
|
|
40
16
|
* A worker-backed browser client plus the Worker instance it owns.
|
|
41
17
|
*/
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"worker.d.ts","names":[],"sources":["../src/worker.ts"],"mappings":";;;
|
|
1
|
+
{"version":3,"file":"worker.d.ts","names":[],"sources":["../src/worker.ts"],"mappings":";;;KAUY,sBAAA,iBACM,gBAAA,GAAmB,gBAAA,IACjC,OAAA;AAAA,KACQ,4BAAA,GAA+B,4BAAA;AAAA,KAC/B,gBAAA,WAA2B,gBAAA,CAAiB,MAAA;AAAA,cAE3C,sBAAA,SAA+B,mBAAA;EAClC,KAAA,EAAO,mBAAA;EACP,QAAA,EAAU,mBAAA;EACV,MAAA,EAAQ,mBAAA;EACR,UAAA,EAAY,mBAAA;AAAA;AAAA,KAGV,6BAAA,iBACM,sBAAA,GAAyB,sBAAA,IACvC,0BAAA,CAA2B,OAAA;AAAA,KACnB,wBAAA,GAA2B,qBAAA;;;;UAKtB,sBAAA;EACf,MAAA,EAAQ,sBAAA;EACR,MAAA,EAAQ,MAAA;EACR,OAAA;AAAA;;;AApBF;UA0BiB,oCAAA;EA1BW;EA4B1B,SAAA,EAAW,GAAA;EA5BgB;EA+B3B,UAAA,GAAa,aAAA;EA/ByC;EAkCtD,UAAA;AAAA;AAhCF;;;AAAA,iBAsCgB,qBAAA,CACd,QAAA,EAAU,4BAAA,GACT,sBAAA;;;;iBAOa,4BAAA,CAA6B,OAAA;EAC3C,YAAA,QAAoB,MAAA;AAAA,IAClB,sBAAA;;;;iBAgBY,4BAAA,CACd,OAAA,EAAS,oCAAA,GACR,sBAAA;;;;iBAaa,sBAAA,CACd,OAAA,EAAS,6BAAA,GACR,wBAAA"}
|