@lunora/client 1.0.0-alpha.156 → 1.0.0-alpha.158

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.
@@ -1,4 +1,4 @@
1
- import { U as User, L as LunoraClient } from "../packem_shared/lunora-client.d-DuKXBo1d.mjs";
1
+ import { U as User, L as LunoraClient } from "../packem_shared/lunora-client.d-D1vYlx1k.mjs";
2
2
  import '@lunora/errors';
3
3
  import "../packem_shared/function-reference.d-Br_hsKje.mjs";
4
4
  import '@lunora/runtime';
@@ -1,4 +1,4 @@
1
- import { U as User, L as LunoraClient } from "../packem_shared/lunora-client.d-Drc1BNio.js";
1
+ import { U as User, L as LunoraClient } from "../packem_shared/lunora-client.d-C1obXESH.js";
2
2
  import '@lunora/errors';
3
3
  import "../packem_shared/function-reference.d-Br_hsKje.js";
4
4
  import '@lunora/runtime';
package/dist/index.d.mts CHANGED
@@ -1,8 +1,8 @@
1
- import { c as PersistenceAdapter, Q as QueryCacheAdapter, B as BookmarkStorage, C as ConnectionStatus, S as SubscriptionError, H as HttpStreamRef, d as HttpStreamArgsOf, e as HttpStreamChunkOf, f as StreamIterable, O as OfflineQueueOptions, R as ReconnectOptions, L as LunoraClient } from "./packem_shared/lunora-client.d-DuKXBo1d.mjs";
2
- export { type A as ActionCallOptions, type g as BatchSlot, type h as CachedQuery, type i as ClientDebugShard, type j as ClientDebugSnapshot, type k as ClientDebugSubscription, type l as ClientMessage, type m as ClientQueryRef, type n as ClientShapeSubscribeMessage, type o as ClientShapeUnsubscribeMessage, D as DEFAULT_MAX_BUFFER, type F as FunctionArgumentDescriptor, type p as FunctionDescriptor, type G as GlobalFacetResult, type q as GlobalFacetValue, type r as GlobalFilterClause, type s as GlobalTableInfo, type t as GlobalTablePage, type u as HttpStreamCallArgs, type v as LunoraClientError, type w as LunoraClientOptions, type M as MutationCallOptions, type x as MutationSettledEvent, type y as OptimisticLocalStore, type z as OptimisticUpdate, type E as OutboxMutation, type I as OutboxSink, type J as PersistedMutation, type P as Preloaded, type K as ReplayCredential, type N as ReplayIdentityVerdict, type T as RowOp, type V as RpcEnvelope, type W as RpcResponseBody, type X as ScheduleRecord, type Y as ScheduleRetryPolicy, type Z as SchedulerPoolStatus, type _ as SchedulerStatus, type $ as ServerMessage, type a0 as ServerPokeEndMessage, type a1 as ServerPokePartMessage, type a2 as ServerPokeStartMessage, type a3 as ShardTrafficEntry, type a4 as ShardTrafficResult, type a5 as StorageListPage, type a6 as StorageObject, type a7 as StoredQuery, type a8 as StreamHandle, type a9 as SubscriptionCallback, type b as SubscriptionErrorCallback, aa as SubscriptionRegistry, type ab as SubscriptionState, type ac as SyncWatermark, type a as Unsubscribe, type U as User, type ad as WorkflowInstanceAction, type ae as WorkflowInstanceDetail, type af as WorkflowInstancePage, type ag as WorkflowInstanceStatus, type ah as WorkflowInstanceSummary, type ai as WorkflowStepDetail, type aj as WsTokenProvider, ak as createClientQuery, al as createLocalStore, am as createStream } from "./packem_shared/lunora-client.d-DuKXBo1d.mjs";
1
+ import { c as PersistenceAdapter, Q as QueryCacheAdapter, B as BookmarkStorage, C as ConnectionStatus, S as SubscriptionError, H as HttpStreamRef, d as HttpStreamArgsOf, e as HttpStreamChunkOf, f as StreamIterable, O as OfflineQueueOptions, R as ReconnectOptions, L as LunoraClient } from "./packem_shared/lunora-client.d-D1vYlx1k.mjs";
2
+ export { type A as ActionCallOptions, type g as BatchSlot, type h as CachedQuery, type i as ClientDebugShard, type j as ClientDebugSnapshot, type k as ClientDebugSubscription, type l as ClientMessage, type m as ClientQueryRef, type n as ClientShapeSubscribeMessage, type o as ClientShapeUnsubscribeMessage, D as DEFAULT_MAX_BUFFER, type F as FunctionArgumentDescriptor, type p as FunctionDescriptor, type G as GlobalFacetResult, type q as GlobalFacetValue, type r as GlobalFilterClause, type s as GlobalTableInfo, type t as GlobalTablePage, type u as HttpStreamCallArgs, type v as LunoraClientError, type w as LunoraClientOptions, type M as MutationCallOptions, type x as MutationSettledEvent, type y as OptimisticLocalStore, type z as OptimisticUpdate, type E as OutboxMutation, type I as OutboxSink, type J as PersistedMutation, type P as Preloaded, type K as ReplayCredential, type N as ReplayIdentityVerdict, type T as RowOp, type V as RpcEnvelope, type W as RpcResponseBody, type X as ScheduleRecord, type Y as ScheduleRetryPolicy, type Z as SchedulerPoolStatus, type _ as SchedulerStatus, type $ as ServerMessage, type a0 as ServerPokeEndMessage, type a1 as ServerPokePartMessage, type a2 as ServerPokeStartMessage, type a3 as ShardTrafficEntry, type a4 as ShardTrafficResult, type a5 as StorageListPage, type a6 as StorageObject, type a7 as StoredQuery, type a8 as StreamHandle, type a9 as SubscriptionCallback, type b as SubscriptionErrorCallback, aa as SubscriptionRegistry, type ab as SubscriptionState, type ac as SyncWatermark, type a as Unsubscribe, type U as User, type ad as WorkflowInstanceAction, type ae as WorkflowInstanceDetail, type af as WorkflowInstancePage, type ag as WorkflowInstanceStatus, type ah as WorkflowInstanceSummary, type ai as WorkflowStepDetail, type aj as WsTokenProvider, ak as createClientQuery, al as createLocalStore, am as createStream } from "./packem_shared/lunora-client.d-D1vYlx1k.mjs";
3
3
  import { LunoraError, LunoraErrorCode } from '@lunora/errors';
4
4
  export type { LunoraErrorCode } from '@lunora/errors';
5
- export { p as preloadQuery, a as preloadedQueryResult } from "./packem_shared/preload.d-DgOAB0eA.mjs";
5
+ export { p as preloadQuery, a as preloadedQueryResult } from "./packem_shared/preload.d-CZ9D2dq9.mjs";
6
6
  import { F as FunctionReference } from "./packem_shared/function-reference.d-Br_hsKje.mjs";
7
7
  export type { A as ArgsOf, R as ReturnOf } from "./packem_shared/function-reference.d-Br_hsKje.mjs";
8
8
  export type { AuthCapabilities, AuthConfigInfo, AuthImpersonation, AuthPage, AuthSession, AuthUser, AuthUserFieldSpec, CronJobInfo, KvKeyEntry, KvKeyListResult, KvNamespaceSummary, KvValueResult, PipelineLogColumnMap, PipelineLogCursor, PipelineLogField, PipelineLogPage, PipelineLogQuery, PipelineLogRow, VectorIndexSummary, VectorQueryMatch } from '@lunora/runtime';
