@prabhask5/stellar-engine 1.1.11 → 1.1.13
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/bin/install-pwa.js +19 -123
- package/dist/bin/install-pwa.js.map +1 -1
- package/dist/conflicts.d.ts +13 -0
- package/dist/conflicts.d.ts.map +1 -1
- package/dist/conflicts.js +32 -2
- package/dist/conflicts.js.map +1 -1
- package/dist/diagnostics.d.ts +217 -0
- package/dist/diagnostics.d.ts.map +1 -0
- package/dist/diagnostics.js +266 -0
- package/dist/diagnostics.js.map +1 -0
- package/dist/engine.d.ts +54 -10
- package/dist/engine.d.ts.map +1 -1
- package/dist/engine.js +62 -125
- package/dist/engine.js.map +1 -1
- package/dist/entries/types.d.ts +1 -0
- package/dist/entries/types.d.ts.map +1 -1
- package/dist/entries/utils.d.ts +5 -3
- package/dist/entries/utils.d.ts.map +1 -1
- package/dist/entries/utils.js +12 -3
- package/dist/entries/utils.js.map +1 -1
- package/dist/index.d.ts +3 -1
- package/dist/index.d.ts.map +1 -1
- package/dist/index.js +8 -1
- package/dist/index.js.map +1 -1
- package/dist/queue.d.ts.map +1 -1
- package/dist/queue.js +18 -3
- package/dist/queue.js.map +1 -1
- package/dist/realtime.d.ts +19 -10
- package/dist/realtime.d.ts.map +1 -1
- package/dist/realtime.js +29 -18
- package/dist/realtime.js.map +1 -1
- package/dist/stores/network.d.ts.map +1 -1
- package/dist/stores/network.js +7 -1
- package/dist/stores/network.js.map +1 -1
- package/dist/utils.d.ts +12 -0
- package/dist/utils.d.ts.map +1 -1
- package/dist/utils.js +24 -0
- package/dist/utils.js.map +1 -1
- package/package.json +1 -1
|
@@ -0,0 +1,217 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* @fileoverview Unified Diagnostics Module
|
|
3
|
+
*
|
|
4
|
+
* Provides a single entry point for inspecting the internal state of the
|
|
5
|
+
* stellar-engine sync system. The main `getDiagnostics()` function returns a
|
|
6
|
+
* comprehensive JSON snapshot covering sync cycles, egress, queue, realtime,
|
|
7
|
+
* network, conflict history, errors, and configuration.
|
|
8
|
+
*
|
|
9
|
+
* Each call returns a **point-in-time snapshot** — the data is not reactive.
|
|
10
|
+
* For a live dashboard, the consumer app should poll `getDiagnostics()` at the
|
|
11
|
+
* desired frequency (e.g., via `setInterval` or `onSyncComplete` callback).
|
|
12
|
+
*
|
|
13
|
+
* Sub-category functions (`getSyncDiagnostics`, `getRealtimeDiagnostics`, etc.)
|
|
14
|
+
* are also exported for lightweight access to specific sections without
|
|
15
|
+
* incurring the cost of async operations (queue/conflict reads).
|
|
16
|
+
*
|
|
17
|
+
* **Dependency direction:** This module imports from engine, realtime, queue,
|
|
18
|
+
* conflicts, config, deviceId, stores, and utils. No module imports from
|
|
19
|
+
* diagnostics — this guarantees zero circular dependency risk.
|
|
20
|
+
*
|
|
21
|
+
* @module diagnostics
|
|
22
|
+
* @see {@link ./engine.ts} for the core sync engine
|
|
23
|
+
* @see {@link ./realtime.ts} for WebSocket connection management
|
|
24
|
+
* @see {@link ./conflicts.ts} for conflict resolution history
|
|
25
|
+
*/
|
|
26
|
+
import type { ConflictHistoryEntry, SyncStatus } from './types';
|
|
27
|
+
import type { RealtimeConnectionState } from './realtime';
|
|
28
|
+
import type { SyncError } from './stores/sync';
|
|
29
|
+
/**
|
|
30
|
+
* Comprehensive diagnostics snapshot returned by {@link getDiagnostics}.
|
|
31
|
+
*
|
|
32
|
+
* Contains every observable aspect of the sync engine's runtime state,
|
|
33
|
+
* structured into logical sections for easy consumption by dashboards,
|
|
34
|
+
* logging pipelines, or browser console inspection.
|
|
35
|
+
*/
|
|
36
|
+
export interface DiagnosticsSnapshot {
|
|
37
|
+
/** ISO 8601 timestamp of when this snapshot was captured */
|
|
38
|
+
timestamp: string;
|
|
39
|
+
/** Engine prefix (e.g., `"engine"` or `"stellar"`) */
|
|
40
|
+
prefix: string;
|
|
41
|
+
/** Stable device identifier for this browser/device */
|
|
42
|
+
deviceId: string;
|
|
43
|
+
/** Sync cycle statistics and cursor state */
|
|
44
|
+
sync: {
|
|
45
|
+
status: SyncStatus;
|
|
46
|
+
totalCycles: number;
|
|
47
|
+
lastSyncTime: string | null;
|
|
48
|
+
lastSuccessfulSyncTimestamp: string | null;
|
|
49
|
+
syncMessage: string | null;
|
|
50
|
+
recentCycles: Array<{
|
|
51
|
+
timestamp: string;
|
|
52
|
+
trigger: string;
|
|
53
|
+
pushedItems: number;
|
|
54
|
+
pulledTables: number;
|
|
55
|
+
pulledRecords: number;
|
|
56
|
+
egressBytes: number;
|
|
57
|
+
durationMs: number;
|
|
58
|
+
}>;
|
|
59
|
+
cyclesLastMinute: number;
|
|
60
|
+
hasHydrated: boolean;
|
|
61
|
+
schemaValidated: boolean;
|
|
62
|
+
pendingCount: number;
|
|
63
|
+
};
|
|
64
|
+
/** Cumulative egress (bandwidth) statistics for the current session */
|
|
65
|
+
egress: {
|
|
66
|
+
sessionStart: string;
|
|
67
|
+
totalBytes: number;
|
|
68
|
+
totalFormatted: string;
|
|
69
|
+
totalRecords: number;
|
|
70
|
+
byTable: Record<string, {
|
|
71
|
+
bytes: number;
|
|
72
|
+
formatted: string;
|
|
73
|
+
records: number;
|
|
74
|
+
percentage: string;
|
|
75
|
+
}>;
|
|
76
|
+
};
|
|
77
|
+
/** Pending sync queue state */
|
|
78
|
+
queue: {
|
|
79
|
+
pendingOperations: number;
|
|
80
|
+
pendingEntityIds: string[];
|
|
81
|
+
byTable: Record<string, number>;
|
|
82
|
+
byOperationType: Record<string, number>;
|
|
83
|
+
oldestPendingTimestamp: string | null;
|
|
84
|
+
itemsInBackoff: number;
|
|
85
|
+
};
|
|
86
|
+
/** Realtime WebSocket connection state */
|
|
87
|
+
realtime: {
|
|
88
|
+
connectionState: RealtimeConnectionState;
|
|
89
|
+
healthy: boolean;
|
|
90
|
+
reconnectAttempts: number;
|
|
91
|
+
lastError: string | null;
|
|
92
|
+
userId: string | null;
|
|
93
|
+
deviceId: string;
|
|
94
|
+
recentlyProcessedCount: number;
|
|
95
|
+
operationInProgress: boolean;
|
|
96
|
+
reconnectScheduled: boolean;
|
|
97
|
+
};
|
|
98
|
+
/** Browser network connectivity */
|
|
99
|
+
network: {
|
|
100
|
+
online: boolean;
|
|
101
|
+
};
|
|
102
|
+
/** Engine-internal state (locks, visibility, auth) */
|
|
103
|
+
engine: {
|
|
104
|
+
isTabVisible: boolean;
|
|
105
|
+
tabHiddenAt: string | null;
|
|
106
|
+
lockHeld: boolean;
|
|
107
|
+
lockHeldForMs: number | null;
|
|
108
|
+
recentlyModifiedCount: number;
|
|
109
|
+
wasOffline: boolean;
|
|
110
|
+
authValidatedAfterReconnect: boolean;
|
|
111
|
+
};
|
|
112
|
+
/** Recent conflict resolution history */
|
|
113
|
+
conflicts: {
|
|
114
|
+
recentHistory: ConflictHistoryEntry[];
|
|
115
|
+
totalCount: number;
|
|
116
|
+
};
|
|
117
|
+
/** Error state from the sync status store */
|
|
118
|
+
errors: {
|
|
119
|
+
lastError: string | null;
|
|
120
|
+
lastErrorDetails: string | null;
|
|
121
|
+
recentErrors: SyncError[];
|
|
122
|
+
};
|
|
123
|
+
/** Engine configuration summary */
|
|
124
|
+
config: {
|
|
125
|
+
tableCount: number;
|
|
126
|
+
tableNames: string[];
|
|
127
|
+
syncDebounceMs: number;
|
|
128
|
+
syncIntervalMs: number;
|
|
129
|
+
tombstoneMaxAgeDays: number;
|
|
130
|
+
};
|
|
131
|
+
}
|
|
132
|
+
/**
|
|
133
|
+
* Capture a comprehensive diagnostics snapshot of the sync engine.
|
|
134
|
+
*
|
|
135
|
+
* This async function reads from all engine subsystems and returns a single
|
|
136
|
+
* JSON-serializable object. The async operations (queue reads, conflict
|
|
137
|
+
* history) are run in parallel for minimal latency.
|
|
138
|
+
*
|
|
139
|
+
* @returns A complete {@link DiagnosticsSnapshot}
|
|
140
|
+
*
|
|
141
|
+
* @example
|
|
142
|
+
* ```ts
|
|
143
|
+
* const snapshot = await getDiagnostics();
|
|
144
|
+
* console.log(JSON.stringify(snapshot, null, 2));
|
|
145
|
+
* ```
|
|
146
|
+
*/
|
|
147
|
+
export declare function getDiagnostics(): Promise<DiagnosticsSnapshot>;
|
|
148
|
+
/**
|
|
149
|
+
* Get sync cycle and egress diagnostics (synchronous).
|
|
150
|
+
*
|
|
151
|
+
* @returns Sync stats, egress totals, and per-table breakdown
|
|
152
|
+
*/
|
|
153
|
+
export declare function getSyncDiagnostics(): Pick<DiagnosticsSnapshot, 'sync' | 'egress'>;
|
|
154
|
+
/**
|
|
155
|
+
* Get realtime WebSocket connection diagnostics (synchronous).
|
|
156
|
+
*
|
|
157
|
+
* @returns Current realtime connection state and metadata
|
|
158
|
+
*/
|
|
159
|
+
export declare function getRealtimeDiagnostics(): {
|
|
160
|
+
connectionState: RealtimeConnectionState;
|
|
161
|
+
healthy: boolean;
|
|
162
|
+
reconnectAttempts: number;
|
|
163
|
+
lastError: string | null;
|
|
164
|
+
userId: string | null;
|
|
165
|
+
deviceId: string;
|
|
166
|
+
recentlyProcessedCount: number;
|
|
167
|
+
operationInProgress: boolean;
|
|
168
|
+
reconnectScheduled: boolean;
|
|
169
|
+
};
|
|
170
|
+
/**
|
|
171
|
+
* Get pending sync queue diagnostics (async — reads IndexedDB).
|
|
172
|
+
*
|
|
173
|
+
* @returns Pending operation count, entity IDs, and breakdowns by table/operation type
|
|
174
|
+
*/
|
|
175
|
+
export declare function getQueueDiagnostics(): Promise<DiagnosticsSnapshot['queue']>;
|
|
176
|
+
/**
|
|
177
|
+
* Get conflict resolution history diagnostics (async — reads IndexedDB).
|
|
178
|
+
*
|
|
179
|
+
* @returns Recent conflict entries and total count
|
|
180
|
+
*/
|
|
181
|
+
export declare function getConflictDiagnostics(): Promise<{
|
|
182
|
+
recentHistory: ConflictHistoryEntry[];
|
|
183
|
+
totalCount: number;
|
|
184
|
+
}>;
|
|
185
|
+
/**
|
|
186
|
+
* Get engine-internal state diagnostics (synchronous).
|
|
187
|
+
*
|
|
188
|
+
* @returns Lock state, visibility, auth validation status
|
|
189
|
+
*/
|
|
190
|
+
export declare function getEngineDiagnostics(): {
|
|
191
|
+
isTabVisible: boolean;
|
|
192
|
+
tabHiddenAt: string | null;
|
|
193
|
+
lockHeld: boolean;
|
|
194
|
+
lockHeldForMs: number | null;
|
|
195
|
+
recentlyModifiedCount: number;
|
|
196
|
+
wasOffline: boolean;
|
|
197
|
+
authValidatedAfterReconnect: boolean;
|
|
198
|
+
};
|
|
199
|
+
/**
|
|
200
|
+
* Get network connectivity diagnostics (synchronous).
|
|
201
|
+
*
|
|
202
|
+
* @returns Current online/offline status
|
|
203
|
+
*/
|
|
204
|
+
export declare function getNetworkDiagnostics(): {
|
|
205
|
+
online: boolean;
|
|
206
|
+
};
|
|
207
|
+
/**
|
|
208
|
+
* Get error state diagnostics (synchronous).
|
|
209
|
+
*
|
|
210
|
+
* @returns Latest error info and recent error history
|
|
211
|
+
*/
|
|
212
|
+
export declare function getErrorDiagnostics(): {
|
|
213
|
+
lastError: string | null;
|
|
214
|
+
lastErrorDetails: string | null;
|
|
215
|
+
recentErrors: SyncError[];
|
|
216
|
+
};
|
|
217
|
+
//# sourceMappingURL=diagnostics.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"diagnostics.d.ts","sourceRoot":"","sources":["../src/diagnostics.ts"],"names":[],"mappings":"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"}
|
|
@@ -0,0 +1,266 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* @fileoverview Unified Diagnostics Module
|
|
3
|
+
*
|
|
4
|
+
* Provides a single entry point for inspecting the internal state of the
|
|
5
|
+
* stellar-engine sync system. The main `getDiagnostics()` function returns a
|
|
6
|
+
* comprehensive JSON snapshot covering sync cycles, egress, queue, realtime,
|
|
7
|
+
* network, conflict history, errors, and configuration.
|
|
8
|
+
*
|
|
9
|
+
* Each call returns a **point-in-time snapshot** — the data is not reactive.
|
|
10
|
+
* For a live dashboard, the consumer app should poll `getDiagnostics()` at the
|
|
11
|
+
* desired frequency (e.g., via `setInterval` or `onSyncComplete` callback).
|
|
12
|
+
*
|
|
13
|
+
* Sub-category functions (`getSyncDiagnostics`, `getRealtimeDiagnostics`, etc.)
|
|
14
|
+
* are also exported for lightweight access to specific sections without
|
|
15
|
+
* incurring the cost of async operations (queue/conflict reads).
|
|
16
|
+
*
|
|
17
|
+
* **Dependency direction:** This module imports from engine, realtime, queue,
|
|
18
|
+
* conflicts, config, deviceId, stores, and utils. No module imports from
|
|
19
|
+
* diagnostics — this guarantees zero circular dependency risk.
|
|
20
|
+
*
|
|
21
|
+
* @module diagnostics
|
|
22
|
+
* @see {@link ./engine.ts} for the core sync engine
|
|
23
|
+
* @see {@link ./realtime.ts} for WebSocket connection management
|
|
24
|
+
* @see {@link ./conflicts.ts} for conflict resolution history
|
|
25
|
+
*/
|
|
26
|
+
import { _getEngineDiagnostics } from './engine';
|
|
27
|
+
import { _getRealtimeDiagnostics } from './realtime';
|
|
28
|
+
import { _getRecentConflictHistory } from './conflicts';
|
|
29
|
+
import { getPendingSync, getPendingEntityIds } from './queue';
|
|
30
|
+
import { getEngineConfig } from './config';
|
|
31
|
+
import { getDeviceId } from './deviceId';
|
|
32
|
+
import { syncStatusStore } from './stores/sync';
|
|
33
|
+
import { isOnline } from './stores/network';
|
|
34
|
+
import { formatBytes } from './utils';
|
|
35
|
+
import { get } from 'svelte/store';
|
|
36
|
+
// =============================================================================
|
|
37
|
+
// Main Diagnostics Function
|
|
38
|
+
// =============================================================================
|
|
39
|
+
/**
|
|
40
|
+
* Capture a comprehensive diagnostics snapshot of the sync engine.
|
|
41
|
+
*
|
|
42
|
+
* This async function reads from all engine subsystems and returns a single
|
|
43
|
+
* JSON-serializable object. The async operations (queue reads, conflict
|
|
44
|
+
* history) are run in parallel for minimal latency.
|
|
45
|
+
*
|
|
46
|
+
* @returns A complete {@link DiagnosticsSnapshot}
|
|
47
|
+
*
|
|
48
|
+
* @example
|
|
49
|
+
* ```ts
|
|
50
|
+
* const snapshot = await getDiagnostics();
|
|
51
|
+
* console.log(JSON.stringify(snapshot, null, 2));
|
|
52
|
+
* ```
|
|
53
|
+
*/
|
|
54
|
+
export async function getDiagnostics() {
|
|
55
|
+
const config = getEngineConfig();
|
|
56
|
+
const engineState = _getEngineDiagnostics();
|
|
57
|
+
const realtimeState = _getRealtimeDiagnostics();
|
|
58
|
+
const syncState = get(syncStatusStore);
|
|
59
|
+
// Run async operations in parallel
|
|
60
|
+
const [queueData, conflictData] = await Promise.all([
|
|
61
|
+
getQueueDiagnostics(),
|
|
62
|
+
getConflictDiagnostics()
|
|
63
|
+
]);
|
|
64
|
+
// Build egress section with formatted values
|
|
65
|
+
const egressByTable = {};
|
|
66
|
+
for (const [table, stats] of Object.entries(engineState.egressStats.byTable)) {
|
|
67
|
+
const pct = engineState.egressStats.totalBytes > 0
|
|
68
|
+
? ((stats.bytes / engineState.egressStats.totalBytes) * 100).toFixed(1)
|
|
69
|
+
: '0.0';
|
|
70
|
+
egressByTable[table] = {
|
|
71
|
+
bytes: stats.bytes,
|
|
72
|
+
formatted: formatBytes(stats.bytes),
|
|
73
|
+
records: stats.records,
|
|
74
|
+
percentage: `${pct}%`
|
|
75
|
+
};
|
|
76
|
+
}
|
|
77
|
+
// Count cycles in the last minute
|
|
78
|
+
const oneMinuteAgo = Date.now() - 60000;
|
|
79
|
+
const cyclesLastMinute = engineState.syncStats.filter((s) => new Date(s.timestamp).getTime() > oneMinuteAgo).length;
|
|
80
|
+
return {
|
|
81
|
+
timestamp: new Date().toISOString(),
|
|
82
|
+
prefix: config.prefix || 'engine',
|
|
83
|
+
deviceId: getDeviceId(),
|
|
84
|
+
sync: {
|
|
85
|
+
status: syncState.status,
|
|
86
|
+
totalCycles: engineState.totalSyncCycles,
|
|
87
|
+
lastSyncTime: syncState.lastSyncTime,
|
|
88
|
+
lastSuccessfulSyncTimestamp: engineState.lastSuccessfulSyncTimestamp
|
|
89
|
+
? new Date(engineState.lastSuccessfulSyncTimestamp).toISOString()
|
|
90
|
+
: null,
|
|
91
|
+
syncMessage: syncState.syncMessage,
|
|
92
|
+
recentCycles: engineState.syncStats,
|
|
93
|
+
cyclesLastMinute,
|
|
94
|
+
hasHydrated: engineState.hasHydrated,
|
|
95
|
+
schemaValidated: engineState.schemaValidated,
|
|
96
|
+
pendingCount: syncState.pendingCount
|
|
97
|
+
},
|
|
98
|
+
egress: {
|
|
99
|
+
sessionStart: engineState.egressStats.sessionStart,
|
|
100
|
+
totalBytes: engineState.egressStats.totalBytes,
|
|
101
|
+
totalFormatted: formatBytes(engineState.egressStats.totalBytes),
|
|
102
|
+
totalRecords: engineState.egressStats.totalRecords,
|
|
103
|
+
byTable: egressByTable
|
|
104
|
+
},
|
|
105
|
+
queue: queueData,
|
|
106
|
+
realtime: realtimeState,
|
|
107
|
+
network: getNetworkDiagnostics(),
|
|
108
|
+
engine: {
|
|
109
|
+
isTabVisible: engineState.isTabVisible,
|
|
110
|
+
tabHiddenAt: engineState.tabHiddenAt ? new Date(engineState.tabHiddenAt).toISOString() : null,
|
|
111
|
+
lockHeld: engineState.lockHeld,
|
|
112
|
+
lockHeldForMs: engineState.lockHeldForMs,
|
|
113
|
+
recentlyModifiedCount: engineState.recentlyModifiedCount,
|
|
114
|
+
wasOffline: engineState.wasOffline,
|
|
115
|
+
authValidatedAfterReconnect: engineState.authValidatedAfterReconnect
|
|
116
|
+
},
|
|
117
|
+
conflicts: conflictData,
|
|
118
|
+
errors: getErrorDiagnostics(),
|
|
119
|
+
config: {
|
|
120
|
+
tableCount: config.tables.length,
|
|
121
|
+
tableNames: config.tables.map((t) => t.supabaseName),
|
|
122
|
+
syncDebounceMs: config.syncDebounceMs ?? 2000,
|
|
123
|
+
syncIntervalMs: config.syncIntervalMs ?? 900000,
|
|
124
|
+
tombstoneMaxAgeDays: config.tombstoneMaxAgeDays ?? 7
|
|
125
|
+
}
|
|
126
|
+
};
|
|
127
|
+
}
|
|
128
|
+
// =============================================================================
|
|
129
|
+
// Sub-Category Diagnostics Functions
|
|
130
|
+
// =============================================================================
|
|
131
|
+
/**
|
|
132
|
+
* Get sync cycle and egress diagnostics (synchronous).
|
|
133
|
+
*
|
|
134
|
+
* @returns Sync stats, egress totals, and per-table breakdown
|
|
135
|
+
*/
|
|
136
|
+
export function getSyncDiagnostics() {
|
|
137
|
+
const engineState = _getEngineDiagnostics();
|
|
138
|
+
const syncState = get(syncStatusStore);
|
|
139
|
+
const egressByTable = {};
|
|
140
|
+
for (const [table, stats] of Object.entries(engineState.egressStats.byTable)) {
|
|
141
|
+
const pct = engineState.egressStats.totalBytes > 0
|
|
142
|
+
? ((stats.bytes / engineState.egressStats.totalBytes) * 100).toFixed(1)
|
|
143
|
+
: '0.0';
|
|
144
|
+
egressByTable[table] = {
|
|
145
|
+
bytes: stats.bytes,
|
|
146
|
+
formatted: formatBytes(stats.bytes),
|
|
147
|
+
records: stats.records,
|
|
148
|
+
percentage: `${pct}%`
|
|
149
|
+
};
|
|
150
|
+
}
|
|
151
|
+
const oneMinuteAgo = Date.now() - 60000;
|
|
152
|
+
const cyclesLastMinute = engineState.syncStats.filter((s) => new Date(s.timestamp).getTime() > oneMinuteAgo).length;
|
|
153
|
+
return {
|
|
154
|
+
sync: {
|
|
155
|
+
status: syncState.status,
|
|
156
|
+
totalCycles: engineState.totalSyncCycles,
|
|
157
|
+
lastSyncTime: syncState.lastSyncTime,
|
|
158
|
+
lastSuccessfulSyncTimestamp: engineState.lastSuccessfulSyncTimestamp
|
|
159
|
+
? new Date(engineState.lastSuccessfulSyncTimestamp).toISOString()
|
|
160
|
+
: null,
|
|
161
|
+
syncMessage: syncState.syncMessage,
|
|
162
|
+
recentCycles: engineState.syncStats,
|
|
163
|
+
cyclesLastMinute,
|
|
164
|
+
hasHydrated: engineState.hasHydrated,
|
|
165
|
+
schemaValidated: engineState.schemaValidated,
|
|
166
|
+
pendingCount: syncState.pendingCount
|
|
167
|
+
},
|
|
168
|
+
egress: {
|
|
169
|
+
sessionStart: engineState.egressStats.sessionStart,
|
|
170
|
+
totalBytes: engineState.egressStats.totalBytes,
|
|
171
|
+
totalFormatted: formatBytes(engineState.egressStats.totalBytes),
|
|
172
|
+
totalRecords: engineState.egressStats.totalRecords,
|
|
173
|
+
byTable: egressByTable
|
|
174
|
+
}
|
|
175
|
+
};
|
|
176
|
+
}
|
|
177
|
+
/**
|
|
178
|
+
* Get realtime WebSocket connection diagnostics (synchronous).
|
|
179
|
+
*
|
|
180
|
+
* @returns Current realtime connection state and metadata
|
|
181
|
+
*/
|
|
182
|
+
export function getRealtimeDiagnostics() {
|
|
183
|
+
return _getRealtimeDiagnostics();
|
|
184
|
+
}
|
|
185
|
+
/**
|
|
186
|
+
* Get pending sync queue diagnostics (async — reads IndexedDB).
|
|
187
|
+
*
|
|
188
|
+
* @returns Pending operation count, entity IDs, and breakdowns by table/operation type
|
|
189
|
+
*/
|
|
190
|
+
export async function getQueueDiagnostics() {
|
|
191
|
+
const pending = await getPendingSync();
|
|
192
|
+
const entityIds = await getPendingEntityIds();
|
|
193
|
+
// Breakdown by table
|
|
194
|
+
const byTable = {};
|
|
195
|
+
const byOperationType = {};
|
|
196
|
+
let oldestTimestamp = null;
|
|
197
|
+
let itemsInBackoff = 0;
|
|
198
|
+
for (const item of pending) {
|
|
199
|
+
byTable[item.table] = (byTable[item.table] || 0) + 1;
|
|
200
|
+
byOperationType[item.operationType] = (byOperationType[item.operationType] || 0) + 1;
|
|
201
|
+
if (!oldestTimestamp || item.timestamp < oldestTimestamp) {
|
|
202
|
+
oldestTimestamp = item.timestamp;
|
|
203
|
+
}
|
|
204
|
+
if (item.retries > 0) {
|
|
205
|
+
itemsInBackoff++;
|
|
206
|
+
}
|
|
207
|
+
}
|
|
208
|
+
return {
|
|
209
|
+
pendingOperations: pending.length,
|
|
210
|
+
pendingEntityIds: Array.from(entityIds),
|
|
211
|
+
byTable,
|
|
212
|
+
byOperationType,
|
|
213
|
+
oldestPendingTimestamp: oldestTimestamp,
|
|
214
|
+
itemsInBackoff
|
|
215
|
+
};
|
|
216
|
+
}
|
|
217
|
+
/**
|
|
218
|
+
* Get conflict resolution history diagnostics (async — reads IndexedDB).
|
|
219
|
+
*
|
|
220
|
+
* @returns Recent conflict entries and total count
|
|
221
|
+
*/
|
|
222
|
+
export async function getConflictDiagnostics() {
|
|
223
|
+
const { entries, totalCount } = await _getRecentConflictHistory();
|
|
224
|
+
return { recentHistory: entries, totalCount };
|
|
225
|
+
}
|
|
226
|
+
/**
|
|
227
|
+
* Get engine-internal state diagnostics (synchronous).
|
|
228
|
+
*
|
|
229
|
+
* @returns Lock state, visibility, auth validation status
|
|
230
|
+
*/
|
|
231
|
+
export function getEngineDiagnostics() {
|
|
232
|
+
const engineState = _getEngineDiagnostics();
|
|
233
|
+
return {
|
|
234
|
+
isTabVisible: engineState.isTabVisible,
|
|
235
|
+
tabHiddenAt: engineState.tabHiddenAt ? new Date(engineState.tabHiddenAt).toISOString() : null,
|
|
236
|
+
lockHeld: engineState.lockHeld,
|
|
237
|
+
lockHeldForMs: engineState.lockHeldForMs,
|
|
238
|
+
recentlyModifiedCount: engineState.recentlyModifiedCount,
|
|
239
|
+
wasOffline: engineState.wasOffline,
|
|
240
|
+
authValidatedAfterReconnect: engineState.authValidatedAfterReconnect
|
|
241
|
+
};
|
|
242
|
+
}
|
|
243
|
+
/**
|
|
244
|
+
* Get network connectivity diagnostics (synchronous).
|
|
245
|
+
*
|
|
246
|
+
* @returns Current online/offline status
|
|
247
|
+
*/
|
|
248
|
+
export function getNetworkDiagnostics() {
|
|
249
|
+
return {
|
|
250
|
+
online: get(isOnline)
|
|
251
|
+
};
|
|
252
|
+
}
|
|
253
|
+
/**
|
|
254
|
+
* Get error state diagnostics (synchronous).
|
|
255
|
+
*
|
|
256
|
+
* @returns Latest error info and recent error history
|
|
257
|
+
*/
|
|
258
|
+
export function getErrorDiagnostics() {
|
|
259
|
+
const syncState = get(syncStatusStore);
|
|
260
|
+
return {
|
|
261
|
+
lastError: syncState.lastError,
|
|
262
|
+
lastErrorDetails: syncState.lastErrorDetails,
|
|
263
|
+
recentErrors: syncState.syncErrors
|
|
264
|
+
};
|
|
265
|
+
}
|
|
266
|
+
//# sourceMappingURL=diagnostics.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"diagnostics.js","sourceRoot":"","sources":["../src/diagnostics.ts"],"names":[],"mappings":"AAAA;;;;;;;;;;;;;;;;;;;;;;;;GAwBG;AAEH,OAAO,EAAE,qBAAqB,EAAE,MAAM,UAAU,CAAC;AACjD,OAAO,EAAE,uBAAuB,EAAE,MAAM,YAAY,CAAC;AACrD,OAAO,EAAE,yBAAyB,EAAE,MAAM,aAAa,CAAC;AACxD,OAAO,EAAE,cAAc,EAAE,mBAAmB,EAAE,MAAM,SAAS,CAAC;AAC9D,OAAO,EAAE,eAAe,EAAE,MAAM,UAAU,CAAC;AAC3C,OAAO,EAAE,WAAW,EAAE,MAAM,YAAY,CAAC;AACzC,OAAO,EAAE,eAAe,EAAE,MAAM,eAAe,CAAC;AAChD,OAAO,EAAE,QAAQ,EAAE,MAAM,kBAAkB,CAAC;AAC5C,OAAO,EAAE,WAAW,EAAE,MAAM,SAAS,CAAC;AACtC,OAAO,EAAE,GAAG,EAAE,MAAM,cAAc,CAAC;AA0HnC,gFAAgF;AAChF,4BAA4B;AAC5B,gFAAgF;AAEhF;;;;;;;;;;;;;;GAcG;AACH,MAAM,CAAC,KAAK,UAAU,cAAc;IAClC,MAAM,MAAM,GAAG,eAAe,EAAE,CAAC;IACjC,MAAM,WAAW,GAAG,qBAAqB,EAAE,CAAC;IAC5C,MAAM,aAAa,GAAG,uBAAuB,EAAE,CAAC;IAChD,MAAM,SAAS,GAAG,GAAG,CAAC,eAAe,CAAC,CAAC;IAEvC,mCAAmC;IACnC,MAAM,CAAC,SAAS,EAAE,YAAY,CAAC,GAAG,MAAM,OAAO,CAAC,GAAG,CAAC;QAClD,mBAAmB,EAAE;QACrB,sBAAsB,EAAE;KACzB,CAAC,CAAC;IAEH,6CAA6C;IAC7C,MAAM,aAAa,GAA6C,EAAE,CAAC;IACnE,KAAK,MAAM,CAAC,KAAK,EAAE,KAAK,CAAC,IAAI,MAAM,CAAC,OAAO,CAAC,WAAW,CAAC,WAAW,CAAC,OAAO,CAAC,EAAE,CAAC;QAC7E,MAAM,GAAG,GACP,WAAW,CAAC,WAAW,CAAC,UAAU,GAAG,CAAC;YACpC,CAAC,CAAC,CAAC,CAAC,KAAK,CAAC,KAAK,GAAG,WAAW,CAAC,WAAW,CAAC,UAAU,CAAC,GAAG,GAAG,CAAC,CAAC,OAAO,CAAC,CAAC,CAAC;YACvE,CAAC,CAAC,KAAK,CAAC;QACZ,aAAa,CAAC,KAAK,CAAC,GAAG;YACrB,KAAK,EAAE,KAAK,CAAC,KAAK;YAClB,SAAS,EAAE,WAAW,CAAC,KAAK,CAAC,KAAK,CAAC;YACnC,OAAO,EAAE,KAAK,CAAC,OAAO;YACtB,UAAU,EAAE,GAAG,GAAG,GAAG;SACtB,CAAC;IACJ,CAAC;IAED,kCAAkC;IAClC,MAAM,YAAY,GAAG,IAAI,CAAC,GAAG,EAAE,GAAG,KAAK,CAAC;IACxC,MAAM,gBAAgB,GAAG,WAAW,CAAC,SAAS,CAAC,MAAM,CACnD,CAAC,CAAC,EAAE,EAAE,CAAC,IAAI,IAAI,CAAC,CAAC,CAAC,SAAS,CAAC,CAAC,OAAO,EAAE,GAAG,YAAY,CACtD,CAAC,MAAM,CAAC;IAET,OAAO;QACL,SAAS,EAAE,IAAI,IAAI,EAAE,CAAC,WAAW,EAAE;QACnC,MAAM,EAAE,MAAM,CAAC,MAAM,IAAI,QAAQ;QACjC,QAAQ,EAAE,WAAW,EAAE;QAEvB,IAAI,EAAE;YACJ,MAAM,EAAE,SAAS,CAAC,MAAM;YACxB,WAAW,EAAE,WAAW,CAAC,eAAe;YACxC,YAAY,EAAE,SAAS,CAAC,YAAY;YACpC,2BAA2B,EAAE,WAAW,CAAC,2BAA2B;gBAClE,CAAC,CAAC,IAAI,IAAI,CAAC,WAAW,CAAC,2BAA2B,CAAC,CAAC,WAAW,EAAE;gBACjE,CAAC,CAAC,IAAI;YACR,WAAW,EAAE,SAAS,CAAC,WAAW;YAClC,YAAY,EAAE,WAAW,CAAC,SAAS;YACnC,gBAAgB;YAChB,WAAW,EAAE,WAAW,CAAC,WAAW;YACpC,eAAe,EAAE,WAAW,CAAC,eAAe;YAC5C,YAAY,EAAE,SAAS,CAAC,YAAY;SACrC;QAED,MAAM,EAAE;YACN,YAAY,EAAE,WAAW,CAAC,WAAW,CAAC,YAAY;YAClD,UAAU,EAAE,WAAW,CAAC,WAAW,CAAC,UAAU;YAC9C,cAAc,EAAE,WAAW,CAAC,WAAW,CAAC,WAAW,CAAC,UAAU,CAAC;YAC/D,YAAY,EAAE,WAAW,CAAC,WAAW,CAAC,YAAY;YAClD,OAAO,EAAE,aAAa;SACvB;QAED,KAAK,EAAE,SAAS;QAEhB,QAAQ,EAAE,aAAa;QAEvB,OAAO,EAAE,qBAAqB,EAAE;QAEhC,MAAM,EAAE;YACN,YAAY,EAAE,WAAW,CAAC,YAAY;YACtC,WAAW,EAAE,WAAW,CAAC,WAAW,CAAC,CAAC,CAAC,IAAI,IAAI,CAAC,WAAW,CAAC,WAAW,CAAC,CAAC,WAAW,EAAE,CAAC,CAAC,CAAC,IAAI;YAC7F,QAAQ,EAAE,WAAW,CAAC,QAAQ;YAC9B,aAAa,EAAE,WAAW,CAAC,aAAa;YACxC,qBAAqB,EAAE,WAAW,CAAC,qBAAqB;YACxD,UAAU,EAAE,WAAW,CAAC,UAAU;YAClC,2BAA2B,EAAE,WAAW,CAAC,2BAA2B;SACrE;QAED,SAAS,EAAE,YAAY;QAEvB,MAAM,EAAE,mBAAmB,EAAE;QAE7B,MAAM,EAAE;YACN,UAAU,EAAE,MAAM,CAAC,MAAM,CAAC,MAAM;YAChC,UAAU,EAAE,MAAM,CAAC,MAAM,CAAC,GAAG,CAAC,CAAC,CAAC,EAAE,EAAE,CAAC,CAAC,CAAC,YAAY,CAAC;YACpD,cAAc,EAAE,MAAM,CAAC,cAAc,IAAI,IAAI;YAC7C,cAAc,EAAE,MAAM,CAAC,cAAc,IAAI,MAAM;YAC/C,mBAAmB,EAAE,MAAM,CAAC,mBAAmB,IAAI,CAAC;SACrD;KACF,CAAC;AACJ,CAAC;AAED,gFAAgF;AAChF,qCAAqC;AACrC,gFAAgF;AAEhF;;;;GAIG;AACH,MAAM,UAAU,kBAAkB;IAChC,MAAM,WAAW,GAAG,qBAAqB,EAAE,CAAC;IAC5C,MAAM,SAAS,GAAG,GAAG,CAAC,eAAe,CAAC,CAAC;IAEvC,MAAM,aAAa,GAA6C,EAAE,CAAC;IACnE,KAAK,MAAM,CAAC,KAAK,EAAE,KAAK,CAAC,IAAI,MAAM,CAAC,OAAO,CAAC,WAAW,CAAC,WAAW,CAAC,OAAO,CAAC,EAAE,CAAC;QAC7E,MAAM,GAAG,GACP,WAAW,CAAC,WAAW,CAAC,UAAU,GAAG,CAAC;YACpC,CAAC,CAAC,CAAC,CAAC,KAAK,CAAC,KAAK,GAAG,WAAW,CAAC,WAAW,CAAC,UAAU,CAAC,GAAG,GAAG,CAAC,CAAC,OAAO,CAAC,CAAC,CAAC;YACvE,CAAC,CAAC,KAAK,CAAC;QACZ,aAAa,CAAC,KAAK,CAAC,GAAG;YACrB,KAAK,EAAE,KAAK,CAAC,KAAK;YAClB,SAAS,EAAE,WAAW,CAAC,KAAK,CAAC,KAAK,CAAC;YACnC,OAAO,EAAE,KAAK,CAAC,OAAO;YACtB,UAAU,EAAE,GAAG,GAAG,GAAG;SACtB,CAAC;IACJ,CAAC;IAED,MAAM,YAAY,GAAG,IAAI,CAAC,GAAG,EAAE,GAAG,KAAK,CAAC;IACxC,MAAM,gBAAgB,GAAG,WAAW,CAAC,SAAS,CAAC,MAAM,CACnD,CAAC,CAAC,EAAE,EAAE,CAAC,IAAI,IAAI,CAAC,CAAC,CAAC,SAAS,CAAC,CAAC,OAAO,EAAE,GAAG,YAAY,CACtD,CAAC,MAAM,CAAC;IAET,OAAO;QACL,IAAI,EAAE;YACJ,MAAM,EAAE,SAAS,CAAC,MAAM;YACxB,WAAW,EAAE,WAAW,CAAC,eAAe;YACxC,YAAY,EAAE,SAAS,CAAC,YAAY;YACpC,2BAA2B,EAAE,WAAW,CAAC,2BAA2B;gBAClE,CAAC,CAAC,IAAI,IAAI,CAAC,WAAW,CAAC,2BAA2B,CAAC,CAAC,WAAW,EAAE;gBACjE,CAAC,CAAC,IAAI;YACR,WAAW,EAAE,SAAS,CAAC,WAAW;YAClC,YAAY,EAAE,WAAW,CAAC,SAAS;YACnC,gBAAgB;YAChB,WAAW,EAAE,WAAW,CAAC,WAAW;YACpC,eAAe,EAAE,WAAW,CAAC,eAAe;YAC5C,YAAY,EAAE,SAAS,CAAC,YAAY;SACrC;QACD,MAAM,EAAE;YACN,YAAY,EAAE,WAAW,CAAC,WAAW,CAAC,YAAY;YAClD,UAAU,EAAE,WAAW,CAAC,WAAW,CAAC,UAAU;YAC9C,cAAc,EAAE,WAAW,CAAC,WAAW,CAAC,WAAW,CAAC,UAAU,CAAC;YAC/D,YAAY,EAAE,WAAW,CAAC,WAAW,CAAC,YAAY;YAClD,OAAO,EAAE,aAAa;SACvB;KACF,CAAC;AACJ,CAAC;AAED;;;;GAIG;AACH,MAAM,UAAU,sBAAsB;IACpC,OAAO,uBAAuB,EAAE,CAAC;AACnC,CAAC;AAED;;;;GAIG;AACH,MAAM,CAAC,KAAK,UAAU,mBAAmB;IACvC,MAAM,OAAO,GAAG,MAAM,cAAc,EAAE,CAAC;IACvC,MAAM,SAAS,GAAG,MAAM,mBAAmB,EAAE,CAAC;IAE9C,qBAAqB;IACrB,MAAM,OAAO,GAA2B,EAAE,CAAC;IAC3C,MAAM,eAAe,GAA2B,EAAE,CAAC;IACnD,IAAI,eAAe,GAAkB,IAAI,CAAC;IAC1C,IAAI,cAAc,GAAG,CAAC,CAAC;IAEvB,KAAK,MAAM,IAAI,IAAI,OAAO,EAAE,CAAC;QAC3B,OAAO,CAAC,IAAI,CAAC,KAAK,CAAC,GAAG,CAAC,OAAO,CAAC,IAAI,CAAC,KAAK,CAAC,IAAI,CAAC,CAAC,GAAG,CAAC,CAAC;QACrD,eAAe,CAAC,IAAI,CAAC,aAAa,CAAC,GAAG,CAAC,eAAe,CAAC,IAAI,CAAC,aAAa,CAAC,IAAI,CAAC,CAAC,GAAG,CAAC,CAAC;QACrF,IAAI,CAAC,eAAe,IAAI,IAAI,CAAC,SAAS,GAAG,eAAe,EAAE,CAAC;YACzD,eAAe,GAAG,IAAI,CAAC,SAAS,CAAC;QACnC,CAAC;QACD,IAAI,IAAI,CAAC,OAAO,GAAG,CAAC,EAAE,CAAC;YACrB,cAAc,EAAE,CAAC;QACnB,CAAC;IACH,CAAC;IAED,OAAO;QACL,iBAAiB,EAAE,OAAO,CAAC,MAAM;QACjC,gBAAgB,EAAE,KAAK,CAAC,IAAI,CAAC,SAAS,CAAC;QACvC,OAAO;QACP,eAAe;QACf,sBAAsB,EAAE,eAAe;QACvC,cAAc;KACf,CAAC;AACJ,CAAC;AAED;;;;GAIG;AACH,MAAM,CAAC,KAAK,UAAU,sBAAsB;IAI1C,MAAM,EAAE,OAAO,EAAE,UAAU,EAAE,GAAG,MAAM,yBAAyB,EAAE,CAAC;IAClE,OAAO,EAAE,aAAa,EAAE,OAAO,EAAE,UAAU,EAAE,CAAC;AAChD,CAAC;AAED;;;;GAIG;AACH,MAAM,UAAU,oBAAoB;IAClC,MAAM,WAAW,GAAG,qBAAqB,EAAE,CAAC;IAC5C,OAAO;QACL,YAAY,EAAE,WAAW,CAAC,YAAY;QACtC,WAAW,EAAE,WAAW,CAAC,WAAW,CAAC,CAAC,CAAC,IAAI,IAAI,CAAC,WAAW,CAAC,WAAW,CAAC,CAAC,WAAW,EAAE,CAAC,CAAC,CAAC,IAAI;QAC7F,QAAQ,EAAE,WAAW,CAAC,QAAQ;QAC9B,aAAa,EAAE,WAAW,CAAC,aAAa;QACxC,qBAAqB,EAAE,WAAW,CAAC,qBAAqB;QACxD,UAAU,EAAE,WAAW,CAAC,UAAU;QAClC,2BAA2B,EAAE,WAAW,CAAC,2BAA2B;KACrE,CAAC;AACJ,CAAC;AAED;;;;GAIG;AACH,MAAM,UAAU,qBAAqB;IACnC,OAAO;QACL,MAAM,EAAE,GAAG,CAAC,QAAQ,CAAC;KACtB,CAAC;AACJ,CAAC;AAED;;;;GAIG;AACH,MAAM,UAAU,mBAAmB;IACjC,MAAM,SAAS,GAAG,GAAG,CAAC,eAAe,CAAC,CAAC;IACvC,OAAO;QACL,SAAS,EAAE,SAAS,CAAC,SAAS;QAC9B,gBAAgB,EAAE,SAAS,CAAC,gBAAgB;QAC5C,YAAY,EAAE,SAAS,CAAC,UAAU;KACnC,CAAC;AACJ,CAAC"}
|
package/dist/engine.d.ts
CHANGED
|
@@ -73,6 +73,16 @@
|
|
|
73
73
|
* ```
|
|
74
74
|
*/
|
|
75
75
|
export declare function clearPendingSyncQueue(): Promise<number>;
|
|
76
|
+
/** Stats captured for each sync cycle (push + pull) */
|
|
77
|
+
interface SyncCycleStats {
|
|
78
|
+
timestamp: string;
|
|
79
|
+
trigger: string;
|
|
80
|
+
pushedItems: number;
|
|
81
|
+
pulledTables: number;
|
|
82
|
+
pulledRecords: number;
|
|
83
|
+
egressBytes: number;
|
|
84
|
+
durationMs: number;
|
|
85
|
+
}
|
|
76
86
|
/**
|
|
77
87
|
* Mark an entity as recently modified to protect it from being overwritten by pull.
|
|
78
88
|
*
|
|
@@ -82,6 +92,39 @@ export declare function clearPendingSyncQueue(): Promise<number>;
|
|
|
82
92
|
* @param entityId - The UUID of the entity that was just modified locally
|
|
83
93
|
*/
|
|
84
94
|
export declare function markEntityModified(entityId: string): void;
|
|
95
|
+
/**
|
|
96
|
+
* Return a snapshot of engine-internal state for diagnostics.
|
|
97
|
+
*
|
|
98
|
+
* This function is prefixed with `_` to signal that it exposes module-private
|
|
99
|
+
* state and should only be consumed by the diagnostics module.
|
|
100
|
+
*
|
|
101
|
+
* @returns A plain object containing current engine state values
|
|
102
|
+
*/
|
|
103
|
+
export declare function _getEngineDiagnostics(): {
|
|
104
|
+
syncStats: SyncCycleStats[];
|
|
105
|
+
totalSyncCycles: number;
|
|
106
|
+
egressStats: {
|
|
107
|
+
byTable: {
|
|
108
|
+
[x: string]: {
|
|
109
|
+
bytes: number;
|
|
110
|
+
records: number;
|
|
111
|
+
};
|
|
112
|
+
};
|
|
113
|
+
totalBytes: number;
|
|
114
|
+
totalRecords: number;
|
|
115
|
+
sessionStart: string;
|
|
116
|
+
};
|
|
117
|
+
hasHydrated: boolean;
|
|
118
|
+
schemaValidated: boolean;
|
|
119
|
+
isTabVisible: boolean;
|
|
120
|
+
tabHiddenAt: number | null;
|
|
121
|
+
lockHeld: boolean;
|
|
122
|
+
lockHeldForMs: number | null;
|
|
123
|
+
recentlyModifiedCount: number;
|
|
124
|
+
wasOffline: boolean;
|
|
125
|
+
authValidatedAfterReconnect: boolean;
|
|
126
|
+
lastSuccessfulSyncTimestamp: number;
|
|
127
|
+
};
|
|
85
128
|
/**
|
|
86
129
|
* Register a callback to be invoked when a sync cycle completes.
|
|
87
130
|
*
|
|
@@ -145,16 +188,16 @@ export declare function runFullSync(quiet?: boolean, skipPull?: boolean): Promis
|
|
|
145
188
|
* This is the main "boot" function for the sync engine. It:
|
|
146
189
|
* 1. Ensures the Dexie DB is open and upgraded
|
|
147
190
|
* 2. Cleans up any existing listeners (idempotent restart support)
|
|
148
|
-
* 3.
|
|
149
|
-
* 4.
|
|
150
|
-
* 5. Registers
|
|
151
|
-
* 6.
|
|
152
|
-
* 7. Starts
|
|
153
|
-
* 8.
|
|
154
|
-
* 9.
|
|
155
|
-
* 10. Runs initial
|
|
156
|
-
* 11.
|
|
157
|
-
* 12.
|
|
191
|
+
* 3. Subscribes to Supabase auth state changes (handles sign-out/token-refresh)
|
|
192
|
+
* 4. Registers online/offline handlers with auth validation
|
|
193
|
+
* 5. Registers visibility change handler for smart tab-return syncing
|
|
194
|
+
* 6. Starts realtime WebSocket subscriptions
|
|
195
|
+
* 7. Starts periodic background sync interval
|
|
196
|
+
* 8. Validates Supabase schema (one-time)
|
|
197
|
+
* 9. Runs initial hydration (if local DB is empty) or full sync
|
|
198
|
+
* 10. Runs initial cleanup (tombstones, conflicts, failed items)
|
|
199
|
+
* 11. Starts the watchdog timer
|
|
200
|
+
* 12. Registers debug window utilities (Tombstones, Sync, Diagnostics)
|
|
158
201
|
*
|
|
159
202
|
* **Must be called after `initEngine()`** — requires configuration to be set.
|
|
160
203
|
* Safe to call multiple times (previous listeners are cleaned up first).
|
|
@@ -183,4 +226,5 @@ export declare function stopSyncEngine(): Promise<void>;
|
|
|
183
226
|
* database is still open when clearing tables.
|
|
184
227
|
*/
|
|
185
228
|
export declare function clearLocalCache(): Promise<void>;
|
|
229
|
+
export {};
|
|
186
230
|
//# sourceMappingURL=engine.d.ts.map
|
package/dist/engine.d.ts.map
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"engine.d.ts","sourceRoot":"","sources":["../src/engine.ts"],"names":[],"mappings":"AAAA;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;GAwDG;
|
|
1
|
+
{"version":3,"file":"engine.d.ts","sourceRoot":"","sources":["../src/engine.ts"],"names":[],"mappings":"AAAA;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;GAwDG;AA+KH;;;;;;;;;;;;;;;;GAgBG;AACH,wBAAsB,qBAAqB,IAAI,OAAO,CAAC,MAAM,CAAC,CAW7D;AAuCD,uDAAuD;AACvD,UAAU,cAAc;IACtB,SAAS,EAAE,MAAM,CAAC;IAClB,OAAO,EAAE,MAAM,CAAC;IAChB,WAAW,EAAE,MAAM,CAAC;IACpB,YAAY,EAAE,MAAM,CAAC;IACrB,aAAa,EAAE,MAAM,CAAC;IACtB,WAAW,EAAE,MAAM,CAAC;IACpB,UAAU,EAAE,MAAM,CAAC;CACpB;AAgLD;;;;;;;GAOG;AACH,wBAAgB,kBAAkB,CAAC,QAAQ,EAAE,MAAM,GAAG,IAAI,CAEzD;AAED;;;;;;;GAOG;AACH,wBAAgB,qBAAqB;;;;;;uBAxLF,MAAM;yBAAW,MAAM;;;oBAF5C,MAAM;sBACJ,MAAM;sBAEN,MAAM;;;;;;;;;;;;EAuMrB;AAgLD;;;;;;;;;;;;;;;;;;GAkBG;AACH,wBAAgB,cAAc,CAAC,QAAQ,EAAE,MAAM,IAAI,GAAG,MAAM,IAAI,CAO/D;AAuCD;;;;;;;;;;;;;;GAcG;AACH,wBAAgB,gBAAgB,IAAI,IAAI,CAavC;AA67BD;;;;;;;;;;;;;;;;;;;GAmBG;AACH,wBAAsB,WAAW,CAC/B,KAAK,GAAE,OAAe,EACtB,QAAQ,GAAE,OAAe,GACxB,OAAO,CAAC,IAAI,CAAC,CA0Mf;AAolBD;;;;;;;;;;;;;;;;;;;GAmBG;AACH,wBAAsB,eAAe,IAAI,OAAO,CAAC,IAAI,CAAC,CAuYrD;AAED;;;;;;;;;;GAUG;AACH,wBAAsB,cAAc,IAAI,OAAO,CAAC,IAAI,CAAC,CA+DpD;AAED;;;;;;;;;GASG;AACH,wBAAsB,eAAe,IAAI,OAAO,CAAC,IAAI,CAAC,CA2BrD"}
|