@topgunbuild/client 0.2.0 → 0.3.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/dist/index.d.mts +840 -10
- package/dist/index.d.ts +840 -10
- package/dist/index.js +2258 -187
- package/dist/index.js.map +1 -1
- package/dist/index.mjs +2257 -180
- package/dist/index.mjs.map +1 -1
- package/package.json +2 -2
package/dist/index.d.ts
CHANGED
|
@@ -1,4 +1,4 @@
|
|
|
1
|
-
import { LWWRecord, ORMapRecord, PredicateNode, LWWMap, ORMap, Timestamp, HLC } from '@topgunbuild/core';
|
|
1
|
+
import { LWWRecord, ORMapRecord, PredicateNode, LWWMap, ORMap, Timestamp, HLC, NodeHealth, ConnectionPoolConfig, PartitionRouterConfig, PartitionMap, ClusterClientConfig } from '@topgunbuild/core';
|
|
2
2
|
export { LWWMap, LWWRecord, PredicateNode, Predicates } from '@topgunbuild/core';
|
|
3
3
|
import pino from 'pino';
|
|
4
4
|
|
|
@@ -304,6 +304,104 @@ interface OperationDroppedEvent {
|
|
|
304
304
|
key: string;
|
|
305
305
|
}
|
|
306
306
|
|
|
307
|
+
/**
|
|
308
|
+
* Connection Provider Types
|
|
309
|
+
*
|
|
310
|
+
* IConnectionProvider abstracts WebSocket connection handling to support
|
|
311
|
+
* both single-server and cluster modes.
|
|
312
|
+
*/
|
|
313
|
+
/**
|
|
314
|
+
* Events emitted by IConnectionProvider.
|
|
315
|
+
*/
|
|
316
|
+
type ConnectionProviderEvent = 'connected' | 'disconnected' | 'reconnected' | 'message' | 'partitionMapUpdated' | 'error';
|
|
317
|
+
/**
|
|
318
|
+
* Connection event handler type.
|
|
319
|
+
*/
|
|
320
|
+
type ConnectionEventHandler = (...args: any[]) => void;
|
|
321
|
+
/**
|
|
322
|
+
* Abstract interface for WebSocket connection providers.
|
|
323
|
+
*
|
|
324
|
+
* Implementations:
|
|
325
|
+
* - SingleServerProvider: Direct connection to a single server
|
|
326
|
+
* - ClusterClient: Multi-node connection pool with partition routing
|
|
327
|
+
*/
|
|
328
|
+
interface IConnectionProvider {
|
|
329
|
+
/**
|
|
330
|
+
* Connect to the server(s).
|
|
331
|
+
* In cluster mode, connects to all seed nodes.
|
|
332
|
+
*/
|
|
333
|
+
connect(): Promise<void>;
|
|
334
|
+
/**
|
|
335
|
+
* Get connection for a specific key.
|
|
336
|
+
* In cluster mode: routes to partition owner based on key hash.
|
|
337
|
+
* In single-server mode: returns the only connection.
|
|
338
|
+
*
|
|
339
|
+
* @param key - The key to route (used for partition-aware routing)
|
|
340
|
+
* @throws Error if not connected
|
|
341
|
+
*/
|
|
342
|
+
getConnection(key: string): WebSocket;
|
|
343
|
+
/**
|
|
344
|
+
* Get any available connection.
|
|
345
|
+
* Used for subscriptions, metadata requests, and non-key-specific operations.
|
|
346
|
+
*
|
|
347
|
+
* @throws Error if not connected
|
|
348
|
+
*/
|
|
349
|
+
getAnyConnection(): WebSocket;
|
|
350
|
+
/**
|
|
351
|
+
* Check if at least one connection is active and ready.
|
|
352
|
+
*/
|
|
353
|
+
isConnected(): boolean;
|
|
354
|
+
/**
|
|
355
|
+
* Get all connected node IDs.
|
|
356
|
+
* Single-server mode returns ['default'].
|
|
357
|
+
* Cluster mode returns actual node IDs.
|
|
358
|
+
*/
|
|
359
|
+
getConnectedNodes(): string[];
|
|
360
|
+
/**
|
|
361
|
+
* Subscribe to connection events.
|
|
362
|
+
*
|
|
363
|
+
* Events:
|
|
364
|
+
* - 'connected': A connection was established (nodeId?: string)
|
|
365
|
+
* - 'disconnected': A connection was lost (nodeId?: string)
|
|
366
|
+
* - 'reconnected': A connection was re-established after disconnect (nodeId?: string)
|
|
367
|
+
* - 'message': A message was received (nodeId: string, data: any)
|
|
368
|
+
* - 'partitionMapUpdated': Partition map was updated (cluster mode only)
|
|
369
|
+
* - 'error': An error occurred (error: Error)
|
|
370
|
+
*/
|
|
371
|
+
on(event: ConnectionProviderEvent, handler: ConnectionEventHandler): void;
|
|
372
|
+
/**
|
|
373
|
+
* Unsubscribe from connection events.
|
|
374
|
+
*/
|
|
375
|
+
off(event: ConnectionProviderEvent, handler: ConnectionEventHandler): void;
|
|
376
|
+
/**
|
|
377
|
+
* Send a message via the appropriate connection.
|
|
378
|
+
* In cluster mode, routes based on key if provided.
|
|
379
|
+
*
|
|
380
|
+
* @param data - Serialized message data
|
|
381
|
+
* @param key - Optional key for routing (cluster mode)
|
|
382
|
+
*/
|
|
383
|
+
send(data: ArrayBuffer | Uint8Array, key?: string): void;
|
|
384
|
+
/**
|
|
385
|
+
* Close all connections gracefully.
|
|
386
|
+
*/
|
|
387
|
+
close(): Promise<void>;
|
|
388
|
+
}
|
|
389
|
+
/**
|
|
390
|
+
* Configuration for SingleServerProvider.
|
|
391
|
+
*/
|
|
392
|
+
interface SingleServerProviderConfig {
|
|
393
|
+
/** WebSocket URL to connect to */
|
|
394
|
+
url: string;
|
|
395
|
+
/** Maximum reconnection attempts (default: 10) */
|
|
396
|
+
maxReconnectAttempts?: number;
|
|
397
|
+
/** Initial reconnect delay in ms (default: 1000) */
|
|
398
|
+
reconnectDelayMs?: number;
|
|
399
|
+
/** Backoff multiplier for reconnect delay (default: 2) */
|
|
400
|
+
backoffMultiplier?: number;
|
|
401
|
+
/** Maximum reconnect delay in ms (default: 30000) */
|
|
402
|
+
maxReconnectDelayMs?: number;
|
|
403
|
+
}
|
|
404
|
+
|
|
307
405
|
interface HeartbeatConfig {
|
|
308
406
|
intervalMs: number;
|
|
309
407
|
timeoutMs: number;
|
|
@@ -323,7 +421,10 @@ interface BackoffConfig {
|
|
|
323
421
|
}
|
|
324
422
|
interface SyncEngineConfig {
|
|
325
423
|
nodeId: string;
|
|
326
|
-
|
|
424
|
+
/** @deprecated Use connectionProvider instead */
|
|
425
|
+
serverUrl?: string;
|
|
426
|
+
/** Connection provider (preferred over serverUrl) */
|
|
427
|
+
connectionProvider?: IConnectionProvider;
|
|
327
428
|
storageAdapter: IStorageAdapter;
|
|
328
429
|
reconnectInterval?: number;
|
|
329
430
|
heartbeat?: Partial<HeartbeatConfig>;
|
|
@@ -337,6 +438,8 @@ declare class SyncEngine {
|
|
|
337
438
|
private readonly hlc;
|
|
338
439
|
private readonly stateMachine;
|
|
339
440
|
private readonly backoffConfig;
|
|
441
|
+
private readonly connectionProvider;
|
|
442
|
+
private readonly useConnectionProvider;
|
|
340
443
|
private websocket;
|
|
341
444
|
private opLog;
|
|
342
445
|
private maps;
|
|
@@ -357,6 +460,7 @@ declare class SyncEngine {
|
|
|
357
460
|
private waitingForCapacity;
|
|
358
461
|
private highWaterMarkEmitted;
|
|
359
462
|
private backpressureListeners;
|
|
463
|
+
private pendingWriteConcernPromises;
|
|
360
464
|
constructor(config: SyncEngineConfig);
|
|
361
465
|
/**
|
|
362
466
|
* Get the current connection state
|
|
@@ -383,6 +487,14 @@ declare class SyncEngine {
|
|
|
383
487
|
* Check if fully connected and synced
|
|
384
488
|
*/
|
|
385
489
|
private isConnected;
|
|
490
|
+
/**
|
|
491
|
+
* Initialize connection using IConnectionProvider (Phase 4.5 cluster mode).
|
|
492
|
+
* Sets up event handlers for the connection provider.
|
|
493
|
+
*/
|
|
494
|
+
private initConnectionProvider;
|
|
495
|
+
/**
|
|
496
|
+
* Initialize connection using direct WebSocket (legacy single-server mode).
|
|
497
|
+
*/
|
|
386
498
|
private initConnection;
|
|
387
499
|
private scheduleReconnect;
|
|
388
500
|
private calculateBackoffDelay;
|
|
@@ -390,6 +502,18 @@ declare class SyncEngine {
|
|
|
390
502
|
* Reset backoff counter (called on successful connection)
|
|
391
503
|
*/
|
|
392
504
|
private resetBackoff;
|
|
505
|
+
/**
|
|
506
|
+
* Send a message through the current connection.
|
|
507
|
+
* Uses connectionProvider if in cluster mode, otherwise uses direct websocket.
|
|
508
|
+
* @param message Message object to serialize and send
|
|
509
|
+
* @param key Optional key for routing (cluster mode only)
|
|
510
|
+
* @returns true if message was sent, false otherwise
|
|
511
|
+
*/
|
|
512
|
+
private sendMessage;
|
|
513
|
+
/**
|
|
514
|
+
* Check if we can send messages (connection is ready).
|
|
515
|
+
*/
|
|
516
|
+
private canSend;
|
|
393
517
|
private loadOpLog;
|
|
394
518
|
private saveOpLog;
|
|
395
519
|
registerMap(mapName: string, map: LWWMap<any, any> | ORMap<any, any>): void;
|
|
@@ -424,6 +548,11 @@ declare class SyncEngine {
|
|
|
424
548
|
releaseLock(name: string, requestId: string, fencingToken: number): Promise<boolean>;
|
|
425
549
|
private handleServerMessage;
|
|
426
550
|
getHLC(): HLC;
|
|
551
|
+
/**
|
|
552
|
+
* Helper method to apply a single server event to the local map.
|
|
553
|
+
* Used by both SERVER_EVENT and SERVER_BATCH_EVENT handlers.
|
|
554
|
+
*/
|
|
555
|
+
private applyServerEvent;
|
|
427
556
|
/**
|
|
428
557
|
* Closes the WebSocket connection and cleans up resources.
|
|
429
558
|
*/
|
|
@@ -433,6 +562,43 @@ declare class SyncEngine {
|
|
|
433
562
|
* Use after fatal errors to start fresh.
|
|
434
563
|
*/
|
|
435
564
|
resetConnection(): void;
|
|
565
|
+
/**
|
|
566
|
+
* Wait for a partition map update from the connection provider.
|
|
567
|
+
* Used when an operation fails with NOT_OWNER error and needs
|
|
568
|
+
* to wait for an updated partition map before retrying.
|
|
569
|
+
*
|
|
570
|
+
* @param timeoutMs - Maximum time to wait (default: 5000ms)
|
|
571
|
+
* @returns Promise that resolves when partition map is updated or times out
|
|
572
|
+
*/
|
|
573
|
+
waitForPartitionMapUpdate(timeoutMs?: number): Promise<void>;
|
|
574
|
+
/**
|
|
575
|
+
* Wait for the connection to be available.
|
|
576
|
+
* Used when an operation fails due to connection issues and needs
|
|
577
|
+
* to wait for reconnection before retrying.
|
|
578
|
+
*
|
|
579
|
+
* @param timeoutMs - Maximum time to wait (default: 10000ms)
|
|
580
|
+
* @returns Promise that resolves when connected or rejects on timeout
|
|
581
|
+
*/
|
|
582
|
+
waitForConnection(timeoutMs?: number): Promise<void>;
|
|
583
|
+
/**
|
|
584
|
+
* Wait for a specific sync state.
|
|
585
|
+
* Useful for waiting until fully connected and synced.
|
|
586
|
+
*
|
|
587
|
+
* @param targetState - The state to wait for
|
|
588
|
+
* @param timeoutMs - Maximum time to wait (default: 30000ms)
|
|
589
|
+
* @returns Promise that resolves when state is reached or rejects on timeout
|
|
590
|
+
*/
|
|
591
|
+
waitForState(targetState: SyncState, timeoutMs?: number): Promise<void>;
|
|
592
|
+
/**
|
|
593
|
+
* Check if the connection provider is connected.
|
|
594
|
+
* Convenience method for failover logic.
|
|
595
|
+
*/
|
|
596
|
+
isProviderConnected(): boolean;
|
|
597
|
+
/**
|
|
598
|
+
* Get the connection provider for direct access.
|
|
599
|
+
* Use with caution - prefer using SyncEngine methods.
|
|
600
|
+
*/
|
|
601
|
+
getConnectionProvider(): IConnectionProvider;
|
|
436
602
|
private resetMap;
|
|
437
603
|
/**
|
|
438
604
|
* Starts the heartbeat mechanism after successful connection.
|
|
@@ -514,6 +680,26 @@ declare class SyncEngine {
|
|
|
514
680
|
* Drop the oldest pending operation (used by 'drop-oldest' strategy).
|
|
515
681
|
*/
|
|
516
682
|
private dropOldestOp;
|
|
683
|
+
/**
|
|
684
|
+
* Register a pending Write Concern promise for an operation.
|
|
685
|
+
* The promise will be resolved when the server sends an ACK with the operation result.
|
|
686
|
+
*
|
|
687
|
+
* @param opId - Operation ID
|
|
688
|
+
* @param timeout - Timeout in ms (default: 5000)
|
|
689
|
+
* @returns Promise that resolves with the Write Concern result
|
|
690
|
+
*/
|
|
691
|
+
registerWriteConcernPromise(opId: string, timeout?: number): Promise<any>;
|
|
692
|
+
/**
|
|
693
|
+
* Resolve a pending Write Concern promise with the server result.
|
|
694
|
+
*
|
|
695
|
+
* @param opId - Operation ID
|
|
696
|
+
* @param result - Result from server ACK
|
|
697
|
+
*/
|
|
698
|
+
private resolveWriteConcernPromise;
|
|
699
|
+
/**
|
|
700
|
+
* Cancel all pending Write Concern promises (e.g., on disconnect).
|
|
701
|
+
*/
|
|
702
|
+
private cancelAllWriteConcernPromises;
|
|
517
703
|
}
|
|
518
704
|
|
|
519
705
|
interface ILock {
|
|
@@ -532,19 +718,55 @@ declare class DistributedLock implements ILock {
|
|
|
532
718
|
isLocked(): boolean;
|
|
533
719
|
}
|
|
534
720
|
|
|
721
|
+
/**
|
|
722
|
+
* Cluster mode configuration for TopGunClient.
|
|
723
|
+
* When provided, the client connects to multiple nodes with partition-aware routing.
|
|
724
|
+
*/
|
|
725
|
+
interface TopGunClusterConfig {
|
|
726
|
+
/** Initial seed nodes (at least one required) */
|
|
727
|
+
seeds: string[];
|
|
728
|
+
/** Connection pool size per node (default: 1) */
|
|
729
|
+
connectionsPerNode?: number;
|
|
730
|
+
/** Enable smart routing to partition owner (default: true) */
|
|
731
|
+
smartRouting?: boolean;
|
|
732
|
+
/** Partition map refresh interval in ms (default: 30000) */
|
|
733
|
+
partitionMapRefreshMs?: number;
|
|
734
|
+
/** Connection timeout per node in ms (default: 5000) */
|
|
735
|
+
connectionTimeoutMs?: number;
|
|
736
|
+
/** Retry attempts for failed operations (default: 3) */
|
|
737
|
+
retryAttempts?: number;
|
|
738
|
+
}
|
|
739
|
+
/**
|
|
740
|
+
* Default values for cluster configuration
|
|
741
|
+
*/
|
|
742
|
+
declare const DEFAULT_CLUSTER_CONFIG: Required<Omit<TopGunClusterConfig, 'seeds'>>;
|
|
743
|
+
/**
|
|
744
|
+
* TopGunClient configuration options
|
|
745
|
+
*/
|
|
746
|
+
interface TopGunClientConfig {
|
|
747
|
+
/** Unique node identifier (auto-generated if not provided) */
|
|
748
|
+
nodeId?: string;
|
|
749
|
+
/** Single-server mode: WebSocket URL to connect to */
|
|
750
|
+
serverUrl?: string;
|
|
751
|
+
/** Cluster mode: Configuration for multi-node routing */
|
|
752
|
+
cluster?: TopGunClusterConfig;
|
|
753
|
+
/** Storage adapter for local persistence */
|
|
754
|
+
storage: IStorageAdapter;
|
|
755
|
+
/** Backoff configuration for reconnection */
|
|
756
|
+
backoff?: Partial<BackoffConfig>;
|
|
757
|
+
/** Backpressure configuration */
|
|
758
|
+
backpressure?: Partial<BackpressureConfig>;
|
|
759
|
+
}
|
|
535
760
|
declare class TopGunClient {
|
|
536
761
|
private readonly nodeId;
|
|
537
762
|
private readonly syncEngine;
|
|
538
763
|
private readonly maps;
|
|
539
764
|
private readonly storageAdapter;
|
|
540
765
|
private readonly topicHandles;
|
|
541
|
-
|
|
542
|
-
|
|
543
|
-
|
|
544
|
-
|
|
545
|
-
backoff?: Partial<BackoffConfig>;
|
|
546
|
-
backpressure?: Partial<BackpressureConfig>;
|
|
547
|
-
});
|
|
766
|
+
private readonly clusterClient?;
|
|
767
|
+
private readonly isClusterMode;
|
|
768
|
+
private readonly clusterConfig?;
|
|
769
|
+
constructor(config: TopGunClientConfig);
|
|
548
770
|
start(): Promise<void>;
|
|
549
771
|
setAuthToken(token: string): void;
|
|
550
772
|
setAuthTokenProvider(provider: () => Promise<string | null>): void;
|
|
@@ -581,6 +803,46 @@ declare class TopGunClient {
|
|
|
581
803
|
* Closes the client, disconnecting from the server and cleaning up resources.
|
|
582
804
|
*/
|
|
583
805
|
close(): void;
|
|
806
|
+
/**
|
|
807
|
+
* Check if running in cluster mode
|
|
808
|
+
*/
|
|
809
|
+
isCluster(): boolean;
|
|
810
|
+
/**
|
|
811
|
+
* Get list of connected cluster nodes (cluster mode only)
|
|
812
|
+
* @returns Array of connected node IDs, or empty array in single-server mode
|
|
813
|
+
*/
|
|
814
|
+
getConnectedNodes(): string[];
|
|
815
|
+
/**
|
|
816
|
+
* Get the current partition map version (cluster mode only)
|
|
817
|
+
* @returns Partition map version, or 0 in single-server mode
|
|
818
|
+
*/
|
|
819
|
+
getPartitionMapVersion(): number;
|
|
820
|
+
/**
|
|
821
|
+
* Check if direct routing is active (cluster mode only)
|
|
822
|
+
* Direct routing sends operations directly to partition owners.
|
|
823
|
+
* @returns true if routing is active, false otherwise
|
|
824
|
+
*/
|
|
825
|
+
isRoutingActive(): boolean;
|
|
826
|
+
/**
|
|
827
|
+
* Get health status for all cluster nodes (cluster mode only)
|
|
828
|
+
* @returns Map of node IDs to their health status
|
|
829
|
+
*/
|
|
830
|
+
getClusterHealth(): Map<string, NodeHealth>;
|
|
831
|
+
/**
|
|
832
|
+
* Force refresh of partition map (cluster mode only)
|
|
833
|
+
* Use this after detecting routing errors.
|
|
834
|
+
*/
|
|
835
|
+
refreshPartitionMap(): Promise<void>;
|
|
836
|
+
/**
|
|
837
|
+
* Get cluster router statistics (cluster mode only)
|
|
838
|
+
*/
|
|
839
|
+
getClusterStats(): {
|
|
840
|
+
mapVersion: number;
|
|
841
|
+
partitionCount: number;
|
|
842
|
+
nodeCount: number;
|
|
843
|
+
lastRefresh: number;
|
|
844
|
+
isStale: boolean;
|
|
845
|
+
} | null;
|
|
584
846
|
/**
|
|
585
847
|
* Get the current connection state
|
|
586
848
|
*/
|
|
@@ -771,6 +1033,574 @@ declare class BackpressureError extends Error {
|
|
|
771
1033
|
constructor(pendingCount: number, maxPending: number);
|
|
772
1034
|
}
|
|
773
1035
|
|
|
1036
|
+
/**
|
|
1037
|
+
* ConnectionPool - Manages WebSocket connections to multiple cluster nodes
|
|
1038
|
+
*
|
|
1039
|
+
* Phase 4: Partition-Aware Client Routing
|
|
1040
|
+
*
|
|
1041
|
+
* Features:
|
|
1042
|
+
* - Maintains connections to all known cluster nodes
|
|
1043
|
+
* - Automatic reconnection with exponential backoff
|
|
1044
|
+
* - Health monitoring and status tracking
|
|
1045
|
+
* - Connection lifecycle management
|
|
1046
|
+
*/
|
|
1047
|
+
|
|
1048
|
+
interface ConnectionPoolEvents {
|
|
1049
|
+
'node:connected': (nodeId: string) => void;
|
|
1050
|
+
'node:disconnected': (nodeId: string, reason: string) => void;
|
|
1051
|
+
'node:healthy': (nodeId: string) => void;
|
|
1052
|
+
'node:unhealthy': (nodeId: string, reason: string) => void;
|
|
1053
|
+
'message': (nodeId: string, message: any) => void;
|
|
1054
|
+
'error': (nodeId: string, error: Error) => void;
|
|
1055
|
+
}
|
|
1056
|
+
declare class ConnectionPool {
|
|
1057
|
+
private readonly listeners;
|
|
1058
|
+
private readonly config;
|
|
1059
|
+
private readonly connections;
|
|
1060
|
+
private primaryNodeId;
|
|
1061
|
+
private healthCheckTimer;
|
|
1062
|
+
private authToken;
|
|
1063
|
+
constructor(config?: Partial<ConnectionPoolConfig>);
|
|
1064
|
+
on(event: string, listener: (...args: any[]) => void): this;
|
|
1065
|
+
off(event: string, listener: (...args: any[]) => void): this;
|
|
1066
|
+
emit(event: string, ...args: any[]): boolean;
|
|
1067
|
+
removeAllListeners(event?: string): this;
|
|
1068
|
+
/**
|
|
1069
|
+
* Set authentication token for all connections
|
|
1070
|
+
*/
|
|
1071
|
+
setAuthToken(token: string): void;
|
|
1072
|
+
/**
|
|
1073
|
+
* Add a node to the connection pool
|
|
1074
|
+
*/
|
|
1075
|
+
addNode(nodeId: string, endpoint: string): Promise<void>;
|
|
1076
|
+
/**
|
|
1077
|
+
* Remove a node from the connection pool
|
|
1078
|
+
*/
|
|
1079
|
+
removeNode(nodeId: string): Promise<void>;
|
|
1080
|
+
/**
|
|
1081
|
+
* Get connection for a specific node
|
|
1082
|
+
*/
|
|
1083
|
+
getConnection(nodeId: string): WebSocket | null;
|
|
1084
|
+
/**
|
|
1085
|
+
* Get primary connection (first/seed node)
|
|
1086
|
+
*/
|
|
1087
|
+
getPrimaryConnection(): WebSocket | null;
|
|
1088
|
+
/**
|
|
1089
|
+
* Get any healthy connection
|
|
1090
|
+
*/
|
|
1091
|
+
getAnyHealthyConnection(): {
|
|
1092
|
+
nodeId: string;
|
|
1093
|
+
socket: WebSocket;
|
|
1094
|
+
} | null;
|
|
1095
|
+
/**
|
|
1096
|
+
* Send message to a specific node
|
|
1097
|
+
*/
|
|
1098
|
+
send(nodeId: string, message: any): boolean;
|
|
1099
|
+
/**
|
|
1100
|
+
* Send message to primary node
|
|
1101
|
+
*/
|
|
1102
|
+
sendToPrimary(message: any): boolean;
|
|
1103
|
+
/**
|
|
1104
|
+
* Get health status for all nodes
|
|
1105
|
+
*/
|
|
1106
|
+
getHealthStatus(): Map<string, NodeHealth>;
|
|
1107
|
+
/**
|
|
1108
|
+
* Get list of connected node IDs
|
|
1109
|
+
*/
|
|
1110
|
+
getConnectedNodes(): string[];
|
|
1111
|
+
/**
|
|
1112
|
+
* Get all node IDs
|
|
1113
|
+
*/
|
|
1114
|
+
getAllNodes(): string[];
|
|
1115
|
+
/**
|
|
1116
|
+
* Check if node is connected and authenticated
|
|
1117
|
+
*/
|
|
1118
|
+
isNodeConnected(nodeId: string): boolean;
|
|
1119
|
+
/**
|
|
1120
|
+
* Check if connected to a specific node.
|
|
1121
|
+
* Alias for isNodeConnected() for IConnectionProvider compatibility.
|
|
1122
|
+
*/
|
|
1123
|
+
isConnected(nodeId: string): boolean;
|
|
1124
|
+
/**
|
|
1125
|
+
* Start health monitoring
|
|
1126
|
+
*/
|
|
1127
|
+
startHealthCheck(): void;
|
|
1128
|
+
/**
|
|
1129
|
+
* Stop health monitoring
|
|
1130
|
+
*/
|
|
1131
|
+
stopHealthCheck(): void;
|
|
1132
|
+
/**
|
|
1133
|
+
* Close all connections and cleanup
|
|
1134
|
+
*/
|
|
1135
|
+
close(): void;
|
|
1136
|
+
private connect;
|
|
1137
|
+
private sendAuth;
|
|
1138
|
+
private handleMessage;
|
|
1139
|
+
private flushPendingMessages;
|
|
1140
|
+
private scheduleReconnect;
|
|
1141
|
+
private performHealthCheck;
|
|
1142
|
+
}
|
|
1143
|
+
|
|
1144
|
+
/**
|
|
1145
|
+
* PartitionRouter - Routes operations to the correct cluster node
|
|
1146
|
+
*
|
|
1147
|
+
* Phase 4: Partition-Aware Client Routing
|
|
1148
|
+
*
|
|
1149
|
+
* Features:
|
|
1150
|
+
* - Maintains local copy of partition map
|
|
1151
|
+
* - Routes keys to owner nodes using consistent hashing
|
|
1152
|
+
* - Handles stale routing with automatic refresh
|
|
1153
|
+
* - Supports fallback to server-side forwarding
|
|
1154
|
+
*/
|
|
1155
|
+
|
|
1156
|
+
interface RoutingResult {
|
|
1157
|
+
nodeId: string;
|
|
1158
|
+
partitionId: number;
|
|
1159
|
+
isOwner: boolean;
|
|
1160
|
+
isBackup: boolean;
|
|
1161
|
+
}
|
|
1162
|
+
interface PartitionRouterEvents {
|
|
1163
|
+
'partitionMap:updated': (version: number, changesCount: number) => void;
|
|
1164
|
+
'partitionMap:stale': (currentVersion: number, lastRefresh: number) => void;
|
|
1165
|
+
'routing:miss': (key: string, expectedOwner: string, actualOwner: string) => void;
|
|
1166
|
+
}
|
|
1167
|
+
declare class PartitionRouter {
|
|
1168
|
+
private readonly listeners;
|
|
1169
|
+
private readonly config;
|
|
1170
|
+
private readonly connectionPool;
|
|
1171
|
+
private partitionMap;
|
|
1172
|
+
private lastRefreshTime;
|
|
1173
|
+
private refreshTimer;
|
|
1174
|
+
private pendingRefresh;
|
|
1175
|
+
constructor(connectionPool: ConnectionPool, config?: Partial<PartitionRouterConfig>);
|
|
1176
|
+
on(event: string, listener: (...args: any[]) => void): this;
|
|
1177
|
+
off(event: string, listener: (...args: any[]) => void): this;
|
|
1178
|
+
once(event: string, listener: (...args: any[]) => void): this;
|
|
1179
|
+
emit(event: string, ...args: any[]): boolean;
|
|
1180
|
+
removeListener(event: string, listener: (...args: any[]) => void): this;
|
|
1181
|
+
removeAllListeners(event?: string): this;
|
|
1182
|
+
/**
|
|
1183
|
+
* Get the partition ID for a given key
|
|
1184
|
+
*/
|
|
1185
|
+
getPartitionId(key: string): number;
|
|
1186
|
+
/**
|
|
1187
|
+
* Route a key to the owner node
|
|
1188
|
+
*/
|
|
1189
|
+
route(key: string): RoutingResult | null;
|
|
1190
|
+
/**
|
|
1191
|
+
* Route a key and get the WebSocket connection to use
|
|
1192
|
+
*/
|
|
1193
|
+
routeToConnection(key: string): {
|
|
1194
|
+
nodeId: string;
|
|
1195
|
+
socket: WebSocket;
|
|
1196
|
+
} | null;
|
|
1197
|
+
/**
|
|
1198
|
+
* Get routing info for multiple keys (batch routing)
|
|
1199
|
+
*/
|
|
1200
|
+
routeBatch(keys: string[]): Map<string, RoutingResult[]>;
|
|
1201
|
+
/**
|
|
1202
|
+
* Get all partitions owned by a specific node
|
|
1203
|
+
*/
|
|
1204
|
+
getPartitionsForNode(nodeId: string): number[];
|
|
1205
|
+
/**
|
|
1206
|
+
* Get current partition map version
|
|
1207
|
+
*/
|
|
1208
|
+
getMapVersion(): number;
|
|
1209
|
+
/**
|
|
1210
|
+
* Check if partition map is available
|
|
1211
|
+
*/
|
|
1212
|
+
hasPartitionMap(): boolean;
|
|
1213
|
+
/**
|
|
1214
|
+
* Get owner node for a key.
|
|
1215
|
+
* Returns null if partition map is not available.
|
|
1216
|
+
*/
|
|
1217
|
+
getOwner(key: string): string | null;
|
|
1218
|
+
/**
|
|
1219
|
+
* Get backup nodes for a key.
|
|
1220
|
+
* Returns empty array if partition map is not available.
|
|
1221
|
+
*/
|
|
1222
|
+
getBackups(key: string): string[];
|
|
1223
|
+
/**
|
|
1224
|
+
* Get the full partition map.
|
|
1225
|
+
* Returns null if not available.
|
|
1226
|
+
*/
|
|
1227
|
+
getMap(): PartitionMap | null;
|
|
1228
|
+
/**
|
|
1229
|
+
* Update entire partition map.
|
|
1230
|
+
* Only accepts newer versions.
|
|
1231
|
+
*/
|
|
1232
|
+
updateMap(map: PartitionMap): boolean;
|
|
1233
|
+
/**
|
|
1234
|
+
* Update a single partition (for delta updates).
|
|
1235
|
+
*/
|
|
1236
|
+
updatePartition(partitionId: number, owner: string, backups: string[]): void;
|
|
1237
|
+
/**
|
|
1238
|
+
* Check if partition map is stale
|
|
1239
|
+
*/
|
|
1240
|
+
isMapStale(): boolean;
|
|
1241
|
+
/**
|
|
1242
|
+
* Request fresh partition map from server
|
|
1243
|
+
*/
|
|
1244
|
+
refreshPartitionMap(): Promise<void>;
|
|
1245
|
+
/**
|
|
1246
|
+
* Start periodic partition map refresh
|
|
1247
|
+
*/
|
|
1248
|
+
startPeriodicRefresh(): void;
|
|
1249
|
+
/**
|
|
1250
|
+
* Stop periodic refresh
|
|
1251
|
+
*/
|
|
1252
|
+
stopPeriodicRefresh(): void;
|
|
1253
|
+
/**
|
|
1254
|
+
* Handle NOT_OWNER error from server
|
|
1255
|
+
*/
|
|
1256
|
+
handleNotOwnerError(key: string, actualOwner: string, newMapVersion: number): void;
|
|
1257
|
+
/**
|
|
1258
|
+
* Get statistics about routing
|
|
1259
|
+
*/
|
|
1260
|
+
getStats(): {
|
|
1261
|
+
mapVersion: number;
|
|
1262
|
+
partitionCount: number;
|
|
1263
|
+
nodeCount: number;
|
|
1264
|
+
lastRefresh: number;
|
|
1265
|
+
isStale: boolean;
|
|
1266
|
+
};
|
|
1267
|
+
/**
|
|
1268
|
+
* Cleanup resources
|
|
1269
|
+
*/
|
|
1270
|
+
close(): void;
|
|
1271
|
+
private handlePartitionMap;
|
|
1272
|
+
private handlePartitionMapDelta;
|
|
1273
|
+
private applyPartitionChange;
|
|
1274
|
+
private updateConnectionPool;
|
|
1275
|
+
private doRefreshPartitionMap;
|
|
1276
|
+
}
|
|
1277
|
+
|
|
1278
|
+
/**
|
|
1279
|
+
* ClusterClient - Cluster-aware client wrapper
|
|
1280
|
+
*
|
|
1281
|
+
* Phase 4: Partition-Aware Client Routing
|
|
1282
|
+
* Phase 4.5: Implements IConnectionProvider for SyncEngine abstraction
|
|
1283
|
+
*
|
|
1284
|
+
* Wraps the standard TopGunClient with cluster-aware routing capabilities.
|
|
1285
|
+
* Coordinates between ConnectionPool and PartitionRouter for optimal
|
|
1286
|
+
* request routing in a clustered environment.
|
|
1287
|
+
*/
|
|
1288
|
+
|
|
1289
|
+
interface ClusterClientEvents {
|
|
1290
|
+
'connected': () => void;
|
|
1291
|
+
'disconnected': (reason: string) => void;
|
|
1292
|
+
'partitionMap:ready': (version: number) => void;
|
|
1293
|
+
'routing:active': () => void;
|
|
1294
|
+
'error': (error: Error) => void;
|
|
1295
|
+
'circuit:open': (nodeId: string) => void;
|
|
1296
|
+
'circuit:closed': (nodeId: string) => void;
|
|
1297
|
+
'circuit:half-open': (nodeId: string) => void;
|
|
1298
|
+
}
|
|
1299
|
+
/**
|
|
1300
|
+
* Circuit breaker state for a node.
|
|
1301
|
+
*/
|
|
1302
|
+
interface CircuitState {
|
|
1303
|
+
/** Number of consecutive failures */
|
|
1304
|
+
failures: number;
|
|
1305
|
+
/** Timestamp of last failure */
|
|
1306
|
+
lastFailure: number;
|
|
1307
|
+
/** Current circuit state */
|
|
1308
|
+
state: 'closed' | 'open' | 'half-open';
|
|
1309
|
+
}
|
|
1310
|
+
/**
|
|
1311
|
+
* Routing metrics for monitoring smart routing effectiveness.
|
|
1312
|
+
*/
|
|
1313
|
+
interface RoutingMetrics {
|
|
1314
|
+
/** Operations routed directly to partition owner */
|
|
1315
|
+
directRoutes: number;
|
|
1316
|
+
/** Operations falling back to any node (owner unavailable) */
|
|
1317
|
+
fallbackRoutes: number;
|
|
1318
|
+
/** Operations when partition map is missing/stale */
|
|
1319
|
+
partitionMisses: number;
|
|
1320
|
+
/** Total routing decisions made */
|
|
1321
|
+
totalRoutes: number;
|
|
1322
|
+
}
|
|
1323
|
+
type ClusterRoutingMode = 'direct' | 'forward';
|
|
1324
|
+
/**
|
|
1325
|
+
* ClusterClient implements IConnectionProvider for multi-node cluster mode.
|
|
1326
|
+
* It provides partition-aware routing and connection management.
|
|
1327
|
+
*/
|
|
1328
|
+
declare class ClusterClient implements IConnectionProvider {
|
|
1329
|
+
private readonly listeners;
|
|
1330
|
+
private readonly connectionPool;
|
|
1331
|
+
private readonly partitionRouter;
|
|
1332
|
+
private readonly config;
|
|
1333
|
+
private initialized;
|
|
1334
|
+
private routingActive;
|
|
1335
|
+
private readonly routingMetrics;
|
|
1336
|
+
private readonly circuits;
|
|
1337
|
+
private readonly circuitBreakerConfig;
|
|
1338
|
+
constructor(config: ClusterClientConfig);
|
|
1339
|
+
on(event: string, listener: (...args: any[]) => void): this;
|
|
1340
|
+
off(event: string, listener: (...args: any[]) => void): this;
|
|
1341
|
+
emit(event: string, ...args: any[]): boolean;
|
|
1342
|
+
removeAllListeners(event?: string): this;
|
|
1343
|
+
/**
|
|
1344
|
+
* Connect to cluster nodes (IConnectionProvider interface).
|
|
1345
|
+
* Alias for start() method.
|
|
1346
|
+
*/
|
|
1347
|
+
connect(): Promise<void>;
|
|
1348
|
+
/**
|
|
1349
|
+
* Get connection for a specific key (IConnectionProvider interface).
|
|
1350
|
+
* Routes to partition owner based on key hash when smart routing is enabled.
|
|
1351
|
+
* @throws Error if not connected
|
|
1352
|
+
*/
|
|
1353
|
+
getConnection(key: string): WebSocket;
|
|
1354
|
+
/**
|
|
1355
|
+
* Get fallback connection when owner is unavailable.
|
|
1356
|
+
* @throws Error if no connection available
|
|
1357
|
+
*/
|
|
1358
|
+
private getFallbackConnection;
|
|
1359
|
+
/**
|
|
1360
|
+
* Request a partition map refresh in the background.
|
|
1361
|
+
* Called when routing to an unknown/disconnected owner.
|
|
1362
|
+
*/
|
|
1363
|
+
private requestPartitionMapRefresh;
|
|
1364
|
+
/**
|
|
1365
|
+
* Request partition map from a specific node.
|
|
1366
|
+
* Called on first node connection.
|
|
1367
|
+
*/
|
|
1368
|
+
private requestPartitionMapFromNode;
|
|
1369
|
+
/**
|
|
1370
|
+
* Check if at least one connection is active (IConnectionProvider interface).
|
|
1371
|
+
*/
|
|
1372
|
+
isConnected(): boolean;
|
|
1373
|
+
/**
|
|
1374
|
+
* Send data via the appropriate connection (IConnectionProvider interface).
|
|
1375
|
+
* Routes based on key if provided.
|
|
1376
|
+
*/
|
|
1377
|
+
send(data: ArrayBuffer | Uint8Array, key?: string): void;
|
|
1378
|
+
/**
|
|
1379
|
+
* Send data with automatic retry and rerouting on failure.
|
|
1380
|
+
* @param data - Data to send
|
|
1381
|
+
* @param key - Optional key for routing
|
|
1382
|
+
* @param options - Retry options
|
|
1383
|
+
* @throws Error after max retries exceeded
|
|
1384
|
+
*/
|
|
1385
|
+
sendWithRetry(data: ArrayBuffer | Uint8Array, key?: string, options?: {
|
|
1386
|
+
maxRetries?: number;
|
|
1387
|
+
retryDelayMs?: number;
|
|
1388
|
+
retryOnNotOwner?: boolean;
|
|
1389
|
+
}): Promise<void>;
|
|
1390
|
+
/**
|
|
1391
|
+
* Check if an error is retryable.
|
|
1392
|
+
*/
|
|
1393
|
+
private isRetryableError;
|
|
1394
|
+
/**
|
|
1395
|
+
* Wait for partition map update.
|
|
1396
|
+
*/
|
|
1397
|
+
private waitForPartitionMapUpdateInternal;
|
|
1398
|
+
/**
|
|
1399
|
+
* Wait for at least one connection to be available.
|
|
1400
|
+
*/
|
|
1401
|
+
private waitForConnectionInternal;
|
|
1402
|
+
/**
|
|
1403
|
+
* Helper delay function.
|
|
1404
|
+
*/
|
|
1405
|
+
private delay;
|
|
1406
|
+
/**
|
|
1407
|
+
* Initialize cluster connections
|
|
1408
|
+
*/
|
|
1409
|
+
start(): Promise<void>;
|
|
1410
|
+
/**
|
|
1411
|
+
* Set authentication token
|
|
1412
|
+
*/
|
|
1413
|
+
setAuthToken(token: string): void;
|
|
1414
|
+
/**
|
|
1415
|
+
* Send operation with automatic routing (legacy API for cluster operations).
|
|
1416
|
+
* @deprecated Use send(data, key) for IConnectionProvider interface
|
|
1417
|
+
*/
|
|
1418
|
+
sendMessage(key: string, message: any): boolean;
|
|
1419
|
+
/**
|
|
1420
|
+
* Send directly to partition owner
|
|
1421
|
+
*/
|
|
1422
|
+
sendDirect(key: string, message: any): boolean;
|
|
1423
|
+
/**
|
|
1424
|
+
* Send to primary node for server-side forwarding
|
|
1425
|
+
*/
|
|
1426
|
+
sendForward(message: any): boolean;
|
|
1427
|
+
/**
|
|
1428
|
+
* Send batch of operations with routing
|
|
1429
|
+
*/
|
|
1430
|
+
sendBatch(operations: Array<{
|
|
1431
|
+
key: string;
|
|
1432
|
+
message: any;
|
|
1433
|
+
}>): Map<string, boolean>;
|
|
1434
|
+
/**
|
|
1435
|
+
* Get connection pool health status
|
|
1436
|
+
*/
|
|
1437
|
+
getHealthStatus(): Map<string, NodeHealth>;
|
|
1438
|
+
/**
|
|
1439
|
+
* Get partition router stats
|
|
1440
|
+
*/
|
|
1441
|
+
getRouterStats(): ReturnType<PartitionRouter['getStats']>;
|
|
1442
|
+
/**
|
|
1443
|
+
* Get routing metrics for monitoring smart routing effectiveness.
|
|
1444
|
+
*/
|
|
1445
|
+
getRoutingMetrics(): RoutingMetrics;
|
|
1446
|
+
/**
|
|
1447
|
+
* Reset routing metrics counters.
|
|
1448
|
+
* Useful for monitoring intervals.
|
|
1449
|
+
*/
|
|
1450
|
+
resetRoutingMetrics(): void;
|
|
1451
|
+
/**
|
|
1452
|
+
* Check if cluster routing is active
|
|
1453
|
+
*/
|
|
1454
|
+
isRoutingActive(): boolean;
|
|
1455
|
+
/**
|
|
1456
|
+
* Get list of connected nodes
|
|
1457
|
+
*/
|
|
1458
|
+
getConnectedNodes(): string[];
|
|
1459
|
+
/**
|
|
1460
|
+
* Check if cluster client is initialized
|
|
1461
|
+
*/
|
|
1462
|
+
isInitialized(): boolean;
|
|
1463
|
+
/**
|
|
1464
|
+
* Force refresh of partition map
|
|
1465
|
+
*/
|
|
1466
|
+
refreshPartitionMap(): Promise<void>;
|
|
1467
|
+
/**
|
|
1468
|
+
* Shutdown cluster client (IConnectionProvider interface).
|
|
1469
|
+
*/
|
|
1470
|
+
close(): Promise<void>;
|
|
1471
|
+
/**
|
|
1472
|
+
* Get the connection pool (for internal use)
|
|
1473
|
+
*/
|
|
1474
|
+
getConnectionPool(): ConnectionPool;
|
|
1475
|
+
/**
|
|
1476
|
+
* Get the partition router (for internal use)
|
|
1477
|
+
*/
|
|
1478
|
+
getPartitionRouter(): PartitionRouter;
|
|
1479
|
+
/**
|
|
1480
|
+
* Get any healthy WebSocket connection (IConnectionProvider interface).
|
|
1481
|
+
* @throws Error if not connected
|
|
1482
|
+
*/
|
|
1483
|
+
getAnyConnection(): WebSocket;
|
|
1484
|
+
/**
|
|
1485
|
+
* Get any healthy WebSocket connection, or null if none available.
|
|
1486
|
+
* Use this for optional connection checks.
|
|
1487
|
+
*/
|
|
1488
|
+
getAnyConnectionOrNull(): WebSocket | null;
|
|
1489
|
+
/**
|
|
1490
|
+
* Get circuit breaker state for a node.
|
|
1491
|
+
*/
|
|
1492
|
+
getCircuit(nodeId: string): CircuitState;
|
|
1493
|
+
/**
|
|
1494
|
+
* Check if a node can be used (circuit not open).
|
|
1495
|
+
*/
|
|
1496
|
+
canUseNode(nodeId: string): boolean;
|
|
1497
|
+
/**
|
|
1498
|
+
* Record a successful operation to a node.
|
|
1499
|
+
* Resets circuit breaker on success.
|
|
1500
|
+
*/
|
|
1501
|
+
recordSuccess(nodeId: string): void;
|
|
1502
|
+
/**
|
|
1503
|
+
* Record a failed operation to a node.
|
|
1504
|
+
* Opens circuit breaker after threshold failures.
|
|
1505
|
+
*/
|
|
1506
|
+
recordFailure(nodeId: string): void;
|
|
1507
|
+
/**
|
|
1508
|
+
* Get all circuit breaker states.
|
|
1509
|
+
*/
|
|
1510
|
+
getCircuitStates(): Map<string, CircuitState>;
|
|
1511
|
+
/**
|
|
1512
|
+
* Reset circuit breaker for a specific node.
|
|
1513
|
+
*/
|
|
1514
|
+
resetCircuit(nodeId: string): void;
|
|
1515
|
+
/**
|
|
1516
|
+
* Reset all circuit breakers.
|
|
1517
|
+
*/
|
|
1518
|
+
resetAllCircuits(): void;
|
|
1519
|
+
private setupEventHandlers;
|
|
1520
|
+
private waitForPartitionMap;
|
|
1521
|
+
}
|
|
1522
|
+
|
|
1523
|
+
/**
|
|
1524
|
+
* SingleServerProvider implements IConnectionProvider for single-server mode.
|
|
1525
|
+
*
|
|
1526
|
+
* This is an adapter that wraps direct WebSocket connection handling,
|
|
1527
|
+
* providing the same interface used by ClusterClient for multi-node mode.
|
|
1528
|
+
*/
|
|
1529
|
+
declare class SingleServerProvider implements IConnectionProvider {
|
|
1530
|
+
private readonly url;
|
|
1531
|
+
private readonly config;
|
|
1532
|
+
private ws;
|
|
1533
|
+
private reconnectAttempts;
|
|
1534
|
+
private reconnectTimer;
|
|
1535
|
+
private isClosing;
|
|
1536
|
+
private listeners;
|
|
1537
|
+
constructor(config: SingleServerProviderConfig);
|
|
1538
|
+
/**
|
|
1539
|
+
* Connect to the WebSocket server.
|
|
1540
|
+
*/
|
|
1541
|
+
connect(): Promise<void>;
|
|
1542
|
+
/**
|
|
1543
|
+
* Get connection for a specific key.
|
|
1544
|
+
* In single-server mode, key is ignored.
|
|
1545
|
+
*/
|
|
1546
|
+
getConnection(_key: string): WebSocket;
|
|
1547
|
+
/**
|
|
1548
|
+
* Get any available connection.
|
|
1549
|
+
*/
|
|
1550
|
+
getAnyConnection(): WebSocket;
|
|
1551
|
+
/**
|
|
1552
|
+
* Check if connected.
|
|
1553
|
+
*/
|
|
1554
|
+
isConnected(): boolean;
|
|
1555
|
+
/**
|
|
1556
|
+
* Get connected node IDs.
|
|
1557
|
+
* Single-server mode returns ['default'] when connected.
|
|
1558
|
+
*/
|
|
1559
|
+
getConnectedNodes(): string[];
|
|
1560
|
+
/**
|
|
1561
|
+
* Subscribe to connection events.
|
|
1562
|
+
*/
|
|
1563
|
+
on(event: ConnectionProviderEvent, handler: ConnectionEventHandler): void;
|
|
1564
|
+
/**
|
|
1565
|
+
* Unsubscribe from connection events.
|
|
1566
|
+
*/
|
|
1567
|
+
off(event: ConnectionProviderEvent, handler: ConnectionEventHandler): void;
|
|
1568
|
+
/**
|
|
1569
|
+
* Send data via the WebSocket connection.
|
|
1570
|
+
* In single-server mode, key parameter is ignored.
|
|
1571
|
+
*/
|
|
1572
|
+
send(data: ArrayBuffer | Uint8Array, _key?: string): void;
|
|
1573
|
+
/**
|
|
1574
|
+
* Close the WebSocket connection.
|
|
1575
|
+
*/
|
|
1576
|
+
close(): Promise<void>;
|
|
1577
|
+
/**
|
|
1578
|
+
* Emit an event to all listeners.
|
|
1579
|
+
*/
|
|
1580
|
+
private emit;
|
|
1581
|
+
/**
|
|
1582
|
+
* Schedule a reconnection attempt with exponential backoff.
|
|
1583
|
+
*/
|
|
1584
|
+
private scheduleReconnect;
|
|
1585
|
+
/**
|
|
1586
|
+
* Calculate backoff delay with exponential increase.
|
|
1587
|
+
*/
|
|
1588
|
+
private calculateBackoffDelay;
|
|
1589
|
+
/**
|
|
1590
|
+
* Get the WebSocket URL this provider connects to.
|
|
1591
|
+
*/
|
|
1592
|
+
getUrl(): string;
|
|
1593
|
+
/**
|
|
1594
|
+
* Get current reconnection attempt count.
|
|
1595
|
+
*/
|
|
1596
|
+
getReconnectAttempts(): number;
|
|
1597
|
+
/**
|
|
1598
|
+
* Reset reconnection counter.
|
|
1599
|
+
* Called externally after successful authentication.
|
|
1600
|
+
*/
|
|
1601
|
+
resetReconnectAttempts(): void;
|
|
1602
|
+
}
|
|
1603
|
+
|
|
774
1604
|
declare const logger: pino.Logger<never, boolean>;
|
|
775
1605
|
|
|
776
|
-
export { type BackoffConfig, type BackpressureConfig, BackpressureError, type BackpressureStatus, type BackpressureStrategy, type BackpressureThresholdEvent, DEFAULT_BACKPRESSURE_CONFIG, EncryptedStorageAdapter, type HeartbeatConfig, IDBAdapter, type IStorageAdapter, type OpLogEntry, type OperationDroppedEvent, type QueryFilter, QueryHandle, type QueryResultItem, type QueryResultSource, type StateChangeEvent, type StateChangeListener, SyncEngine, type SyncEngineConfig, SyncState, SyncStateMachine, type SyncStateMachineConfig, TopGun, TopGunClient, type TopicCallback, TopicHandle, VALID_TRANSITIONS, isValidTransition, logger };
|
|
1606
|
+
export { type BackoffConfig, type BackpressureConfig, BackpressureError, type BackpressureStatus, type BackpressureStrategy, type BackpressureThresholdEvent, type CircuitState, ClusterClient, type ClusterClientEvents, type ClusterRoutingMode, type ConnectionEventHandler, ConnectionPool, type ConnectionPoolEvents, type ConnectionProviderEvent, DEFAULT_BACKPRESSURE_CONFIG, DEFAULT_CLUSTER_CONFIG, EncryptedStorageAdapter, type HeartbeatConfig, type IConnectionProvider, IDBAdapter, type IStorageAdapter, type OpLogEntry, type OperationDroppedEvent, PartitionRouter, type PartitionRouterEvents, type QueryFilter, QueryHandle, type QueryResultItem, type QueryResultSource, type RoutingMetrics, type RoutingResult, SingleServerProvider, type SingleServerProviderConfig, type StateChangeEvent, type StateChangeListener, SyncEngine, type SyncEngineConfig, SyncState, SyncStateMachine, type SyncStateMachineConfig, TopGun, TopGunClient, type TopGunClientConfig, type TopGunClusterConfig, type TopicCallback, TopicHandle, VALID_TRANSITIONS, isValidTransition, logger };
|