@@ -945,92 +945,4 @@ declare const createReconnect: (options?: ReconnectOptions, random?: () => numbe
945
945
  * ```
946
946
  */
947
947
  declare const createSnapshotPrecondition: (client: LunoraClient, functionRef: FunctionReference, args: Record<string, unknown>, shardKey?: string) => (() => boolean);
948
- /**
949
- * Client-side service-worker registration and lifecycle management.
950
- *
951
- * Usage:
952
- * ```ts
953
- * const sw = new ClientServiceWorker({ swUrl: "/sw.js" });
954
- * await sw.register();
955
- *
956
- * if (sw.active) {
957
- * sw.postMessage({ type: "sync" });
958
- * }
959
- * ```
960
- */
961
- type ServiceWorkerStatus = "unsupported" | "unregistered" | "registering" | "active" | "error";
962
- interface ClientSwOptions {
963
- /** Called when the status changes. */
964
- onStatusChange?: (status: ServiceWorkerStatus) => void;
965
- /** Optional registration scope. Defaults to `/`. */
966
- scope?: string;
967
- /** URL of the service worker script (relative to origin). */
968
- swUrl: string;
969
- }
970
- /**
971
- * Manages service-worker registration and provides a simple API for
972
- * sending messages and listening for responses.
973
- */
974
- declare class ClientServiceWorker {
975
- #private;
976
- readonly swUrl: string;
977
- readonly scope: string;
978
- constructor(options: ClientSwOptions);
979
- /** Current registration status. */
980
- get status(): ServiceWorkerStatus;
981
- /** The underlying `ServiceWorkerRegistration`, if registered. */
982
- get registration(): ServiceWorkerRegistration | undefined;
983
- /** Whether the SW is currently controlling this page. */
984
- get active(): boolean;
985
- /**
986
- * Register the service worker.
987
- *
988
- * Returns `false` when the browser does not support service workers.
989
- */
990
- register(): Promise<boolean>;
991
- /**
992
- * Remove the active service worker registration and clear listeners.
993
- *
994
- * Returns `false` when no registration is currently held.
995
- */
996
- unregister(): Promise<boolean>;
997
- /**
998
- * Send a message to the active service worker.
999
- */
1000
- postMessage(message: unknown): void;
1001
- /**
1002
- * Register a handler for messages **from** the service worker.
1003
- * @returns Unsubscribe function.
1004
- */
1005
- onMessage(handler: (event: MessageEvent) => void): () => void;
1006
- }
1007
- /**
1008
- * Outbound message from the client to the SW.
1009
- */
1010
- interface ClientToSwMessage {
1011
- /** Opaque correlation ID for request/response patterns. */
1012
- correlationId?: string;
1013
- payload?: unknown;
1014
- type: string;
1015
- }
1016
- /**
1017
- * Inbound message from the SW to the client.
1018
- */
1019
- interface SwToClientMessage {
1020
- /** Echoes the correlation ID from the client request, if any. */
1021
- correlationId?: string;
1022
- payload?: unknown;
1023
- type: string;
1024
- }
1025
- /**
1026
- * Send a typed message to the service worker and optionally await a
1027
- * matching response.
1028
- * @returns A promise that resolves when the SW sends a reply with the
1029
- * same `correlationId` (if `expectResponse` is true).
1030
- */
1031
- declare const sendToSw: (sw: ServiceWorker | null, message: ClientToSwMessage, expectResponse?: boolean) => Promise<unknown>;
1032
- /**
1033
- * Create a reply for a client message (call from inside the SW).
1034
- */
1035
- declare const createReply: (original: ClientToSwMessage, payload?: unknown) => SwToClientMessage;
1036
- export { type AsyncStorageLike, type AsyncStoragePersistenceOptions, type AsyncStorageQueryCacheOptions, type BookmarkStorage, CONFLICT_ERROR_CODE, ClientServiceWorker, type ClientSwOptions, type ClientToSwMessage, type ConnectionStatus, type FunctionReference, type HttpStreamArgsOf, type HttpStreamChunkOf, type HttpStreamOptions, type HttpStreamRef, type IndexedDbPersistenceOptions, type IndexedDbQueryCacheOptions, LunoraClient, type MutationDelta, type MutatorHandle, type MutatorRunnerSinks, type MutatorTransaction, OfflineQueue, type OfflineQueueOptions, type OptimisticMessage, type PersistenceAdapter, type QueryCacheAdapter, type QueuedMutation, RETIRE_AFTER_DURABLE_SEQ_ADVANCE, type ReconcileDurableMessage, type ReconnectCalculator, type ReconnectOptions, type ServiceWorkerStatus, type StreamIterable, type SubscriptionError, type SwToClientMessage, TabCoordinator, TransportError, anyApi, applyDelta, createAsyncStoragePersistence, createAsyncStorageQueryCache, createCallRunner, createInMemoryBookmarkStorage, createInMemoryPersistence, createInMemoryQueryCache, createIndexedDbPersistence, createIndexedDbQueryCache, createMutatorRunner, createReconnect, createReply, createSnapshotPrecondition, getErrorCode, getRetryAfterMs, httpStream, isAuthReplayFailure, isConflictError, isForbiddenError, isMutationDelta, isRateLimitedError, isUnauthorizedError, maxSeq, queryCacheKey, reconcileOptimistic, sendToSw };
948
+ export { type AsyncStorageLike, type AsyncStoragePersistenceOptions, type AsyncStorageQueryCacheOptions, type BookmarkStorage, CONFLICT_ERROR_CODE, type ConnectionStatus, type FunctionReference, type HttpStreamArgsOf, type HttpStreamChunkOf, type HttpStreamOptions, type HttpStreamRef, type IndexedDbPersistenceOptions, type IndexedDbQueryCacheOptions, LunoraClient, type MutationDelta, type MutatorHandle, type MutatorRunnerSinks, type MutatorTransaction, OfflineQueue, type OfflineQueueOptions, type OptimisticMessage, type PersistenceAdapter, type QueryCacheAdapter, type QueuedMutation, RETIRE_AFTER_DURABLE_SEQ_ADVANCE, type ReconcileDurableMessage, type ReconnectCalculator, type ReconnectOptions, type StreamIterable, type SubscriptionError, TabCoordinator, TransportError, anyApi, applyDelta, createAsyncStoragePersistence, createAsyncStorageQueryCache, createCallRunner, createInMemoryBookmarkStorage, createInMemoryPersistence, createInMemoryQueryCache, createIndexedDbPersistence, createIndexedDbQueryCache, createMutatorRunner, createReconnect, createSnapshotPrecondition, getErrorCode, getRetryAfterMs, httpStream, isAuthReplayFailure, isConflictError, isForbiddenError, isMutationDelta, isRateLimitedError, isUnauthorizedError, maxSeq, queryCacheKey, reconcileOptimistic };
package/dist/index.d.ts CHANGED
@@ -1,8 +1,8 @@
1
- import { c as PersistenceAdapter, Q as QueryCacheAdapter, B as BookmarkStorage, C as ConnectionStatus, S as SubscriptionError, H as HttpStreamRef, d as HttpStreamArgsOf, e as HttpStreamChunkOf, f as StreamIterable, O as OfflineQueueOptions, R as ReconnectOptions, L as LunoraClient } from "./packem_shared/lunora-client.d-Drc1BNio.js";
2
- export { type A as ActionCallOptions, type g as BatchSlot, type h as CachedQuery, type i as ClientDebugShard, type j as ClientDebugSnapshot, type k as ClientDebugSubscription, type l as ClientMessage, type m as ClientQueryRef, type n as ClientShapeSubscribeMessage, type o as ClientShapeUnsubscribeMessage, D as DEFAULT_MAX_BUFFER, type F as FunctionArgumentDescriptor, type p as FunctionDescriptor, type G as GlobalFacetResult, type q as GlobalFacetValue, type r as GlobalFilterClause, type s as GlobalTableInfo, type t as GlobalTablePage, type u as HttpStreamCallArgs, type v as LunoraClientError, type w as LunoraClientOptions, type M as MutationCallOptions, type x as MutationSettledEvent, type y as OptimisticLocalStore, type z as OptimisticUpdate, type E as OutboxMutation, type I as OutboxSink, type J as PersistedMutation, type P as Preloaded, type K as ReplayCredential, type N as ReplayIdentityVerdict, type T as RowOp, type V as RpcEnvelope, type W as RpcResponseBody, type X as ScheduleRecord, type Y as ScheduleRetryPolicy, type Z as SchedulerPoolStatus, type _ as SchedulerStatus, type $ as ServerMessage, type a0 as ServerPokeEndMessage, type a1 as ServerPokePartMessage, type a2 as ServerPokeStartMessage, type a3 as ShardTrafficEntry, type a4 as ShardTrafficResult, type a5 as StorageListPage, type a6 as StorageObject, type a7 as StoredQuery, type a8 as StreamHandle, type a9 as SubscriptionCallback, type b as SubscriptionErrorCallback, aa as SubscriptionRegistry, type ab as SubscriptionState, type ac as SyncWatermark, type a as Unsubscribe, type U as User, type ad as WorkflowInstanceAction, type ae as WorkflowInstanceDetail, type af as WorkflowInstancePage, type ag as WorkflowInstanceStatus, type ah as WorkflowInstanceSummary, type ai as WorkflowStepDetail, type aj as WsTokenProvider, ak as createClientQuery, al as createLocalStore, am as createStream } from "./packem_shared/lunora-client.d-Drc1BNio.js";
1
+ import { c as PersistenceAdapter, Q as QueryCacheAdapter, B as BookmarkStorage, C as ConnectionStatus, S as SubscriptionError, H as HttpStreamRef, d as HttpStreamArgsOf, e as HttpStreamChunkOf, f as StreamIterable, O as OfflineQueueOptions, R as ReconnectOptions, L as LunoraClient } from "./packem_shared/lunora-client.d-C1obXESH.js";
2
+ export { type A as ActionCallOptions, type g as BatchSlot, type h as CachedQuery, type i as ClientDebugShard, type j as ClientDebugSnapshot, type k as ClientDebugSubscription, type l as ClientMessage, type m as ClientQueryRef, type n as ClientShapeSubscribeMessage, type o as ClientShapeUnsubscribeMessage, D as DEFAULT_MAX_BUFFER, type F as FunctionArgumentDescriptor, type p as FunctionDescriptor, type G as GlobalFacetResult, type q as GlobalFacetValue, type r as GlobalFilterClause, type s as GlobalTableInfo, type t as GlobalTablePage, type u as HttpStreamCallArgs, type v as LunoraClientError, type w as LunoraClientOptions, type M as MutationCallOptions, type x as MutationSettledEvent, type y as OptimisticLocalStore, type z as OptimisticUpdate, type E as OutboxMutation, type I as OutboxSink, type J as PersistedMutation, type P as Preloaded, type K as ReplayCredential, type N as ReplayIdentityVerdict, type T as RowOp, type V as RpcEnvelope, type W as RpcResponseBody, type X as ScheduleRecord, type Y as ScheduleRetryPolicy, type Z as SchedulerPoolStatus, type _ as SchedulerStatus, type $ as ServerMessage, type a0 as ServerPokeEndMessage, type a1 as ServerPokePartMessage, type a2 as ServerPokeStartMessage, type a3 as ShardTrafficEntry, type a4 as ShardTrafficResult, type a5 as StorageListPage, type a6 as StorageObject, type a7 as StoredQuery, type a8 as StreamHandle, type a9 as SubscriptionCallback, type b as SubscriptionErrorCallback, aa as SubscriptionRegistry, type ab as SubscriptionState, type ac as SyncWatermark, type a as Unsubscribe, type U as User, type ad as WorkflowInstanceAction, type ae as WorkflowInstanceDetail, type af as WorkflowInstancePage, type ag as WorkflowInstanceStatus, type ah as WorkflowInstanceSummary, type ai as WorkflowStepDetail, type aj as WsTokenProvider, ak as createClientQuery, al as createLocalStore, am as createStream } from "./packem_shared/lunora-client.d-C1obXESH.js";
3
3
  import { LunoraError, LunoraErrorCode } from '@lunora/errors';
4
4
  export type { LunoraErrorCode } from '@lunora/errors';
5
- export { p as preloadQuery, a as preloadedQueryResult } from "./packem_shared/preload.d-DXQqsalx.js";
5
+ export { p as preloadQuery, a as preloadedQueryResult } from "./packem_shared/preload.d-Bn2hWjKv.js";
6
6
  import { F as FunctionReference } from "./packem_shared/function-reference.d-Br_hsKje.js";
7
7
  export type { A as ArgsOf, R as ReturnOf } from "./packem_shared/function-reference.d-Br_hsKje.js";
8
8
  export type { AuthCapabilities, AuthConfigInfo, AuthImpersonation, AuthPage, AuthSession, AuthUser, AuthUserFieldSpec, CronJobInfo, KvKeyEntry, KvKeyListResult, KvNamespaceSummary, KvValueResult, PipelineLogColumnMap, PipelineLogCursor, PipelineLogField, PipelineLogPage, PipelineLogQuery, PipelineLogRow, VectorIndexSummary, VectorQueryMatch } from '@lunora/runtime';
@@ -945,92 +945,4 @@ declare const createReconnect: (options?: ReconnectOptions, random?: () => numbe
945
945
  * ```
946
946
  */
947
947
  declare const createSnapshotPrecondition: (client: LunoraClient, functionRef: FunctionReference, args: Record<string, unknown>, shardKey?: string) => (() => boolean);
948
- /**
949
- * Client-side service-worker registration and lifecycle management.
950
- *
951
- * Usage:
952
- * ```ts
953
- * const sw = new ClientServiceWorker({ swUrl: "/sw.js" });
954
- * await sw.register();
955
- *
956
- * if (sw.active) {
957
- * sw.postMessage({ type: "sync" });
958
- * }
959
- * ```
960
- */
961
- type ServiceWorkerStatus = "unsupported" | "unregistered" | "registering" | "active" | "error";
962
- interface ClientSwOptions {
963
- /** Called when the status changes. */
964
- onStatusChange?: (status: ServiceWorkerStatus) => void;
965
- /** Optional registration scope. Defaults to `/`. */
966
- scope?: string;
967
- /** URL of the service worker script (relative to origin). */
968
- swUrl: string;
969
- }
970
- /**
971
- * Manages service-worker registration and provides a simple API for
972
- * sending messages and listening for responses.
973
- */
974
- declare class ClientServiceWorker {
975
- #private;
976
- readonly swUrl: string;
977
- readonly scope: string;
978
- constructor(options: ClientSwOptions);
979
- /** Current registration status. */
980
- get status(): ServiceWorkerStatus;
981
- /** The underlying `ServiceWorkerRegistration`, if registered. */
982
- get registration(): ServiceWorkerRegistration | undefined;
983
- /** Whether the SW is currently controlling this page. */
984
- get active(): boolean;
985
- /**
986
- * Register the service worker.
987
- *
988
- * Returns `false` when the browser does not support service workers.
989
- */
990
- register(): Promise<boolean>;
991
- /**
992
- * Remove the active service worker registration and clear listeners.
993
- *
994
- * Returns `false` when no registration is currently held.
995
- */
996
- unregister(): Promise<boolean>;
997
- /**
998
- * Send a message to the active service worker.
999
- */
1000
- postMessage(message: unknown): void;
1001
- /**
1002
- * Register a handler for messages **from** the service worker.
1003
- * @returns Unsubscribe function.
1004
- */
1005
- onMessage(handler: (event: MessageEvent) => void): () => void;
1006
- }
1007
- /**
1008
- * Outbound message from the client to the SW.
1009
- */
1010
- interface ClientToSwMessage {
1011
- /** Opaque correlation ID for request/response patterns. */
1012
- correlationId?: string;
1013
- payload?: unknown;
1014
- type: string;
1015
- }
1016
- /**
1017
- * Inbound message from the SW to the client.
1018
- */
1019
- interface SwToClientMessage {
1020
- /** Echoes the correlation ID from the client request, if any. */
1021
- correlationId?: string;
1022
- payload?: unknown;
1023
- type: string;
1024
- }
1025
- /**
1026
- * Send a typed message to the service worker and optionally await a
1027
- * matching response.
1028
- * @returns A promise that resolves when the SW sends a reply with the
1029
- * same `correlationId` (if `expectResponse` is true).
1030
- */
1031
- declare const sendToSw: (sw: ServiceWorker | null, message: ClientToSwMessage, expectResponse?: boolean) => Promise<unknown>;
1032
- /**
1033
- * Create a reply for a client message (call from inside the SW).
1034
- */
1035
- declare const createReply: (original: ClientToSwMessage, payload?: unknown) => SwToClientMessage;
1036
- export { type AsyncStorageLike, type AsyncStoragePersistenceOptions, type AsyncStorageQueryCacheOptions, type BookmarkStorage, CONFLICT_ERROR_CODE, ClientServiceWorker, type ClientSwOptions, type ClientToSwMessage, type ConnectionStatus, type FunctionReference, type HttpStreamArgsOf, type HttpStreamChunkOf, type HttpStreamOptions, type HttpStreamRef, type IndexedDbPersistenceOptions, type IndexedDbQueryCacheOptions, LunoraClient, type MutationDelta, type MutatorHandle, type MutatorRunnerSinks, type MutatorTransaction, OfflineQueue, type OfflineQueueOptions, type OptimisticMessage, type PersistenceAdapter, type QueryCacheAdapter, type QueuedMutation, RETIRE_AFTER_DURABLE_SEQ_ADVANCE, type ReconcileDurableMessage, type ReconnectCalculator, type ReconnectOptions, type ServiceWorkerStatus, type StreamIterable, type SubscriptionError, type SwToClientMessage, TabCoordinator, TransportError, anyApi, applyDelta, createAsyncStoragePersistence, createAsyncStorageQueryCache, createCallRunner, createInMemoryBookmarkStorage, createInMemoryPersistence, createInMemoryQueryCache, createIndexedDbPersistence, createIndexedDbQueryCache, createMutatorRunner, createReconnect, createReply, createSnapshotPrecondition, getErrorCode, getRetryAfterMs, httpStream, isAuthReplayFailure, isConflictError, isForbiddenError, isMutationDelta, isRateLimitedError, isUnauthorizedError, maxSeq, queryCacheKey, reconcileOptimistic, sendToSw };
948
+ export { type AsyncStorageLike, type AsyncStoragePersistenceOptions, type AsyncStorageQueryCacheOptions, type BookmarkStorage, CONFLICT_ERROR_CODE, type ConnectionStatus, type FunctionReference, type HttpStreamArgsOf, type HttpStreamChunkOf, type HttpStreamOptions, type HttpStreamRef, type IndexedDbPersistenceOptions, type IndexedDbQueryCacheOptions, LunoraClient, type MutationDelta, type MutatorHandle, type MutatorRunnerSinks, type MutatorTransaction, OfflineQueue, type OfflineQueueOptions, type OptimisticMessage, type PersistenceAdapter, type QueryCacheAdapter, type QueuedMutation, RETIRE_AFTER_DURABLE_SEQ_ADVANCE, type ReconcileDurableMessage, type ReconnectCalculator, type ReconnectOptions, type StreamIterable, type SubscriptionError, TabCoordinator, TransportError, anyApi, applyDelta, createAsyncStoragePersistence, createAsyncStorageQueryCache, createCallRunner, createInMemoryBookmarkStorage, createInMemoryPersistence, createInMemoryQueryCache, createIndexedDbPersistence, createIndexedDbQueryCache, createMutatorRunner, createReconnect, createSnapshotPrecondition, getErrorCode, getRetryAfterMs, httpStream, isAuthReplayFailure, isConflictError, isForbiddenError, isMutationDelta, isRateLimitedError, isUnauthorizedError, maxSeq, queryCacheKey, reconcileOptimistic };
package/dist/index.mjs CHANGED
@@ -1 +1 @@
1
- import{anyApi as o}from"./packem_shared/anyApi-CBOws2ZA.mjs";import{RETIRE_AFTER_DURABLE_SEQ_ADVANCE as a,maxSeq as p,reconcileOptimistic as c}from"./packem_shared/RETIRE_AFTER_DURABLE_SEQ_ADVANCE-DoEHtuR8.mjs";import{createAsyncStoragePersistence as i}from"./packem_shared/createAsyncStoragePersistence-CeUW9NTj.mjs";import{createAsyncStorageQueryCache as f}from"./packem_shared/createAsyncStorageQueryCache-Dpszf7UD.mjs";import{default as x}from"./packem_shared/createInMemoryBookmarkStorage-BooZhW0n.mjs";import{createCallRunner as l}from"./packem_shared/createCallRunner-Bwcrfh76.mjs";import{createClientQuery as d}from"./packem_shared/createClientQuery-B8Nfj-7o.mjs";import{TabCoordinator as E}from"./packem_shared/TabCoordinator-CXD7vulJ.mjs";import{a as S,i as A}from"./packem_shared/delta-merge-D_5ChS-C.mjs";import{CONFLICT_ERROR_CODE as D,TransportError as Q,getErrorCode as _,getRetryAfterMs as F,isAuthReplayFailure as I,isConflictError as M,isForbiddenError as T,isRateLimitedError as g,isUnauthorizedError as L}from"./packem_shared/CONFLICT_ERROR_CODE-B7qNZMMk.mjs";import{httpStream as b}from"./packem_shared/httpStream-v4etRV7m.mjs";import{c as U}from"./packem_shared/local-store-DDppw8Qr.mjs";import{LunoraClient as B}from"./packem_shared/LunoraClient-BWZ8TiRn.mjs";import{createMutatorRunner as N}from"./packem_shared/createMutatorRunner-CuMRJpUx.mjs";import{O as w}from"./packem_shared/offline-queue-D_fr-uQ3.mjs";import{createInMemoryPersistence as K,createIndexedDbPersistence as V}from"./packem_shared/createInMemoryPersistence-Cz2W6XVj.mjs";import{preloadQuery as X,preloadedQueryResult as j}from"./packem_shared/preloadQuery-uFy24PCR.mjs";import{createInMemoryQueryCache as H,createIndexedDbQueryCache as J,queryCacheKey as Y}from"./packem_shared/createInMemoryQueryCache-D2uNHLfM.mjs";import{createReconnect as $}from"./packem_shared/createReconnect-CjTmjJDH.mjs";import{default as re}from"./packem_shared/createSnapshotPrecondition-5GQ_5fFu.mjs";import{DEFAULT_MAX_BUFFER as te,createStream as ae}from"./packem_shared/DEFAULT_MAX_BUFFER-D3QH2iaq.mjs";import{SubscriptionRegistry as ce}from"./packem_shared/SubscriptionRegistry-C3kLqped.mjs";import{ClientServiceWorker as ie}from"./packem_shared/ClientServiceWorker-DXnBXeWK.mjs";import{createReply as fe,sendToSw as se}from"./packem_shared/createReply-CwFABEJs.mjs";export{D as CONFLICT_ERROR_CODE,ie as ClientServiceWorker,te as DEFAULT_MAX_BUFFER,B as LunoraClient,w as OfflineQueue,a as RETIRE_AFTER_DURABLE_SEQ_ADVANCE,ce as SubscriptionRegistry,E as TabCoordinator,Q as TransportError,o as anyApi,S as applyDelta,i as createAsyncStoragePersistence,f as createAsyncStorageQueryCache,l as createCallRunner,d as createClientQuery,x as createInMemoryBookmarkStorage,K as createInMemoryPersistence,H as createInMemoryQueryCache,V as createIndexedDbPersistence,J as createIndexedDbQueryCache,U as createLocalStore,N as createMutatorRunner,$ as createReconnect,fe as createReply,re as createSnapshotPrecondition,ae as createStream,_ as getErrorCode,F as getRetryAfterMs,b as httpStream,I as isAuthReplayFailure,M as isConflictError,T as isForbiddenError,A as isMutationDelta,g as isRateLimitedError,L as isUnauthorizedError,p as maxSeq,X as preloadQuery,j as preloadedQueryResult,Y as queryCacheKey,c as reconcileOptimistic,se as sendToSw};
1
+ import{anyApi as o}from"./packem_shared/anyApi-CBOws2ZA.mjs";import{RETIRE_AFTER_DURABLE_SEQ_ADVANCE as a,maxSeq as c,reconcileOptimistic as p}from"./packem_shared/RETIRE_AFTER_DURABLE_SEQ_ADVANCE-DoEHtuR8.mjs";import{createAsyncStoragePersistence as i}from"./packem_shared/createAsyncStoragePersistence-CeUW9NTj.mjs";import{createAsyncStorageQueryCache as f}from"./packem_shared/createAsyncStorageQueryCache-Dpszf7UD.mjs";import{default as x}from"./packem_shared/createInMemoryBookmarkStorage-BooZhW0n.mjs";import{createCallRunner as l}from"./packem_shared/createCallRunner-Bwcrfh76.mjs";import{createClientQuery as d}from"./packem_shared/createClientQuery-B8Nfj-7o.mjs";import{TabCoordinator as R}from"./packem_shared/TabCoordinator-CXD7vulJ.mjs";import{a as A,i as S}from"./packem_shared/delta-merge-D_5ChS-C.mjs";import{CONFLICT_ERROR_CODE as D,TransportError as Q,getErrorCode as _,getRetryAfterMs as F,isAuthReplayFailure as I,isConflictError as M,isForbiddenError as g,isRateLimitedError as L,isUnauthorizedError as O}from"./packem_shared/CONFLICT_ERROR_CODE-B7qNZMMk.mjs";import{httpStream as b}from"./packem_shared/httpStream-v4etRV7m.mjs";import{c as U}from"./packem_shared/local-store-DDppw8Qr.mjs";import{LunoraClient as k}from"./packem_shared/LunoraClient-B9s5sUe6.mjs";import{createMutatorRunner as N}from"./packem_shared/createMutatorRunner-CuMRJpUx.mjs";import{O as K}from"./packem_shared/offline-queue-D_fr-uQ3.mjs";import{createInMemoryPersistence as X,createIndexedDbPersistence as j}from"./packem_shared/createInMemoryPersistence-Cz2W6XVj.mjs";import{preloadQuery as w,preloadedQueryResult as G}from"./packem_shared/preloadQuery-uFy24PCR.mjs";import{createInMemoryQueryCache as J,createIndexedDbQueryCache as W,queryCacheKey as Y}from"./packem_shared/createInMemoryQueryCache-D2uNHLfM.mjs";import{createReconnect as $}from"./packem_shared/createReconnect-CjTmjJDH.mjs";import{default as re}from"./packem_shared/createSnapshotPrecondition-5GQ_5fFu.mjs";import{DEFAULT_MAX_BUFFER as te,createStream as ae}from"./packem_shared/DEFAULT_MAX_BUFFER-D3QH2iaq.mjs";import{SubscriptionRegistry as pe}from"./packem_shared/SubscriptionRegistry-C3kLqped.mjs";export{D as CONFLICT_ERROR_CODE,te as DEFAULT_MAX_BUFFER,k as LunoraClient,K as OfflineQueue,a as RETIRE_AFTER_DURABLE_SEQ_ADVANCE,pe as SubscriptionRegistry,R as TabCoordinator,Q as TransportError,o as anyApi,A as applyDelta,i as createAsyncStoragePersistence,f as createAsyncStorageQueryCache,l as createCallRunner,d as createClientQuery,x as createInMemoryBookmarkStorage,X as createInMemoryPersistence,J as createInMemoryQueryCache,j as createIndexedDbPersistence,W as createIndexedDbQueryCache,U as createLocalStore,N as createMutatorRunner,$ as createReconnect,re as createSnapshotPrecondition,ae as createStream,_ as getErrorCode,F as getRetryAfterMs,b as httpStream,I as isAuthReplayFailure,M as isConflictError,g as isForbiddenError,S as isMutationDelta,L as isRateLimitedError,O as isUnauthorizedError,c as maxSeq,w as preloadQuery,G as preloadedQueryResult,Y as queryCacheKey,p as reconcileOptimistic};
@@ -0,0 +1 @@
1
+ import{LunoraError as y}from"@lunora/errors";import{t as Ce,e as L,d as g}from"./wire-codec-BeIi1K-T.mjs";import{i as ke,a as we,P as Ee}from"./delta-merge-D_5ChS-C.mjs";import{s as ee}from"./wire-key-DCPYV4t8.mjs";import Ae from"./createInMemoryBookmarkStorage-BooZhW0n.mjs";import{ClientQueryStore as _e}from"./createClientQuery-B8Nfj-7o.mjs";import{TabCoordinator as Ie}from"./TabCoordinator-CXD7vulJ.mjs";import{TransportError as te,isAuthReplayFailure as D}from"./CONFLICT_ERROR_CODE-B7qNZMMk.mjs";import{httpStream as Oe}from"./httpStream-v4etRV7m.mjs";import{d as K,n as A,f as _,a as Re,c as Pe,b as Fe,e as Me}from"./local-store-DDppw8Qr.mjs";import{O as Le,n as se,i as He,r as Ue}from"./offline-queue-D_fr-uQ3.mjs";import{resolvePersistenceAdapter as xe}from"./createInMemoryPersistence-Cz2W6XVj.mjs";import{resolveQueryCacheAdapter as Ne,queryCacheKey as I}from"./createInMemoryQueryCache-D2uNHLfM.mjs";import{createReconnect as re}from"./createReconnect-CjTmjJDH.mjs";import{i as U,e as M,u as P,a as ie,d as ne,r as Be,b as Qe,c as De,M as Ke,f as qe,g as We}from"./replay-CXXDZ1_h.mjs";import je from"./createSnapshotPrecondition-5GQ_5fFu.mjs";import{createStream as $e}from"./DEFAULT_MAX_BUFFER-D3QH2iaq.mjs";import{SubscriptionRegistry as C}from"./SubscriptionRegistry-C3kLqped.mjs";const q=500,Ge=async c=>{const e=[];let t;for(;;){const s=await c(t);if(e.push(...Array.isArray(s.records)?s.records:[]),s.truncated!==!0||typeof s.cursor!="string"||s.cursor.length===0)return e;if(s.cursor===t)throw new Error("collectPages: the list did not advance its cursor — refusing to page forever");t=s.cursor}},ae=(c,e)=>{if(c.size<e)return;const t=c.keys().next().value;t!==void 0&&c.delete(t)};new TextDecoder;const Ve=new TextEncoder,ze=c=>Ce(Ve.encode(JSON.stringify(c))),Je="x-lunora-expect-subject",Ye=c=>ze({subject:c}),oe=Symbol.for("lunora:session-change"),Xe="lunora:session-change",Ze="better-auth.message",et="signout",me=()=>{const c=globalThis;let e=c[oe];return e===void 0&&(e={detach:void 0,listeners:new Set,tab:`${Date.now().toString(36)}-${Math.random().toString(36).slice(2)}`},c[oe]=e),e},tt=()=>"document"in globalThis,st=async()=>{const c=[];for(const e of me().listeners)try{c.push(e())}catch{}await Promise.allSettled(c)},rt=(c,e)=>{if(c!==Ze||e===null)return!1;try{const t=JSON.parse(e);return t?.event==="session"&&t.data?.trigger===et}catch{return!1}},it=c=>{const e=[],t=()=>{st().catch(()=>{})};let s;try{s=typeof BroadcastChannel=="function"?new BroadcastChannel(Xe):void 0}catch{s=void 0}if(s!==void 0){const i=s;i.addEventListener("message",n=>{n.data?.type==="lunora:session-change"&&n.data.tab!==c&&t()}),e.push(()=>{i.close()})}const r=globalThis;if(typeof r.addEventListener=="function"){const i=n=>{rt(n.key,n.newValue)&&t()};r.addEventListener("storage",i),e.push(()=>{r.removeEventListener?.("storage",i)})}return()=>{for(const i of e)i()}},nt=c=>{const e=me();return e.listeners.add(c),e.detach===void 0&&tt()&&(e.detach=it(e.tab)),()=>{e.listeners.delete(c),e.listeners.size===0&&(e.detach?.(),e.detach=void 0)}};class O{listeners=new Set;add(e){return this.listeners.add(e),()=>{this.listeners.delete(e)}}emit(...e){const[t]=e;for(const s of this.listeners)try{s(t)}catch{}}clear(){this.listeners.clear()}}const at=c=>{const{afterFailedAttempts:e,intervalMs:t,onReachable:s,onStateChange:r,poll:i}=c,n=t>0&&e>0;let a=0,o,h=!1,d=!1;const u=()=>{o!==void 0&&(clearInterval(o),o=void 0,h=!1,r())},f=p=>{if(o!==void 0){if(!p){u();return}h||(h=!0,r()),s()}},m=()=>{d||(d=!0,i().then(f).finally(()=>{d=!1}).catch(()=>{}))};return{isPolling:()=>o!==void 0&&h,noteFailedOpen:()=>{a+=1,!(!n||o!==void 0||a<e)&&(o=setInterval(m,t),r(),m())},noteOpen:()=>{a=0,u()},stop:u}},ot="/_lunora/rpc",W="/_lunora/rpc-batch",ct="/_lunora/ws",j=c=>c===void 0||c===""?"":`&bucket=${encodeURIComponent(c)}`,F=c=>{for(let e=c.length-1;e>=0;e-=1)c[e]?.()},ce=Symbol("lunora.unmergeableDelta"),ht=(c,e)=>{for(const t of e)t.op==="delete"?c.delete(t.key):t.value!==void 0&&c.set(t.key,t.value)},dt="lunora-ping",ut=3e4,lt=1e4,ft=5e3,pt=3,mt=250,yt=5e3,bt=5e3,St=64,vt=3,gt=1e4,Tt=8,Ct="/_lunora/admin/shard-traffic",kt="/_lunora/admin/scheduled",wt="/_lunora/admin/scheduled/status",Et="/_lunora/admin/scheduled/ws",At="/_lunora/admin/scheduled/cancel",he="/_lunora/admin/scheduled/dead",_t="/_lunora/admin/scheduled/dead/retry",It="/_lunora/admin/scheduled/dead/cancel",Ot="/_lunora/admin/workflows/instances",Rt="/_lunora/admin/workflows/instance",Pt="/_lunora/admin/workflows/status",$="/_lunora/admin/storage",Ft="/_lunora/admin/storage/url",Mt="/_lunora/admin/storage/buckets",Lt="/_lunora/admin/functions",Ht="/_lunora/admin/cron-jobs",Ut="/_lunora/admin/cron-jobs/run",xt="/_lunora/admin/openapi",Nt="/_lunora/admin/openrpc",Bt="/_lunora/admin/global/tables",Qt="/_lunora/admin/global/table",Dt="/_lunora/admin/global/facet",Kt="/_lunora/admin/vector/indexes",qt="/_lunora/admin/vector/query",Wt="/_lunora/admin/logs/archive",jt="/_lunora/admin/kv/namespaces",$t="/_lunora/admin/kv/keys",G="/_lunora/admin/kv/value",Gt="/_lunora/admin/auth/users",Vt="/_lunora/admin/auth/sessions",zt="/_lunora/admin/auth/users/create",Jt="/_lunora/admin/auth/users/role",Yt="/_lunora/admin/auth/users/ban",Xt="/_lunora/admin/auth/users/unban",Zt="/_lunora/admin/auth/users/password",es="/_lunora/admin/auth/users/remove",ts="/_lunora/admin/auth/users/impersonate",ss="/_lunora/admin/auth/sessions/revoke",rs="/_lunora/admin/auth/sessions/revoke-all",is="/_lunora/admin/auth/capabilities",ns="/_lunora/admin/auth/users/update",as="/_lunora/admin/auth/accounts",os="/_lunora/admin/auth/accounts/unlink",cs="/_lunora/admin/auth/passkeys",hs="/_lunora/admin/auth/passkeys/delete",ds="/_lunora/admin/auth/two-factor/disable",us="/_lunora/admin/auth/organizations",ls="/_lunora/admin/auth/organizations/members",fs="/_lunora/admin/auth/organizations/invitations",ps="/_lunora/admin/auth/organizations/members/remove",ms="/_lunora/admin/auth/organizations/invitations/cancel",ys="/_lunora/admin/auth/config",bs="/_lunora/admin/auth/sign-up-invitations",Ss="/_lunora/admin/auth/sign-up-invitations/create",vs="/_lunora/admin/auth/sign-up-invitations/revoke",gs="/_lunora/admin/auth/organizations/create",Ts="/_lunora/admin/auth/organizations/update",Cs="/_lunora/admin/auth/organizations/remove",ks="/_lunora/admin/auth/organizations/members/add",ws="/_lunora/admin/auth/organizations/members/invite",Es="/_lunora/admin/auth/organizations/members/role",As="/_lunora/admin/auth/organizations/teams",_s="/_lunora/admin/auth/organizations/teams/create",Is="/_lunora/admin/auth/organizations/teams/update",Os="/_lunora/admin/auth/organizations/teams/remove",Rs="/_lunora/admin/auth/organizations/teams/members",Ps="/_lunora/admin/auth/organizations/teams/members/add",Fs="/_lunora/admin/auth/organizations/teams/members/remove",Ms="/_lunora/admin/auth/organizations/roles",Ls="/_lunora/admin/auth/organizations/roles/create",Hs="/_lunora/admin/auth/organizations/roles/update",Us="/_lunora/admin/auth/organizations/roles/remove",xs="/api/auth",Ns="/get-session",V=c=>c==="connected"||c==="polling",Bs=(c,e,t)=>c!==null||e&&t===null,de=c=>c.startsWith("https://")?`wss://${c.slice(8)}`:c.startsWith("http://")?`ws://${c.slice(7)}`:c,k=(c,e)=>`${c.endsWith("/")?c.slice(0,-1):c}${e}`,b=(c,e)=>{const t=new URLSearchParams;for(const[r,i]of Object.entries(e))i!==void 0&&i!==""&&t.set(r,String(i));const s=t.toString();return s===""?c:`${c}?${s}`},Qs=[Ee],l=c=>c??"",ye=(c,e)=>{const t=c.error,s=typeof t?.code=="string"?t.code:void 0,r=typeof t?.message=="string"?t.message:void 0;return{code:s,messageText:(typeof c.message=="string"?c.message:void 0)??r??e}},Ds=c=>{const{code:e,messageText:t}=ye(c,"stream error");return e===void 0?new Error(t):new y(e,t)},ue=c=>{const{code:e,messageText:t}=ye(c,"subscription error");return{message:t,...e===void 0?{}:{code:e}}};function z(c){if(c!==void 0)return e=>{c(e)}}const w=(c,e)=>{for(const t of c)try{t(e)}catch{}},Ks=new TextDecoder,qs=c=>{if(typeof c=="string")return c;if(c instanceof ArrayBuffer)return Ks.decode(c)},v=(c,e)=>{if(!c.socket||c.wsState!=="open")return!1;try{return c.socket.send(JSON.stringify(e)),!0}catch{return!1}},Ws=c=>{if(!c.pendingStreams||c.pendingStreams.length===0)return;const e=c.pendingStreams;c.pendingStreams=[];for(const t of e)v(c,t)},X=c=>{const e=new Error(c.message??"request failed");if(e.code=c.code,c.data!==void 0)try{e.data=g(c.data)}catch{}return c.hint!==void 0&&(e.hint=c.hint),c.docsUrl!==void 0&&(e.docsUrl=c.docsUrl),e},le=(c,e)=>{const t=X(c),s=qe(t,e);return s!==void 0&&(t.data=s),t},E=(c,e)=>{try{return L(c)}catch(t){const s=t instanceof Error?t.message:String(t);throw new TypeError(`LunoraClient: cannot encode ${e} — ${s}`,t instanceof Error?{cause:t}:void 0)}},js=1e4,fe=async c=>{const e=new AbortController;let t;const s=new Promise((r,i)=>{t=setTimeout(()=>{e.abort(),i(new TypeError("LunoraClient: poll timed out"))},js)});try{return await Promise.race([c(e.signal),s])}catch(r){throw e.signal.aborted?new TypeError("LunoraClient: poll timed out"):r}finally{clearTimeout(t)}},pe=c=>{try{return L(c),!0}catch{return!1}},J=c=>"args"in c?{...c,args:g(c.args)}:c,be=c=>{const e=M(c);return e===void 0?We():X(e)},$s=(c,e)=>{const t=Array.from({length:e});for(const s of c){if(typeof s.id!="number"||s.id<0||s.id>=e)continue;const r=s.body;t[s.id]=r!==void 0&&"error"in r?{error:be(r),ok:!1}:{ok:!0,value:g(r?.result)}}return t.map(s=>s??{error:new Error("batch call returned no result"),ok:!1})},Y=(c,e)=>e!==null?{}:c===null?{expectSubject:null}:c?.startsWith("subj:")===!0?{expectSubject:c.slice(5)}:{},Gs=Promise.resolve();class Se{static MAX_POKE_BUFFERS=256;static createClientQuery(e,t){return{defaultValue:t,key:e}}url;wsUrl;clientQueryStore;wsToken;authBasePath;fetchImpl;WebSocketImpl;bookmark;reconnectOptions;connectTimeoutMs;heartbeatIntervalMs;pollingFallbackAfterFailedAttempts;pollingFallbackIntervalMs;offlineQueue;outbox;clientId;shardCursors=new Map;defaultShardKey;readyResolved=!1;readyResolve;readyPromise;clientWatermarks=new Map;outboxMutationCounter=0;onPersistenceError;persistence;persistenceVersion;outboxLeaderRelease;queryCache;hydratedQueryCache=new Map;cacheSeededQueries=new Map;pendingCacheWrites=new Map;cacheFlushTimer;subscriptions=new C;tabCoordinator;leaderStatus;leaderWasEverConnected=!1;connections=new Map;idleClosedShards=new Set;defaultConnectionContext;connectionContexts=new Map;connectionContextHolders=new Map;authToken=null;authSubject=void 0;subjectToken=null;sessionProbesInFlight=0;sessionProbeGeneration=0;identityQuestions=0;identityAnsweredAt=0;releaseSessionChangeListener;warnedIdentityDisagreement=!1;identityResolutionExpected=!1;identitySettled=!1;queuedIdentities=new Map;queuedOfflineShardKeys=new Set;closed=!1;authTokenListeners=new O;statusListeners=new O;tokenExpiredListeners=new O;identityChangeListeners=new O;retiredIdentities=0;authRefusalNotifiedFor;replayCredentials=new WeakMap;mutationSettledListeners=new O;pendingChangeListeners=new O;whisperHandlers=new Map;lastStatus="idle";nextSubId=0;nextStreamId=0;streams=new Map;adminSocketTeardowns=new Set;offlineFlushes=new Map;replayRetryState=new Map;replayRetryTimers=new Map;shapeSubscriptions=new Map;pokeBuffers=new Map;nextShapeId=0;constructor(e){this.url=e.url,this.wsUrl=e.wsUrl??k(de(e.url),ct),this.wsToken=e.wsToken;const t=e.authBasePath??xs;this.authBasePath=t.endsWith("/")?t.slice(0,-1):t,this.fetchImpl=e.fetch??(typeof fetch=="function"?fetch.bind(globalThis):void 0),this.WebSocketImpl=e.WebSocket??(typeof WebSocket=="function"?WebSocket:void 0),this.bookmark=e.bookmarkStorage??Ae(),this.reconnectOptions=e.reconnect,this.heartbeatIntervalMs=e.heartbeatIntervalMs??ut,this.connectTimeoutMs=e.connectTimeoutMs??lt,this.pollingFallbackIntervalMs=e.pollingFallback?.intervalMs??ft,this.pollingFallbackAfterFailedAttempts=e.pollingFallback?.afterFailedAttempts??pt,this.defaultConnectionContext=e.connectionContext,this.persistence=xe(e.persistence,e.outbox===void 0),this.persistenceVersion=e.persistenceVersion,this.queryCache=Ne(e.queryCache),this.onPersistenceError=e.offlineQueue?.onPersistenceError,this.clientQueryStore=new _e,e.crossTabSync?(this.tabCoordinator=this.createTabCoordinator(),this.tabCoordinator.start()):this.tabCoordinator=void 0,e.hydrateOnStart&&this.queryCache?this.readyPromise=new Promise(s=>{this.readyResolve=s}):(this.readyResolved=!0,this.readyPromise=Gs),this.offlineQueue=new Le(e.offlineQueue,{onEvict:(s,r)=>{this.emitItemSettled(s,"rejected",r),this.releaseIdleShard(s.shardKey)},onSizeChange:s=>{this.pendingChangeListeners.emit(s)},persistence:this.persistence,version:e.persistenceVersion}),this.outbox=e.outbox,this.clientId=e.clientId??`client-${se()}`,this.persistence&&queueMicrotask(()=>{this.hydrateAsOutboxLeader()}),this.queryCache&&queueMicrotask(()=>{(async()=>{try{await this.hydrateQueryCache()}catch{}finally{this.readyResolved=!0,this.readyResolve?.()}})().catch(()=>{})}),"document"in globalThis&&(this.releaseSessionChangeListener=nt(async()=>{!this.closed&&this.authToken===null&&await this.getCurrentUser().catch(()=>{})}))}setAuthToken(e,t){const s=this.authToken!==e,r=this.identityFingerprint(),i=this.authSubject===void 0||this.subjectToken===this.authToken,n=this.subjectAwaitingReconfirm(),a=this.isKnownNobody(),o=this.authToken;this.authToken=e,this.applySubject(e,t);const h=this.identityFingerprint();h!==r&&(!s&&e!==null&&i?(this.restampQueuedIdentity(r,h),this.restampWatermarks(r,h),this.restampConnectionIdentity(r,h),this.reseedFromHydratedCache()):!s&&e===null&&r===null&&i&&!a?(this.restampWatermarks(r,h),this.restampConnectionIdentity(r,h),this.reseedFromHydratedCache()):(this.rejectQueuedForIdentityChange(r),this.warnRefreshWithoutSubject(o,e),Bs(r,a,e)&&this.evictPreviousIdentitySession()),this.restartTabCoordinatorForIdentity()),this.syncReadCacheToCredential(n),s&&this.authTokenListeners.emit(e),(h!==r||s||n)&&this.offlineQueue.size>0&&V(this.computeStatus())&&this.flushAllOfflineQueues()}getAuthToken(){return this.authToken}currentIdentity(){return this.identityFingerprint()}expectIdentityResolution(){this.identityResolutionExpected=!0}currentBaseline(e){return this.baselineCursorFor(e)}replayIdentityVerdict(e){const t=this.identityVerdict(e);if(t!=="match")return{verdict:t};const s=Object.freeze({});return this.replayCredentials.set(s,{authToken:this.authToken,stamp:e}),{credential:s,verdict:t}}clientIdentifier(){return this.clientId}confirmedMutationWatermark(e){return this.clientWatermarks.get(this.identityFingerprint()??"")?.get(e??"")??0}async callMutator(e,t,s){const r=s?.clientSeq;if(r!==void 0&&(!Number.isInteger(r)||r<=0))throw new y("INTERNAL",`callMutator: clientSeq must be a positive integer, got ${String(r)}`);const i=s?.shardKey??"",n=this.identityFingerprint();let a,o,h;try{o=await this.rpc(e,t,s?.shardKey,{captureBookmark:!0,clientId:this.clientId,clientSeq:r,onMutationAck:u=>{a=u}})}catch(u){if(!U(u))throw u;h=u}if(a!==void 0&&a>(this.clientWatermarks.get(n??"")?.get(i)??0)){let u=this.clientWatermarks.get(n??"");u===void 0&&(ae(this.clientWatermarks,Tt),u=new Map,this.clientWatermarks.set(n??"",u)),u.set(i,a)}if(h!==void 0)throw h;return{applied:a===void 0||a===r,result:o}}onAuthTokenChange(e){return this.authTokenListeners.add(e)}onIdentityChange(e){return this.identityChangeListeners.add(e)}identityEpoch(){return this.retiredIdentities}async getCurrentUser(){if(this.identityResolutionExpected=!0,this.closed||!this.fetchImpl)return this.identitySettled=!0,null;const e={},t=this.authToken;this.authToken&&(e.authorization=`Bearer ${this.authToken}`),this.sessionProbesInFlight+=1,this.identityQuestions+=1,this.sessionProbeGeneration=this.identityQuestions;const s=this.sessionProbeGeneration;try{const r=await this.fetchImpl(k(this.url,`${this.authBasePath}${Ns}`),{credentials:"include",headers:e,method:"GET"});if(!r.ok)return this.identitySettled=!0,r.status===401&&this.adoptResolvedSubject(t,null,s),null;const n=(await r.json())?.user??null;return this.identitySettled=!0,this.adoptResolvedSubject(t,n,s),n}finally{this.releaseSessionProbe()}}setWsToken(e){this.wsToken!==e&&(this.wsToken=e,this.bounceShardSockets())}setConnectionContext(e,t={}){this.assertLeaderOwnedSurface("setConnectionContext");const s=l(t.shardKey);e===void 0?this.connectionContexts.delete(s):this.connectionContexts.set(s,e),this.refreshConnectionContext(s),e===void 0&&this.releaseIdleShard(t.shardKey)}acquireConnectionContext(e,t={}){if(this.followsAnotherTab())return()=>{};const s=l(t.shardKey),r={context:e},i=this.connectionContextHolders.get(s);i?i.push(r):this.connectionContextHolders.set(s,[r]),this.refreshConnectionContext(s);let n=!1;return()=>{if(n)return;n=!0;const a=this.connectionContextHolders.get(s);if(!a)return;const o=a.indexOf(r);o!==-1&&a.splice(o,1),a.length===0&&this.connectionContextHolders.delete(s),this.refreshConnectionContext(s),this.releaseIdleShard(t.shardKey)}}whisperSubscribe(e,t,s={}){this.assertLeaderOwnedSurface("whisperSubscribe");const r=l(s.shardKey);let i=this.whisperHandlers.get(r);i||(i=new Map,this.whisperHandlers.set(r,i));let n=i.get(e);const a=n===void 0;if(n||(n=new Set,i.set(e,n)),n.add(t),this.ensureSocket(s.shardKey),a){const o=this.getConnection(s.shardKey);o&&v(o,{topic:e,type:"whisper_subscribe"})}return()=>{const o=this.whisperHandlers.get(r),h=o?.get(e);if(!h?.delete(t)||h.size>0)return;o?.delete(e),o?.size===0&&this.whisperHandlers.delete(r);const d=this.getConnection(s.shardKey);d&&v(d,{topic:e,type:"whisper_unsubscribe"}),this.releaseIdleShard(s.shardKey)}}whisper(e,t,s={}){this.assertLeaderOwnedSurface("whisper"),this.ensureSocket(s.shardKey);const r=this.getConnection(s.shardKey);r&&v(r,{data:E(t??null,`whisper data for topic '${e}'`),topic:e,type:"whisper"}),this.releaseIdleShard(s.shardKey)}onTokenExpired(e){return this.tokenExpiredListeners.add(e)}connectionStatus(){return this.computeStatus()}onConnectionStatus(e){const t=this.statusListeners.add(e);return e(this.computeStatus()),t}pendingCount(){return this.offlineQueue.size}debug(){const e=[],t=this.clientWatermarks.get(this.identityFingerprint()??""),s=new Set([...this.connections.keys(),...t?.keys()??[]]);for(const i of s){const n=this.connections.get(i);e.push({confirmedMutationWatermark:t?.get(i)??0,hasSocket:n?.socket!==void 0,shardKey:i===""?void 0:i,wasEverConnected:n?.wasEverConnected??!1,wsState:n?.wsState??"idle"})}const r=this.subscriptions.all().map(i=>({acked:i.acked,functionPath:i.fn.__lunoraRef,id:i.id,kind:"query",lastMutationId:i.lastMutationId,pendingOptimisticLayers:i.optimisticLayers.length,serverCursor:i.serverCursor,shardKey:i.shardKey,subscriberCount:i.callbacks.size}));for(const i of this.shapeSubscriptions.values())r.push({acked:i.serverCursor!==void 0,functionPath:`shape:${i.name}`,id:i.id,kind:"shape",lastMutationId:i.lastMutationId,pendingOptimisticLayers:0,rowCount:i.rows.size,serverCursor:i.serverCursor,shardKey:i.shardKey,subscriberCount:i.callbacks.size});return{clientId:this.clientId,closed:this.closed,connectionStatus:this.computeStatus(),pendingWrites:this.offlineQueue.size,shards:e.toSorted((i,n)=>(i.shardKey??"").localeCompare(n.shardKey??"")),subscriptions:r.toSorted((i,n)=>i.functionPath.localeCompare(n.functionPath))}}onPendingChange(e){const t=this.pendingChangeListeners.add(e);return e(this.offlineQueue.size),t}onMutationSettled(e){return this.mutationSettledListeners.add(e)}getWebSocketImpl(){return this.WebSocketImpl}getClientQuery(e){return this.clientQueryStore.get(e)}setClientQuery(e,t){this.clientQueryStore.set(e,t)}subscribeClientQuery(e,t){return this.clientQueryStore.subscribe(e,t)}resetClientQuery(e){this.clientQueryStore.reset(e)}snapshotPrecondition(e,t,s){return je(this,e,t,s)}whenReady(){return this.readyPromise}get isReady(){return this.readyResolved}peekHydratedQuery(e,t,s){if(!this.readyResolved)return;const r=ee(t),i=I(e,r,s),n=this.hydratedQueryCache.get(i);if(n!==void 0)return this.cachedQueryMatchesIdentity(n)?n.value:void 0}peekActiveQuerySnapshot(e,t,s){const r=C.key(e,t,s),i=this.subscriptions.get(r);return{present:i!==void 0,value:i?.lastValue}}async query(e,t,s={}){return this.assertOpen(),await this.rpc(e.__lunoraRef,t,s.shardKey,{attachBookmark:!0})}async batch(e){return this.sendBatch(e)}async mutation(e,t,s={}){const{value:r}=await this.runMutation(e,t,s);return r}canQueueOffline(e){const{wasEverConnected:t}=this.connectionGateState(e);return this.WebSocketImpl!==void 0&&(t||this.offlineQueue.queueBeforeFirstConnect)}async action(e,t,s={}){return this.assertOpen(),await this.rpc(e.__lunoraRef,t,s.shardKey,{attachBookmark:!0,captureBookmark:!0})}async importRows(e,t,s={}){this.assertOpen();const r=Math.max(1,Math.trunc(s.chunkSize??500)),i=s.toArgs??(d=>({rows:d})),n=t.length;let a=0,o=0,h=0;for(let d=0;d<n;d+=r){const u=t.slice(d,d+r),f=h,{committed:m}=await this.runMutation(e,i(u),{...s.importId===void 0?{}:{mutationId:`${s.importId}:${String(f)}`},shardKey:s.shardKey});h+=1,a+=u.length,m&&(o+=u.length),s.onProgress?.({done:a,total:n})}return{chunks:h,imported:o,queued:a-o}}async shardTraffic(e){this.assertOpen();const t=await this.adminFetch(Ct,"POST",{table:e});return{failed:t.failed??0,ok:t.ok??0,shards:t.shards??[]}}async listScheduledJobs(){return this.assertOpen(),((await this.adminFetch(kt,"GET")).records??[]).map(t=>J(t))}async schedulerStatus(){this.assertOpen();const e=await this.adminFetch(wt,"GET");return{backlog:e.backlog??0,inFlight:e.inFlight??0,pools:e.pools??[]}}async cancelScheduledJob(e){return this.assertOpen(),{cancelled:(await this.adminFetch(At,"POST",{id:e})).cancelled===!0}}async listDeadJobs(){return this.assertOpen(),(await Ge(async t=>await this.adminFetch(t===void 0?he:`${he}?cursor=${encodeURIComponent(t)}`,"GET"))).map(t=>J(t))}async retryDeadJob(e){return this.assertOpen(),{retried:(await this.adminFetch(_t,"POST",{id:e})).retried===!0}}async removeDeadJob(e){return this.assertOpen(),{removed:(await this.adminFetch(It,"POST",{id:e})).removed===!0}}async listWorkflowInstances(e){this.assertOpen();const t=new URLSearchParams({name:e.name});e.status!==void 0&&t.set("status",e.status),e.page!==void 0&&t.set("page",String(e.page)),e.perPage!==void 0&&t.set("perPage",String(e.perPage));const s=await this.adminFetch(`${Ot}?${t.toString()}`,"GET");return{configured:s.configured,instances:s.instances??[],page:s.page??1,perPage:s.perPage??e.perPage??0,totalCount:s.totalCount}}async getWorkflowInstance(e){this.assertOpen();const t=new URLSearchParams({id:e.id,name:e.name}),s=await this.adminFetch(`${Rt}?${t.toString()}`,"GET");return{createdOn:s.createdOn,endedOn:s.endedOn,error:s.error,id:s.id??e.id,output:s.output,params:s.params,startedOn:s.startedOn,status:s.status??"unknown",steps:s.steps??[]}}async setWorkflowInstanceStatus(e){return this.assertOpen(),{status:(await this.adminFetch(Pt,"POST",{action:e.action,id:e.id,name:e.name})).status??"unknown"}}subscribeScheduledJobs(e){if(this.assertOpen(),this.WebSocketImpl===void 0)return()=>{};const t=k(de(this.url),Et),s=re(this.reconnectOptions),r={connectTimer:void 0,heartbeatTimer:void 0,lastFrameAt:0,socket:void 0};let i,n=!1;const a=()=>{n||this.closed||(i=setTimeout(d,s.next()))},o=f=>{if(n||this.WebSocketImpl===void 0)return;const m=f===void 0?t:`${t}?token=${encodeURIComponent(f)}`;this.openManagedSocket(r,m,this.connectTimeoutMs,{onClose:()=>{a()},onMessage:p=>{let S;try{S=JSON.parse(typeof p.data=="string"?p.data:"")}catch{return}S.type==="jobs"&&Array.isArray(S.records)&&(s.reset(),e(S.records.map(T=>J(T))))}})},h=async f=>{let m;try{m=await f()}catch{a();return}o(m)},d=()=>{if(n||this.WebSocketImpl===void 0)return;const{wsToken:f}=this;if(typeof f=="function"){h(f).catch(()=>{});return}o(f)};d();const u=()=>{n=!0,i!==void 0&&(clearTimeout(i),i=void 0),r.connectTimer!==void 0&&(clearTimeout(r.connectTimer),r.connectTimer=void 0),this.stopHeartbeat(r),r.socket?.close(),r.socket=void 0};return this.adminSocketTeardowns.add(u),()=>{this.adminSocketTeardowns.delete(u),u()}}async listFunctions(){return this.assertOpen(),(await this.adminFetch(Lt,"GET")).functions??[]}async getCronJobs(){return this.assertOpen(),(await this.adminFetch(Ht,"GET")).jobs??[]}async runCronJob(e){this.assertOpen();const t=await this.adminFetch(Ut,"POST",{name:e});return{name:t.name??e,ran:t.ran===!0}}async fetchOpenApi(){return this.assertOpen(),await this.adminFetch(xt,"GET")}async fetchOpenRpc(){return this.assertOpen(),await this.adminFetch(Nt,"GET")}async listStorageObjects(e={}){this.assertOpen();const t=b($,{bucket:e.bucket,cursor:e.cursor,limit:e.limit,prefix:e.prefix}),s=await this.adminFetch(t,"GET");return{cursor:s.cursor,objects:s.objects??[]}}async deleteStorageObject(e,t){this.assertOpen();const s=`${$}?key=${encodeURIComponent(e)}${j(t?.bucket)}`,r=await this.adminFetch(s,"DELETE");return{deleted:r.deleted===!0,key:r.key??e}}async listStorageBuckets(){return this.assertOpen(),(await this.adminFetch(Mt,"GET")).buckets??[]}async uploadStorageObject(e){this.assertOpen();const t=`${$}?key=${encodeURIComponent(e.key)}${j(e.bucket)}`,s=await this.adminFetch(t,"PUT",e.body,e.contentType);return{etag:s.etag,key:s.key??e.key}}async signedStorageUrl(e,t){this.assertOpen();const s=t?.expiresInSeconds,r=s===void 0?"":`&expiresIn=${encodeURIComponent(s.toString())}`,i=`${Ft}?key=${encodeURIComponent(e)}${r}${j(t?.bucket)}`,n=await this.adminFetch(i,"GET");if(typeof n.url!="string")throw new TypeError("LunoraClient: storage URL endpoint returned no `url`");return n.url}async listGlobalTables(){return this.assertOpen(),await this.adminFetch(Bt,"GET")}async readGlobalTablePage(e){this.assertOpen();const t=new URLSearchParams({table:e.table});return e.limit!==void 0&&t.set("limit",String(e.limit)),e.offset!==void 0&&t.set("offset",String(e.offset)),e.filters!==void 0&&e.filters.length>0&&t.set("filters",JSON.stringify(L(e.filters))),g(await this.adminFetch(`${Qt}?${t.toString()}`,"GET"))}async facetGlobalColumn(e){this.assertOpen();const t=new URLSearchParams({column:e.column,table:e.table});return e.limit!==void 0&&t.set("limit",String(e.limit)),e.filters!==void 0&&e.filters.length>0&&t.set("filters",JSON.stringify(L(e.filters))),g(await this.adminFetch(`${Dt}?${t.toString()}`,"GET"))}async listVectorIndexes(){return this.assertOpen(),(await this.adminFetch(Kt,"GET")).indexes??[]}async queryVectorIndex(e){return this.assertOpen(),(await this.adminFetch(qt,"POST",e)).matches??[]}async queryLogArchive(e={}){this.assertOpen();const t=await this.adminFetch(Wt,"POST",e);return{nextCursor:t.nextCursor,rows:t.rows??[]}}async listKvNamespaces(){return this.assertOpen(),(await this.adminFetch(jt,"GET")).namespaces??[]}async listKvKeys(e){this.assertOpen();const t=b($t,{cursor:e.cursor,limit:e.limit,namespace:e.namespace,prefix:e.prefix});return await this.adminFetch(t,"GET")}async getKvValue(e){this.assertOpen();const t=b(G,{key:e.key,namespace:e.namespace});return await this.adminFetch(t,"GET")}async putKvValue(e){this.assertOpen(),await this.adminFetch(G,"PUT",e)}async deleteKvKey(e){this.assertOpen();const t=b(G,{key:e.key,namespace:e.namespace});await this.adminFetch(t,"DELETE")}async listAuthUsers(e={}){this.assertOpen();const t=b(Gt,{filterField:e.filterField,filterValue:e.filterValue,limit:e.limit,offset:e.offset,search:e.search,searchField:e.searchField,sortBy:e.sortBy,sortDirection:e.sortDirection});return await this.adminFetch(t,"GET")}async createAuthUser(e){return await this.adminFetch(zt,"POST",e)}async setAuthUserRole(e){return await this.adminFetch(Jt,"POST",e)}async banAuthUser(e){return await this.adminFetch(Yt,"POST",e)}async unbanAuthUser(e){return await this.adminFetch(Xt,"POST",e)}async setAuthUserPassword(e){await this.adminFetch(Zt,"POST",e)}async removeAuthUser(e){await this.adminFetch(es,"POST",e)}async impersonateAuthUser(e){return await this.adminFetch(ts,"POST",e)}async revokeAuthSession(e){await this.adminFetch(ss,"POST",e)}async revokeAuthUserSessions(e){await this.adminFetch(rs,"POST",e)}async getAuthCapabilities(){return await this.adminFetch(is,"GET")}async updateAuthUser(e){return await this.adminFetch(ns,"POST",e)}async listAuthAccounts(e){return await this.adminFetch(b(as,{userId:e.userId}),"GET")}async unlinkAuthAccount(e){await this.adminFetch(os,"POST",e)}async listAuthPasskeys(e){return await this.adminFetch(b(cs,{userId:e.userId}),"GET")}async deleteAuthPasskey(e){await this.adminFetch(hs,"POST",e)}async disableAuthTwoFactor(e){await this.adminFetch(ds,"POST",e)}async listAuthOrganizations(e={}){return await this.adminFetch(b(us,{limit:e.limit,offset:e.offset}),"GET")}async listAuthOrgMembers(e){const t=b(ls,{limit:e.limit,offset:e.offset,organizationId:e.organizationId});return await this.adminFetch(t,"GET")}async listAuthOrgInvitations(e){const t=b(fs,{limit:e.limit,offset:e.offset,organizationId:e.organizationId});return await this.adminFetch(t,"GET")}async listAuthSignUpInvitations(e={}){const t=b(bs,{limit:e.limit,offset:e.offset});return await this.adminFetch(t,"GET")}async createAuthSignUpInvitation(e){return await this.adminFetch(Ss,"POST",e)}async revokeAuthSignUpInvitation(e){await this.adminFetch(vs,"POST",e)}async removeAuthOrgMember(e){await this.adminFetch(ps,"POST",e)}async cancelAuthOrgInvitation(e){await this.adminFetch(ms,"POST",e)}async getAuthConfig(){return await this.adminFetch(ys,"GET")}async createAuthOrganization(e){return await this.adminFetch(gs,"POST",e)}async updateAuthOrganization(e){return await this.adminFetch(Ts,"POST",e)}async deleteAuthOrganization(e){await this.adminFetch(Cs,"POST",e)}async addAuthOrgMember(e){return await this.adminFetch(ks,"POST",e)}async inviteAuthOrgMember(e){return await this.adminFetch(ws,"POST",e)}async setAuthOrgMemberRole(e){return await this.adminFetch(Es,"POST",e)}async listAuthOrgTeams(e){const t=b(As,{limit:e.limit,offset:e.offset,organizationId:e.organizationId});return await this.adminFetch(t,"GET")}async createAuthOrgTeam(e){return await this.adminFetch(_s,"POST",e)}async updateAuthOrgTeam(e){return await this.adminFetch(Is,"POST",e)}async removeAuthOrgTeam(e){await this.adminFetch(Os,"POST",e)}async listAuthOrgTeamMembers(e){const t=b(Rs,{limit:e.limit,offset:e.offset,teamId:e.teamId});return await this.adminFetch(t,"GET")}async addAuthOrgTeamMember(e){return await this.adminFetch(Ps,"POST",e)}async removeAuthOrgTeamMember(e){await this.adminFetch(Fs,"POST",e)}async listAuthOrgRoles(e){const t=b(Ms,{limit:e.limit,offset:e.offset,organizationId:e.organizationId});return await this.adminFetch(t,"GET")}async createAuthOrgRole(e){return await this.adminFetch(Ls,"POST",e)}async updateAuthOrgRole(e){return await this.adminFetch(Hs,"POST",e)}async deleteAuthOrgRole(e){await this.adminFetch(Us,"POST",e)}async listAuthSessions(e={}){this.assertOpen();const t=b(Vt,{limit:e.limit,offset:e.offset,userId:e.userId});return await this.adminFetch(t,"GET")}subscribe(e,t,s,r={}){this.assertOpen();const i=t??{},n=C.key(e.__lunoraRef,i,r.shardKey);let a=this.subscriptions.get(n);const o=z(s),h=z(r.onError),d=z(r.onCheckpoint);if(!a){this.nextSubId+=1;const f=`sub_${this.nextSubId.toString()}`,m=ee(i),p=this.takeHydratedCache(e.__lunoraRef,m,r.shardKey);a={acked:!1,args:i,argsKey:m,callbacks:new Set,checkpointCallbacks:new Set,errorCallbacks:new Set,fn:e,id:f,lastValue:p?.value,optimisticLayers:[],serverBase:p?.value,serverCursor:p?.serverCursor,shardKey:r.shardKey,wireArgs:E(i,`args for '${e.__lunoraRef}'`),...p?.serverEpoch===void 0?{}:{serverEpoch:p.serverEpoch}},this.subscriptions.add(a),p!==void 0&&this.cacheSeededQueries.set(n,p)}if(a.callbacks.add(o),h&&a.errorCallbacks.add(h),d&&a.checkpointCallbacks.add(d),a.lastValue!==void 0)try{o(a.lastValue)}catch{}this.ensureSocket(r.shardKey),this.sendSubscribeIfOpen(a);const u=a;return()=>{u.callbacks.delete(o),h&&u.errorCallbacks.delete(h),d&&u.checkpointCallbacks.delete(d),u.callbacks.size===0&&(this.sendOrQueueUnsubscribe(u.shardKey,u.id,"unsubscribe"),this.returnCacheSeed(C.keyOf(u)),this.subscriptions.remove(u),this.releaseIdleShard(u.shardKey))}}subscribeShape(e,t,s={}){if(this.assertOpen(),this.followsAnotherTab()){const{onError:n}=s;return n!==void 0&&queueMicrotask(()=>{n({code:"NOT_IMPLEMENTED",message:"LunoraClient: `subscribeShape` is unavailable on a cross-tab follower tab. The `crossTabSync` channel only carries data from the leader tab outward and shape pokes are not part of that broadcast set, so this subscription could never resolve. Turn off `crossTabSync`, or use a `list`-backed collection, which IS relayed."})}),()=>{}}this.nextShapeId+=1;const r=`shape_${this.nextShapeId.toString()}`,i={args:e.args,callbacks:new Set([t]),errorCallbacks:s.onError?new Set([s.onError]):new Set,id:r,name:e.name,onCheckpoint:s.onCheckpoint,rows:new Map,shardKey:s.shardKey,wireArgs:e.args===void 0?void 0:E(e.args,`shape args for '${e.name}'`)};return this.shapeSubscriptions.set(r,i),this.ensureSocket(s.shardKey),this.sendShapeSubscribeIfOpen(i),()=>{this.shapeSubscriptions.delete(r),this.sendOrQueueUnsubscribe(i.shardKey,r,"shape_unsubscribe"),this.releaseIdleShard(i.shardKey)}}stream(e,t,s={}){if(this.assertOpen(),this.WebSocketImpl===void 0)throw new y("INTERNAL","LunoraClient: streams require a WebSocket implementation");this.nextStreamId+=1;const r=`stream_${this.nextStreamId.toString()}`,{shardKey:i}=s,n=t??{},{handle:a,iterable:o}=$e({maxBuffer:s.maxBuffer,onCancel:()=>{this.cancelStream(r,i)}});this.ensureSocket(i);const h=this.getConnection(i),d={id:r,query:{args:E(n,`stream args for '${e.__lunoraRef}'`),functionPath:e.__lunoraRef,shardKey:i},type:"stream"},u={durable:s.durable===!0,generation:void 0,handle:a,lastSeq:0,message:d,shardKey:i};this.streams.set(r,u);const f=h?.wsState==="open"&&v(h,d);if(!f&&h===void 0)return this.forgetStream(r),a.fail(new y("STREAM_DISCONNECTED","stream unavailable: this tab is not the cross-tab WebSocket leader, so it holds no socket to stream over")),o;if(!f){for(h.pendingStreams=h.pendingStreams??[];h.pendingStreams.length>=St;){const p=h.pendingStreams.shift()?.id,S=p?this.streams.get(p):void 0;S&&(S.handle.fail(new y("STREAM_QUEUE_OVERFLOW","stream-start frame evicted while socket was unreachable")),this.forgetStream(p))}h.pendingStreams.push(d)}return o}httpStream(e,t,s={}){if(this.closed)throw new y("CLIENT_CLOSED","LunoraClient is closed");if(!this.fetchImpl)throw new y("INTERNAL","LunoraClient: no `fetch` implementation available");const r={...this.authToken?{authorization:`Bearer ${this.authToken}`}:{},...s.headers};return Oe(e,t,{baseUrl:this.url,fetch:this.fetchImpl,headers:r,maxBuffer:s.maxBuffer,signal:s.signal})}close(){this.closed=!0,this.releaseSessionChangeListener?.(),this.releaseSessionChangeListener=void 0,this.outboxLeaderRelease?.(),this.outboxLeaderRelease=void 0;for(const e of this.streams.values())e.handle.fail(new y("CLIENT_CLOSED","LunoraClient closed"));this.streams.clear();for(const e of this.connections.values())this.teardownConnection(e);for(const e of this.adminSocketTeardowns)e();this.adminSocketTeardowns.clear();for(const e of this.replayRetryTimers.values())clearTimeout(e);this.replayRetryTimers.clear(),this.replayRetryState.clear(),this.offlineQueue.clear(),this.queuedIdentities.clear(),this.cacheFlushTimer!==void 0&&(clearTimeout(this.cacheFlushTimer),this.cacheFlushTimer=void 0),this.pendingCacheWrites.size>0&&this.flushQueryCacheWrites().catch(()=>{}),this.authTokenListeners.clear(),this.statusListeners.clear(),this.tokenExpiredListeners.clear(),this.identityChangeListeners.clear(),this.mutationSettledListeners.clear(),this.pendingChangeListeners.clear(),this.whisperHandlers.clear(),this.shapeSubscriptions.clear(),this.pokeBuffers.clear(),this.subscriptions.clear(),this.clientQueryStore.clear(),this.hydratedQueryCache.clear(),this.cacheSeededQueries.clear(),this.tabCoordinator?.stop(),this.tabCoordinator=void 0}assertOpen(){if(this.closed)throw new y("INTERNAL","LunoraClient is closed")}followsAnotherTab(){const e=this.tabCoordinator;if(e===void 0||e.isLeader())return!1;const t=e.leaderTabId;return t!==void 0&&t!==e.id}assertLeaderOwnedSurface(e){if(this.followsAnotherTab())throw new y("NOT_IMPLEMENTED",`LunoraClient: \`${e}\` is unavailable on a cross-tab follower tab. The \`crossTabSync\` channel only carries data from the leader tab outward, so this call could never reach the server. Turn off \`crossTabSync\`, or keep \`${e}\` on the leader tab.`)}clearConnectionTimers(e){clearTimeout(e.reconnectTimer),clearTimeout(e.connectTimer),clearTimeout(e.stableTimer),e.reconnectTimer=void 0,e.connectTimer=void 0,e.stableTimer=void 0}shardInUse(e){const t=s=>l(s)===e;return this.subscriptions.all().some(s=>t(s.shardKey))||[...this.shapeSubscriptions.values()].some(s=>t(s.shardKey))||[...this.streams.values()].some(s=>t(s.shardKey))||this.whisperHandlers.has(e)||this.connectionContexts.has(e)||this.connectionContextHolders.has(e)||this.offlineFlushes.has(e)||this.offlineQueue.hasPending(s=>t(s.shardKey))}releaseIdleShard(e){const t=l(e),s=this.connections.get(t);this.closed||t===""||s===void 0||(clearTimeout(s.idleTimer),s.idleTimer=setTimeout(()=>{s.idleTimer=void 0,!(this.closed||this.connections.get(t)!==s||this.shardInUse(t))&&(s.wasEverConnected&&this.idleClosedShards.add(t),this.teardownConnection(s),this.connections.delete(t),this.emitConnectionStatus())},bt))}forgetStream(e){const t=this.streams.get(e);this.streams.delete(e),t&&this.releaseIdleShard(t.shardKey)}teardownConnection(e){e.polling.stop();const t=l(e.shardKey);for(const[r,i]of this.streams)l(i.shardKey)===t&&(i.handle.fail(new y("STREAM_DISCONNECTED","stream terminated: the connection carrying it was torn down")),this.streams.delete(r));e.pendingStreams=void 0,e.pendingUnsubscribes=[],this.clearResubscribeQueue(e),this.clearConnectionTimers(e),clearTimeout(e.idleTimer),e.idleTimer=void 0,this.stopHeartbeat(e);const{socket:s}=e;if(s){e.socket=void 0;try{s.close()}catch{}}e.wsState="closed"}createTabCoordinator(){const e=`lunora-bridge::${this.url}::${this.identityFingerprint()??"anon"}`;return new Ie({channelName:e,onBecomeLeader:()=>{for(const t of this.subscriptions.all())this.ensureSocket(t.shardKey),this.queueResubscribe(t);for(const t of this.queuedOfflineShardKeys)this.ensureSocket(t);this.tabCoordinator?.broadcastConnectionStatus(this.computeStatus(),this.identityFingerprint())},onStopBeingLeader:()=>{for(const[t,s]of this.connections)this.teardownConnection(s),this.connections.delete(t);this.leaderStatus=void 0,this.leaderWasEverConnected=!1},onConnectionStatus:(t,s)=>{if(s!==void 0&&s!==this.identityFingerprint())return;const r=t==="connected"&&this.leaderStatus!=="connected"||t==="polling"&&this.leaderStatus!=="connected"&&this.leaderStatus!=="polling";this.leaderStatus=t,t==="connected"&&(this.leaderWasEverConnected=!0),this.emitConnectionStatus(),r&&this.flushAllOfflineQueues()},onSubscriptionData:(t,s,r,i,n)=>{if(n!==void 0&&n!==this.identityFingerprint())return;const a=this.subscriptions.get(t);a&&(a.serverBase=s,this.dropCacheSeed(t),r!==void 0&&(a.serverCursor=r,i!==void 0&&(a.serverEpoch=i),K(a,r)),A(a,_(s,a.optimisticLayers)))},onLeaderClaimAnswered:()=>{this.tabCoordinator?.isLeader()&&this.tabCoordinator.broadcastConnectionStatus(this.computeStatus(),this.identityFingerprint())},onSubscriptionError:(t,s,r)=>{if(r!==void 0&&r!==this.identityFingerprint())return;const i=this.subscriptions.get(t);i&&w(i.errorCallbacks,s)},onSubscriptionSettled:(t,s,r,i,n,a)=>{if(a!==void 0&&a!==this.identityFingerprint())return;const o=this.subscriptions.get(t);if(o){this.ackAndAdvanceCursor(o,s,r),i!==void 0&&n===this.clientId&&(o.lastMutationId=Math.max(o.lastMutationId??0,i));for(const h of o.checkpointCallbacks)h({checkpoint:o.serverCursor,mutationId:o.lastMutationId})}}})}async sendBatch(e,t){if(this.assertOpen(),!this.fetchImpl)throw new y("INTERNAL","LunoraClient: no `fetch` implementation available");if(e.length===0)return[];const s=await this.fetchImpl(k(this.url,W),{body:JSON.stringify({calls:e.map((a,o)=>({args:E(a.args??{},`args for batch call '${a.fn.__lunoraRef}'`),functionPath:a.fn.__lunoraRef,id:o,shardKey:a.shardKey}))}),headers:this.rpcRequestHeaders({attachBookmark:!0}),method:"POST",signal:t}),r=s.headers.get("x-d1-bookmark");r&&this.bookmark.set(r);let i;try{i=await s.json()}catch{throw new y("INTERNAL",`LunoraClient: batch response was not JSON (status ${s.status.toString()})`)}const n=M(i);if(!s.ok||n!==void 0&&!i.results)throw n!==void 0?X(n):new y("INTERNAL",`LunoraClient: batch request failed (status ${s.status.toString()})`);for(const a of i.results??[]){const o=a.body?.commitCursor;typeof a.id=="number"&&typeof o=="number"&&this.recordShardCursor(e[a.id]?.shardKey,o)}return $s(i.results??[],e.length)}async runMutation(e,t,s){this.assertOpen();const r=t,i=s.mutationId??se(),n=this.takeReplayCredential(s.replayCredential),a=s.replayBaseline===void 0?this.baselineCursorFor(s.shardKey):s.replayBaseline??void 0,{confirms:o,rollbacks:h}=this.applyOptimisticUpdates(e.__lunoraRef,r,s.shardKey,s.optimistic);s.optimisticUpdate&&this.applyOptimisticUpdate(s.optimisticUpdate,t,s.shardKey,h,o);const d=this.offlineFlushes.get(l(s.shardKey));d!==void 0&&await d;const{hasSocket:u,idleClosed:f,polling:m,wasEverConnected:p,wsState:S}=this.connectionGateState(s.shardKey),{queueBeforeFirstConnect:T}=this.offlineQueue,H=p||T,x=this.WebSocketImpl!==void 0&&H,N=m||f,ve=S==="connecting"&&H&&!N,ge=S!=="open"&&!u&&x&&!N,Te=x&&s.replayBaseline===void 0&&this.hasPendingWriteAhead(s.shardKey),Z=async()=>this.enqueueOfflineMutation(e,r,s.shardKey,a,i,h,o,s.precondition,s.mutationId,n?.stamp);if(ge||ve||Te)return Z();let B;try{const R=await this.rpc(e.__lunoraRef,r,s.shardKey,{baselineSeq:a,captureBookmark:!0,...n?.flags,mutationId:i,onCommitCursor:Q=>{B=Q}});for(const Q of o)Q(B);return{committed:!0,value:R}}catch(R){if(N&&x&&R instanceof TypeError&&pe(r))return Z();throw this.settleFailedDirectWrite(R,B,o,h,n?.flags.authToken),R}}settleFailedDirectWrite(e,t,s,r,i){if(this.noteIdentityMismatch(e),i!==void 0&&this.noteReplayAuthRefusal(e,i),U(e)){for(const n of s)n(t);return}F(r)}async enqueueOfflineMutation(e,t,s,r,i,n,a,o,h,d){const u=d===void 0?this.identityFingerprint():d;if(this.outbox){this.outboxMutationCounter+=1;const m=this.outboxMutationCounter;try{await this.outbox.enqueue({args:t,baselineSeq:r,clientId:this.clientId,functionPath:e.__lunoraRef,idempotencyKey:h??`${this.clientId}:${String(m)}`,identity:u,mutationId:m,...n.length>0&&{onRejected:()=>{F(n)}},shardKey:s})}catch(p){throw F(n),p instanceof Error?p:new Error(String(p))}for(const p of a)p(void 0);return{committed:!1,value:void 0}}return{committed:!0,value:await new Promise((m,p)=>{const S={args:t,functionPath:e.__lunoraRef,liveAwaiter:!0,baselineSeq:r,id:i,clientId:this.clientId,identity:u,precondition:o,onCommit:T=>{for(const H of a)H(T)},reject:T=>{this.queuedIdentities.delete(i),U(T)||F(n),p(T instanceof Error?T:new Error(String(T))),this.releaseIdleShard(s)},resolve:m,shardKey:s};this.offlineQueue.enqueue(S),this.queuedOfflineShardKeys.add(s),this.ensureSocket(s),S.id!==void 0&&this.queuedIdentities.set(S.id,u)})}}hasPendingWriteAhead(e){if(this.outbox)return this.outbox.pending?.()??!1;const t=l(e);return this.offlineQueue.hasPending(s=>l(s.shardKey)===t)}async hydratePersistedQueue(){try{const e=await this.offlineQueue.hydrate();for(const t of e)this.queuedOfflineShardKeys.add(t),this.ensureSocket(t)}catch{}}hydrateAsOutboxLeader(){const e=()=>{this.hydratePersistedQueue().catch(()=>{})},t=globalThis.navigator?.locks;if(!t){e();return}t.request(`lunora:outbox-leader:${this.url}`,()=>(this.closed||e(),new Promise(s=>{if(this.closed){s();return}this.outboxLeaderRelease=s}))).catch(e)}async hydrateQueryCache(){if(this.queryCache)try{const e=await this.queryCache.load(),t=new Map;for(const s of this.subscriptions.all())t.set(I(s.fn.__lunoraRef,s.argsKey,s.shardKey),s);for(const{key:s,...r}of e){if(He(this.persistenceVersion,r.version)){this.queryCache.remove(s).catch(()=>{});continue}const i=t.get(s);if(i&&this.cachedQueryMatchesIdentity(r)){this.seedSubscriptionFromCache(i,r);continue}this.hydratedQueryCache.set(s,r)}}catch{}}seedSubscriptionFromCache(e,t){e.serverBase!==void 0||e.lastValue!==void 0||!this.cachedQueryMatchesIdentity(t)||(e.serverBase=t.value,e.serverCursor=t.serverCursor,t.serverEpoch!==void 0&&(e.serverEpoch=t.serverEpoch),this.cacheSeededQueries.set(I(e.fn.__lunoraRef,e.argsKey,e.shardKey),t),A(e,_(t.value,e.optimisticLayers)))}syncReadCacheToCredential(e){this.subjectAwaitingReconfirm()?this.revokeCacheSeededValues():e&&this.reseedFromHydratedCache()}dropCacheSeed(e){this.cacheSeededQueries.delete(e),this.hydratedQueryCache.delete(e)}returnCacheSeed(e){const t=this.cacheSeededQueries.get(e);t!==void 0&&(this.cacheSeededQueries.delete(e),this.hydratedQueryCache.set(e,t))}revokeCacheSeededValues(){if(this.cacheSeededQueries.size!==0){for(const[e,t]of this.cacheSeededQueries){const s=this.subscriptions.get(e);s!==void 0&&(s.serverBase=void 0,s.serverCursor=void 0,s.serverEpoch=void 0,A(s,_(void 0,s.optimisticLayers))),this.hydratedQueryCache.set(e,t)}this.cacheSeededQueries.clear()}}takeHydratedCache(e,t,s){const r=I(e,t,s),i=this.hydratedQueryCache.get(r);if(!(i===void 0||!this.cachedQueryMatchesIdentity(i)))return this.hydratedQueryCache.delete(r),i}reseedFromHydratedCache(){if(this.hydratedQueryCache.size!==0)for(const e of this.subscriptions.all()){const t=I(e.fn.__lunoraRef,e.argsKey,e.shardKey),s=this.hydratedQueryCache.get(t);s!==void 0&&this.cachedQueryMatchesIdentity(s)&&(this.hydratedQueryCache.delete(t),this.seedSubscriptionFromCache(e,s))}}persistQueryValue(e){const t=e.serverBase;if(!this.queryCache||t===void 0)return;const s=I(e.fn.__lunoraRef,e.argsKey,e.shardKey),r=this.getConnection(e.shardKey)?.identity,i=r===void 0?this.identityFingerprint():r;i===null&&this.identityUnresolved()||(this.pendingCacheWrites.set(s,{identity:i,serverCursor:e.serverCursor,ts:Date.now(),value:t,...i===this.identityFingerprint()&&!this.subjectAwaitingReconfirm()?this.credentialStamp():{},...e.serverEpoch===void 0?{}:{serverEpoch:e.serverEpoch},...this.persistenceVersion===void 0?{}:{version:this.persistenceVersion}}),this.cacheFlushTimer??=setTimeout(()=>{this.flushQueryCacheWrites().catch(()=>{})},mt))}async flushQueryCacheWrites(){this.cacheFlushTimer=void 0;const{queryCache:e}=this;if(!e){this.pendingCacheWrites.clear();return}const t=[...this.pendingCacheWrites.entries()];this.pendingCacheWrites.clear(),await Promise.allSettled(t.map(async([s,r])=>e.put(s,r)))}computeStatus(){if(this.tabCoordinator&&!this.tabCoordinator.isLeader())return this.leaderStatus??"idle";const e=[...this.connections.values()];return e.length===0?"idle":e.some(t=>t.wsState==="open")?"connected":e.some(t=>t.polling.isPolling())?"polling":e.some(t=>t.wsState==="connecting")?"connecting":"offline"}baselineCursorFor(e){const t=l(e);let s;for(const r of this.subscriptions.all())l(r.shardKey)!==t||r.serverCursor===void 0||(s=s===void 0?r.serverCursor:Math.max(s,r.serverCursor));return s}async pollSubscriptions(e){const t=l(e),s=[];for(const a of this.subscriptions.all())l(a.shardKey)===t&&(pe(a.args)?s.push(a):w(a.errorCallbacks,{code:"WIRE_ENCODE_FAILED",message:"could not encode this subscription's args for a poll"}));if(s.length===0)return this.probeOrigin();const r=Me(),i=this.identityFingerprint();let n;try{n=await fe(async a=>this.sendBatch(s.map(o=>({args:o.args,fn:o.fn,shardKey:o.shardKey})),a))}catch(a){return!(a instanceof TypeError)}if(this.identityFingerprint()!==i)return!0;for(const[a,o]of s.entries()){const h=n[a];if(h!==void 0){if(!h.ok){w(o.errorCallbacks,{code:h.error.code,message:h.error.message});continue}this.handleDataMessage({data:L(h.value),id:o.id,type:"data"},r)}}return!0}async probeOrigin(){const{fetchImpl:e}=this;if(!e)return!1;try{return await fe(async t=>e(k(this.url,W),{body:JSON.stringify({calls:[]}),headers:this.rpcRequestHeaders({}),method:"POST",signal:t})),!0}catch{return!1}}emitConnectionStatus(){const e=this.computeStatus();e!==this.lastStatus&&(this.lastStatus=e,this.statusListeners.emit(e),this.tabCoordinator?.isLeader()&&this.tabCoordinator.broadcastConnectionStatus(e,this.identityFingerprint()))}emitItemSettled(e,t,s){this.mutationSettledListeners.emit({args:e.args,code:s===void 0?void 0:s.code,error:s,functionPath:e.functionPath,hadAwaiter:e.liveAwaiter??!1,id:e.id??"",shardKey:e.shardKey,status:t})}applyOptimisticUpdates(e,t,s,r){const i=[],n=[];if(!r)return{confirms:i,rollbacks:n};const a=C.key(e,t,s),o=this.subscriptions.get(a);if(o){const h=Re(o,r);h&&(i.push(h.confirm),n.push(h.rollback))}return{confirms:i,rollbacks:n}}applyOptimisticUpdate(e,t,s,r,i){const{confirms:n,rollbacks:a,store:o}=Pe(this.subscriptions,s);try{e(o,t)}catch{F(a);return}r.push(...a),i.push(...n)}getConnection(e){return this.connections.get(l(e))}sendOrQueueUnsubscribe(e,t,s){const r=this.getConnection(e);r&&!v(r,{id:t,type:s})&&r.pendingUnsubscribes.push({id:t,type:s})}connectionGateState(e){if(this.tabCoordinator&&!this.tabCoordinator.isLeader()){let r="idle";return this.leaderStatus==="connected"?r="open":this.leaderStatus==="connecting"&&(r="connecting"),{hasSocket:!1,idleClosed:!1,polling:this.leaderStatus==="polling",wasEverConnected:this.leaderWasEverConnected,wsState:r}}const t=this.getConnection(e),s=t===void 0&&this.idleClosedShards.has(l(e));return{hasSocket:t?.socket!==void 0,idleClosed:s,polling:t?.polling.isPolling()??!1,wasEverConnected:t?.wasEverConnected??s,wsState:t?.wsState??"idle"}}getOrCreateConnection(e){const t=l(e);let s=this.connections.get(t);return s||(s={connectTimer:void 0,heartbeatTimer:void 0,lastFrameAt:0,pendingUnsubscribes:[],polling:at({afterFailedAttempts:this.pollingFallbackAfterFailedAttempts,intervalMs:this.pollingFallbackIntervalMs,onReachable:()=>{this.flushOfflineQueue(e).catch(()=>{})},onStateChange:()=>{this.emitConnectionStatus()},poll:async()=>this.pollSubscriptions(e)}),reconnect:re(this.reconnectOptions),reconnectTimer:void 0,resubscribePending:new Map,resubscribeQueue:[],shardKey:e,socket:void 0,stableTimer:void 0,wasEverConnected:this.idleClosedShards.delete(t),wsState:"idle"},this.connections.set(t,s)),s}wsUrlFor(e,t){const s=[];if(e!==void 0&&s.push(`shard=${encodeURIComponent(e)}`),t!==void 0&&s.push(`token=${encodeURIComponent(t)}`),s.length===0)return this.wsUrl;const r=this.wsUrl.includes("?")?"&":"?";return`${this.wsUrl}${r}${s.join("&")}`}rpcRequestHeaders(e,t){const s={"content-type":"application/json"};e.expectSubject!==void 0&&(s[Je]=Ye(e.expectSubject));const r=this.shardCursors.get(this.cursorKeyFor(t));r!==void 0&&(s["x-lunora-min-seq"]=r.toString());const i=e.authToken===void 0?this.authToken:e.authToken;if(i&&(s.authorization=`Bearer ${i}`),e.mutationId&&(s["x-lunora-mutation-id"]=e.mutationId),(e.clientId!==void 0||e.mutationId!==void 0)&&(s["x-lunora-client-id"]=e.clientId??this.clientId),e.clientSeq!==void 0&&(s["x-lunora-client-seq"]=e.clientSeq.toString()),e.baselineSeq!==void 0&&(s["x-lunora-base-seq"]=e.baselineSeq.toString()),e.attachBookmark){const n=this.bookmark.get();n&&(s["x-d1-bookmark"]=n)}return s}async rpc(e,t,s,r={}){if(!this.fetchImpl)throw new te("LunoraClient: no `fetch` implementation available");const i=this.rpcRequestHeaders(r,s),n=r.authToken===void 0?this.authToken:r.authToken,a=await this.fetchImpl(k(this.url,ot),{body:JSON.stringify({args:E(t,`args for '${e}'`),functionPath:e,shardKey:s}),headers:i,method:"POST"});if(r.captureBookmark){const u=a.headers.get("x-d1-bookmark");u&&this.bookmark.set(u)}let o;try{o=await a.json()}catch{throw P(a.status,a.statusText,a.headers.get("retry-after"))}const h=o;if(typeof h!="object"||h===null||Array.isArray(h))throw P(a.status,a.statusText,a.headers.get("retry-after"));const d=M(o);if(d!==void 0)throw le(d,a.headers.get("retry-after"));if(!a.ok)throw P(a.status,a.statusText,a.headers.get("retry-after"));r.onMutationAck?.(o.lastMutationId),r.onCommitCursor?.(o.commitCursor),this.noteCredentialAccepted(n),this.learnDefaultShardKey(a,s),this.recordShardCursor(s,o.commitCursor);try{return g(o.result)}catch(u){throw ie(u)}}async adminFetch(e,t,s,r){if(!this.fetchImpl)throw new y("INTERNAL","LunoraClient: no `fetch` implementation available");const i={};this.authToken&&(i.authorization=`Bearer ${this.authToken}`);const n=s instanceof ArrayBuffer||s instanceof Blob;let a;s===void 0?a=void 0:n?(a=s,r!==void 0&&(i["content-type"]=r)):(a=JSON.stringify(s),i["content-type"]="application/json");const o=await this.fetchImpl(k(this.url,e),{body:a,headers:i,method:t});let h;try{h=await o.json()}catch{const u=o.statusText?` ${o.statusText}`:"";throw new y("INTERNAL",`LunoraClient: response was not JSON (status ${o.status.toString()}${u})`)}const d=M(h);if(d!==void 0){const u=new Error(d.message??"admin request failed");throw u.code=d.code,u}if(!o.ok){const u=o.statusText?` ${o.statusText}`:"";throw new y("INTERNAL",`LunoraClient: admin request failed (status ${o.status.toString()}${u})`)}return h}effectiveConnectionContext(e){const t=this.connectionContextHolders.get(e);return t&&t.length>0?t[t.length-1]?.context:this.connectionContexts.get(e)??this.defaultConnectionContext}refreshConnectionContext(e){const t=this.connections.get(e);t?.wsState==="open"&&this.sendConnectEnvelope(t)}sendConnectEnvelope(e){const t=this.effectiveConnectionContext(l(e.shardKey));v(e,{caps:Qs,clientId:this.clientId,id:"connect",type:"connect",...t===void 0?{}:{context:t}})}resendShapeSubscriptions(e){for(const t of this.shapeSubscriptions.values())l(t.shardKey)===l(e)&&this.sendShapeSubscribeIfOpen(t)}ensureSocket(e){if(this.closed||this.WebSocketImpl===void 0||this.tabCoordinator&&!this.tabCoordinator.isLeader())return;const t=this.getOrCreateConnection(e);if(!(t.wsState==="open"||t.wsState==="connecting")){if(t.wsState="connecting",this.emitConnectionStatus(),typeof this.wsToken=="function"){this.openSocketWithProvidedToken(t,e,this.wsToken).catch(()=>{});return}this.openSocket(t,e,this.wsToken)}}async openSocketWithProvidedToken(e,t,s){let r;try{r=await s()}catch{this.handleDisconnect(e);return}this.closed||this.WebSocketImpl===void 0||e.wsState!=="connecting"||e.socket!==void 0||this.openSocket(e,t,r)}openManagedSocket(e,t,s,r){const{WebSocketImpl:i}=this;if(i===void 0)throw new y("INTERNAL","no WebSocket implementation available");const n=new i(t);e.socket=n;const a=()=>{this.stopHeartbeat(e),e.connectTimer!==void 0&&(clearTimeout(e.connectTimer),e.connectTimer=void 0),e.socket===n&&(e.socket=void 0)},o=h=>{a(),r.onClose(h)};s>0&&(e.connectTimer=setTimeout(()=>{if(e.connectTimer=void 0,e.socket===n){try{n.close()}catch{}o()}},s)),n.addEventListener("open",()=>{if(e.socket===n){e.connectTimer!==void 0&&(clearTimeout(e.connectTimer),e.connectTimer=void 0),e.lastFrameAt=Date.now();try{r.onOpen?.()}catch(h){console.error("[lunora] connection open handler threw",h)}this.startHeartbeat(e,o)}}),n.addEventListener("message",h=>{if(e.socket===n){e.lastFrameAt=Date.now();try{r.onMessage(h)}catch(d){console.error("[lunora] server frame handler threw",d)}}}),n.addEventListener("close",h=>{e.socket===n&&o(h)}),n.addEventListener("error",()=>{e.socket===n&&o()})}openSocket(e,t,s){this.WebSocketImpl!==void 0&&(e.identity=this.identityFingerprint(),s===void 0&&this.authToken===null?(this.identityQuestions+=1,e.identityQuestion=this.identityQuestions):e.identityQuestion=void 0,e.retired=!1,this.openManagedSocket(e,this.wsUrlFor(t,s),this.connectTimeoutMs,{onClose:r=>{r?.code===4001&&this.notifyTokenExpired(),this.handleDisconnect(e)},onMessage:r=>{e.retired!==!0&&this.handleServerMessage(r.data,t)},onOpen:()=>{e.wsState="open",e.wasEverConnected=!0,e.polling.noteOpen(),clearTimeout(e.stableTimer),e.stableTimer=setTimeout(()=>{e.wsState==="open"&&e.reconnect.reset()},yt),this.emitConnectionStatus(),this.sendConnectEnvelope(e),this.markShardPendingAck(t),this.clearResubscribeQueue(e);for(const i of this.subscriptions.all())l(i.shardKey)===l(t)&&this.queueResubscribe(i);if(this.resendShapeSubscriptions(t),e.pendingUnsubscribes.length>0){const i=e.pendingUnsubscribes;e.pendingUnsubscribes=[];for(const{id:n,type:a}of i)v(e,{id:n,type:a});this.releaseIdleShard(t)}Ws(e);const r=this.whisperHandlers.get(l(t));if(r)for(const i of r.keys())v(e,{topic:i,type:"whisper_subscribe"});this.flushOfflineQueue(t).catch(()=>{})}}))}cancelStream(e,t){const s=this.getConnection(t);s&&(s.pendingStreams=s.pendingStreams?.filter(r=>r.id!==e),v(s,{id:e,type:"unsubscribe"})),this.forgetStream(e)}handleDisconnect(e){if(this.closed||e.wsState==="idle"||e.wsState==="closed")return;e.wsState==="connecting"&&e.polling.noteFailedOpen(),this.stopHeartbeat(e),this.clearConnectionTimers(e),e.socket=void 0,e.wsState="idle",this.emitConnectionStatus(),this.markShardPendingAck(e.shardKey),this.clearResubscribeQueue(e);const t=new Set((e.pendingStreams??[]).map(r=>r.id));for(const[r,i]of this.streams)if(!(l(i.shardKey)!==l(e.shardKey)||t.has(r))){if(i.durable){const n={...i.message,...i.generation===void 0?{}:{generation:i.generation},sinceChunk:i.lastSeq};i.message=n,e.pendingStreams=[...(e.pendingStreams??[]).filter(a=>a.id!==r),n];continue}i.handle.fail(new y("STREAM_DISCONNECTED","stream terminated: WebSocket disconnected")),this.forgetStream(r)}if(this.WebSocketImpl===void 0)return;const s=e.reconnect.next();e.reconnectTimer=setTimeout(()=>{e.reconnectTimer=void 0,this.ensureSocket(e.shardKey)},s)}startHeartbeat(e,t){this.stopHeartbeat(e),!(this.heartbeatIntervalMs<=0)&&(e.heartbeatTimer=setInterval(()=>{if(!e.socket)return;const{socket:s}=e;if(Date.now()-e.lastFrameAt>this.heartbeatIntervalMs*2.5){try{s.close()}catch{}t();return}try{s.send(dt)}catch{}},this.heartbeatIntervalMs))}stopHeartbeat(e){e.heartbeatTimer!==void 0&&(clearInterval(e.heartbeatTimer),e.heartbeatTimer=void 0)}markShardPendingAck(e){const t=l(e);for(const s of this.subscriptions.all())l(s.shardKey)===t&&(s.acked=!1)}queueResubscribe(e){const t=this.getConnection(e.shardKey);t&&(t.resubscribeQueue.push(e),this.drainResubscribeQueue(t))}drainResubscribeQueue(e){for(;e.resubscribePending.size<vt;){const t=e.resubscribeQueue.shift();if(!t)return;this.subscriptions.getById(t.id)&&this.sendSubscribeIfOpen(t)&&e.resubscribePending.set(t.id,setTimeout(()=>{this.releaseResubscribeSlot(e,t.id)},gt))}}releaseResubscribeSlot(e,t){const s=e.resubscribePending.get(t);s!==void 0&&(clearTimeout(s),e.resubscribePending.delete(t),this.drainResubscribeQueue(e))}clearResubscribeQueue(e){for(const t of e.resubscribePending.values())clearTimeout(t);e.resubscribePending.clear(),e.resubscribeQueue=[]}sendSubscribeIfOpen(e){const t=this.getConnection(e.shardKey);if(t?.wsState!=="open"||e.acked)return!1;const s=e.serverCursor!==void 0&&e.serverBase!==void 0;return v(t,{id:e.id,query:{args:e.wireArgs,functionPath:e.fn.__lunoraRef,table:e.fn.__lunoraRef,...s?{sinceSeq:e.serverCursor}:{},...s&&e.serverEpoch!==void 0?{sinceEpoch:e.serverEpoch}:{}},type:"subscribe"})}sendShapeSubscribeIfOpen(e){const t=this.getConnection(e.shardKey);t?.wsState==="open"&&v(t,{id:e.id,shape:{name:e.name,...e.wireArgs===void 0?{}:{args:e.wireArgs}},type:"shape_subscribe",...e.serverCursor===void 0?{}:{sinceCheckpoint:e.serverCursor},...e.serverEpoch===void 0?{}:{sinceEpoch:e.serverEpoch}})}handleServerMessage(e,t){const s=qs(e);if(s===void 0)return;let r;try{r=JSON.parse(s)}catch{return}if(r.type!=="error"&&this.getConnection(t)?.reconnect.reset(),typeof r.id=="string"){const i=this.getConnection(t);i&&this.releaseResubscribeSlot(i,r.id)}switch(r.type){case"ack":{const i=this.subscriptions.getById(r.id);i&&(i.acked=!0);return}case"chunk":{const{data:i,generation:n,id:a,seq:o}=r,h=this.streams.get(a);h&&typeof o=="number"&&(h.lastSeq=o,typeof n=="number"&&(h.generation=n),h.durable=!0),h?.handle.push(g(i));return}case"complete":{this.handleCompleteMessage(r.id);return}case"data":case"delta":{this.handleDataMessage(r);return}case"error":{this.handleErrorMessage(r);break}case"identity":{this.handleIdentityFrame(r,t);break}case"pokeEnd":{this.handlePokeEnd(r,t);break}case"pokePart":{this.handlePokePart(r,t);break}case"pokeStart":{this.handlePokeStart(r,t);break}case"resume":{this.handleResumeMessage(r);break}case"settled":{this.handleSettledMessage(r);break}case"whisper":{this.dispatchWhisper(r,t);break}}}handleErrorMessage(e){if(e.error?.code==="TOKEN_EXPIRED"){this.notifyTokenExpired();return}const{id:s}=e,r=s===void 0?void 0:this.streams.get(s);if(r&&s!==void 0){r.handle.fail(Ds(e)),this.forgetStream(s);return}const i=s===void 0?void 0:this.subscriptions.getById(s);if(i){const a=ue(e),o=this.identityFingerprint(),h=C.keyOf(i);w(i.errorCallbacks,a),this.tabCoordinator?.isLeader()&&this.tabCoordinator.broadcastSubscriptionError(h,a,o);return}const n=s===void 0?void 0:this.shapeSubscriptions.get(s);n&&w(n.errorCallbacks,ue(e))}pokeBufferKey(e,t){return`${l(e)}\0${t}`}handlePokeStart(e,t){ae(this.pokeBuffers,Se.MAX_POKE_BUFFERS),this.pokeBuffers.set(this.pokeBufferKey(t,e.pokeId),{baseCheckpoint:e.baseCheckpoint,bases:new Map,epoch:e.epoch,lastMutationId:new Map,parts:new Map,resets:new Set,undecodable:new Map})}handlePokePart(e,t){const s=this.pokeBuffers.get(this.pokeBufferKey(t,e.pokeId));if(!s)return;const r=[];try{for(const a of e.rowsPatch)r.push(a.value===void 0?a:{...a,value:g(a.value)})}catch(a){s.undecodable.set(e.shapeId,a);return}const i=s.parts.get(e.shapeId)??[];for(const a of r)i.push(a);s.parts.set(e.shapeId,i),e.lastMutationId!==void 0&&s.lastMutationId.set(e.shapeId,e.lastMutationId);const n=e.baseCheckpoint??s.baseCheckpoint;n!==void 0&&s.bases.set(e.shapeId,n),e.reset===!0&&s.resets.add(e.shapeId)}handlePokeEnd(e,t){const s=this.pokeBufferKey(t,e.pokeId),r=this.pokeBuffers.get(s);if(r){this.pokeBuffers.delete(s);for(const[i,n]of r.undecodable){const a=this.shapeSubscriptions.get(i);a&&w(a.errorCallbacks,{code:"WIRE_DECODE_FAILED",message:`could not decode a poke for this shape — ${n instanceof Error?n.message:String(n)}`})}for(const i of r.parts.keys()){const n=this.shapeSubscriptions.get(i);n&&!r.undecodable.has(i)&&this.applyPokePart(n,r,e)}}}applyPokePart(e,t,s){const r=t.parts.get(e.id)??[],i=t.resets.has(e.id),n=t.bases.get(e.id),a=t.epoch!==void 0&&e.serverEpoch!==void 0&&t.epoch!==e.serverEpoch,o=n!==void 0&&e.serverCursor!==void 0&&e.serverCursor!==n;if(!i&&(a||o)){e.rows.clear(),e.serverCursor=void 0,e.serverEpoch=void 0,this.emitShapeRows(e),this.sendShapeSubscribeIfOpen(e);return}i&&e.rows.clear(),ht(e.rows,r),s.checkpoint!==void 0&&(e.serverCursor=s.checkpoint),s.epoch!==void 0&&(e.serverEpoch=s.epoch);const h=t.lastMutationId.get(e.id);h!==void 0&&(e.lastMutationId=h),this.emitShapeRows(e),e.onCheckpoint?.({checkpoint:e.serverCursor,mutationId:e.lastMutationId})}resnapshotSubscription(e){e.acked=!1,e.serverCursor=void 0,e.serverEpoch=void 0,console.warn("[lunora] could not merge a row delta into the cached result; re-subscribing for a full snapshot"),this.sendSubscribeIfOpen(e)}emitShapeRows(e){const t=[...e.rows.values()];for(const s of e.callbacks)try{s(t)}catch{}}handleDataMessage(e,t){const{id:s}=e,r=s?this.subscriptions.getById(s):void 0;if(!r)return;let i;try{i=this.resolveDataPayload(e,r)}catch(n){w(r.errorCallbacks,{code:"WIRE_DECODE_FAILED",message:`could not decode a server frame for this subscription — ${n instanceof Error?n.message:String(n)}`});return}if(i===ce){this.resnapshotSubscription(r);return}if(r.serverBase=i,this.dropCacheSeed(C.keyOf(r)),e.cursor!==void 0&&(r.serverCursor=e.cursor),e.epoch!==void 0&&(r.serverEpoch=e.epoch),e.lastMutationId!==void 0){r.lastMutationId=Math.max(r.lastMutationId??0,e.lastMutationId);for(const n of r.checkpointCallbacks)n({checkpoint:r.serverCursor,mutationId:r.lastMutationId,rowsFollow:!0})}if(this.persistQueryValue(r),K(r,r.serverCursor),t!==void 0&&Fe(r,t),A(r,_(i,r.optimisticLayers)),this.tabCoordinator?.isLeader()){const n=C.keyOf(r);this.tabCoordinator.broadcastSubscriptionData(n,i,r.serverCursor,r.serverEpoch,this.identityFingerprint())}}handleResumeMessage(e){const t=this.subscriptions.getById(e.id);t&&this.ackAndAdvanceCursor(t,e.cursor,e.epoch)}handleSettledMessage(e){const t=this.subscriptions.getById(e.id);if(t){this.ackAndAdvanceCursor(t,e.cursor,e.epoch),e.lastMutationId!==void 0&&(t.lastMutationId=Math.max(t.lastMutationId??0,e.lastMutationId));for(const s of t.checkpointCallbacks)s({checkpoint:t.serverCursor,mutationId:t.lastMutationId});if(this.tabCoordinator?.isLeader()){const s=C.keyOf(t);this.tabCoordinator.broadcastSubscriptionSettled(s,t.serverCursor,t.serverEpoch,t.lastMutationId,this.clientId,this.identityFingerprint())}}}ackAndAdvanceCursor(e,t,s){e.acked=!0,(t!==void 0&&t!==e.serverCursor||s!==void 0&&s!==e.serverEpoch)&&(t!==void 0&&(e.serverCursor=t),s!==void 0&&(e.serverEpoch=s),this.persistQueryValue(e),K(e,e.serverCursor)&&A(e,_(e.serverBase,e.optimisticLayers)))}resolveDataPayload(e,t){if("data"in e&&e.data!==void 0)return g(e.data);const s=g(e.delta);return ke(s)?t.serverBase===void 0?s:we(t.serverBase,s)??ce:s}dispatchWhisper(e,t){const s=this.whisperHandlers.get(l(t))?.get(e.topic);if(!s)return;const r=g(e.data);for(const i of s)try{i(r,e.from)}catch{}}notifyTokenExpired(){this.tokenExpiredListeners.emit()}handleCompleteMessage(e){const t=this.streams.get(e);if(t){t.handle.complete(),this.forgetStream(e);return}const s=this.subscriptions.getById(e);s&&(s.acked=!1,w(s.errorCallbacks,{code:"SUBSCRIPTION_CANCELLED",message:"subscription was cancelled by the server"}))}unpersist(e){e&&this.persistence?.remove(e).catch(t=>{Ue(this.onPersistenceError,"remove",t,e)})}identityFingerprint(){if(this.authSubject!==void 0)return this.authSubject===null?null:`subj:${this.authSubject}`;const e=this.authToken;return e===null?null:this.hashToken(e)}hashToken(e){let t=2166136261,s=5381;for(let r=0;r<e.length;r+=1){const i=e.charCodeAt(r);t^=i,t=Math.imul(t,16777619),s=Math.imul(s,33)+i}return`${e.length.toString(36)}:${(t>>>0).toString(36)}:${(s>>>0).toString(36)}`}credentialStamp(){const e=this.authToken;return e===null?{}:{credential:this.hashToken(e)}}cachedQueryMatchesIdentity(e){return this.identityFingerprint()===null&&this.identityUnresolved()?!1:!this.subjectAwaitingReconfirm()&&e.identity===this.identityFingerprint()||this.isSameCredentialUnderTokenHash(e.identity)?!0:e.credential!==void 0&&e.credential===this.credentialStamp().credential}isSameCredentialUnderTokenHash(e){if(e===null||e.startsWith("subj:"))return!1;const t=this.authToken;return t===null?!1:this.hashToken(t)===e}releaseSessionProbe(){this.sessionProbesInFlight-=1,!(this.identityUnresolved()||this.identityFingerprint()!==null)&&!this.closed&&this.offlineQueue.size>0&&V(this.computeStatus())&&this.flushAllOfflineQueues()}identityUnresolved(){return this.sessionProbesInFlight>0?!0:this.identityResolutionExpected&&!this.identitySettled}adoptResolvedSubject(e,t,s){if(!(this.closed||this.authToken!==e||s!==this.sessionProbeGeneration)){if(e===null){this.adoptCookieSubject(t?.id??null,s);return}t!==null&&this.setAuthToken(e,t.id)}}adoptCookieSubject(e,t){return this.closed||this.authToken!==null||t<this.identityAnsweredAt?!1:(this.identityAnsweredAt=t,this.identitySettled=!0,this.setAuthToken(null,e),!0)}handleIdentityFrame(e,t){const s=this.getConnection(t)?.identityQuestion,{subject:r}=e;s===void 0||r!==null&&typeof r!="string"||this.adoptCookieSubject(r,s)||!this.closed&&this.authToken===null&&(r===null?null:`subj:${r}`)!==this.identityFingerprint()&&this.evictPreviousIdentitySession()}applySubject(e,t){if(t!==void 0){this.authSubject=t,this.subjectToken=e;return}(e===null&&this.authSubject!==null||e!==null&&this.authSubject===null)&&(this.authSubject=void 0,this.subjectToken=null)}isKnownNobody(){return this.authSubject===null&&this.authToken===null}subjectAwaitingReconfirm(){return this.authSubject!==void 0&&this.authSubject!==null&&this.subjectToken!==this.authToken}stampOf(e){const t=e.id===void 0?void 0:this.queuedIdentities.get(e.id);return t===void 0?e.identity:t}warnRefreshWithoutSubject(e,t){e===null||t===null||this.authSubject!==void 0||this.authRefusalNotifiedFor!==this.hashToken(e)||console.warn("[lunora] setAuthToken replaced a token that was just refused for a queued write, with no subject: without one a refresh reads as a user switch, so the held writes were discarded (OFFLINE_IDENTITY_CHANGED). Pass the user id, e.g. setAuthToken(token, user.id), to keep them across a refresh.")}rejectQueuedForIdentityChange(e){const t=this.offlineQueue.drain(),s=[];for(const r of t){if(this.identityVerdict(this.stampOf(r))!=="mismatch"){s.push(r);continue}this.queuedIdentities.delete(r.id??""),this.unpersist(r.id);const i=new Error("offline mutation discarded: auth identity changed before replay");i.code="OFFLINE_IDENTITY_CHANGED",r.reject(i),this.emitItemSettled(r,"rejected",i)}this.offlineQueue.requeue(s),e!==null&&this.clearQueryCacheForIdentityChange()}restampConnectionIdentity(e,t){for(const s of this.connections.values())s.identity===e&&(s.identity=t)}restampQueuedIdentity(e,t){for(const[s,r]of this.queuedIdentities)r===e&&this.queuedIdentities.set(s,t);this.offlineQueue.restampIdentity(e,t)}restampWatermarks(e,t){const s=e??"",r=this.clientWatermarks.get(s);if(r===void 0)return;this.clientWatermarks.delete(s);const i=t??"",n=this.clientWatermarks.get(i);if(n===void 0)this.clientWatermarks.set(i,r);else for(const[a,o]of r)n.set(a,o)}clearQueryCacheForIdentityChange(){this.revokeCacheSeededValues(),this.cacheFlushTimer!==void 0&&(clearTimeout(this.cacheFlushTimer),this.cacheFlushTimer=void 0),this.pendingCacheWrites.clear(),this.hydratedQueryCache.clear(),this.queryCache?.clear().catch(()=>{})}evictPreviousIdentitySession(){this.revokeCacheSeededValues();for(const e of this.subscriptions.all())e.serverBase=void 0,e.serverCursor=void 0,e.serverEpoch=void 0,e.acked=!1,A(e,_(void 0,e.optimisticLayers));for(const e of this.shapeSubscriptions.values())e.rows.clear(),e.serverCursor=void 0,e.serverEpoch=void 0,this.emitShapeRows(e);this.bounceShardSockets(),this.retiredIdentities+=1,this.identityChangeListeners.emit()}restartTabCoordinatorForIdentity(){if(!this.tabCoordinator)return;const e=this.tabCoordinator.isLeader();this.tabCoordinator.stop(),this.tabCoordinator=this.createTabCoordinator(),this.tabCoordinator.start(),e&&this.tabCoordinator.promoteImmediately()}bounceShardSockets(){for(const e of this.connections.values())if(e.socket){e.retired=!0;try{e.socket.close()}catch{}}}flushAllOfflineQueues(){for(const e of this.queuedOfflineShardKeys)this.flushOfflineQueue(e).catch(()=>{})}async flushOfflineQueue(e){const t=l(e),s=this.offlineFlushes.get(t);if(s===void 0&&this.offlineQueue.size===0)return;const r=(async()=>{await(s??Promise.resolve());const{authToken:i}=this;try{await this.drainOfflineQueue(e,i)}catch{}!this.closed&&this.authToken!==i&&this.offlineQueue.size>0&&V(this.computeStatus())&&this.flushOfflineQueue(e).catch(()=>{})})();this.offlineFlushes.set(t,r),await r,this.offlineFlushes.get(t)===r&&(this.offlineFlushes.delete(t),this.releaseIdleShard(e))}async drainOfflineQueue(e,t){const s=this.offlineQueue.drainConflict();for(const d of s){this.unpersist(d.id),this.queuedIdentities.delete(d.id??"");const u=new Error("offline mutation skipped: precondition failed before replay");u.code="OFFLINE_PRECONDITION_FAILED",this.emitItemSettled(d,"rejected",u)}const r=l(e),i=this.offlineQueue.drain(d=>l(d.shardKey)===r);if(i.length===0)return;const n=[],a=[];for(const d of i){const u=this.replayGateVerdict(d);u==="send"?n.push(d):u==="hold"&&a.push(d)}if(this.offlineQueue.requeue(a),a.length>0&&this.subjectAwaitingReconfirm()&&(this.getCurrentUser().catch(()=>{}),this.noteHeldRetryDelay(e)),n.length===0){this.scheduleRateLimitedRetry(e);return}const o=this.encodableOrSettleTerminal(n);if(o.length===0){this.scheduleRateLimitedRetry(e);return}if(o.length===1){await this.replaySequential(o,e,t),this.scheduleRateLimitedRetry(e);return}const h=[];for(let d=0;d<o.length;d+=q){const u=o.slice(d,d+q),f=await this.replayBatched(u,e,t);if(h.push(...f.requeue),f.stop){h.push(...o.slice(d+q));break}}h.length>0&&this.offlineQueue.requeue(h),this.scheduleRateLimitedRetry(e)}noteHeldRetryDelay(e){const t=l(e),s=this.replayRetryState.get(t),r=(s?.attempts??0)+1;this.replayRetryState.set(t,{attempts:r,delayMs:Math.max(s?.delayMs??0,ne(r))})}noteReplayRetryDelay(e,t,s){const r=l(e),i=this.replayRetryState.get(r),n=(i?.attempts??0)+1,a=Be(t,n)??(s===null&&D(t)?ne(n):void 0);this.replayRetryState.set(r,{attempts:n,delayMs:a===void 0?i?.delayMs:Math.max(i?.delayMs??0,a)})}scheduleRateLimitedRetry(e){const t=l(e),s=this.replayRetryState.get(t),r=s?.delayMs;if(s===void 0||r===void 0||this.closed||this.offlineQueue.size===0){this.replayRetryState.delete(t);return}s.delayMs=void 0;const i=this.replayRetryTimers.get(t);i!==void 0&&clearTimeout(i),this.replayRetryTimers.set(t,setTimeout(()=>{this.replayRetryTimers.delete(t),this.flushOfflineQueue(e).catch(()=>{})},r))}encodableOrSettleTerminal(e){const t=[];for(const s of e)try{E(s.args,`args for '${s.functionPath}'`),t.push(s)}catch(r){this.settleReplayTerminal(s,r instanceof Error?r:new Error(String(r)))}return t}identityVerdict(e){if(this.subjectAwaitingReconfirm())return"unknown";const t=this.identityFingerprint();return t===null&&this.identityUnresolved()?"unknown":e===t||e!==void 0&&this.isSameCredentialUnderTokenHash(e)?"match":t===null?"unknown":"mismatch"}replayGateVerdict(e){const t=this.stampOf(e);if(t===void 0)return this.queuedIdentities.delete(e.id??""),"send";const s=this.identityVerdict(t);if(s==="unknown")return"hold";if(this.queuedIdentities.delete(e.id??""),s==="match")return"send";this.unpersist(e.id);const r=new Error("offline mutation skipped: auth identity changed before replay");return r.code="OFFLINE_IDENTITY_CHANGED",e.reject(r),this.emitItemSettled(e,"rejected",r),"reject"}settleReplaySuccess(e,t,s){this.unpersist(e.id),this.recordShardCursor(e.shardKey,s),e.onCommit?.(s),e.resolve(t),this.emitItemSettled(e,"committed")}cursorKeyFor(e){return e??this.defaultShardKey??""}learnDefaultShardKey(e,t){const s=e.headers.get("x-lunora-shard-key");if(s===null||t!==void 0||this.defaultShardKey===s)return;this.defaultShardKey=s;const r=this.shardCursors.get("");r!==void 0&&(this.shardCursors.set(s,Math.max(this.shardCursors.get(s)??0,r)),this.shardCursors.delete(""))}recordShardCursor(e,t){if(typeof t!="number")return;const s=this.cursorKeyFor(e);this.shardCursors.set(s,Math.max(this.shardCursors.get(s)??0,t))}shouldRequeueReplayFailure(e,t){return this.noteIdentityMismatch(e)?!0:this.noteReplayAuthRefusal(e,t)||Qe(e)}noteReplayAuthRefusal(e,t){if(!D(e))return!1;const s=this.hashToken(t??"");return t===this.authToken&&this.authRefusalNotifiedFor!==s&&(this.authRefusalNotifiedFor=s,this.notifyTokenExpired()),!0}noteCredentialAccepted(e){this.authRefusalNotifiedFor!==void 0&&this.authRefusalNotifiedFor===this.hashToken(e??"")&&(this.authRefusalNotifiedFor=void 0)}takeReplayCredential(e){if(e===void 0)return;const t=this.replayCredentials.get(e);if(t===void 0)throw new TypeError("LunoraClient: `replayCredential` must come from this client's `replayIdentityVerdict`, and is single use");return this.replayCredentials.delete(e),{flags:{authToken:t.authToken,...Y(t.stamp,t.authToken)},stamp:t.stamp}}noteIdentityMismatch(e){if(e?.code!=="IDENTITY_MISMATCH")return!1;const t=this.identityFingerprint();return this.getCurrentUser().then(()=>{!this.warnedIdentityDisagreement&&this.identityFingerprint()===t&&(this.warnedIdentityDisagreement=!0,console.warn('[lunora] a replayed write was refused with IDENTITY_MISMATCH, but `/get-session` still names the same user. The worker\'s `resolveIdentity` must return the same `userId` as the better-auth `user.id`, and RPC requests must carry the session cookie (`credentials: "include"` on a cross-origin fetch).'))}).catch(()=>{}),!0}settleReplayUndecodable(e,t,s){this.unpersist(e.id),this.recordShardCursor(e.shardKey,s),e.onCommit?.(s),e.reject(t),this.emitItemSettled(e,"committed",t)}settleReplayTerminal(e,t){this.unpersist(e.id),e.reject(t),this.emitItemSettled(e,"rejected",t)}async replaySequential(e,t,s){for(let r=0;r<e.length;r+=1){const i=e[r];if(!i)continue;let n;try{const a=await this.rpc(i.functionPath,i.args,i.shardKey,{authToken:s,baselineSeq:i.baselineSeq,captureBookmark:!0,clientId:i.clientId??this.clientId,...Y(i.identity,s),mutationId:i.id,onCommitCursor:o=>{n=o}});this.settleReplaySuccess(i,a,n)}catch(a){if(U(a)){this.settleReplayUndecodable(i,a,n);continue}if(!this.shouldRequeueReplayFailure(a,s)){this.settleReplayTerminal(i,a);continue}this.noteReplayRetryDelay(t,a,s),this.offlineQueue.requeue(e.slice(r));return}}}async replayBatched(e,t,s){if(!this.fetchImpl)return{requeue:e,stop:!0};const r=JSON.stringify({calls:e.map((h,d)=>({args:E(h.args,`args for '${h.functionPath}'`),baselineSeq:h.baselineSeq,functionPath:h.functionPath,id:d,clientId:h.clientId??this.clientId,mutationId:h.id,shardKey:h.shardKey}))});if(e.length>1&&De(r)>Ke)return await this.replayBatchedHalves(e,t,s);let i;try{i=await this.fetchImpl(k(this.url,W),{body:r,headers:this.rpcRequestHeaders({attachBookmark:!0,authToken:s,...Y(e.find(h=>h.identity!==void 0)?.identity,s)}),method:"POST"})}catch{return{requeue:e,stop:!0}}const n=i.headers.get("x-d1-bookmark");if(n&&this.bookmark.set(n),i.status===413&&e.length>1)return await this.replayBatchedHalves(e,t,s);let a;const o=i.headers.get("retry-after");try{a=await i.json()}catch{return this.settleWholeBatchError(e,P(i.status,i.statusText,o),t,s)}if(!a.results){const h=M(a),d=h===void 0?P(i.status,i.statusText,o):le(h,o);return this.settleWholeBatchError(e,d,t,s)}return{requeue:this.settleReplayBatchSlots(e,a.results,t,s),stop:!1}}settleWholeBatchError(e,t,s,r){if(t instanceof te||t.code!==void 0&&this.shouldRequeueReplayFailure(t,r))return this.noteReplayRetryDelay(s,t,r),{requeue:e,stop:!0};for(const i of e)this.settleReplayTerminal(i,t);return{requeue:[],stop:!1}}async replayBatchedHalves(e,t,s){const r=Math.ceil(e.length/2),i=await this.replayBatched(e.slice(0,r),t,s);if(i.stop)return{requeue:[...i.requeue,...e.slice(r)],stop:!0};const n=await this.replayBatched(e.slice(r),t,s);return{requeue:[...i.requeue,...n.requeue],stop:n.stop}}settleReplayBatchSlots(e,t,s,r){const i=new Map;for(const h of t)typeof h.id=="number"&&h.body!==void 0&&i.set(h.id,h.body);const n=[];let a=!1,o=!1;for(const[h,d]of e.entries()){const u=i.get(h);if(u===void 0)n.push(d);else if("error"in u){const f=be(u);o||=D(f),this.shouldRequeueReplayFailure(f,r)?(this.noteReplayRetryDelay(s,f,r),n.push(d)):this.settleReplayTerminal(d,f)}else a=!0,this.settleReplayBatchResult(d,u)}return a&&!o&&this.noteCredentialAccepted(r),n}settleReplayBatchResult(e,t){let s;try{s=g(t.result)}catch(r){this.settleReplayUndecodable(e,ie(r),t.commitCursor);return}this.settleReplaySuccess(e,s,t.commitCursor)}}export{Se as LunoraClient};
@@ -1 +1 @@
1
- import{LunoraClient as r}from"./LunoraClient-BWZ8TiRn.mjs";const c=e=>{const t=new r({fetch:e.fetch,url:e.url});return e.token!==void 0&&t.setAuthToken(e.token),t};export{c as createServerClient};
1
+ import{LunoraClient as r}from"./LunoraClient-B9s5sUe6.mjs";const c=e=>{const t=new r({fetch:e.fetch,url:e.url});return e.token!==void 0&&t.setAuthToken(e.token),t};export{c as createServerClient};
@@ -2456,6 +2456,16 @@ declare class LunoraClient {
2456
2456
  * identity from the cookie/token in effect); use this to refresh a
2457
2457
  * short-lived token first — e.g. call {@link setWsToken} / {@link setAuthToken}
2458
2458
  * with a freshly minted one. Returns an unsubscribe function.
2459
+ *
2460
+ * Also fired, once per credential, when a queued write's replay is refused
2461
+ * `TOKEN_EXPIRED` / `UNAUTHENTICATED`. The write is held for the refresh, and
2462
+ * survives it only if the identity is keyed on a `subject`: pass the same user
2463
+ * id with the new token, `setAuthToken(freshToken, user.id)` (or have passed
2464
+ * it before — the subject is sticky). With no subject the identity is the
2465
+ * token hash, so a refresh cannot be told from an account switch and the held
2466
+ * writes are rejected `OFFLINE_IDENTITY_CHANGED`. A cookie session has no
2467
+ * token to replace: renew the cookie, and the held write is re-sent on a
2468
+ * backoff with it.
2459
2469
  */
2460
2470
  onTokenExpired(listener: () => void): Unsubscribe;
2461
2471
  /**
@@ -4305,6 +4315,14 @@ declare class LunoraClient {
4305
4315
  * must not collapse into `undefined` — hence `=== undefined`, not `??`.
4306
4316
  */
4307
4317
  private stampOf;
4318
+ /**
4319
+ * Warn when a token refused for a queued write is replaced with no subject
4320
+ * keyed: the likely refresh reads as a user switch, so the writes it was
4321
+ * meant to rescue were just rejected `OFFLINE_IDENTITY_CHANGED`. Dropping is
4322
+ * the safe default — a refresh and an account switch look the same without
4323
+ * a subject — so this only says how to keep them.
4324
+ */
4325
+ private warnRefreshWithoutSubject;
4308
4326
  /**
4309
4327
  * Reject the in-memory offline writes that can no longer replay under the
4310
4328
  * identity now signed in, dropping their durable records so a later
@@ -4472,6 +4490,11 @@ declare class LunoraClient {
4472
4490
  * wait, so the drain can honour it before trying again
4473
4491
  * ({@link LunoraClient.replayRetryState}). Counts the attempt either way:
4474
4492
  * that is what a hintless refusal backs off on.
4493
+ *
4494
+ * A credential refused under a cookie session (`authToken === null`) backs
4495
+ * off on the hintless ramp too. A bearer refusal waits for `setAuthToken`,
4496
+ * which re-flushes; a cookie is renewed in the browser, invisibly to this
4497
+ * client, so the only way to learn it was is to send again.
4475
4498
  */
4476
4499
  private noteReplayRetryDelay;
4477
4500
  /**
@@ -4589,6 +4612,13 @@ declare class LunoraClient {
4589
4612
  * spurious.
4590
4613
  */
4591
4614
  private noteReplayAuthRefusal;
4615
+ /**
4616
+ * A request under `authToken` succeeded: if a refusal of that credential was
4617
+ * reported, its next refusal is news again. A bearer re-arms by changing; a
4618
+ * cookie session's `null` never does, so without this the app could be asked
4619
+ * to refresh a cookie only once per page.
4620
+ */
4621
+ private noteCredentialAccepted;
4592
4622
  /**
4593
4623
  * Redeem a {@link ReplayCredential} (single use) into the request flags it
4594
4624
  * pins (the judged bearer, and the subject a cookie replay names) and the
@@ -2456,6 +2456,16 @@ declare class LunoraClient {
2456
2456
  * identity from the cookie/token in effect); use this to refresh a
2457
2457
  * short-lived token first — e.g. call {@link setWsToken} / {@link setAuthToken}
2458
2458
  * with a freshly minted one. Returns an unsubscribe function.
2459
+ *
2460
+ * Also fired, once per credential, when a queued write's replay is refused
2461
+ * `TOKEN_EXPIRED` / `UNAUTHENTICATED`. The write is held for the refresh, and
2462
+ * survives it only if the identity is keyed on a `subject`: pass the same user
2463
+ * id with the new token, `setAuthToken(freshToken, user.id)` (or have passed
2464
+ * it before — the subject is sticky). With no subject the identity is the
2465
+ * token hash, so a refresh cannot be told from an account switch and the held
2466
+ * writes are rejected `OFFLINE_IDENTITY_CHANGED`. A cookie session has no
2467
+ * token to replace: renew the cookie, and the held write is re-sent on a
2468
+ * backoff with it.
2459
2469
  */
2460
2470
  onTokenExpired(listener: () => void): Unsubscribe;
2461
2471
  /**
@@ -4305,6 +4315,14 @@ declare class LunoraClient {
4305
4315
  * must not collapse into `undefined` — hence `=== undefined`, not `??`.
4306
4316
  */
4307
4317
  private stampOf;
4318
+ /**
4319
+ * Warn when a token refused for a queued write is replaced with no subject
4320
+ * keyed: the likely refresh reads as a user switch, so the writes it was
4321
+ * meant to rescue were just rejected `OFFLINE_IDENTITY_CHANGED`. Dropping is
4322
+ * the safe default — a refresh and an account switch look the same without
4323
+ * a subject — so this only says how to keep them.
4324
+ */
4325
+ private warnRefreshWithoutSubject;
4308
4326
  /**
4309
4327
  * Reject the in-memory offline writes that can no longer replay under the
4310
4328
  * identity now signed in, dropping their durable records so a later
@@ -4472,6 +4490,11 @@ declare class LunoraClient {
4472
4490
  * wait, so the drain can honour it before trying again
4473
4491
  * ({@link LunoraClient.replayRetryState}). Counts the attempt either way:
4474
4492
  * that is what a hintless refusal backs off on.
4493
+ *
4494
+ * A credential refused under a cookie session (`authToken === null`) backs
4495
+ * off on the hintless ramp too. A bearer refusal waits for `setAuthToken`,
4496
+ * which re-flushes; a cookie is renewed in the browser, invisibly to this
4497
+ * client, so the only way to learn it was is to send again.
4475
4498
  */
4476
4499
  private noteReplayRetryDelay;
4477
4500
  /**
@@ -4589,6 +4612,13 @@ declare class LunoraClient {
4589
4612
  * spurious.
4590
4613
  */
4591
4614
  private noteReplayAuthRefusal;
4615
+ /**
4616
+ * A request under `authToken` succeeded: if a refusal of that credential was
4617
+ * reported, its next refusal is news again. A bearer re-arms by changing; a
4618
+ * cookie session's `null` never does, so without this the app could be asked
4619
+ * to refresh a cookie only once per page.
4620
+ */
4621
+ private noteCredentialAccepted;
4592
4622
  /**
4593
4623
  * Redeem a {@link ReplayCredential} (single use) into the request flags it
4594
4624
  * pins (the judged bearer, and the subject a cookie replay names) and the
@@ -1,4 +1,4 @@
1
- import { L as LunoraClient, P as Preloaded } from "./lunora-client.d-Drc1BNio.js";
1
+ import { L as LunoraClient, P as Preloaded } from "./lunora-client.d-C1obXESH.js";
2
2
  import { F as FunctionReference, A as ArgsOf, R as ReturnOf } from "./function-reference.d-Br_hsKje.js";
3
3
  /**
4
4
  * Run a query once on the server (during SSR) and capture its result in a
@@ -1,4 +1,4 @@
1
- import { L as LunoraClient, P as Preloaded } from "./lunora-client.d-DuKXBo1d.mjs";
1
+ import { L as LunoraClient, P as Preloaded } from "./lunora-client.d-D1vYlx1k.mjs";
2
2
  import { F as FunctionReference, A as ArgsOf, R as ReturnOf } from "./function-reference.d-Br_hsKje.mjs";
3
3
  /**
4
4
  * Run a query once on the server (during SSR) and capture its result in a
@@ -1,4 +1,4 @@
1
- import { S as SubscriptionError, L as LunoraClient, a as Unsubscribe } from "../packem_shared/lunora-client.d-DuKXBo1d.mjs";
1
+ import { S as SubscriptionError, L as LunoraClient, a as Unsubscribe } from "../packem_shared/lunora-client.d-D1vYlx1k.mjs";
2
2
  export type {
3
3
  /**
4
4
  * `@lunora/client/query` — the framework-neutral live-query state machine shared
@@ -10,7 +10,7 @@ export type {
10
10
  * framework — each adapter supplies thin sinks that write into its own ref /
11
11
  * store / signal / cache.
12
12
  */
13
- b as SubscriptionErrorCallback } from "../packem_shared/lunora-client.d-DuKXBo1d.mjs";
13
+ b as SubscriptionErrorCallback } from "../packem_shared/lunora-client.d-D1vYlx1k.mjs";
14
14
  import { F as FunctionReference, A as ArgsOf, R as ReturnOf } from "../packem_shared/function-reference.d-Br_hsKje.mjs";
