@grainql/analytics-web 2.7.1 → 2.9.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/README.md +36 -3
- package/dist/cjs/consent.d.ts +38 -7
- package/dist/cjs/consent.d.ts.map +1 -1
- package/dist/cjs/consent.js +82 -23
- package/dist/cjs/consent.js.map +1 -1
- package/dist/cjs/debug-agent.d.ts +171 -0
- package/dist/cjs/debug-agent.d.ts.map +1 -0
- package/dist/cjs/debug-agent.js +1219 -0
- package/dist/cjs/debug-agent.js.map +1 -0
- package/dist/cjs/id-manager.d.ts +66 -0
- package/dist/cjs/id-manager.d.ts.map +1 -0
- package/dist/cjs/id-manager.js +212 -0
- package/dist/cjs/id-manager.js.map +1 -0
- package/dist/cjs/index.d.ts +26 -8
- package/dist/cjs/index.d.ts.map +1 -1
- package/dist/cjs/index.js.map +1 -1
- package/dist/cjs/interaction-tracking.d.ts +6 -0
- package/dist/cjs/interaction-tracking.d.ts.map +1 -1
- package/dist/cjs/interaction-tracking.js +55 -5
- package/dist/cjs/interaction-tracking.js.map +1 -1
- package/dist/cjs/page-tracking.d.ts +6 -0
- package/dist/cjs/page-tracking.d.ts.map +1 -1
- package/dist/cjs/page-tracking.js +23 -2
- package/dist/cjs/page-tracking.js.map +1 -1
- package/dist/cjs/react/hooks/useConsent.d.ts +18 -2
- package/dist/cjs/react/hooks/useConsent.d.ts.map +1 -1
- package/dist/cjs/react/hooks/useConsent.js +52 -1
- package/dist/cjs/react/hooks/useConsent.js.map +1 -1
- package/dist/consent.d.ts +38 -7
- package/dist/consent.d.ts.map +1 -1
- package/dist/consent.js +82 -23
- package/dist/debug-agent.d.ts +171 -0
- package/dist/debug-agent.d.ts.map +1 -0
- package/dist/debug-agent.js +1219 -0
- package/dist/esm/consent.d.ts +38 -7
- package/dist/esm/consent.d.ts.map +1 -1
- package/dist/esm/consent.js +82 -23
- package/dist/esm/consent.js.map +1 -1
- package/dist/esm/debug-agent.d.ts +171 -0
- package/dist/esm/debug-agent.d.ts.map +1 -0
- package/dist/esm/debug-agent.js +1215 -0
- package/dist/esm/debug-agent.js.map +1 -0
- package/dist/esm/id-manager.d.ts +66 -0
- package/dist/esm/id-manager.d.ts.map +1 -0
- package/dist/esm/id-manager.js +208 -0
- package/dist/esm/id-manager.js.map +1 -0
- package/dist/esm/index.d.ts +26 -8
- package/dist/esm/index.d.ts.map +1 -1
- package/dist/esm/index.js.map +1 -1
- package/dist/esm/interaction-tracking.d.ts +6 -0
- package/dist/esm/interaction-tracking.d.ts.map +1 -1
- package/dist/esm/interaction-tracking.js +55 -5
- package/dist/esm/interaction-tracking.js.map +1 -1
- package/dist/esm/page-tracking.d.ts +6 -0
- package/dist/esm/page-tracking.d.ts.map +1 -1
- package/dist/esm/page-tracking.js +23 -2
- package/dist/esm/page-tracking.js.map +1 -1
- package/dist/esm/react/hooks/useConsent.d.ts +18 -2
- package/dist/esm/react/hooks/useConsent.d.ts.map +1 -1
- package/dist/esm/react/hooks/useConsent.js +49 -1
- package/dist/esm/react/hooks/useConsent.js.map +1 -1
- package/dist/id-manager.d.ts +66 -0
- package/dist/id-manager.d.ts.map +1 -0
- package/dist/id-manager.js +212 -0
- package/dist/index.d.ts +26 -8
- package/dist/index.d.ts.map +1 -1
- package/dist/index.global.dev.js +1635 -86
- package/dist/index.global.dev.js.map +4 -4
- package/dist/index.global.js +506 -2
- package/dist/index.global.js.map +4 -4
- package/dist/index.js +171 -44
- package/dist/index.mjs +172 -45
- package/dist/interaction-tracking.d.ts +6 -0
- package/dist/interaction-tracking.d.ts.map +1 -1
- package/dist/interaction-tracking.js +55 -5
- package/dist/page-tracking.d.ts +6 -0
- package/dist/page-tracking.d.ts.map +1 -1
- package/dist/page-tracking.js +23 -2
- package/dist/react/hooks/useConsent.d.ts +18 -2
- package/dist/react/hooks/useConsent.d.ts.map +1 -1
- package/dist/react/hooks/useConsent.js +52 -1
- package/dist/react/hooks/useConsent.mjs +49 -1
- package/package.json +1 -1
package/dist/index.js
CHANGED
|
@@ -44,6 +44,7 @@ const cookies_1 = require("./cookies");
|
|
|
44
44
|
const activity_1 = require("./activity");
|
|
45
45
|
const heartbeat_1 = require("./heartbeat");
|
|
46
46
|
const page_tracking_1 = require("./page-tracking");
|
|
47
|
+
const id_manager_1 = require("./id-manager");
|
|
47
48
|
const attribution_1 = require("./attribution");
|
|
48
49
|
Object.defineProperty(exports, "categorizeReferrer", { enumerable: true, get: function () { return attribution_1.categorizeReferrer; } });
|
|
49
50
|
Object.defineProperty(exports, "parseUTMParameters", { enumerable: true, get: function () { return attribution_1.parseUTMParameters; } });
|
|
@@ -59,13 +60,13 @@ class GrainAnalytics {
|
|
|
59
60
|
this.flushTimer = null;
|
|
60
61
|
this.isDestroyed = false;
|
|
61
62
|
this.globalUserId = null;
|
|
62
|
-
this.persistentAnonymousUserId = null;
|
|
63
|
+
this.persistentAnonymousUserId = null; // Deprecated: use idManager instead
|
|
63
64
|
// Remote Config properties
|
|
64
65
|
this.configCache = null;
|
|
65
66
|
this.configRefreshTimer = null;
|
|
66
67
|
this.configChangeListeners = [];
|
|
67
68
|
this.configFetchPromise = null;
|
|
68
|
-
this.cookiesEnabled = false;
|
|
69
|
+
this.cookiesEnabled = false; // Deprecated: cookies no longer used for IDs
|
|
69
70
|
// Automatic Tracking properties
|
|
70
71
|
this.activityDetector = null;
|
|
71
72
|
this.heartbeatManager = null;
|
|
@@ -79,6 +80,9 @@ class GrainAnalytics {
|
|
|
79
80
|
// Session tracking
|
|
80
81
|
this.sessionStartTime = Date.now();
|
|
81
82
|
this.sessionEventCount = 0;
|
|
83
|
+
// Debug mode properties
|
|
84
|
+
this.debugAgent = null;
|
|
85
|
+
this.isDebugMode = false;
|
|
82
86
|
this.config = {
|
|
83
87
|
apiUrl: 'https://api.grainql.com',
|
|
84
88
|
authStrategy: 'NONE',
|
|
@@ -93,38 +97,37 @@ class GrainAnalytics {
|
|
|
93
97
|
configCacheKey: 'grain_config',
|
|
94
98
|
configRefreshInterval: 300000, // 5 minutes
|
|
95
99
|
enableConfigCache: true,
|
|
96
|
-
// Privacy defaults
|
|
97
|
-
consentMode: '
|
|
100
|
+
// Privacy defaults (v2.0)
|
|
101
|
+
consentMode: 'cookieless', // Default: privacy-first, no permanent tracking
|
|
98
102
|
waitForConsent: false,
|
|
99
|
-
enableCookies: false,
|
|
100
|
-
anonymizeIP: false,
|
|
101
103
|
disableAutoProperties: false,
|
|
102
104
|
// Automatic Tracking defaults
|
|
103
105
|
enableHeartbeat: true,
|
|
104
106
|
heartbeatActiveInterval: 120000, // 2 minutes
|
|
105
107
|
heartbeatInactiveInterval: 300000, // 5 minutes
|
|
106
108
|
enableAutoPageView: true,
|
|
107
|
-
stripQueryParams: true,
|
|
109
|
+
stripQueryParams: true, // Privacy-first: strip by default
|
|
110
|
+
stripHash: false,
|
|
108
111
|
// Heatmap Tracking defaults
|
|
109
112
|
enableHeatmapTracking: true,
|
|
110
113
|
...config,
|
|
111
114
|
tenantId: config.tenantId,
|
|
112
115
|
};
|
|
113
|
-
// Initialize consent manager
|
|
116
|
+
// Initialize consent manager (v2.0)
|
|
114
117
|
this.consentManager = new consent_1.ConsentManager(this.config.tenantId, this.config.consentMode);
|
|
115
|
-
//
|
|
116
|
-
|
|
117
|
-
|
|
118
|
-
|
|
119
|
-
|
|
120
|
-
|
|
121
|
-
}
|
|
118
|
+
// Initialize ID manager (v2.0)
|
|
119
|
+
const idMode = this.consentManager.getIdMode();
|
|
120
|
+
this.idManager = new id_manager_1.IdManager({
|
|
121
|
+
mode: idMode,
|
|
122
|
+
tenantId: this.config.tenantId,
|
|
123
|
+
useLocalStorage: true, // For permanent IDs when consented
|
|
124
|
+
});
|
|
122
125
|
// Set global userId if provided in config
|
|
123
126
|
if (config.userId) {
|
|
124
127
|
this.globalUserId = config.userId;
|
|
125
128
|
}
|
|
126
129
|
this.validateConfig();
|
|
127
|
-
|
|
130
|
+
// Deprecated: initializePersistentAnonymousUserId() - now handled by IdManager
|
|
128
131
|
this.setupBeforeUnload();
|
|
129
132
|
this.startFlushTimer();
|
|
130
133
|
this.initializeConfigCache();
|
|
@@ -132,6 +135,8 @@ class GrainAnalytics {
|
|
|
132
135
|
this.ephemeralSessionId = this.generateUUID();
|
|
133
136
|
// Initialize automatic tracking (browser only)
|
|
134
137
|
if (typeof window !== 'undefined') {
|
|
138
|
+
// Check for debug mode before initializing tracking
|
|
139
|
+
this.checkAndInitializeDebugMode();
|
|
135
140
|
this.initializeAutomaticTracking();
|
|
136
141
|
// Track session start
|
|
137
142
|
this.trackSessionStart();
|
|
@@ -140,8 +145,11 @@ class GrainAnalytics {
|
|
|
140
145
|
this.initializeHeatmapTracking();
|
|
141
146
|
}
|
|
142
147
|
}
|
|
143
|
-
// Set up consent change listener to flush waiting events
|
|
148
|
+
// Set up consent change listener to sync IdManager and flush waiting events (v2.0)
|
|
144
149
|
this.consentManager.addListener((state) => {
|
|
150
|
+
// Sync IdManager with consent state
|
|
151
|
+
const idMode = this.consentManager.getIdMode();
|
|
152
|
+
this.idManager.setMode(idMode);
|
|
145
153
|
if (state.granted) {
|
|
146
154
|
this.handleConsentGranted();
|
|
147
155
|
}
|
|
@@ -183,11 +191,14 @@ class GrainAnalytics {
|
|
|
183
191
|
*/
|
|
184
192
|
shouldAllowPersistentStorage() {
|
|
185
193
|
const hasConsent = this.consentManager.hasConsent('analytics');
|
|
186
|
-
const
|
|
194
|
+
const isCookieless = this.config.consentMode === 'cookieless';
|
|
187
195
|
const userExplicitlyIdentified = !!this.globalUserId;
|
|
188
196
|
const isJWTAuth = this.config.authStrategy === 'JWT';
|
|
197
|
+
// Never allow persistent storage in cookieless mode
|
|
198
|
+
if (isCookieless)
|
|
199
|
+
return false;
|
|
189
200
|
// Allow persistent storage if any of these conditions are met
|
|
190
|
-
return hasConsent ||
|
|
201
|
+
return hasConsent || userExplicitlyIdentified || isJWTAuth;
|
|
191
202
|
}
|
|
192
203
|
/**
|
|
193
204
|
* Generate a proper UUIDv4 identifier for anonymous user ID
|
|
@@ -281,23 +292,21 @@ class GrainAnalytics {
|
|
|
281
292
|
}
|
|
282
293
|
}
|
|
283
294
|
/**
|
|
284
|
-
* Get the effective user ID (
|
|
295
|
+
* Get the effective user ID (v2.0)
|
|
285
296
|
*
|
|
286
|
-
*
|
|
287
|
-
*
|
|
297
|
+
* Privacy-first implementation:
|
|
298
|
+
* - Returns global userId if explicitly set (via identify/login)
|
|
299
|
+
* - Otherwise uses IdManager to generate:
|
|
300
|
+
* - Daily rotating ID (cookieless mode)
|
|
301
|
+
* - Permanent ID (with consent)
|
|
288
302
|
*/
|
|
289
303
|
getEffectiveUserIdInternal() {
|
|
304
|
+
// Explicit user identification always takes precedence
|
|
290
305
|
if (this.globalUserId) {
|
|
291
306
|
return this.globalUserId;
|
|
292
307
|
}
|
|
293
|
-
|
|
294
|
-
|
|
295
|
-
}
|
|
296
|
-
// Generate a new UUIDv4 identifier as fallback
|
|
297
|
-
this.persistentAnonymousUserId = this.generateAnonymousUserId();
|
|
298
|
-
// Try to persist it (will be skipped in opt-in mode without consent)
|
|
299
|
-
this.savePersistentAnonymousUserId(this.persistentAnonymousUserId);
|
|
300
|
-
return this.persistentAnonymousUserId;
|
|
308
|
+
// Use IdManager to generate appropriate ID based on consent
|
|
309
|
+
return this.idManager.getCurrentUserId();
|
|
301
310
|
}
|
|
302
311
|
log(...args) {
|
|
303
312
|
if (this.config.debug) {
|
|
@@ -668,6 +677,7 @@ class GrainAnalytics {
|
|
|
668
677
|
try {
|
|
669
678
|
this.pageTrackingManager = new page_tracking_1.PageTrackingManager(this, {
|
|
670
679
|
stripQueryParams: this.config.stripQueryParams,
|
|
680
|
+
stripHash: this.config.stripHash,
|
|
671
681
|
debug: this.config.debug,
|
|
672
682
|
tenantId: this.config.tenantId,
|
|
673
683
|
});
|
|
@@ -760,6 +770,8 @@ class GrainAnalytics {
|
|
|
760
770
|
debug: this.config.debug,
|
|
761
771
|
enableMutationObserver: true,
|
|
762
772
|
mutationDebounceDelay: 500,
|
|
773
|
+
tenantId: this.config.tenantId,
|
|
774
|
+
apiUrl: this.config.apiUrl,
|
|
763
775
|
});
|
|
764
776
|
this.log('Interaction tracking initialized');
|
|
765
777
|
}
|
|
@@ -963,12 +975,13 @@ class GrainAnalytics {
|
|
|
963
975
|
return;
|
|
964
976
|
const hasConsent = this.consentManager.hasConsent('analytics');
|
|
965
977
|
// Create event with appropriate user ID
|
|
978
|
+
// v2.0: Always use IdManager which returns daily rotating ID or permanent ID based on consent
|
|
966
979
|
const event = {
|
|
967
980
|
eventName,
|
|
968
|
-
userId:
|
|
981
|
+
userId: this.getEffectiveUserId(), // IdManager handles daily vs permanent based on consent
|
|
969
982
|
properties: {
|
|
970
983
|
...properties,
|
|
971
|
-
_minimal: !hasConsent, // Flag to indicate minimal tracking
|
|
984
|
+
_minimal: !hasConsent, // Flag to indicate minimal tracking (daily rotating ID)
|
|
972
985
|
_consent_status: hasConsent ? 'granted' : 'pending',
|
|
973
986
|
},
|
|
974
987
|
};
|
|
@@ -1065,17 +1078,22 @@ class GrainAnalytics {
|
|
|
1065
1078
|
event.properties = filtered;
|
|
1066
1079
|
}
|
|
1067
1080
|
const formattedEvent = this.formatEvent(event);
|
|
1068
|
-
// Check consent
|
|
1081
|
+
// Check if we should wait for consent (only if explicitly configured)
|
|
1069
1082
|
if (this.consentManager.shouldWaitForConsent() && this.config.waitForConsent) {
|
|
1070
1083
|
// Queue event until consent is granted
|
|
1071
1084
|
this.waitingForConsentQueue.push(formattedEvent);
|
|
1072
1085
|
this.log(`Event waiting for consent: ${event.eventName}`, event.properties);
|
|
1073
1086
|
return;
|
|
1074
1087
|
}
|
|
1075
|
-
|
|
1076
|
-
|
|
1077
|
-
|
|
1078
|
-
|
|
1088
|
+
// v2.0: GDPR Strict falls back to cookie-less mode (daily rotating IDs)
|
|
1089
|
+
// Events are never blocked - IdManager already provides correct ID (daily or permanent)
|
|
1090
|
+
const hasConsent = this.consentManager.hasConsent('analytics');
|
|
1091
|
+
// Add tracking flags to indicate consent status
|
|
1092
|
+
formattedEvent.properties = {
|
|
1093
|
+
...formattedEvent.properties,
|
|
1094
|
+
_minimal: !hasConsent, // Flag: true = daily rotating ID, false = permanent ID
|
|
1095
|
+
_consent_status: hasConsent ? 'granted' : 'pending',
|
|
1096
|
+
};
|
|
1079
1097
|
this.eventQueue.push(formattedEvent);
|
|
1080
1098
|
this.eventCountSinceLastHeartbeat++;
|
|
1081
1099
|
this.sessionEventCount++;
|
|
@@ -1763,13 +1781,24 @@ class GrainAnalytics {
|
|
|
1763
1781
|
}
|
|
1764
1782
|
// Privacy & Consent Methods
|
|
1765
1783
|
/**
|
|
1766
|
-
* Grant consent for tracking
|
|
1784
|
+
* Grant consent for tracking (v2.0)
|
|
1785
|
+
* Switches from cookie-less mode to permanent IDs
|
|
1767
1786
|
* @param categories - Optional array of consent categories (e.g., ['analytics', 'functional'])
|
|
1768
1787
|
*/
|
|
1769
1788
|
grantConsent(categories) {
|
|
1770
1789
|
try {
|
|
1771
1790
|
this.consentManager.grantConsent(categories);
|
|
1772
|
-
|
|
1791
|
+
// Sync ID manager with consent state
|
|
1792
|
+
const idMode = this.consentManager.getIdMode();
|
|
1793
|
+
this.idManager.setMode(idMode);
|
|
1794
|
+
this.log('Consent granted, switched to permanent IDs', categories);
|
|
1795
|
+
// Process any queued events waiting for consent
|
|
1796
|
+
if (this.waitingForConsentQueue.length > 0) {
|
|
1797
|
+
this.log(`Processing ${this.waitingForConsentQueue.length} queued events`);
|
|
1798
|
+
this.eventQueue.push(...this.waitingForConsentQueue);
|
|
1799
|
+
this.waitingForConsentQueue = [];
|
|
1800
|
+
this.flush();
|
|
1801
|
+
}
|
|
1773
1802
|
}
|
|
1774
1803
|
catch (error) {
|
|
1775
1804
|
const formattedError = this.formatError(error, 'grantConsent');
|
|
@@ -1777,16 +1806,22 @@ class GrainAnalytics {
|
|
|
1777
1806
|
}
|
|
1778
1807
|
}
|
|
1779
1808
|
/**
|
|
1780
|
-
* Revoke consent for tracking (
|
|
1809
|
+
* Revoke consent for tracking (v2.0)
|
|
1810
|
+
* Switches from permanent IDs to cookie-less mode
|
|
1781
1811
|
* @param categories - Optional array of categories to revoke (if not provided, revokes all)
|
|
1782
1812
|
*/
|
|
1783
1813
|
revokeConsent(categories) {
|
|
1784
1814
|
try {
|
|
1785
1815
|
this.consentManager.revokeConsent(categories);
|
|
1786
|
-
|
|
1787
|
-
|
|
1788
|
-
this.
|
|
1789
|
-
this.
|
|
1816
|
+
// Sync ID manager with consent state
|
|
1817
|
+
const idMode = this.consentManager.getIdMode();
|
|
1818
|
+
this.idManager.setMode(idMode);
|
|
1819
|
+
this.log('Consent revoked, switched to cookie-less mode', categories);
|
|
1820
|
+
// Clear queued events when consent is fully revoked
|
|
1821
|
+
if (!this.consentManager.hasConsent()) {
|
|
1822
|
+
this.eventQueue = [];
|
|
1823
|
+
this.waitingForConsentQueue = [];
|
|
1824
|
+
}
|
|
1790
1825
|
}
|
|
1791
1826
|
catch (error) {
|
|
1792
1827
|
const formattedError = this.formatError(error, 'revokeConsent');
|
|
@@ -1818,6 +1853,93 @@ class GrainAnalytics {
|
|
|
1818
1853
|
offConsentChange(listener) {
|
|
1819
1854
|
this.consentManager.removeListener(listener);
|
|
1820
1855
|
}
|
|
1856
|
+
/**
|
|
1857
|
+
* Check for debug mode parameters and initialize debug agent if valid
|
|
1858
|
+
*/
|
|
1859
|
+
checkAndInitializeDebugMode() {
|
|
1860
|
+
if (typeof window === 'undefined')
|
|
1861
|
+
return;
|
|
1862
|
+
try {
|
|
1863
|
+
const urlParams = new URLSearchParams(window.location.search);
|
|
1864
|
+
const isDebug = urlParams.get('grain_debug') === '1';
|
|
1865
|
+
const sessionId = urlParams.get('grain_session');
|
|
1866
|
+
if (!isDebug || !sessionId) {
|
|
1867
|
+
return;
|
|
1868
|
+
}
|
|
1869
|
+
this.log('Debug mode detected, verifying session:', sessionId);
|
|
1870
|
+
// Verify session with API
|
|
1871
|
+
this.verifyDebugSession(sessionId, window.location.hostname)
|
|
1872
|
+
.then((valid) => {
|
|
1873
|
+
if (valid) {
|
|
1874
|
+
this.log('Debug session verified, initializing debug agent');
|
|
1875
|
+
this.isDebugMode = true;
|
|
1876
|
+
this.initializeDebugAgent(sessionId);
|
|
1877
|
+
}
|
|
1878
|
+
else {
|
|
1879
|
+
this.log('Debug session verification failed');
|
|
1880
|
+
}
|
|
1881
|
+
})
|
|
1882
|
+
.catch((error) => {
|
|
1883
|
+
this.log('Failed to verify debug session:', error);
|
|
1884
|
+
});
|
|
1885
|
+
}
|
|
1886
|
+
catch (error) {
|
|
1887
|
+
this.log('Error checking debug mode:', error);
|
|
1888
|
+
}
|
|
1889
|
+
}
|
|
1890
|
+
/**
|
|
1891
|
+
* Verify debug session with API
|
|
1892
|
+
*/
|
|
1893
|
+
async verifyDebugSession(sessionId, domain) {
|
|
1894
|
+
try {
|
|
1895
|
+
const url = `${this.config.apiUrl}/v1/tenant/${encodeURIComponent(this.config.tenantId)}/debug-sessions/verify`;
|
|
1896
|
+
const response = await fetch(url, {
|
|
1897
|
+
method: 'POST',
|
|
1898
|
+
headers: {
|
|
1899
|
+
'Content-Type': 'application/json',
|
|
1900
|
+
},
|
|
1901
|
+
body: JSON.stringify({
|
|
1902
|
+
sessionId,
|
|
1903
|
+
domain,
|
|
1904
|
+
}),
|
|
1905
|
+
});
|
|
1906
|
+
if (!response.ok) {
|
|
1907
|
+
return false;
|
|
1908
|
+
}
|
|
1909
|
+
const result = await response.json();
|
|
1910
|
+
return result.valid === true;
|
|
1911
|
+
}
|
|
1912
|
+
catch (error) {
|
|
1913
|
+
this.log('Debug session verification error:', error);
|
|
1914
|
+
return false;
|
|
1915
|
+
}
|
|
1916
|
+
}
|
|
1917
|
+
/**
|
|
1918
|
+
* Initialize debug agent
|
|
1919
|
+
*/
|
|
1920
|
+
initializeDebugAgent(sessionId) {
|
|
1921
|
+
if (typeof window === 'undefined')
|
|
1922
|
+
return;
|
|
1923
|
+
try {
|
|
1924
|
+
this.log('Loading debug agent module');
|
|
1925
|
+
Promise.resolve().then(() => __importStar(require('./debug-agent'))).then(({ DebugAgent }) => {
|
|
1926
|
+
try {
|
|
1927
|
+
this.debugAgent = new DebugAgent(this, sessionId, this.config.tenantId, this.config.apiUrl, {
|
|
1928
|
+
debug: this.config.debug,
|
|
1929
|
+
});
|
|
1930
|
+
this.log('Debug agent initialized');
|
|
1931
|
+
}
|
|
1932
|
+
catch (error) {
|
|
1933
|
+
this.log('Failed to initialize debug agent:', error);
|
|
1934
|
+
}
|
|
1935
|
+
}).catch((error) => {
|
|
1936
|
+
this.log('Failed to load debug agent module:', error);
|
|
1937
|
+
});
|
|
1938
|
+
}
|
|
1939
|
+
catch (error) {
|
|
1940
|
+
this.log('Error initializing debug agent:', error);
|
|
1941
|
+
}
|
|
1942
|
+
}
|
|
1821
1943
|
/**
|
|
1822
1944
|
* Destroy the client and clean up resources
|
|
1823
1945
|
*/
|
|
@@ -1857,6 +1979,11 @@ class GrainAnalytics {
|
|
|
1857
1979
|
this.heatmapTrackingManager.destroy();
|
|
1858
1980
|
this.heatmapTrackingManager = null;
|
|
1859
1981
|
}
|
|
1982
|
+
// Destroy debug agent
|
|
1983
|
+
if (this.debugAgent) {
|
|
1984
|
+
this.debugAgent.destroy();
|
|
1985
|
+
this.debugAgent = null;
|
|
1986
|
+
}
|
|
1860
1987
|
// Send any remaining events (in chunks if necessary)
|
|
1861
1988
|
if (this.eventQueue.length > 0) {
|
|
1862
1989
|
const eventsToSend = [...this.eventQueue];
|