15
15
  import '@lunora/errors';
16
16
  import '@lunora/runtime';
@@ -1,4 +1,4 @@
1
- import { S as SubscriptionError, L as LunoraClient, a as Unsubscribe } from "../packem_shared/lunora-client.d-Drc1BNio.js";
1
+ import { S as SubscriptionError, L as LunoraClient, a as Unsubscribe } from "../packem_shared/lunora-client.d-C1obXESH.js";
2
2
  export type {
3
3
  /**
4
4
  * `@lunora/client/query` — the framework-neutral live-query state machine shared
@@ -10,7 +10,7 @@ export type {
10
10
  * framework — each adapter supplies thin sinks that write into its own ref /
11
11
  * store / signal / cache.
12
12
  */
13
- b as SubscriptionErrorCallback } from "../packem_shared/lunora-client.d-Drc1BNio.js";
13
+ b as SubscriptionErrorCallback } from "../packem_shared/lunora-client.d-C1obXESH.js";
14
14
  import { F as FunctionReference, A as ArgsOf, R as ReturnOf } from "../packem_shared/function-reference.d-Br_hsKje.js";
15
15
  import '@lunora/errors';
16
16
  import '@lunora/runtime';
@@ -1,4 +1,4 @@
1
- import { P as Preloaded, L as LunoraClient } from "../packem_shared/lunora-client.d-DuKXBo1d.mjs";
1
+ import { P as Preloaded, L as LunoraClient } from "../packem_shared/lunora-client.d-D1vYlx1k.mjs";
2
2
  export type { A as ArgsOf, F as FunctionReference, R as ReturnOf } from "../packem_shared/function-reference.d-Br_hsKje.mjs";
3
3
  export {
4
4
  /**
@@ -20,7 +20,7 @@ p as preloadQuery,
20
20
  * WebSocket or touches a UI framework, so it is safe to import from any SSR
21
21
  * loader.
22
22
  */
23
- a as preloadedQueryResult } from "../packem_shared/preload.d-DgOAB0eA.mjs";
23
+ a as preloadedQueryResult } from "../packem_shared/preload.d-CZ9D2dq9.mjs";
24
24
  import '@lunora/errors';
25
25
  import '@lunora/runtime';
26
26
  /**
@@ -1,4 +1,4 @@
1
- import { P as Preloaded, L as LunoraClient } from "../packem_shared/lunora-client.d-Drc1BNio.js";
1
+ import { P as Preloaded, L as LunoraClient } from "../packem_shared/lunora-client.d-C1obXESH.js";
2
2
  export type { A as ArgsOf, F as FunctionReference, R as ReturnOf } from "../packem_shared/function-reference.d-Br_hsKje.js";
3
3
  export {
4
4
  /**
@@ -20,7 +20,7 @@ p as preloadQuery,
20
20
  * WebSocket or touches a UI framework, so it is safe to import from any SSR
21
21
  * loader.
22
22
  */
23
- a as preloadedQueryResult } from "../packem_shared/preload.d-DXQqsalx.js";
23
+ a as preloadedQueryResult } from "../packem_shared/preload.d-Bn2hWjKv.js";
24
24
  import '@lunora/errors';
25
25
  import '@lunora/runtime';
26
26
  /**
@@ -1 +1 @@
1
- import{getServerSession as o}from"../packem_shared/getServerSession-BaOoo1p6.mjs";import{deserializePreloaded as l,serializePreloaded as t}from"../packem_shared/deserializePreloaded-Bffy70Wm.mjs";import{createServerClient as i}from"../packem_shared/createServerClient-Bc5veLJ4.mjs";import{preloadQuery as s,preloadedQueryResult as f}from"../packem_shared/preloadQuery-uFy24PCR.mjs";export{i as createServerClient,l as deserializePreloaded,o as getServerSession,s as preloadQuery,f as preloadedQueryResult,t as serializePreloaded};
1
+ import{getServerSession as o}from"../packem_shared/getServerSession-BaOoo1p6.mjs";import{deserializePreloaded as l,serializePreloaded as t}from"../packem_shared/deserializePreloaded-Bffy70Wm.mjs";import{createServerClient as i}from"../packem_shared/createServerClient-BR1Di-tY.mjs";import{preloadQuery as s,preloadedQueryResult as f}from"../packem_shared/preloadQuery-uFy24PCR.mjs";export{i as createServerClient,l as deserializePreloaded,o as getServerSession,s as preloadQuery,f as preloadedQueryResult,t as serializePreloaded};
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@lunora/client",
3
- "version": "1.0.0-alpha.156",
3
+ "version": "1.0.0-alpha.158",
4
4
  "description": "Lunora browser SDK: WebSocket transport, optimistic updates, and an offline mutation queue",
5
5
  "keywords": [
6
6
  "cloudflare",
@@ -70,7 +70,7 @@
70
70
  "access": "public"
71
71
  },
72
72
  "dependencies": {
73
- "@lunora/errors": "1.0.0-alpha.46",
73
+ "@lunora/errors": "1.0.0-alpha.47",
74
74
  "@visulima/storage-client": "1.0.3"
75
75
  },
76
76
  "peerDependencies": {
@@ -1 +0,0 @@
1
- class r{swUrl;scope;#e=void 0;#r="unregistered";#i;#s=new Set;constructor(e){this.swUrl=e.swUrl,this.scope=e.scope??"/",this.#i=e.onStatusChange}get status(){return this.#r}get registration(){return this.#e}get active(){return this.#e?.active!==null&&this.#e?.active!==void 0}async register(){if(!("serviceWorker"in navigator))return this.#t("unsupported"),!1;this.#t("registering");try{this.#e=await navigator.serviceWorker.register(this.swUrl,{scope:this.scope}),this.#t("active"),navigator.serviceWorker.addEventListener("message",this.#a)}catch{return this.#t("error"),!1}return!0}async unregister(){if(!this.#e)return!1;navigator.serviceWorker.removeEventListener("message",this.#a);const e=await this.#e.unregister();return this.#e=void 0,this.#t("unregistered"),e}postMessage(e){const t=this.#e?.active;t&&t.postMessage(e)}onMessage(e){return this.#s.add(e),()=>{this.#s.delete(e)}}#t(e){this.#r=e,this.#i?.(e)}#a=e=>{for(const t of this.#s)try{t(e)}catch{}}}export{r as ClientServiceWorker};
@@ -1 +0,0 @@
1
- import{LunoraError as y}from"@lunora/errors";import{t as ge,e as L,d as g}from"./wire-codec-BeIi1K-T.mjs";import{i as Te,a as Ce,P as ke}from"./delta-merge-D_5ChS-C.mjs";import{s as Z}from"./wire-key-DCPYV4t8.mjs";import we from"./createInMemoryBookmarkStorage-BooZhW0n.mjs";import{ClientQueryStore as Ee}from"./createClientQuery-B8Nfj-7o.mjs";import{TabCoordinator as Ae}from"./TabCoordinator-CXD7vulJ.mjs";import{TransportError as ee,isAuthReplayFailure as _e}from"./CONFLICT_ERROR_CODE-B7qNZMMk.mjs";import{httpStream as Ie}from"./httpStream-v4etRV7m.mjs";import{d as D,n as A,f as _,a as Oe,c as Re,b as Pe,e as Fe}from"./local-store-DDppw8Qr.mjs";import{O as Me,n as te,i as Le,r as He}from"./offline-queue-D_fr-uQ3.mjs";import{resolvePersistenceAdapter as Ue}from"./createInMemoryPersistence-Cz2W6XVj.mjs";import{resolveQueryCacheAdapter as xe,queryCacheKey as I}from"./createInMemoryQueryCache-D2uNHLfM.mjs";import{createReconnect as se}from"./createReconnect-CjTmjJDH.mjs";import{i as U,e as M,u as P,a as re,d as Ne,r as Be,b as Qe,c as De,M as Ke,f as qe,g as We}from"./replay-CXXDZ1_h.mjs";import $e from"./createSnapshotPrecondition-5GQ_5fFu.mjs";import{createStream as je}from"./DEFAULT_MAX_BUFFER-D3QH2iaq.mjs";import{SubscriptionRegistry as C}from"./SubscriptionRegistry-C3kLqped.mjs";const K=500,Ge=async c=>{const e=[];let t;for(;;){const s=await c(t);if(e.push(...Array.isArray(s.records)?s.records:[]),s.truncated!==!0||typeof s.cursor!="string"||s.cursor.length===0)return e;if(s.cursor===t)throw new Error("collectPages: the list did not advance its cursor — refusing to page forever");t=s.cursor}},ie=(c,e)=>{if(c.size<e)return;const t=c.keys().next().value;t!==void 0&&c.delete(t)};new TextDecoder;const Ve=new TextEncoder,ze=c=>ge(Ve.encode(JSON.stringify(c))),Je="x-lunora-expect-subject",Ye=c=>ze({subject:c}),ne=Symbol.for("lunora:session-change"),Xe="lunora:session-change",Ze="better-auth.message",et="signout",fe=()=>{const c=globalThis;let e=c[ne];return e===void 0&&(e={detach:void 0,listeners:new Set,tab:`${Date.now().toString(36)}-${Math.random().toString(36).slice(2)}`},c[ne]=e),e},tt=()=>"document"in globalThis,st=async()=>{const c=[];for(const e of fe().listeners)try{c.push(e())}catch{}await Promise.allSettled(c)},rt=(c,e)=>{if(c!==Ze||e===null)return!1;try{const t=JSON.parse(e);return t?.event==="session"&&t.data?.trigger===et}catch{return!1}},it=c=>{const e=[],t=()=>{st().catch(()=>{})};let s;try{s=typeof BroadcastChannel=="function"?new BroadcastChannel(Xe):void 0}catch{s=void 0}if(s!==void 0){const i=s;i.addEventListener("message",n=>{n.data?.type==="lunora:session-change"&&n.data.tab!==c&&t()}),e.push(()=>{i.close()})}const r=globalThis;if(typeof r.addEventListener=="function"){const i=n=>{rt(n.key,n.newValue)&&t()};r.addEventListener("storage",i),e.push(()=>{r.removeEventListener?.("storage",i)})}return()=>{for(const i of e)i()}},nt=c=>{const e=fe();return e.listeners.add(c),e.detach===void 0&&tt()&&(e.detach=it(e.tab)),()=>{e.listeners.delete(c),e.listeners.size===0&&(e.detach?.(),e.detach=void 0)}};class O{listeners=new Set;add(e){return this.listeners.add(e),()=>{this.listeners.delete(e)}}emit(...e){const[t]=e;for(const s of this.listeners)try{s(t)}catch{}}clear(){this.listeners.clear()}}const at=c=>{const{afterFailedAttempts:e,intervalMs:t,onReachable:s,onStateChange:r,poll:i}=c,n=t>0&&e>0;let a=0,o,h=!1,d=!1;const u=()=>{o!==void 0&&(clearInterval(o),o=void 0,h=!1,r())},p=f=>{if(o!==void 0){if(!f){u();return}h||(h=!0,r()),s()}},m=()=>{d||(d=!0,i().then(p).finally(()=>{d=!1}).catch(()=>{}))};return{isPolling:()=>o!==void 0&&h,noteFailedOpen:()=>{a+=1,!(!n||o!==void 0||a<e)&&(o=setInterval(m,t),r(),m())},noteOpen:()=>{a=0,u()},stop:u}},ot="/_lunora/rpc",q="/_lunora/rpc-batch",ct="/_lunora/ws",W=c=>c===void 0||c===""?"":`&bucket=${encodeURIComponent(c)}`,F=c=>{for(let e=c.length-1;e>=0;e-=1)c[e]?.()},ae=Symbol("lunora.unmergeableDelta"),ht=(c,e)=>{for(const t of e)t.op==="delete"?c.delete(t.key):t.value!==void 0&&c.set(t.key,t.value)},dt="lunora-ping",ut=3e4,lt=1e4,ft=5e3,pt=3,mt=250,yt=5e3,bt=5e3,St=64,vt=3,gt=1e4,Tt=8,Ct="/_lunora/admin/shard-traffic",kt="/_lunora/admin/scheduled",wt="/_lunora/admin/scheduled/status",Et="/_lunora/admin/scheduled/ws",At="/_lunora/admin/scheduled/cancel",oe="/_lunora/admin/scheduled/dead",_t="/_lunora/admin/scheduled/dead/retry",It="/_lunora/admin/scheduled/dead/cancel",Ot="/_lunora/admin/workflows/instances",Rt="/_lunora/admin/workflows/instance",Pt="/_lunora/admin/workflows/status",$="/_lunora/admin/storage",Ft="/_lunora/admin/storage/url",Mt="/_lunora/admin/storage/buckets",Lt="/_lunora/admin/functions",Ht="/_lunora/admin/cron-jobs",Ut="/_lunora/admin/cron-jobs/run",xt="/_lunora/admin/openapi",Nt="/_lunora/admin/openrpc",Bt="/_lunora/admin/global/tables",Qt="/_lunora/admin/global/table",Dt="/_lunora/admin/global/facet",Kt="/_lunora/admin/vector/indexes",qt="/_lunora/admin/vector/query",Wt="/_lunora/admin/logs/archive",$t="/_lunora/admin/kv/namespaces",jt="/_lunora/admin/kv/keys",j="/_lunora/admin/kv/value",Gt="/_lunora/admin/auth/users",Vt="/_lunora/admin/auth/sessions",zt="/_lunora/admin/auth/users/create",Jt="/_lunora/admin/auth/users/role",Yt="/_lunora/admin/auth/users/ban",Xt="/_lunora/admin/auth/users/unban",Zt="/_lunora/admin/auth/users/password",es="/_lunora/admin/auth/users/remove",ts="/_lunora/admin/auth/users/impersonate",ss="/_lunora/admin/auth/sessions/revoke",rs="/_lunora/admin/auth/sessions/revoke-all",is="/_lunora/admin/auth/capabilities",ns="/_lunora/admin/auth/users/update",as="/_lunora/admin/auth/accounts",os="/_lunora/admin/auth/accounts/unlink",cs="/_lunora/admin/auth/passkeys",hs="/_lunora/admin/auth/passkeys/delete",ds="/_lunora/admin/auth/two-factor/disable",us="/_lunora/admin/auth/organizations",ls="/_lunora/admin/auth/organizations/members",fs="/_lunora/admin/auth/organizations/invitations",ps="/_lunora/admin/auth/organizations/members/remove",ms="/_lunora/admin/auth/organizations/invitations/cancel",ys="/_lunora/admin/auth/config",bs="/_lunora/admin/auth/sign-up-invitations",Ss="/_lunora/admin/auth/sign-up-invitations/create",vs="/_lunora/admin/auth/sign-up-invitations/revoke",gs="/_lunora/admin/auth/organizations/create",Ts="/_lunora/admin/auth/organizations/update",Cs="/_lunora/admin/auth/organizations/remove",ks="/_lunora/admin/auth/organizations/members/add",ws="/_lunora/admin/auth/organizations/members/invite",Es="/_lunora/admin/auth/organizations/members/role",As="/_lunora/admin/auth/organizations/teams",_s="/_lunora/admin/auth/organizations/teams/create",Is="/_lunora/admin/auth/organizations/teams/update",Os="/_lunora/admin/auth/organizations/teams/remove",Rs="/_lunora/admin/auth/organizations/teams/members",Ps="/_lunora/admin/auth/organizations/teams/members/add",Fs="/_lunora/admin/auth/organizations/teams/members/remove",Ms="/_lunora/admin/auth/organizations/roles",Ls="/_lunora/admin/auth/organizations/roles/create",Hs="/_lunora/admin/auth/organizations/roles/update",Us="/_lunora/admin/auth/organizations/roles/remove",xs="/api/auth",Ns="/get-session",G=c=>c==="connected"||c==="polling",Bs=(c,e,t)=>c!==null||e&&t===null,ce=c=>c.startsWith("https://")?`wss://${c.slice(8)}`:c.startsWith("http://")?`ws://${c.slice(7)}`:c,k=(c,e)=>`${c.endsWith("/")?c.slice(0,-1):c}${e}`,b=(c,e)=>{const t=new URLSearchParams;for(const[r,i]of Object.entries(e))i!==void 0&&i!==""&&t.set(r,String(i));const s=t.toString();return s===""?c:`${c}?${s}`},Qs=[ke],l=c=>c??"",pe=(c,e)=>{const t=c.error,s=typeof t?.code=="string"?t.code:void 0,r=typeof t?.message=="string"?t.message:void 0;return{code:s,messageText:(typeof c.message=="string"?c.message:void 0)??r??e}},Ds=c=>{const{code:e,messageText:t}=pe(c,"stream error");return e===void 0?new Error(t):new y(e,t)},he=c=>{const{code:e,messageText:t}=pe(c,"subscription error");return{message:t,...e===void 0?{}:{code:e}}};function V(c){if(c!==void 0)return e=>{c(e)}}const w=(c,e)=>{for(const t of c)try{t(e)}catch{}},Ks=new TextDecoder,qs=c=>{if(typeof c=="string")return c;if(c instanceof ArrayBuffer)return Ks.decode(c)},v=(c,e)=>{if(!c.socket||c.wsState!=="open")return!1;try{return c.socket.send(JSON.stringify(e)),!0}catch{return!1}},Ws=c=>{if(!c.pendingStreams||c.pendingStreams.length===0)return;const e=c.pendingStreams;c.pendingStreams=[];for(const t of e)v(c,t)},Y=c=>{const e=new Error(c.message??"request failed");if(e.code=c.code,c.data!==void 0)try{e.data=g(c.data)}catch{}return c.hint!==void 0&&(e.hint=c.hint),c.docsUrl!==void 0&&(e.docsUrl=c.docsUrl),e},de=(c,e)=>{const t=Y(c),s=qe(t,e);return s!==void 0&&(t.data=s),t},E=(c,e)=>{try{return L(c)}catch(t){const s=t instanceof Error?t.message:String(t);throw new TypeError(`LunoraClient: cannot encode ${e} — ${s}`,t instanceof Error?{cause:t}:void 0)}},$s=1e4,ue=async c=>{const e=new AbortController;let t;const s=new Promise((r,i)=>{t=setTimeout(()=>{e.abort(),i(new TypeError("LunoraClient: poll timed out"))},$s)});try{return await Promise.race([c(e.signal),s])}catch(r){throw e.signal.aborted?new TypeError("LunoraClient: poll timed out"):r}finally{clearTimeout(t)}},le=c=>{try{return L(c),!0}catch{return!1}},z=c=>"args"in c?{...c,args:g(c.args)}:c,me=c=>{const e=M(c);return e===void 0?We():Y(e)},js=(c,e)=>{const t=Array.from({length:e});for(const s of c){if(typeof s.id!="number"||s.id<0||s.id>=e)continue;const r=s.body;t[s.id]=r!==void 0&&"error"in r?{error:me(r),ok:!1}:{ok:!0,value:g(r?.result)}}return t.map(s=>s??{error:new Error("batch call returned no result"),ok:!1})},J=(c,e)=>e!==null?{}:c===null?{expectSubject:null}:c?.startsWith("subj:")===!0?{expectSubject:c.slice(5)}:{},Gs=Promise.resolve();class ye{static MAX_POKE_BUFFERS=256;static createClientQuery(e,t){return{defaultValue:t,key:e}}url;wsUrl;clientQueryStore;wsToken;authBasePath;fetchImpl;WebSocketImpl;bookmark;reconnectOptions;connectTimeoutMs;heartbeatIntervalMs;pollingFallbackAfterFailedAttempts;pollingFallbackIntervalMs;offlineQueue;outbox;clientId;shardCursors=new Map;defaultShardKey;readyResolved=!1;readyResolve;readyPromise;clientWatermarks=new Map;outboxMutationCounter=0;onPersistenceError;persistence;persistenceVersion;outboxLeaderRelease;queryCache;hydratedQueryCache=new Map;cacheSeededQueries=new Map;pendingCacheWrites=new Map;cacheFlushTimer;subscriptions=new C;tabCoordinator;leaderStatus;leaderWasEverConnected=!1;connections=new Map;idleClosedShards=new Set;defaultConnectionContext;connectionContexts=new Map;connectionContextHolders=new Map;authToken=null;authSubject=void 0;subjectToken=null;sessionProbesInFlight=0;sessionProbeGeneration=0;identityQuestions=0;identityAnsweredAt=0;releaseSessionChangeListener;warnedIdentityDisagreement=!1;identityResolutionExpected=!1;identitySettled=!1;queuedIdentities=new Map;queuedOfflineShardKeys=new Set;closed=!1;authTokenListeners=new O;statusListeners=new O;tokenExpiredListeners=new O;identityChangeListeners=new O;retiredIdentities=0;authRefusalNotifiedFor;replayCredentials=new WeakMap;mutationSettledListeners=new O;pendingChangeListeners=new O;whisperHandlers=new Map;lastStatus="idle";nextSubId=0;nextStreamId=0;streams=new Map;adminSocketTeardowns=new Set;offlineFlushes=new Map;replayRetryState=new Map;replayRetryTimers=new Map;shapeSubscriptions=new Map;pokeBuffers=new Map;nextShapeId=0;constructor(e){this.url=e.url,this.wsUrl=e.wsUrl??k(ce(e.url),ct),this.wsToken=e.wsToken;const t=e.authBasePath??xs;this.authBasePath=t.endsWith("/")?t.slice(0,-1):t,this.fetchImpl=e.fetch??(typeof fetch=="function"?fetch.bind(globalThis):void 0),this.WebSocketImpl=e.WebSocket??(typeof WebSocket=="function"?WebSocket:void 0),this.bookmark=e.bookmarkStorage??we(),this.reconnectOptions=e.reconnect,this.heartbeatIntervalMs=e.heartbeatIntervalMs??ut,this.connectTimeoutMs=e.connectTimeoutMs??lt,this.pollingFallbackIntervalMs=e.pollingFallback?.intervalMs??ft,this.pollingFallbackAfterFailedAttempts=e.pollingFallback?.afterFailedAttempts??pt,this.defaultConnectionContext=e.connectionContext,this.persistence=Ue(e.persistence,e.outbox===void 0),this.persistenceVersion=e.persistenceVersion,this.queryCache=xe(e.queryCache),this.onPersistenceError=e.offlineQueue?.onPersistenceError,this.clientQueryStore=new Ee,e.crossTabSync?(this.tabCoordinator=this.createTabCoordinator(),this.tabCoordinator.start()):this.tabCoordinator=void 0,e.hydrateOnStart&&this.queryCache?this.readyPromise=new Promise(s=>{this.readyResolve=s}):(this.readyResolved=!0,this.readyPromise=Gs),this.offlineQueue=new Me(e.offlineQueue,{onEvict:(s,r)=>{this.emitItemSettled(s,"rejected",r),this.releaseIdleShard(s.shardKey)},onSizeChange:s=>{this.pendingChangeListeners.emit(s)},persistence:this.persistence,version:e.persistenceVersion}),this.outbox=e.outbox,this.clientId=e.clientId??`client-${te()}`,this.persistence&&queueMicrotask(()=>{this.hydrateAsOutboxLeader()}),this.queryCache&&queueMicrotask(()=>{(async()=>{try{await this.hydrateQueryCache()}catch{}finally{this.readyResolved=!0,this.readyResolve?.()}})().catch(()=>{})}),"document"in globalThis&&(this.releaseSessionChangeListener=nt(async()=>{!this.closed&&this.authToken===null&&await this.getCurrentUser().catch(()=>{})}))}setAuthToken(e,t){const s=this.authToken!==e,r=this.identityFingerprint(),i=this.authSubject===void 0||this.subjectToken===this.authToken,n=this.subjectAwaitingReconfirm(),a=this.isKnownNobody();this.authToken=e,this.applySubject(e,t);const o=this.identityFingerprint();o!==r&&(!s&&e!==null&&i?(this.restampQueuedIdentity(r,o),this.restampWatermarks(r,o),this.restampConnectionIdentity(r,o),this.reseedFromHydratedCache()):!s&&e===null&&r===null&&i&&!a?(this.restampWatermarks(r,o),this.restampConnectionIdentity(r,o),this.reseedFromHydratedCache()):(this.rejectQueuedForIdentityChange(r),Bs(r,a,e)&&this.evictPreviousIdentitySession()),this.restartTabCoordinatorForIdentity()),this.syncReadCacheToCredential(n),s&&this.authTokenListeners.emit(e),(o!==r||s||n)&&this.offlineQueue.size>0&&G(this.computeStatus())&&this.flushAllOfflineQueues()}getAuthToken(){return this.authToken}currentIdentity(){return this.identityFingerprint()}expectIdentityResolution(){this.identityResolutionExpected=!0}currentBaseline(e){return this.baselineCursorFor(e)}replayIdentityVerdict(e){const t=this.identityVerdict(e);if(t!=="match")return{verdict:t};const s=Object.freeze({});return this.replayCredentials.set(s,{authToken:this.authToken,stamp:e}),{credential:s,verdict:t}}clientIdentifier(){return this.clientId}confirmedMutationWatermark(e){return this.clientWatermarks.get(this.identityFingerprint()??"")?.get(e??"")??0}async callMutator(e,t,s){const r=s?.clientSeq;if(r!==void 0&&(!Number.isInteger(r)||r<=0))throw new y("INTERNAL",`callMutator: clientSeq must be a positive integer, got ${String(r)}`);const i=s?.shardKey??"",n=this.identityFingerprint();let a,o,h;try{o=await this.rpc(e,t,s?.shardKey,{captureBookmark:!0,clientId:this.clientId,clientSeq:r,onMutationAck:u=>{a=u}})}catch(u){if(!U(u))throw u;h=u}if(a!==void 0&&a>(this.clientWatermarks.get(n??"")?.get(i)??0)){let u=this.clientWatermarks.get(n??"");u===void 0&&(ie(this.clientWatermarks,Tt),u=new Map,this.clientWatermarks.set(n??"",u)),u.set(i,a)}if(h!==void 0)throw h;return{applied:a===void 0||a===r,result:o}}onAuthTokenChange(e){return this.authTokenListeners.add(e)}onIdentityChange(e){return this.identityChangeListeners.add(e)}identityEpoch(){return this.retiredIdentities}async getCurrentUser(){if(this.identityResolutionExpected=!0,this.closed||!this.fetchImpl)return this.identitySettled=!0,null;const e={},t=this.authToken;this.authToken&&(e.authorization=`Bearer ${this.authToken}`),this.sessionProbesInFlight+=1,this.identityQuestions+=1,this.sessionProbeGeneration=this.identityQuestions;const s=this.sessionProbeGeneration;try{const r=await this.fetchImpl(k(this.url,`${this.authBasePath}${Ns}`),{credentials:"include",headers:e,method:"GET"});if(!r.ok)return this.identitySettled=!0,r.status===401&&this.adoptResolvedSubject(t,null,s),null;const n=(await r.json())?.user??null;return this.identitySettled=!0,this.adoptResolvedSubject(t,n,s),n}finally{this.releaseSessionProbe()}}setWsToken(e){this.wsToken!==e&&(this.wsToken=e,this.bounceShardSockets())}setConnectionContext(e,t={}){this.assertLeaderOwnedSurface("setConnectionContext");const s=l(t.shardKey);e===void 0?this.connectionContexts.delete(s):this.connectionContexts.set(s,e),this.refreshConnectionContext(s),e===void 0&&this.releaseIdleShard(t.shardKey)}acquireConnectionContext(e,t={}){if(this.followsAnotherTab())return()=>{};const s=l(t.shardKey),r={context:e},i=this.connectionContextHolders.get(s);i?i.push(r):this.connectionContextHolders.set(s,[r]),this.refreshConnectionContext(s);let n=!1;return()=>{if(n)return;n=!0;const a=this.connectionContextHolders.get(s);if(!a)return;const o=a.indexOf(r);o!==-1&&a.splice(o,1),a.length===0&&this.connectionContextHolders.delete(s),this.refreshConnectionContext(s),this.releaseIdleShard(t.shardKey)}}whisperSubscribe(e,t,s={}){this.assertLeaderOwnedSurface("whisperSubscribe");const r=l(s.shardKey);let i=this.whisperHandlers.get(r);i||(i=new Map,this.whisperHandlers.set(r,i));let n=i.get(e);const a=n===void 0;if(n||(n=new Set,i.set(e,n)),n.add(t),this.ensureSocket(s.shardKey),a){const o=this.getConnection(s.shardKey);o&&v(o,{topic:e,type:"whisper_subscribe"})}return()=>{const o=this.whisperHandlers.get(r),h=o?.get(e);if(!h?.delete(t)||h.size>0)return;o?.delete(e),o?.size===0&&this.whisperHandlers.delete(r);const d=this.getConnection(s.shardKey);d&&v(d,{topic:e,type:"whisper_unsubscribe"}),this.releaseIdleShard(s.shardKey)}}whisper(e,t,s={}){this.assertLeaderOwnedSurface("whisper"),this.ensureSocket(s.shardKey);const r=this.getConnection(s.shardKey);r&&v(r,{data:E(t??null,`whisper data for topic '${e}'`),topic:e,type:"whisper"}),this.releaseIdleShard(s.shardKey)}onTokenExpired(e){return this.tokenExpiredListeners.add(e)}connectionStatus(){return this.computeStatus()}onConnectionStatus(e){const t=this.statusListeners.add(e);return e(this.computeStatus()),t}pendingCount(){return this.offlineQueue.size}debug(){const e=[],t=this.clientWatermarks.get(this.identityFingerprint()??""),s=new Set([...this.connections.keys(),...t?.keys()??[]]);for(const i of s){const n=this.connections.get(i);e.push({confirmedMutationWatermark:t?.get(i)??0,hasSocket:n?.socket!==void 0,shardKey:i===""?void 0:i,wasEverConnected:n?.wasEverConnected??!1,wsState:n?.wsState??"idle"})}const r=this.subscriptions.all().map(i=>({acked:i.acked,functionPath:i.fn.__lunoraRef,id:i.id,kind:"query",lastMutationId:i.lastMutationId,pendingOptimisticLayers:i.optimisticLayers.length,serverCursor:i.serverCursor,shardKey:i.shardKey,subscriberCount:i.callbacks.size}));for(const i of this.shapeSubscriptions.values())r.push({acked:i.serverCursor!==void 0,functionPath:`shape:${i.name}`,id:i.id,kind:"shape",lastMutationId:i.lastMutationId,pendingOptimisticLayers:0,rowCount:i.rows.size,serverCursor:i.serverCursor,shardKey:i.shardKey,subscriberCount:i.callbacks.size});return{clientId:this.clientId,closed:this.closed,connectionStatus:this.computeStatus(),pendingWrites:this.offlineQueue.size,shards:e.toSorted((i,n)=>(i.shardKey??"").localeCompare(n.shardKey??"")),subscriptions:r.toSorted((i,n)=>i.functionPath.localeCompare(n.functionPath))}}onPendingChange(e){const t=this.pendingChangeListeners.add(e);return e(this.offlineQueue.size),t}onMutationSettled(e){return this.mutationSettledListeners.add(e)}getWebSocketImpl(){return this.WebSocketImpl}getClientQuery(e){return this.clientQueryStore.get(e)}setClientQuery(e,t){this.clientQueryStore.set(e,t)}subscribeClientQuery(e,t){return this.clientQueryStore.subscribe(e,t)}resetClientQuery(e){this.clientQueryStore.reset(e)}snapshotPrecondition(e,t,s){return $e(this,e,t,s)}whenReady(){return this.readyPromise}get isReady(){return this.readyResolved}peekHydratedQuery(e,t,s){if(!this.readyResolved)return;const r=Z(t),i=I(e,r,s),n=this.hydratedQueryCache.get(i);if(n!==void 0)return this.cachedQueryMatchesIdentity(n)?n.value:void 0}peekActiveQuerySnapshot(e,t,s){const r=C.key(e,t,s),i=this.subscriptions.get(r);return{present:i!==void 0,value:i?.lastValue}}async query(e,t,s={}){return this.assertOpen(),await this.rpc(e.__lunoraRef,t,s.shardKey,{attachBookmark:!0})}async batch(e){return this.sendBatch(e)}async mutation(e,t,s={}){const{value:r}=await this.runMutation(e,t,s);return r}canQueueOffline(e){const{wasEverConnected:t}=this.connectionGateState(e);return this.WebSocketImpl!==void 0&&(t||this.offlineQueue.queueBeforeFirstConnect)}async action(e,t,s={}){return this.assertOpen(),await this.rpc(e.__lunoraRef,t,s.shardKey,{attachBookmark:!0,captureBookmark:!0})}async importRows(e,t,s={}){this.assertOpen();const r=Math.max(1,Math.trunc(s.chunkSize??500)),i=s.toArgs??(d=>({rows:d})),n=t.length;let a=0,o=0,h=0;for(let d=0;d<n;d+=r){const u=t.slice(d,d+r),p=h,{committed:m}=await this.runMutation(e,i(u),{...s.importId===void 0?{}:{mutationId:`${s.importId}:${String(p)}`},shardKey:s.shardKey});h+=1,a+=u.length,m&&(o+=u.length),s.onProgress?.({done:a,total:n})}return{chunks:h,imported:o,queued:a-o}}async shardTraffic(e){this.assertOpen();const t=await this.adminFetch(Ct,"POST",{table:e});return{failed:t.failed??0,ok:t.ok??0,shards:t.shards??[]}}async listScheduledJobs(){return this.assertOpen(),((await this.adminFetch(kt,"GET")).records??[]).map(t=>z(t))}async schedulerStatus(){this.assertOpen();const e=await this.adminFetch(wt,"GET");return{backlog:e.backlog??0,inFlight:e.inFlight??0,pools:e.pools??[]}}async cancelScheduledJob(e){return this.assertOpen(),{cancelled:(await this.adminFetch(At,"POST",{id:e})).cancelled===!0}}async listDeadJobs(){return this.assertOpen(),(await Ge(async t=>await this.adminFetch(t===void 0?oe:`${oe}?cursor=${encodeURIComponent(t)}`,"GET"))).map(t=>z(t))}async retryDeadJob(e){return this.assertOpen(),{retried:(await this.adminFetch(_t,"POST",{id:e})).retried===!0}}async removeDeadJob(e){return this.assertOpen(),{removed:(await this.adminFetch(It,"POST",{id:e})).removed===!0}}async listWorkflowInstances(e){this.assertOpen();const t=new URLSearchParams({name:e.name});e.status!==void 0&&t.set("status",e.status),e.page!==void 0&&t.set("page",String(e.page)),e.perPage!==void 0&&t.set("perPage",String(e.perPage));const s=await this.adminFetch(`${Ot}?${t.toString()}`,"GET");return{configured:s.configured,instances:s.instances??[],page:s.page??1,perPage:s.perPage??e.perPage??0,totalCount:s.totalCount}}async getWorkflowInstance(e){this.assertOpen();const t=new URLSearchParams({id:e.id,name:e.name}),s=await this.adminFetch(`${Rt}?${t.toString()}`,"GET");return{createdOn:s.createdOn,endedOn:s.endedOn,error:s.error,id:s.id??e.id,output:s.output,params:s.params,startedOn:s.startedOn,status:s.status??"unknown",steps:s.steps??[]}}async setWorkflowInstanceStatus(e){return this.assertOpen(),{status:(await this.adminFetch(Pt,"POST",{action:e.action,id:e.id,name:e.name})).status??"unknown"}}subscribeScheduledJobs(e){if(this.assertOpen(),this.WebSocketImpl===void 0)return()=>{};const t=k(ce(this.url),Et),s=se(this.reconnectOptions),r={connectTimer:void 0,heartbeatTimer:void 0,lastFrameAt:0,socket:void 0};let i,n=!1;const a=()=>{n||this.closed||(i=setTimeout(d,s.next()))},o=p=>{if(n||this.WebSocketImpl===void 0)return;const m=p===void 0?t:`${t}?token=${encodeURIComponent(p)}`;this.openManagedSocket(r,m,this.connectTimeoutMs,{onClose:()=>{a()},onMessage:f=>{let S;try{S=JSON.parse(typeof f.data=="string"?f.data:"")}catch{return}S.type==="jobs"&&Array.isArray(S.records)&&(s.reset(),e(S.records.map(T=>z(T))))}})},h=async p=>{let m;try{m=await p()}catch{a();return}o(m)},d=()=>{if(n||this.WebSocketImpl===void 0)return;const{wsToken:p}=this;if(typeof p=="function"){h(p).catch(()=>{});return}o(p)};d();const u=()=>{n=!0,i!==void 0&&(clearTimeout(i),i=void 0),r.connectTimer!==void 0&&(clearTimeout(r.connectTimer),r.connectTimer=void 0),this.stopHeartbeat(r),r.socket?.close(),r.socket=void 0};return this.adminSocketTeardowns.add(u),()=>{this.adminSocketTeardowns.delete(u),u()}}async listFunctions(){return this.assertOpen(),(await this.adminFetch(Lt,"GET")).functions??[]}async getCronJobs(){return this.assertOpen(),(await this.adminFetch(Ht,"GET")).jobs??[]}async runCronJob(e){this.assertOpen();const t=await this.adminFetch(Ut,"POST",{name:e});return{name:t.name??e,ran:t.ran===!0}}async fetchOpenApi(){return this.assertOpen(),await this.adminFetch(xt,"GET")}async fetchOpenRpc(){return this.assertOpen(),await this.adminFetch(Nt,"GET")}async listStorageObjects(e={}){this.assertOpen();const t=b($,{bucket:e.bucket,cursor:e.cursor,limit:e.limit,prefix:e.prefix}),s=await this.adminFetch(t,"GET");return{cursor:s.cursor,objects:s.objects??[]}}async deleteStorageObject(e,t){this.assertOpen();const s=`${$}?key=${encodeURIComponent(e)}${W(t?.bucket)}`,r=await this.adminFetch(s,"DELETE");return{deleted:r.deleted===!0,key:r.key??e}}async listStorageBuckets(){return this.assertOpen(),(await this.adminFetch(Mt,"GET")).buckets??[]}async uploadStorageObject(e){this.assertOpen();const t=`${$}?key=${encodeURIComponent(e.key)}${W(e.bucket)}`,s=await this.adminFetch(t,"PUT",e.body,e.contentType);return{etag:s.etag,key:s.key??e.key}}async signedStorageUrl(e,t){this.assertOpen();const s=t?.expiresInSeconds,r=s===void 0?"":`&expiresIn=${encodeURIComponent(s.toString())}`,i=`${Ft}?key=${encodeURIComponent(e)}${r}${W(t?.bucket)}`,n=await this.adminFetch(i,"GET");if(typeof n.url!="string")throw new TypeError("LunoraClient: storage URL endpoint returned no `url`");return n.url}async listGlobalTables(){return this.assertOpen(),await this.adminFetch(Bt,"GET")}async readGlobalTablePage(e){this.assertOpen();const t=new URLSearchParams({table:e.table});return e.limit!==void 0&&t.set("limit",String(e.limit)),e.offset!==void 0&&t.set("offset",String(e.offset)),e.filters!==void 0&&e.filters.length>0&&t.set("filters",JSON.stringify(L(e.filters))),g(await this.adminFetch(`${Qt}?${t.toString()}`,"GET"))}async facetGlobalColumn(e){this.assertOpen();const t=new URLSearchParams({column:e.column,table:e.table});return e.limit!==void 0&&t.set("limit",String(e.limit)),e.filters!==void 0&&e.filters.length>0&&t.set("filters",JSON.stringify(L(e.filters))),g(await this.adminFetch(`${Dt}?${t.toString()}`,"GET"))}async listVectorIndexes(){return this.assertOpen(),(await this.adminFetch(Kt,"GET")).indexes??[]}async queryVectorIndex(e){return this.assertOpen(),(await this.adminFetch(qt,"POST",e)).matches??[]}async queryLogArchive(e={}){this.assertOpen();const t=await this.adminFetch(Wt,"POST",e);return{nextCursor:t.nextCursor,rows:t.rows??[]}}async listKvNamespaces(){return this.assertOpen(),(await this.adminFetch($t,"GET")).namespaces??[]}async listKvKeys(e){this.assertOpen();const t=b(jt,{cursor:e.cursor,limit:e.limit,namespace:e.namespace,prefix:e.prefix});return await this.adminFetch(t,"GET")}async getKvValue(e){this.assertOpen();const t=b(j,{key:e.key,namespace:e.namespace});return await this.adminFetch(t,"GET")}async putKvValue(e){this.assertOpen(),await this.adminFetch(j,"PUT",e)}async deleteKvKey(e){this.assertOpen();const t=b(j,{key:e.key,namespace:e.namespace});await this.adminFetch(t,"DELETE")}async listAuthUsers(e={}){this.assertOpen();const t=b(Gt,{filterField:e.filterField,filterValue:e.filterValue,limit:e.limit,offset:e.offset,search:e.search,searchField:e.searchField,sortBy:e.sortBy,sortDirection:e.sortDirection});return await this.adminFetch(t,"GET")}async createAuthUser(e){return await this.adminFetch(zt,"POST",e)}async setAuthUserRole(e){return await this.adminFetch(Jt,"POST",e)}async banAuthUser(e){return await this.adminFetch(Yt,"POST",e)}async unbanAuthUser(e){return await this.adminFetch(Xt,"POST",e)}async setAuthUserPassword(e){await this.adminFetch(Zt,"POST",e)}async removeAuthUser(e){await this.adminFetch(es,"POST",e)}async impersonateAuthUser(e){return await this.adminFetch(ts,"POST",e)}async revokeAuthSession(e){await this.adminFetch(ss,"POST",e)}async revokeAuthUserSessions(e){await this.adminFetch(rs,"POST",e)}async getAuthCapabilities(){return await this.adminFetch(is,"GET")}async updateAuthUser(e){return await this.adminFetch(ns,"POST",e)}async listAuthAccounts(e){return await this.adminFetch(b(as,{userId:e.userId}),"GET")}async unlinkAuthAccount(e){await this.adminFetch(os,"POST",e)}async listAuthPasskeys(e){return await this.adminFetch(b(cs,{userId:e.userId}),"GET")}async deleteAuthPasskey(e){await this.adminFetch(hs,"POST",e)}async disableAuthTwoFactor(e){await this.adminFetch(ds,"POST",e)}async listAuthOrganizations(e={}){return await this.adminFetch(b(us,{limit:e.limit,offset:e.offset}),"GET")}async listAuthOrgMembers(e){const t=b(ls,{limit:e.limit,offset:e.offset,organizationId:e.organizationId});return await this.adminFetch(t,"GET")}async listAuthOrgInvitations(e){const t=b(fs,{limit:e.limit,offset:e.offset,organizationId:e.organizationId});return await this.adminFetch(t,"GET")}async listAuthSignUpInvitations(e={}){const t=b(bs,{limit:e.limit,offset:e.offset});return await this.adminFetch(t,"GET")}async createAuthSignUpInvitation(e){return await this.adminFetch(Ss,"POST",e)}async revokeAuthSignUpInvitation(e){await this.adminFetch(vs,"POST",e)}async removeAuthOrgMember(e){await this.adminFetch(ps,"POST",e)}async cancelAuthOrgInvitation(e){await this.adminFetch(ms,"POST",e)}async getAuthConfig(){return await this.adminFetch(ys,"GET")}async createAuthOrganization(e){return await this.adminFetch(gs,"POST",e)}async updateAuthOrganization(e){return await this.adminFetch(Ts,"POST",e)}async deleteAuthOrganization(e){await this.adminFetch(Cs,"POST",e)}async addAuthOrgMember(e){return await this.adminFetch(ks,"POST",e)}async inviteAuthOrgMember(e){return await this.adminFetch(ws,"POST",e)}async setAuthOrgMemberRole(e){return await this.adminFetch(Es,"POST",e)}async listAuthOrgTeams(e){const t=b(As,{limit:e.limit,offset:e.offset,organizationId:e.organizationId});return await this.adminFetch(t,"GET")}async createAuthOrgTeam(e){return await this.adminFetch(_s,"POST",e)}async updateAuthOrgTeam(e){return await this.adminFetch(Is,"POST",e)}async removeAuthOrgTeam(e){await this.adminFetch(Os,"POST",e)}async listAuthOrgTeamMembers(e){const t=b(Rs,{limit:e.limit,offset:e.offset,teamId:e.teamId});return await this.adminFetch(t,"GET")}async addAuthOrgTeamMember(e){return await this.adminFetch(Ps,"POST",e)}async removeAuthOrgTeamMember(e){await this.adminFetch(Fs,"POST",e)}async listAuthOrgRoles(e){const t=b(Ms,{limit:e.limit,offset:e.offset,organizationId:e.organizationId});return await this.adminFetch(t,"GET")}async createAuthOrgRole(e){return await this.adminFetch(Ls,"POST",e)}async updateAuthOrgRole(e){return await this.adminFetch(Hs,"POST",e)}async deleteAuthOrgRole(e){await this.adminFetch(Us,"POST",e)}async listAuthSessions(e={}){this.assertOpen();const t=b(Vt,{limit:e.limit,offset:e.offset,userId:e.userId});return await this.adminFetch(t,"GET")}subscribe(e,t,s,r={}){this.assertOpen();const i=t??{},n=C.key(e.__lunoraRef,i,r.shardKey);let a=this.subscriptions.get(n);const o=V(s),h=V(r.onError),d=V(r.onCheckpoint);if(!a){this.nextSubId+=1;const p=`sub_${this.nextSubId.toString()}`,m=Z(i),f=this.takeHydratedCache(e.__lunoraRef,m,r.shardKey);a={acked:!1,args:i,argsKey:m,callbacks:new Set,checkpointCallbacks:new Set,errorCallbacks:new Set,fn:e,id:p,lastValue:f?.value,optimisticLayers:[],serverBase:f?.value,serverCursor:f?.serverCursor,shardKey:r.shardKey,wireArgs:E(i,`args for '${e.__lunoraRef}'`),...f?.serverEpoch===void 0?{}:{serverEpoch:f.serverEpoch}},this.subscriptions.add(a),f!==void 0&&this.cacheSeededQueries.set(n,f)}if(a.callbacks.add(o),h&&a.errorCallbacks.add(h),d&&a.checkpointCallbacks.add(d),a.lastValue!==void 0)try{o(a.lastValue)}catch{}this.ensureSocket(r.shardKey),this.sendSubscribeIfOpen(a);const u=a;return()=>{u.callbacks.delete(o),h&&u.errorCallbacks.delete(h),d&&u.checkpointCallbacks.delete(d),u.callbacks.size===0&&(this.sendOrQueueUnsubscribe(u.shardKey,u.id,"unsubscribe"),this.returnCacheSeed(C.keyOf(u)),this.subscriptions.remove(u),this.releaseIdleShard(u.shardKey))}}subscribeShape(e,t,s={}){if(this.assertOpen(),this.followsAnotherTab()){const{onError:n}=s;return n!==void 0&&queueMicrotask(()=>{n({code:"NOT_IMPLEMENTED",message:"LunoraClient: `subscribeShape` is unavailable on a cross-tab follower tab. The `crossTabSync` channel only carries data from the leader tab outward and shape pokes are not part of that broadcast set, so this subscription could never resolve. Turn off `crossTabSync`, or use a `list`-backed collection, which IS relayed."})}),()=>{}}this.nextShapeId+=1;const r=`shape_${this.nextShapeId.toString()}`,i={args:e.args,callbacks:new Set([t]),errorCallbacks:s.onError?new Set([s.onError]):new Set,id:r,name:e.name,onCheckpoint:s.onCheckpoint,rows:new Map,shardKey:s.shardKey,wireArgs:e.args===void 0?void 0:E(e.args,`shape args for '${e.name}'`)};return this.shapeSubscriptions.set(r,i),this.ensureSocket(s.shardKey),this.sendShapeSubscribeIfOpen(i),()=>{this.shapeSubscriptions.delete(r),this.sendOrQueueUnsubscribe(i.shardKey,r,"shape_unsubscribe"),this.releaseIdleShard(i.shardKey)}}stream(e,t,s={}){if(this.assertOpen(),this.WebSocketImpl===void 0)throw new y("INTERNAL","LunoraClient: streams require a WebSocket implementation");this.nextStreamId+=1;const r=`stream_${this.nextStreamId.toString()}`,{shardKey:i}=s,n=t??{},{handle:a,iterable:o}=je({maxBuffer:s.maxBuffer,onCancel:()=>{this.cancelStream(r,i)}});this.ensureSocket(i);const h=this.getConnection(i),d={id:r,query:{args:E(n,`stream args for '${e.__lunoraRef}'`),functionPath:e.__lunoraRef,shardKey:i},type:"stream"},u={durable:s.durable===!0,generation:void 0,handle:a,lastSeq:0,message:d,shardKey:i};this.streams.set(r,u);const p=h?.wsState==="open"&&v(h,d);if(!p&&h===void 0)return this.forgetStream(r),a.fail(new y("STREAM_DISCONNECTED","stream unavailable: this tab is not the cross-tab WebSocket leader, so it holds no socket to stream over")),o;if(!p){for(h.pendingStreams=h.pendingStreams??[];h.pendingStreams.length>=St;){const f=h.pendingStreams.shift()?.id,S=f?this.streams.get(f):void 0;S&&(S.handle.fail(new y("STREAM_QUEUE_OVERFLOW","stream-start frame evicted while socket was unreachable")),this.forgetStream(f))}h.pendingStreams.push(d)}return o}httpStream(e,t,s={}){if(this.closed)throw new y("CLIENT_CLOSED","LunoraClient is closed");if(!this.fetchImpl)throw new y("INTERNAL","LunoraClient: no `fetch` implementation available");const r={...this.authToken?{authorization:`Bearer ${this.authToken}`}:{},...s.headers};return Ie(e,t,{baseUrl:this.url,fetch:this.fetchImpl,headers:r,maxBuffer:s.maxBuffer,signal:s.signal})}close(){this.closed=!0,this.releaseSessionChangeListener?.(),this.releaseSessionChangeListener=void 0,this.outboxLeaderRelease?.(),this.outboxLeaderRelease=void 0;for(const e of this.streams.values())e.handle.fail(new y("CLIENT_CLOSED","LunoraClient closed"));this.streams.clear();for(const e of this.connections.values())this.teardownConnection(e);for(const e of this.adminSocketTeardowns)e();this.adminSocketTeardowns.clear();for(const e of this.replayRetryTimers.values())clearTimeout(e);this.replayRetryTimers.clear(),this.replayRetryState.clear(),this.offlineQueue.clear(),this.queuedIdentities.clear(),this.cacheFlushTimer!==void 0&&(clearTimeout(this.cacheFlushTimer),this.cacheFlushTimer=void 0),this.pendingCacheWrites.size>0&&this.flushQueryCacheWrites().catch(()=>{}),this.authTokenListeners.clear(),this.statusListeners.clear(),this.tokenExpiredListeners.clear(),this.identityChangeListeners.clear(),this.mutationSettledListeners.clear(),this.pendingChangeListeners.clear(),this.whisperHandlers.clear(),this.shapeSubscriptions.clear(),this.pokeBuffers.clear(),this.subscriptions.clear(),this.clientQueryStore.clear(),this.hydratedQueryCache.clear(),this.cacheSeededQueries.clear(),this.tabCoordinator?.stop(),this.tabCoordinator=void 0}assertOpen(){if(this.closed)throw new y("INTERNAL","LunoraClient is closed")}followsAnotherTab(){const e=this.tabCoordinator;if(e===void 0||e.isLeader())return!1;const t=e.leaderTabId;return t!==void 0&&t!==e.id}assertLeaderOwnedSurface(e){if(this.followsAnotherTab())throw new y("NOT_IMPLEMENTED",`LunoraClient: \`${e}\` is unavailable on a cross-tab follower tab. The \`crossTabSync\` channel only carries data from the leader tab outward, so this call could never reach the server. Turn off \`crossTabSync\`, or keep \`${e}\` on the leader tab.`)}clearConnectionTimers(e){clearTimeout(e.reconnectTimer),clearTimeout(e.connectTimer),clearTimeout(e.stableTimer),e.reconnectTimer=void 0,e.connectTimer=void 0,e.stableTimer=void 0}shardInUse(e){const t=s=>l(s)===e;return this.subscriptions.all().some(s=>t(s.shardKey))||[...this.shapeSubscriptions.values()].some(s=>t(s.shardKey))||[...this.streams.values()].some(s=>t(s.shardKey))||this.whisperHandlers.has(e)||this.connectionContexts.has(e)||this.connectionContextHolders.has(e)||this.offlineFlushes.has(e)||this.offlineQueue.hasPending(s=>t(s.shardKey))}releaseIdleShard(e){const t=l(e),s=this.connections.get(t);this.closed||t===""||s===void 0||(clearTimeout(s.idleTimer),s.idleTimer=setTimeout(()=>{s.idleTimer=void 0,!(this.closed||this.connections.get(t)!==s||this.shardInUse(t))&&(s.wasEverConnected&&this.idleClosedShards.add(t),this.teardownConnection(s),this.connections.delete(t),this.emitConnectionStatus())},bt))}forgetStream(e){const t=this.streams.get(e);this.streams.delete(e),t&&this.releaseIdleShard(t.shardKey)}teardownConnection(e){e.polling.stop();const t=l(e.shardKey);for(const[r,i]of this.streams)l(i.shardKey)===t&&(i.handle.fail(new y("STREAM_DISCONNECTED","stream terminated: the connection carrying it was torn down")),this.streams.delete(r));e.pendingStreams=void 0,e.pendingUnsubscribes=[],this.clearResubscribeQueue(e),this.clearConnectionTimers(e),clearTimeout(e.idleTimer),e.idleTimer=void 0,this.stopHeartbeat(e);const{socket:s}=e;if(s){e.socket=void 0;try{s.close()}catch{}}e.wsState="closed"}createTabCoordinator(){const e=`lunora-bridge::${this.url}::${this.identityFingerprint()??"anon"}`;return new Ae({channelName:e,onBecomeLeader:()=>{for(const t of this.subscriptions.all())this.ensureSocket(t.shardKey),this.queueResubscribe(t);for(const t of this.queuedOfflineShardKeys)this.ensureSocket(t);this.tabCoordinator?.broadcastConnectionStatus(this.computeStatus(),this.identityFingerprint())},onStopBeingLeader:()=>{for(const[t,s]of this.connections)this.teardownConnection(s),this.connections.delete(t);this.leaderStatus=void 0,this.leaderWasEverConnected=!1},onConnectionStatus:(t,s)=>{if(s!==void 0&&s!==this.identityFingerprint())return;const r=t==="connected"&&this.leaderStatus!=="connected"||t==="polling"&&this.leaderStatus!=="connected"&&this.leaderStatus!=="polling";this.leaderStatus=t,t==="connected"&&(this.leaderWasEverConnected=!0),this.emitConnectionStatus(),r&&this.flushAllOfflineQueues()},onSubscriptionData:(t,s,r,i,n)=>{if(n!==void 0&&n!==this.identityFingerprint())return;const a=this.subscriptions.get(t);a&&(a.serverBase=s,this.dropCacheSeed(t),r!==void 0&&(a.serverCursor=r,i!==void 0&&(a.serverEpoch=i),D(a,r)),A(a,_(s,a.optimisticLayers)))},onLeaderClaimAnswered:()=>{this.tabCoordinator?.isLeader()&&this.tabCoordinator.broadcastConnectionStatus(this.computeStatus(),this.identityFingerprint())},onSubscriptionError:(t,s,r)=>{if(r!==void 0&&r!==this.identityFingerprint())return;const i=this.subscriptions.get(t);i&&w(i.errorCallbacks,s)},onSubscriptionSettled:(t,s,r,i,n,a)=>{if(a!==void 0&&a!==this.identityFingerprint())return;const o=this.subscriptions.get(t);if(o){this.ackAndAdvanceCursor(o,s,r),i!==void 0&&n===this.clientId&&(o.lastMutationId=Math.max(o.lastMutationId??0,i));for(const h of o.checkpointCallbacks)h({checkpoint:o.serverCursor,mutationId:o.lastMutationId})}}})}async sendBatch(e,t){if(this.assertOpen(),!this.fetchImpl)throw new y("INTERNAL","LunoraClient: no `fetch` implementation available");if(e.length===0)return[];const s=await this.fetchImpl(k(this.url,q),{body:JSON.stringify({calls:e.map((a,o)=>({args:E(a.args??{},`args for batch call '${a.fn.__lunoraRef}'`),functionPath:a.fn.__lunoraRef,id:o,shardKey:a.shardKey}))}),headers:this.rpcRequestHeaders({attachBookmark:!0}),method:"POST",signal:t}),r=s.headers.get("x-d1-bookmark");r&&this.bookmark.set(r);let i;try{i=await s.json()}catch{throw new y("INTERNAL",`LunoraClient: batch response was not JSON (status ${s.status.toString()})`)}const n=M(i);if(!s.ok||n!==void 0&&!i.results)throw n!==void 0?Y(n):new y("INTERNAL",`LunoraClient: batch request failed (status ${s.status.toString()})`);for(const a of i.results??[]){const o=a.body?.commitCursor;typeof a.id=="number"&&typeof o=="number"&&this.recordShardCursor(e[a.id]?.shardKey,o)}return js(i.results??[],e.length)}async runMutation(e,t,s){this.assertOpen();const r=t,i=s.mutationId??te(),n=this.takeReplayCredential(s.replayCredential),a=s.replayBaseline===void 0?this.baselineCursorFor(s.shardKey):s.replayBaseline??void 0,{confirms:o,rollbacks:h}=this.applyOptimisticUpdates(e.__lunoraRef,r,s.shardKey,s.optimistic);s.optimisticUpdate&&this.applyOptimisticUpdate(s.optimisticUpdate,t,s.shardKey,h,o);const d=this.offlineFlushes.get(l(s.shardKey));d!==void 0&&await d;const{hasSocket:u,idleClosed:p,polling:m,wasEverConnected:f,wsState:S}=this.connectionGateState(s.shardKey),{queueBeforeFirstConnect:T}=this.offlineQueue,H=f||T,x=this.WebSocketImpl!==void 0&&H,N=m||p,be=S==="connecting"&&H&&!N,Se=S!=="open"&&!u&&x&&!N,ve=x&&s.replayBaseline===void 0&&this.hasPendingWriteAhead(s.shardKey),X=async()=>this.enqueueOfflineMutation(e,r,s.shardKey,a,i,h,o,s.precondition,s.mutationId,n?.stamp);if(Se||be||ve)return X();let B;try{const R=await this.rpc(e.__lunoraRef,r,s.shardKey,{baselineSeq:a,captureBookmark:!0,...n?.flags,mutationId:i,onCommitCursor:Q=>{B=Q}});for(const Q of o)Q(B);return{committed:!0,value:R}}catch(R){if(N&&x&&R instanceof TypeError&&le(r))return X();throw this.settleFailedDirectWrite(R,B,o,h,n?.flags.authToken),R}}settleFailedDirectWrite(e,t,s,r,i){if(this.noteIdentityMismatch(e),i!==void 0&&this.noteReplayAuthRefusal(e,i),U(e)){for(const n of s)n(t);return}F(r)}async enqueueOfflineMutation(e,t,s,r,i,n,a,o,h,d){const u=d===void 0?this.identityFingerprint():d;if(this.outbox){this.outboxMutationCounter+=1;const m=this.outboxMutationCounter;try{await this.outbox.enqueue({args:t,baselineSeq:r,clientId:this.clientId,functionPath:e.__lunoraRef,idempotencyKey:h??`${this.clientId}:${String(m)}`,identity:u,mutationId:m,...n.length>0&&{onRejected:()=>{F(n)}},shardKey:s})}catch(f){throw F(n),f instanceof Error?f:new Error(String(f))}for(const f of a)f(void 0);return{committed:!1,value:void 0}}return{committed:!0,value:await new Promise((m,f)=>{const S={args:t,functionPath:e.__lunoraRef,liveAwaiter:!0,baselineSeq:r,id:i,clientId:this.clientId,identity:u,precondition:o,onCommit:T=>{for(const H of a)H(T)},reject:T=>{this.queuedIdentities.delete(i),U(T)||F(n),f(T instanceof Error?T:new Error(String(T))),this.releaseIdleShard(s)},resolve:m,shardKey:s};this.offlineQueue.enqueue(S),this.queuedOfflineShardKeys.add(s),this.ensureSocket(s),S.id!==void 0&&this.queuedIdentities.set(S.id,u)})}}hasPendingWriteAhead(e){if(this.outbox)return this.outbox.pending?.()??!1;const t=l(e);return this.offlineQueue.hasPending(s=>l(s.shardKey)===t)}async hydratePersistedQueue(){try{const e=await this.offlineQueue.hydrate();for(const t of e)this.queuedOfflineShardKeys.add(t),this.ensureSocket(t)}catch{}}hydrateAsOutboxLeader(){const e=()=>{this.hydratePersistedQueue().catch(()=>{})},t=globalThis.navigator?.locks;if(!t){e();return}t.request(`lunora:outbox-leader:${this.url}`,()=>(this.closed||e(),new Promise(s=>{if(this.closed){s();return}this.outboxLeaderRelease=s}))).catch(e)}async hydrateQueryCache(){if(this.queryCache)try{const e=await this.queryCache.load(),t=new Map;for(const s of this.subscriptions.all())t.set(I(s.fn.__lunoraRef,s.argsKey,s.shardKey),s);for(const{key:s,...r}of e){if(Le(this.persistenceVersion,r.version)){this.queryCache.remove(s).catch(()=>{});continue}const i=t.get(s);if(i&&this.cachedQueryMatchesIdentity(r)){this.seedSubscriptionFromCache(i,r);continue}this.hydratedQueryCache.set(s,r)}}catch{}}seedSubscriptionFromCache(e,t){e.serverBase!==void 0||e.lastValue!==void 0||!this.cachedQueryMatchesIdentity(t)||(e.serverBase=t.value,e.serverCursor=t.serverCursor,t.serverEpoch!==void 0&&(e.serverEpoch=t.serverEpoch),this.cacheSeededQueries.set(I(e.fn.__lunoraRef,e.argsKey,e.shardKey),t),A(e,_(t.value,e.optimisticLayers)))}syncReadCacheToCredential(e){this.subjectAwaitingReconfirm()?this.revokeCacheSeededValues():e&&this.reseedFromHydratedCache()}dropCacheSeed(e){this.cacheSeededQueries.delete(e),this.hydratedQueryCache.delete(e)}returnCacheSeed(e){const t=this.cacheSeededQueries.get(e);t!==void 0&&(this.cacheSeededQueries.delete(e),this.hydratedQueryCache.set(e,t))}revokeCacheSeededValues(){if(this.cacheSeededQueries.size!==0){for(const[e,t]of this.cacheSeededQueries){const s=this.subscriptions.get(e);s!==void 0&&(s.serverBase=void 0,s.serverCursor=void 0,s.serverEpoch=void 0,A(s,_(void 0,s.optimisticLayers))),this.hydratedQueryCache.set(e,t)}this.cacheSeededQueries.clear()}}takeHydratedCache(e,t,s){const r=I(e,t,s),i=this.hydratedQueryCache.get(r);if(!(i===void 0||!this.cachedQueryMatchesIdentity(i)))return this.hydratedQueryCache.delete(r),i}reseedFromHydratedCache(){if(this.hydratedQueryCache.size!==0)for(const e of this.subscriptions.all()){const t=I(e.fn.__lunoraRef,e.argsKey,e.shardKey),s=this.hydratedQueryCache.get(t);s!==void 0&&this.cachedQueryMatchesIdentity(s)&&(this.hydratedQueryCache.delete(t),this.seedSubscriptionFromCache(e,s))}}persistQueryValue(e){const t=e.serverBase;if(!this.queryCache||t===void 0)return;const s=I(e.fn.__lunoraRef,e.argsKey,e.shardKey),r=this.getConnection(e.shardKey)?.identity,i=r===void 0?this.identityFingerprint():r;i===null&&this.identityUnresolved()||(this.pendingCacheWrites.set(s,{identity:i,serverCursor:e.serverCursor,ts:Date.now(),value:t,...i===this.identityFingerprint()&&!this.subjectAwaitingReconfirm()?this.credentialStamp():{},...e.serverEpoch===void 0?{}:{serverEpoch:e.serverEpoch},...this.persistenceVersion===void 0?{}:{version:this.persistenceVersion}}),this.cacheFlushTimer??=setTimeout(()=>{this.flushQueryCacheWrites().catch(()=>{})},mt))}async flushQueryCacheWrites(){this.cacheFlushTimer=void 0;const{queryCache:e}=this;if(!e){this.pendingCacheWrites.clear();return}const t=[...this.pendingCacheWrites.entries()];this.pendingCacheWrites.clear(),await Promise.allSettled(t.map(async([s,r])=>e.put(s,r)))}computeStatus(){if(this.tabCoordinator&&!this.tabCoordinator.isLeader())return this.leaderStatus??"idle";const e=[...this.connections.values()];return e.length===0?"idle":e.some(t=>t.wsState==="open")?"connected":e.some(t=>t.polling.isPolling())?"polling":e.some(t=>t.wsState==="connecting")?"connecting":"offline"}baselineCursorFor(e){const t=l(e);let s;for(const r of this.subscriptions.all())l(r.shardKey)!==t||r.serverCursor===void 0||(s=s===void 0?r.serverCursor:Math.max(s,r.serverCursor));return s}async pollSubscriptions(e){const t=l(e),s=[];for(const a of this.subscriptions.all())l(a.shardKey)===t&&(le(a.args)?s.push(a):w(a.errorCallbacks,{code:"WIRE_ENCODE_FAILED",message:"could not encode this subscription's args for a poll"}));if(s.length===0)return this.probeOrigin();const r=Fe(),i=this.identityFingerprint();let n;try{n=await ue(async a=>this.sendBatch(s.map(o=>({args:o.args,fn:o.fn,shardKey:o.shardKey})),a))}catch(a){return!(a instanceof TypeError)}if(this.identityFingerprint()!==i)return!0;for(const[a,o]of s.entries()){const h=n[a];if(h!==void 0){if(!h.ok){w(o.errorCallbacks,{code:h.error.code,message:h.error.message});continue}this.handleDataMessage({data:L(h.value),id:o.id,type:"data"},r)}}return!0}async probeOrigin(){const{fetchImpl:e}=this;if(!e)return!1;try{return await ue(async t=>e(k(this.url,q),{body:JSON.stringify({calls:[]}),headers:this.rpcRequestHeaders({}),method:"POST",signal:t})),!0}catch{return!1}}emitConnectionStatus(){const e=this.computeStatus();e!==this.lastStatus&&(this.lastStatus=e,this.statusListeners.emit(e),this.tabCoordinator?.isLeader()&&this.tabCoordinator.broadcastConnectionStatus(e,this.identityFingerprint()))}emitItemSettled(e,t,s){this.mutationSettledListeners.emit({args:e.args,code:s===void 0?void 0:s.code,error:s,functionPath:e.functionPath,hadAwaiter:e.liveAwaiter??!1,id:e.id??"",shardKey:e.shardKey,status:t})}applyOptimisticUpdates(e,t,s,r){const i=[],n=[];if(!r)return{confirms:i,rollbacks:n};const a=C.key(e,t,s),o=this.subscriptions.get(a);if(o){const h=Oe(o,r);h&&(i.push(h.confirm),n.push(h.rollback))}return{confirms:i,rollbacks:n}}applyOptimisticUpdate(e,t,s,r,i){const{confirms:n,rollbacks:a,store:o}=Re(this.subscriptions,s);try{e(o,t)}catch{F(a);return}r.push(...a),i.push(...n)}getConnection(e){return this.connections.get(l(e))}sendOrQueueUnsubscribe(e,t,s){const r=this.getConnection(e);r&&!v(r,{id:t,type:s})&&r.pendingUnsubscribes.push({id:t,type:s})}connectionGateState(e){if(this.tabCoordinator&&!this.tabCoordinator.isLeader()){let r="idle";return this.leaderStatus==="connected"?r="open":this.leaderStatus==="connecting"&&(r="connecting"),{hasSocket:!1,idleClosed:!1,polling:this.leaderStatus==="polling",wasEverConnected:this.leaderWasEverConnected,wsState:r}}const t=this.getConnection(e),s=t===void 0&&this.idleClosedShards.has(l(e));return{hasSocket:t?.socket!==void 0,idleClosed:s,polling:t?.polling.isPolling()??!1,wasEverConnected:t?.wasEverConnected??s,wsState:t?.wsState??"idle"}}getOrCreateConnection(e){const t=l(e);let s=this.connections.get(t);return s||(s={connectTimer:void 0,heartbeatTimer:void 0,lastFrameAt:0,pendingUnsubscribes:[],polling:at({afterFailedAttempts:this.pollingFallbackAfterFailedAttempts,intervalMs:this.pollingFallbackIntervalMs,onReachable:()=>{this.flushOfflineQueue(e).catch(()=>{})},onStateChange:()=>{this.emitConnectionStatus()},poll:async()=>this.pollSubscriptions(e)}),reconnect:se(this.reconnectOptions),reconnectTimer:void 0,resubscribePending:new Map,resubscribeQueue:[],shardKey:e,socket:void 0,stableTimer:void 0,wasEverConnected:this.idleClosedShards.delete(t),wsState:"idle"},this.connections.set(t,s)),s}wsUrlFor(e,t){const s=[];if(e!==void 0&&s.push(`shard=${encodeURIComponent(e)}`),t!==void 0&&s.push(`token=${encodeURIComponent(t)}`),s.length===0)return this.wsUrl;const r=this.wsUrl.includes("?")?"&":"?";return`${this.wsUrl}${r}${s.join("&")}`}rpcRequestHeaders(e,t){const s={"content-type":"application/json"};e.expectSubject!==void 0&&(s[Je]=Ye(e.expectSubject));const r=this.shardCursors.get(this.cursorKeyFor(t));r!==void 0&&(s["x-lunora-min-seq"]=r.toString());const i=e.authToken===void 0?this.authToken:e.authToken;if(i&&(s.authorization=`Bearer ${i}`),e.mutationId&&(s["x-lunora-mutation-id"]=e.mutationId),(e.clientId!==void 0||e.mutationId!==void 0)&&(s["x-lunora-client-id"]=e.clientId??this.clientId),e.clientSeq!==void 0&&(s["x-lunora-client-seq"]=e.clientSeq.toString()),e.baselineSeq!==void 0&&(s["x-lunora-base-seq"]=e.baselineSeq.toString()),e.attachBookmark){const n=this.bookmark.get();n&&(s["x-d1-bookmark"]=n)}return s}async rpc(e,t,s,r={}){if(!this.fetchImpl)throw new ee("LunoraClient: no `fetch` implementation available");const i=this.rpcRequestHeaders(r,s),n=await this.fetchImpl(k(this.url,ot),{body:JSON.stringify({args:E(t,`args for '${e}'`),functionPath:e,shardKey:s}),headers:i,method:"POST"});if(r.captureBookmark){const d=n.headers.get("x-d1-bookmark");d&&this.bookmark.set(d)}let a;try{a=await n.json()}catch{throw P(n.status,n.statusText,n.headers.get("retry-after"))}const o=a;if(typeof o!="object"||o===null||Array.isArray(o))throw P(n.status,n.statusText,n.headers.get("retry-after"));const h=M(a);if(h!==void 0)throw de(h,n.headers.get("retry-after"));if(!n.ok)throw P(n.status,n.statusText,n.headers.get("retry-after"));r.onMutationAck?.(a.lastMutationId),r.onCommitCursor?.(a.commitCursor),this.learnDefaultShardKey(n,s),this.recordShardCursor(s,a.commitCursor);try{return g(a.result)}catch(d){throw re(d)}}async adminFetch(e,t,s,r){if(!this.fetchImpl)throw new y("INTERNAL","LunoraClient: no `fetch` implementation available");const i={};this.authToken&&(i.authorization=`Bearer ${this.authToken}`);const n=s instanceof ArrayBuffer||s instanceof Blob;let a;s===void 0?a=void 0:n?(a=s,r!==void 0&&(i["content-type"]=r)):(a=JSON.stringify(s),i["content-type"]="application/json");const o=await this.fetchImpl(k(this.url,e),{body:a,headers:i,method:t});let h;try{h=await o.json()}catch{const u=o.statusText?` ${o.statusText}`:"";throw new y("INTERNAL",`LunoraClient: response was not JSON (status ${o.status.toString()}${u})`)}const d=M(h);if(d!==void 0){const u=new Error(d.message??"admin request failed");throw u.code=d.code,u}if(!o.ok){const u=o.statusText?` ${o.statusText}`:"";throw new y("INTERNAL",`LunoraClient: admin request failed (status ${o.status.toString()}${u})`)}return h}effectiveConnectionContext(e){const t=this.connectionContextHolders.get(e);return t&&t.length>0?t[t.length-1]?.context:this.connectionContexts.get(e)??this.defaultConnectionContext}refreshConnectionContext(e){const t=this.connections.get(e);t?.wsState==="open"&&this.sendConnectEnvelope(t)}sendConnectEnvelope(e){const t=this.effectiveConnectionContext(l(e.shardKey));v(e,{caps:Qs,clientId:this.clientId,id:"connect",type:"connect",...t===void 0?{}:{context:t}})}resendShapeSubscriptions(e){for(const t of this.shapeSubscriptions.values())l(t.shardKey)===l(e)&&this.sendShapeSubscribeIfOpen(t)}ensureSocket(e){if(this.closed||this.WebSocketImpl===void 0||this.tabCoordinator&&!this.tabCoordinator.isLeader())return;const t=this.getOrCreateConnection(e);if(!(t.wsState==="open"||t.wsState==="connecting")){if(t.wsState="connecting",this.emitConnectionStatus(),typeof this.wsToken=="function"){this.openSocketWithProvidedToken(t,e,this.wsToken).catch(()=>{});return}this.openSocket(t,e,this.wsToken)}}async openSocketWithProvidedToken(e,t,s){let r;try{r=await s()}catch{this.handleDisconnect(e);return}this.closed||this.WebSocketImpl===void 0||e.wsState!=="connecting"||e.socket!==void 0||this.openSocket(e,t,r)}openManagedSocket(e,t,s,r){const{WebSocketImpl:i}=this;if(i===void 0)throw new y("INTERNAL","no WebSocket implementation available");const n=new i(t);e.socket=n;const a=()=>{this.stopHeartbeat(e),e.connectTimer!==void 0&&(clearTimeout(e.connectTimer),e.connectTimer=void 0),e.socket===n&&(e.socket=void 0)},o=h=>{a(),r.onClose(h)};s>0&&(e.connectTimer=setTimeout(()=>{if(e.connectTimer=void 0,e.socket===n){try{n.close()}catch{}o()}},s)),n.addEventListener("open",()=>{if(e.socket===n){e.connectTimer!==void 0&&(clearTimeout(e.connectTimer),e.connectTimer=void 0),e.lastFrameAt=Date.now();try{r.onOpen?.()}catch(h){console.error("[lunora] connection open handler threw",h)}this.startHeartbeat(e,o)}}),n.addEventListener("message",h=>{if(e.socket===n){e.lastFrameAt=Date.now();try{r.onMessage(h)}catch(d){console.error("[lunora] server frame handler threw",d)}}}),n.addEventListener("close",h=>{e.socket===n&&o(h)}),n.addEventListener("error",()=>{e.socket===n&&o()})}openSocket(e,t,s){this.WebSocketImpl!==void 0&&(e.identity=this.identityFingerprint(),s===void 0&&this.authToken===null?(this.identityQuestions+=1,e.identityQuestion=this.identityQuestions):e.identityQuestion=void 0,e.retired=!1,this.openManagedSocket(e,this.wsUrlFor(t,s),this.connectTimeoutMs,{onClose:r=>{r?.code===4001&&this.notifyTokenExpired(),this.handleDisconnect(e)},onMessage:r=>{e.retired!==!0&&this.handleServerMessage(r.data,t)},onOpen:()=>{e.wsState="open",e.wasEverConnected=!0,e.polling.noteOpen(),clearTimeout(e.stableTimer),e.stableTimer=setTimeout(()=>{e.wsState==="open"&&e.reconnect.reset()},yt),this.emitConnectionStatus(),this.sendConnectEnvelope(e),this.markShardPendingAck(t),this.clearResubscribeQueue(e);for(const i of this.subscriptions.all())l(i.shardKey)===l(t)&&this.queueResubscribe(i);if(this.resendShapeSubscriptions(t),e.pendingUnsubscribes.length>0){const i=e.pendingUnsubscribes;e.pendingUnsubscribes=[];for(const{id:n,type:a}of i)v(e,{id:n,type:a});this.releaseIdleShard(t)}Ws(e);const r=this.whisperHandlers.get(l(t));if(r)for(const i of r.keys())v(e,{topic:i,type:"whisper_subscribe"});this.flushOfflineQueue(t).catch(()=>{})}}))}cancelStream(e,t){const s=this.getConnection(t);s&&(s.pendingStreams=s.pendingStreams?.filter(r=>r.id!==e),v(s,{id:e,type:"unsubscribe"})),this.forgetStream(e)}handleDisconnect(e){if(this.closed||e.wsState==="idle"||e.wsState==="closed")return;e.wsState==="connecting"&&e.polling.noteFailedOpen(),this.stopHeartbeat(e),this.clearConnectionTimers(e),e.socket=void 0,e.wsState="idle",this.emitConnectionStatus(),this.markShardPendingAck(e.shardKey),this.clearResubscribeQueue(e);const t=new Set((e.pendingStreams??[]).map(r=>r.id));for(const[r,i]of this.streams)if(!(l(i.shardKey)!==l(e.shardKey)||t.has(r))){if(i.durable){const n={...i.message,...i.generation===void 0?{}:{generation:i.generation},sinceChunk:i.lastSeq};i.message=n,e.pendingStreams=[...(e.pendingStreams??[]).filter(a=>a.id!==r),n];continue}i.handle.fail(new y("STREAM_DISCONNECTED","stream terminated: WebSocket disconnected")),this.forgetStream(r)}if(this.WebSocketImpl===void 0)return;const s=e.reconnect.next();e.reconnectTimer=setTimeout(()=>{e.reconnectTimer=void 0,this.ensureSocket(e.shardKey)},s)}startHeartbeat(e,t){this.stopHeartbeat(e),!(this.heartbeatIntervalMs<=0)&&(e.heartbeatTimer=setInterval(()=>{if(!e.socket)return;const{socket:s}=e;if(Date.now()-e.lastFrameAt>this.heartbeatIntervalMs*2.5){try{s.close()}catch{}t();return}try{s.send(dt)}catch{}},this.heartbeatIntervalMs))}stopHeartbeat(e){e.heartbeatTimer!==void 0&&(clearInterval(e.heartbeatTimer),e.heartbeatTimer=void 0)}markShardPendingAck(e){const t=l(e);for(const s of this.subscriptions.all())l(s.shardKey)===t&&(s.acked=!1)}queueResubscribe(e){const t=this.getConnection(e.shardKey);t&&(t.resubscribeQueue.push(e),this.drainResubscribeQueue(t))}drainResubscribeQueue(e){for(;e.resubscribePending.size<vt;){const t=e.resubscribeQueue.shift();if(!t)return;this.subscriptions.getById(t.id)&&this.sendSubscribeIfOpen(t)&&e.resubscribePending.set(t.id,setTimeout(()=>{this.releaseResubscribeSlot(e,t.id)},gt))}}releaseResubscribeSlot(e,t){const s=e.resubscribePending.get(t);s!==void 0&&(clearTimeout(s),e.resubscribePending.delete(t),this.drainResubscribeQueue(e))}clearResubscribeQueue(e){for(const t of e.resubscribePending.values())clearTimeout(t);e.resubscribePending.clear(),e.resubscribeQueue=[]}sendSubscribeIfOpen(e){const t=this.getConnection(e.shardKey);if(t?.wsState!=="open"||e.acked)return!1;const s=e.serverCursor!==void 0&&e.serverBase!==void 0;return v(t,{id:e.id,query:{args:e.wireArgs,functionPath:e.fn.__lunoraRef,table:e.fn.__lunoraRef,...s?{sinceSeq:e.serverCursor}:{},...s&&e.serverEpoch!==void 0?{sinceEpoch:e.serverEpoch}:{}},type:"subscribe"})}sendShapeSubscribeIfOpen(e){const t=this.getConnection(e.shardKey);t?.wsState==="open"&&v(t,{id:e.id,shape:{name:e.name,...e.wireArgs===void 0?{}:{args:e.wireArgs}},type:"shape_subscribe",...e.serverCursor===void 0?{}:{sinceCheckpoint:e.serverCursor},...e.serverEpoch===void 0?{}:{sinceEpoch:e.serverEpoch}})}handleServerMessage(e,t){const s=qs(e);if(s===void 0)return;let r;try{r=JSON.parse(s)}catch{return}if(r.type!=="error"&&this.getConnection(t)?.reconnect.reset(),typeof r.id=="string"){const i=this.getConnection(t);i&&this.releaseResubscribeSlot(i,r.id)}switch(r.type){case"ack":{const i=this.subscriptions.getById(r.id);i&&(i.acked=!0);return}case"chunk":{const{data:i,generation:n,id:a,seq:o}=r,h=this.streams.get(a);h&&typeof o=="number"&&(h.lastSeq=o,typeof n=="number"&&(h.generation=n),h.durable=!0),h?.handle.push(g(i));return}case"complete":{this.handleCompleteMessage(r.id);return}case"data":case"delta":{this.handleDataMessage(r);return}case"error":{this.handleErrorMessage(r);break}case"identity":{this.handleIdentityFrame(r,t);break}case"pokeEnd":{this.handlePokeEnd(r,t);break}case"pokePart":{this.handlePokePart(r,t);break}case"pokeStart":{this.handlePokeStart(r,t);break}case"resume":{this.handleResumeMessage(r);break}case"settled":{this.handleSettledMessage(r);break}case"whisper":{this.dispatchWhisper(r,t);break}}}handleErrorMessage(e){if(e.error?.code==="TOKEN_EXPIRED"){this.notifyTokenExpired();return}const{id:s}=e,r=s===void 0?void 0:this.streams.get(s);if(r&&s!==void 0){r.handle.fail(Ds(e)),this.forgetStream(s);return}const i=s===void 0?void 0:this.subscriptions.getById(s);if(i){const a=he(e),o=this.identityFingerprint(),h=C.keyOf(i);w(i.errorCallbacks,a),this.tabCoordinator?.isLeader()&&this.tabCoordinator.broadcastSubscriptionError(h,a,o);return}const n=s===void 0?void 0:this.shapeSubscriptions.get(s);n&&w(n.errorCallbacks,he(e))}pokeBufferKey(e,t){return`${l(e)}\0${t}`}handlePokeStart(e,t){ie(this.pokeBuffers,ye.MAX_POKE_BUFFERS),this.pokeBuffers.set(this.pokeBufferKey(t,e.pokeId),{baseCheckpoint:e.baseCheckpoint,bases:new Map,epoch:e.epoch,lastMutationId:new Map,parts:new Map,resets:new Set,undecodable:new Map})}handlePokePart(e,t){const s=this.pokeBuffers.get(this.pokeBufferKey(t,e.pokeId));if(!s)return;const r=[];try{for(const a of e.rowsPatch)r.push(a.value===void 0?a:{...a,value:g(a.value)})}catch(a){s.undecodable.set(e.shapeId,a);return}const i=s.parts.get(e.shapeId)??[];for(const a of r)i.push(a);s.parts.set(e.shapeId,i),e.lastMutationId!==void 0&&s.lastMutationId.set(e.shapeId,e.lastMutationId);const n=e.baseCheckpoint??s.baseCheckpoint;n!==void 0&&s.bases.set(e.shapeId,n),e.reset===!0&&s.resets.add(e.shapeId)}handlePokeEnd(e,t){const s=this.pokeBufferKey(t,e.pokeId),r=this.pokeBuffers.get(s);if(r){this.pokeBuffers.delete(s);for(const[i,n]of r.undecodable){const a=this.shapeSubscriptions.get(i);a&&w(a.errorCallbacks,{code:"WIRE_DECODE_FAILED",message:`could not decode a poke for this shape — ${n instanceof Error?n.message:String(n)}`})}for(const i of r.parts.keys()){const n=this.shapeSubscriptions.get(i);n&&!r.undecodable.has(i)&&this.applyPokePart(n,r,e)}}}applyPokePart(e,t,s){const r=t.parts.get(e.id)??[],i=t.resets.has(e.id),n=t.bases.get(e.id),a=t.epoch!==void 0&&e.serverEpoch!==void 0&&t.epoch!==e.serverEpoch,o=n!==void 0&&e.serverCursor!==void 0&&e.serverCursor!==n;if(!i&&(a||o)){e.rows.clear(),e.serverCursor=void 0,e.serverEpoch=void 0,this.emitShapeRows(e),this.sendShapeSubscribeIfOpen(e);return}i&&e.rows.clear(),ht(e.rows,r),s.checkpoint!==void 0&&(e.serverCursor=s.checkpoint),s.epoch!==void 0&&(e.serverEpoch=s.epoch);const h=t.lastMutationId.get(e.id);h!==void 0&&(e.lastMutationId=h),this.emitShapeRows(e),e.onCheckpoint?.({checkpoint:e.serverCursor,mutationId:e.lastMutationId})}resnapshotSubscription(e){e.acked=!1,e.serverCursor=void 0,e.serverEpoch=void 0,console.warn("[lunora] could not merge a row delta into the cached result; re-subscribing for a full snapshot"),this.sendSubscribeIfOpen(e)}emitShapeRows(e){const t=[...e.rows.values()];for(const s of e.callbacks)try{s(t)}catch{}}handleDataMessage(e,t){const{id:s}=e,r=s?this.subscriptions.getById(s):void 0;if(!r)return;let i;try{i=this.resolveDataPayload(e,r)}catch(n){w(r.errorCallbacks,{code:"WIRE_DECODE_FAILED",message:`could not decode a server frame for this subscription — ${n instanceof Error?n.message:String(n)}`});return}if(i===ae){this.resnapshotSubscription(r);return}if(r.serverBase=i,this.dropCacheSeed(C.keyOf(r)),e.cursor!==void 0&&(r.serverCursor=e.cursor),e.epoch!==void 0&&(r.serverEpoch=e.epoch),e.lastMutationId!==void 0){r.lastMutationId=Math.max(r.lastMutationId??0,e.lastMutationId);for(const n of r.checkpointCallbacks)n({checkpoint:r.serverCursor,mutationId:r.lastMutationId,rowsFollow:!0})}if(this.persistQueryValue(r),D(r,r.serverCursor),t!==void 0&&Pe(r,t),A(r,_(i,r.optimisticLayers)),this.tabCoordinator?.isLeader()){const n=C.keyOf(r);this.tabCoordinator.broadcastSubscriptionData(n,i,r.serverCursor,r.serverEpoch,this.identityFingerprint())}}handleResumeMessage(e){const t=this.subscriptions.getById(e.id);t&&this.ackAndAdvanceCursor(t,e.cursor,e.epoch)}handleSettledMessage(e){const t=this.subscriptions.getById(e.id);if(t){this.ackAndAdvanceCursor(t,e.cursor,e.epoch),e.lastMutationId!==void 0&&(t.lastMutationId=Math.max(t.lastMutationId??0,e.lastMutationId));for(const s of t.checkpointCallbacks)s({checkpoint:t.serverCursor,mutationId:t.lastMutationId});if(this.tabCoordinator?.isLeader()){const s=C.keyOf(t);this.tabCoordinator.broadcastSubscriptionSettled(s,t.serverCursor,t.serverEpoch,t.lastMutationId,this.clientId,this.identityFingerprint())}}}ackAndAdvanceCursor(e,t,s){e.acked=!0,(t!==void 0&&t!==e.serverCursor||s!==void 0&&s!==e.serverEpoch)&&(t!==void 0&&(e.serverCursor=t),s!==void 0&&(e.serverEpoch=s),this.persistQueryValue(e),D(e,e.serverCursor)&&A(e,_(e.serverBase,e.optimisticLayers)))}resolveDataPayload(e,t){if("data"in e&&e.data!==void 0)return g(e.data);const s=g(e.delta);return Te(s)?t.serverBase===void 0?s:Ce(t.serverBase,s)??ae:s}dispatchWhisper(e,t){const s=this.whisperHandlers.get(l(t))?.get(e.topic);if(!s)return;const r=g(e.data);for(const i of s)try{i(r,e.from)}catch{}}notifyTokenExpired(){this.tokenExpiredListeners.emit()}handleCompleteMessage(e){const t=this.streams.get(e);if(t){t.handle.complete(),this.forgetStream(e);return}const s=this.subscriptions.getById(e);s&&(s.acked=!1,w(s.errorCallbacks,{code:"SUBSCRIPTION_CANCELLED",message:"subscription was cancelled by the server"}))}unpersist(e){e&&this.persistence?.remove(e).catch(t=>{He(this.onPersistenceError,"remove",t,e)})}identityFingerprint(){if(this.authSubject!==void 0)return this.authSubject===null?null:`subj:${this.authSubject}`;const e=this.authToken;return e===null?null:this.hashToken(e)}hashToken(e){let t=2166136261,s=5381;for(let r=0;r<e.length;r+=1){const i=e.charCodeAt(r);t^=i,t=Math.imul(t,16777619),s=Math.imul(s,33)+i}return`${e.length.toString(36)}:${(t>>>0).toString(36)}:${(s>>>0).toString(36)}`}credentialStamp(){const e=this.authToken;return e===null?{}:{credential:this.hashToken(e)}}cachedQueryMatchesIdentity(e){return this.identityFingerprint()===null&&this.identityUnresolved()?!1:!this.subjectAwaitingReconfirm()&&e.identity===this.identityFingerprint()||this.isSameCredentialUnderTokenHash(e.identity)?!0:e.credential!==void 0&&e.credential===this.credentialStamp().credential}isSameCredentialUnderTokenHash(e){if(e===null||e.startsWith("subj:"))return!1;const t=this.authToken;return t===null?!1:this.hashToken(t)===e}releaseSessionProbe(){this.sessionProbesInFlight-=1,!(this.identityUnresolved()||this.identityFingerprint()!==null)&&!this.closed&&this.offlineQueue.size>0&&G(this.computeStatus())&&this.flushAllOfflineQueues()}identityUnresolved(){return this.sessionProbesInFlight>0?!0:this.identityResolutionExpected&&!this.identitySettled}adoptResolvedSubject(e,t,s){if(!(this.closed||this.authToken!==e||s!==this.sessionProbeGeneration)){if(e===null){this.adoptCookieSubject(t?.id??null,s);return}t!==null&&this.setAuthToken(e,t.id)}}adoptCookieSubject(e,t){return this.closed||this.authToken!==null||t<this.identityAnsweredAt?!1:(this.identityAnsweredAt=t,this.identitySettled=!0,this.setAuthToken(null,e),!0)}handleIdentityFrame(e,t){const s=this.getConnection(t)?.identityQuestion,{subject:r}=e;s===void 0||r!==null&&typeof r!="string"||this.adoptCookieSubject(r,s)||!this.closed&&this.authToken===null&&(r===null?null:`subj:${r}`)!==this.identityFingerprint()&&this.evictPreviousIdentitySession()}applySubject(e,t){if(t!==void 0){this.authSubject=t,this.subjectToken=e;return}(e===null&&this.authSubject!==null||e!==null&&this.authSubject===null)&&(this.authSubject=void 0,this.subjectToken=null)}isKnownNobody(){return this.authSubject===null&&this.authToken===null}subjectAwaitingReconfirm(){return this.authSubject!==void 0&&this.authSubject!==null&&this.subjectToken!==this.authToken}stampOf(e){const t=e.id===void 0?void 0:this.queuedIdentities.get(e.id);return t===void 0?e.identity:t}rejectQueuedForIdentityChange(e){const t=this.offlineQueue.drain(),s=[];for(const r of t){if(this.identityVerdict(this.stampOf(r))!=="mismatch"){s.push(r);continue}this.queuedIdentities.delete(r.id??""),this.unpersist(r.id);const i=new Error("offline mutation discarded: auth identity changed before replay");i.code="OFFLINE_IDENTITY_CHANGED",r.reject(i),this.emitItemSettled(r,"rejected",i)}this.offlineQueue.requeue(s),e!==null&&this.clearQueryCacheForIdentityChange()}restampConnectionIdentity(e,t){for(const s of this.connections.values())s.identity===e&&(s.identity=t)}restampQueuedIdentity(e,t){for(const[s,r]of this.queuedIdentities)r===e&&this.queuedIdentities.set(s,t);this.offlineQueue.restampIdentity(e,t)}restampWatermarks(e,t){const s=e??"",r=this.clientWatermarks.get(s);if(r===void 0)return;this.clientWatermarks.delete(s);const i=t??"",n=this.clientWatermarks.get(i);if(n===void 0)this.clientWatermarks.set(i,r);else for(const[a,o]of r)n.set(a,o)}clearQueryCacheForIdentityChange(){this.revokeCacheSeededValues(),this.cacheFlushTimer!==void 0&&(clearTimeout(this.cacheFlushTimer),this.cacheFlushTimer=void 0),this.pendingCacheWrites.clear(),this.hydratedQueryCache.clear(),this.queryCache?.clear().catch(()=>{})}evictPreviousIdentitySession(){this.revokeCacheSeededValues();for(const e of this.subscriptions.all())e.serverBase=void 0,e.serverCursor=void 0,e.serverEpoch=void 0,e.acked=!1,A(e,_(void 0,e.optimisticLayers));for(const e of this.shapeSubscriptions.values())e.rows.clear(),e.serverCursor=void 0,e.serverEpoch=void 0,this.emitShapeRows(e);this.bounceShardSockets(),this.retiredIdentities+=1,this.identityChangeListeners.emit()}restartTabCoordinatorForIdentity(){if(!this.tabCoordinator)return;const e=this.tabCoordinator.isLeader();this.tabCoordinator.stop(),this.tabCoordinator=this.createTabCoordinator(),this.tabCoordinator.start(),e&&this.tabCoordinator.promoteImmediately()}bounceShardSockets(){for(const e of this.connections.values())if(e.socket){e.retired=!0;try{e.socket.close()}catch{}}}flushAllOfflineQueues(){for(const e of this.queuedOfflineShardKeys)this.flushOfflineQueue(e).catch(()=>{})}async flushOfflineQueue(e){const t=l(e),s=this.offlineFlushes.get(t);if(s===void 0&&this.offlineQueue.size===0)return;const r=(async()=>{await(s??Promise.resolve());const{authToken:i}=this;try{await this.drainOfflineQueue(e,i)}catch{}!this.closed&&this.authToken!==i&&this.offlineQueue.size>0&&G(this.computeStatus())&&this.flushOfflineQueue(e).catch(()=>{})})();this.offlineFlushes.set(t,r),await r,this.offlineFlushes.get(t)===r&&(this.offlineFlushes.delete(t),this.releaseIdleShard(e))}async drainOfflineQueue(e,t){const s=this.offlineQueue.drainConflict();for(const d of s){this.unpersist(d.id),this.queuedIdentities.delete(d.id??"");const u=new Error("offline mutation skipped: precondition failed before replay");u.code="OFFLINE_PRECONDITION_FAILED",this.emitItemSettled(d,"rejected",u)}const r=l(e),i=this.offlineQueue.drain(d=>l(d.shardKey)===r);if(i.length===0)return;const n=[],a=[];for(const d of i){const u=this.replayGateVerdict(d);u==="send"?n.push(d):u==="hold"&&a.push(d)}if(this.offlineQueue.requeue(a),a.length>0&&this.subjectAwaitingReconfirm()&&(this.getCurrentUser().catch(()=>{}),this.noteHeldRetryDelay(e)),n.length===0){this.scheduleRateLimitedRetry(e);return}const o=this.encodableOrSettleTerminal(n);if(o.length===0){this.scheduleRateLimitedRetry(e);return}if(o.length===1){await this.replaySequential(o,e,t),this.scheduleRateLimitedRetry(e);return}const h=[];for(let d=0;d<o.length;d+=K){const u=o.slice(d,d+K),p=await this.replayBatched(u,e,t);if(h.push(...p.requeue),p.stop){h.push(...o.slice(d+K));break}}h.length>0&&this.offlineQueue.requeue(h),this.scheduleRateLimitedRetry(e)}noteHeldRetryDelay(e){const t=l(e),s=this.replayRetryState.get(t),r=(s?.attempts??0)+1;this.replayRetryState.set(t,{attempts:r,delayMs:Math.max(s?.delayMs??0,Ne(r))})}noteReplayRetryDelay(e,t){const s=l(e),r=this.replayRetryState.get(s),i=(r?.attempts??0)+1,n=Be(t,i);this.replayRetryState.set(s,{attempts:i,delayMs:n===void 0?r?.delayMs:Math.max(r?.delayMs??0,n)})}scheduleRateLimitedRetry(e){const t=l(e),s=this.replayRetryState.get(t),r=s?.delayMs;if(s===void 0||r===void 0||this.closed||this.offlineQueue.size===0){this.replayRetryState.delete(t);return}s.delayMs=void 0;const i=this.replayRetryTimers.get(t);i!==void 0&&clearTimeout(i),this.replayRetryTimers.set(t,setTimeout(()=>{this.replayRetryTimers.delete(t),this.flushOfflineQueue(e).catch(()=>{})},r))}encodableOrSettleTerminal(e){const t=[];for(const s of e)try{E(s.args,`args for '${s.functionPath}'`),t.push(s)}catch(r){this.settleReplayTerminal(s,r instanceof Error?r:new Error(String(r)))}return t}identityVerdict(e){if(this.subjectAwaitingReconfirm())return"unknown";const t=this.identityFingerprint();return t===null&&this.identityUnresolved()?"unknown":e===t||e!==void 0&&this.isSameCredentialUnderTokenHash(e)?"match":t===null?"unknown":"mismatch"}replayGateVerdict(e){const t=this.stampOf(e);if(t===void 0)return this.queuedIdentities.delete(e.id??""),"send";const s=this.identityVerdict(t);if(s==="unknown")return"hold";if(this.queuedIdentities.delete(e.id??""),s==="match")return"send";this.unpersist(e.id);const r=new Error("offline mutation skipped: auth identity changed before replay");return r.code="OFFLINE_IDENTITY_CHANGED",e.reject(r),this.emitItemSettled(e,"rejected",r),"reject"}settleReplaySuccess(e,t,s){this.unpersist(e.id),this.recordShardCursor(e.shardKey,s),e.onCommit?.(s),e.resolve(t),this.emitItemSettled(e,"committed")}cursorKeyFor(e){return e??this.defaultShardKey??""}learnDefaultShardKey(e,t){const s=e.headers.get("x-lunora-shard-key");if(s===null||t!==void 0||this.defaultShardKey===s)return;this.defaultShardKey=s;const r=this.shardCursors.get("");r!==void 0&&(this.shardCursors.set(s,Math.max(this.shardCursors.get(s)??0,r)),this.shardCursors.delete(""))}recordShardCursor(e,t){if(typeof t!="number")return;const s=this.cursorKeyFor(e);this.shardCursors.set(s,Math.max(this.shardCursors.get(s)??0,t))}shouldRequeueReplayFailure(e,t){return this.noteIdentityMismatch(e)?!0:this.noteReplayAuthRefusal(e,t)||Qe(e)}noteReplayAuthRefusal(e,t){if(!_e(e))return!1;const s=this.hashToken(t??"");return t===this.authToken&&this.authRefusalNotifiedFor!==s&&(this.authRefusalNotifiedFor=s,this.notifyTokenExpired()),!0}takeReplayCredential(e){if(e===void 0)return;const t=this.replayCredentials.get(e);if(t===void 0)throw new TypeError("LunoraClient: `replayCredential` must come from this client's `replayIdentityVerdict`, and is single use");return this.replayCredentials.delete(e),{flags:{authToken:t.authToken,...J(t.stamp,t.authToken)},stamp:t.stamp}}noteIdentityMismatch(e){if(e?.code!=="IDENTITY_MISMATCH")return!1;const t=this.identityFingerprint();return this.getCurrentUser().then(()=>{!this.warnedIdentityDisagreement&&this.identityFingerprint()===t&&(this.warnedIdentityDisagreement=!0,console.warn('[lunora] a replayed write was refused with IDENTITY_MISMATCH, but `/get-session` still names the same user. The worker\'s `resolveIdentity` must return the same `userId` as the better-auth `user.id`, and RPC requests must carry the session cookie (`credentials: "include"` on a cross-origin fetch).'))}).catch(()=>{}),!0}settleReplayUndecodable(e,t,s){this.unpersist(e.id),this.recordShardCursor(e.shardKey,s),e.onCommit?.(s),e.reject(t),this.emitItemSettled(e,"committed",t)}settleReplayTerminal(e,t){this.unpersist(e.id),e.reject(t),this.emitItemSettled(e,"rejected",t)}async replaySequential(e,t,s){for(let r=0;r<e.length;r+=1){const i=e[r];if(!i)continue;let n;try{const a=await this.rpc(i.functionPath,i.args,i.shardKey,{authToken:s,baselineSeq:i.baselineSeq,captureBookmark:!0,clientId:i.clientId??this.clientId,...J(i.identity,s),mutationId:i.id,onCommitCursor:o=>{n=o}});this.settleReplaySuccess(i,a,n)}catch(a){if(U(a)){this.settleReplayUndecodable(i,a,n);continue}if(!this.shouldRequeueReplayFailure(a,s)){this.settleReplayTerminal(i,a);continue}this.noteReplayRetryDelay(t,a),this.offlineQueue.requeue(e.slice(r));return}}}async replayBatched(e,t,s){if(!this.fetchImpl)return{requeue:e,stop:!0};const r=JSON.stringify({calls:e.map((h,d)=>({args:E(h.args,`args for '${h.functionPath}'`),baselineSeq:h.baselineSeq,functionPath:h.functionPath,id:d,clientId:h.clientId??this.clientId,mutationId:h.id,shardKey:h.shardKey}))});if(e.length>1&&De(r)>Ke)return await this.replayBatchedHalves(e,t,s);let i;try{i=await this.fetchImpl(k(this.url,q),{body:r,headers:this.rpcRequestHeaders({attachBookmark:!0,authToken:s,...J(e.find(h=>h.identity!==void 0)?.identity,s)}),method:"POST"})}catch{return{requeue:e,stop:!0}}const n=i.headers.get("x-d1-bookmark");if(n&&this.bookmark.set(n),i.status===413&&e.length>1)return await this.replayBatchedHalves(e,t,s);let a;const o=i.headers.get("retry-after");try{a=await i.json()}catch{return this.settleWholeBatchError(e,P(i.status,i.statusText,o),t,s)}if(!a.results){const h=M(a),d=h===void 0?P(i.status,i.statusText,o):de(h,o);return this.settleWholeBatchError(e,d,t,s)}return{requeue:this.settleReplayBatchSlots(e,a.results,t,s),stop:!1}}settleWholeBatchError(e,t,s,r){if(t instanceof ee||t.code!==void 0&&this.shouldRequeueReplayFailure(t,r))return this.noteReplayRetryDelay(s,t),{requeue:e,stop:!0};for(const i of e)this.settleReplayTerminal(i,t);return{requeue:[],stop:!1}}async replayBatchedHalves(e,t,s){const r=Math.ceil(e.length/2),i=await this.replayBatched(e.slice(0,r),t,s);if(i.stop)return{requeue:[...i.requeue,...e.slice(r)],stop:!0};const n=await this.replayBatched(e.slice(r),t,s);return{requeue:[...i.requeue,...n.requeue],stop:n.stop}}settleReplayBatchSlots(e,t,s,r){const i=new Map;for(const a of t)typeof a.id=="number"&&a.body!==void 0&&i.set(a.id,a.body);const n=[];for(const[a,o]of e.entries()){const h=i.get(a);if(h===void 0)n.push(o);else if("error"in h){const d=me(h);this.shouldRequeueReplayFailure(d,r)?(this.noteReplayRetryDelay(s,d),n.push(o)):this.settleReplayTerminal(o,d)}else this.settleReplayBatchResult(o,h)}return n}settleReplayBatchResult(e,t){let s;try{s=g(t.result)}catch(r){this.settleReplayUndecodable(e,re(r),t.commitCursor);return}this.settleReplaySuccess(e,s,t.commitCursor)}}export{ye as LunoraClient};
@@ -1 +0,0 @@
1
- const v=(e,r,d=!1)=>new Promise((a,s)=>{if(!e){s(new Error("No active service worker"));return}const o=r.correlationId??crypto.randomUUID(),n={...r,correlationId:o};if(d){let i;const t=c=>{c.data.correlationId===o&&(clearTimeout(i),navigator.serviceWorker.removeEventListener("message",t),a(c.data.payload))};i=setTimeout(()=>{navigator.serviceWorker.removeEventListener("message",t),s(new Error(`SW message ${o} timed out`))},3e4),navigator.serviceWorker.addEventListener("message",t),e.postMessage(n)}else e.postMessage(n),a(void 0)}),l=(e,r)=>({type:`${e.type}:reply`,payload:r,correlationId:e.correlationId});export{l as createReply,v as sendToSw};