@magicfeedback/popup-sdk 1.8.2 → 1.8.3
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 +32 -1
- package/dist/index.d.mts +46 -1
- package/dist/index.d.ts +46 -1
- package/dist/index.js +129 -19
- package/dist/index.js.map +1 -1
- package/dist/index.mjs +130 -20
- package/dist/index.mjs.map +1 -1
- package/dist/react-native.d.mts +37 -0
- package/dist/react-native.d.ts +37 -0
- package/dist/react-native.js +127 -17
- package/dist/react-native.js.map +1 -1
- package/dist/react-native.mjs +127 -17
- package/dist/react-native.mjs.map +1 -1
- package/dist/{renderPopup-ERUKQE4U.mjs → renderPopup-3CZ6WTXF.mjs} +3 -3
- package/dist/renderPopup-3CZ6WTXF.mjs.map +1 -0
- package/package.json +1 -1
- package/dist/renderPopup-ERUKQE4U.mjs.map +0 -1
package/dist/react-native.d.mts
CHANGED
|
@@ -156,6 +156,13 @@ interface DeepdotsInitParams {
|
|
|
156
156
|
* to the configured integration; if missing, it stays in dry-run mode (console.log only).
|
|
157
157
|
*/
|
|
158
158
|
analytics?: AnalyticsKeys;
|
|
159
|
+
/**
|
|
160
|
+
* IP geolocation (country/city) added to analytics. Default `true`. The lookup calls
|
|
161
|
+
* third-party services (ipapi.co, then ipwho.is, then ipinfo.io as fallbacks, 3 s timeout
|
|
162
|
+
* each) and only runs when `analytics` is configured, tracking is enabled and the 30-day
|
|
163
|
+
* cache is missing or expired. Set `false` to never call them nor attach country/city.
|
|
164
|
+
*/
|
|
165
|
+
geolocation?: boolean;
|
|
159
166
|
/**
|
|
160
167
|
* Internal user attributes known only by the host (language, age, plan, ...), sent
|
|
161
168
|
* to the backend Contact for segmentation/targeting. Requires `userId`. Equivalent to calling
|
|
@@ -406,11 +413,21 @@ declare class DeepdotsPopups {
|
|
|
406
413
|
* nueva al volver a foreground o al conceder el consentimiento más tarde.
|
|
407
414
|
*/
|
|
408
415
|
private sessionOpen;
|
|
416
|
+
/** Último `user_engagement` emitido (ms epoch): marca el latido. */
|
|
417
|
+
private lastEngagementAt;
|
|
418
|
+
/** Cuándo se ocultó la pestaña por última vez (ms epoch); null si está visible. */
|
|
419
|
+
private hiddenAt;
|
|
409
420
|
/**
|
|
410
421
|
* Idioma resuelto en init() (explícito > navigator.language > Intl). Única fuente de
|
|
411
422
|
* verdad para el context de analytics Y para la segmentación por idioma de los popups.
|
|
412
423
|
*/
|
|
413
424
|
private language;
|
|
425
|
+
/** `geolocation` del init: si es false no se usa ni la caché ni el lookup. */
|
|
426
|
+
private geoEnabled;
|
|
427
|
+
/** Solo se consulta a terceros si el país/ciudad se va a enviar (analytics configurado). */
|
|
428
|
+
private geoWanted;
|
|
429
|
+
/** Evita más de un lookup por instancia (el consentimiento puede ir y venir). */
|
|
430
|
+
private geoLookupStarted;
|
|
414
431
|
/** Initialize the SDK with configuration */
|
|
415
432
|
init(config: DeepdotsInitParams): void;
|
|
416
433
|
/** User id actual (generado por el SDK o provisto por el cliente). Null si tracking off. */
|
|
@@ -522,6 +539,26 @@ declare class DeepdotsPopups {
|
|
|
522
539
|
}): void;
|
|
523
540
|
/** Emite un evento `user_engagement` con el tiempo activo acumulado (#8). */
|
|
524
541
|
private flushEngagement;
|
|
542
|
+
/** Tick del flush periódico: latido de engagement si toca, y envío de lo acumulado. */
|
|
543
|
+
private onAnalyticsFlushTick;
|
|
544
|
+
/**
|
|
545
|
+
* La pestaña vuelve a verse. Tras más de ANALYTICS_SESSION_TIMEOUT_MS oculta, la sesión
|
|
546
|
+
* anterior termina y empieza otra: seguir con el mismo sessionId mezclaba dos visitas y,
|
|
547
|
+
* si el backend ya la había cerrado por inactividad, la partía en dos feedbacks.
|
|
548
|
+
* - Oculta menos de ANALYTICS_SESSION_DISCARD_MS: el backend aún la tiene abierta → se
|
|
549
|
+
* cierra con normalidad (page_view de la pantalla, session_end `idle_timeout`, completed).
|
|
550
|
+
* - Más: ya la cerró el backend → se descarta sin enviar nada.
|
|
551
|
+
*/
|
|
552
|
+
private onDocumentVisible;
|
|
553
|
+
/** Olvida la sesión abierta sin enviar nada (ver onDocumentVisible). */
|
|
554
|
+
private discardSession;
|
|
555
|
+
/**
|
|
556
|
+
* Geolocalización por IP (país/ciudad para analytics). La caché persistente es local y se
|
|
557
|
+
* aplica siempre que `geolocation` no esté desactivado. El lookup a terceros (ipapi.co →
|
|
558
|
+
* ipwho.is → ipinfo.io, fallback con timeout) solo se hace si el dato se va a ENVIAR:
|
|
559
|
+
* analytics configurado + tracking activo + caché ausente o caducada. Una vez por instancia.
|
|
560
|
+
*/
|
|
561
|
+
private resolveGeo;
|
|
525
562
|
private analyticsIdentity;
|
|
526
563
|
/** Flush automático al ocultar/cerrar la página (no perder el lote pendiente). */
|
|
527
564
|
private setupAnalyticsFlush;
|
package/dist/react-native.d.ts
CHANGED
|
@@ -156,6 +156,13 @@ interface DeepdotsInitParams {
|
|
|
156
156
|
* to the configured integration; if missing, it stays in dry-run mode (console.log only).
|
|
157
157
|
*/
|
|
158
158
|
analytics?: AnalyticsKeys;
|
|
159
|
+
/**
|
|
160
|
+
* IP geolocation (country/city) added to analytics. Default `true`. The lookup calls
|
|
161
|
+
* third-party services (ipapi.co, then ipwho.is, then ipinfo.io as fallbacks, 3 s timeout
|
|
162
|
+
* each) and only runs when `analytics` is configured, tracking is enabled and the 30-day
|
|
163
|
+
* cache is missing or expired. Set `false` to never call them nor attach country/city.
|
|
164
|
+
*/
|
|
165
|
+
geolocation?: boolean;
|
|
159
166
|
/**
|
|
160
167
|
* Internal user attributes known only by the host (language, age, plan, ...), sent
|
|
161
168
|
* to the backend Contact for segmentation/targeting. Requires `userId`. Equivalent to calling
|
|
@@ -406,11 +413,21 @@ declare class DeepdotsPopups {
|
|
|
406
413
|
* nueva al volver a foreground o al conceder el consentimiento más tarde.
|
|
407
414
|
*/
|
|
408
415
|
private sessionOpen;
|
|
416
|
+
/** Último `user_engagement` emitido (ms epoch): marca el latido. */
|
|
417
|
+
private lastEngagementAt;
|
|
418
|
+
/** Cuándo se ocultó la pestaña por última vez (ms epoch); null si está visible. */
|
|
419
|
+
private hiddenAt;
|
|
409
420
|
/**
|
|
410
421
|
* Idioma resuelto en init() (explícito > navigator.language > Intl). Única fuente de
|
|
411
422
|
* verdad para el context de analytics Y para la segmentación por idioma de los popups.
|
|
412
423
|
*/
|
|
413
424
|
private language;
|
|
425
|
+
/** `geolocation` del init: si es false no se usa ni la caché ni el lookup. */
|
|
426
|
+
private geoEnabled;
|
|
427
|
+
/** Solo se consulta a terceros si el país/ciudad se va a enviar (analytics configurado). */
|
|
428
|
+
private geoWanted;
|
|
429
|
+
/** Evita más de un lookup por instancia (el consentimiento puede ir y venir). */
|
|
430
|
+
private geoLookupStarted;
|
|
414
431
|
/** Initialize the SDK with configuration */
|
|
415
432
|
init(config: DeepdotsInitParams): void;
|
|
416
433
|
/** User id actual (generado por el SDK o provisto por el cliente). Null si tracking off. */
|
|
@@ -522,6 +539,26 @@ declare class DeepdotsPopups {
|
|
|
522
539
|
}): void;
|
|
523
540
|
/** Emite un evento `user_engagement` con el tiempo activo acumulado (#8). */
|
|
524
541
|
private flushEngagement;
|
|
542
|
+
/** Tick del flush periódico: latido de engagement si toca, y envío de lo acumulado. */
|
|
543
|
+
private onAnalyticsFlushTick;
|
|
544
|
+
/**
|
|
545
|
+
* La pestaña vuelve a verse. Tras más de ANALYTICS_SESSION_TIMEOUT_MS oculta, la sesión
|
|
546
|
+
* anterior termina y empieza otra: seguir con el mismo sessionId mezclaba dos visitas y,
|
|
547
|
+
* si el backend ya la había cerrado por inactividad, la partía en dos feedbacks.
|
|
548
|
+
* - Oculta menos de ANALYTICS_SESSION_DISCARD_MS: el backend aún la tiene abierta → se
|
|
549
|
+
* cierra con normalidad (page_view de la pantalla, session_end `idle_timeout`, completed).
|
|
550
|
+
* - Más: ya la cerró el backend → se descarta sin enviar nada.
|
|
551
|
+
*/
|
|
552
|
+
private onDocumentVisible;
|
|
553
|
+
/** Olvida la sesión abierta sin enviar nada (ver onDocumentVisible). */
|
|
554
|
+
private discardSession;
|
|
555
|
+
/**
|
|
556
|
+
* Geolocalización por IP (país/ciudad para analytics). La caché persistente es local y se
|
|
557
|
+
* aplica siempre que `geolocation` no esté desactivado. El lookup a terceros (ipapi.co →
|
|
558
|
+
* ipwho.is → ipinfo.io, fallback con timeout) solo se hace si el dato se va a ENVIAR:
|
|
559
|
+
* analytics configurado + tracking activo + caché ausente o caducada. Una vez por instancia.
|
|
560
|
+
*/
|
|
561
|
+
private resolveGeo;
|
|
525
562
|
private analyticsIdentity;
|
|
526
563
|
/** Flush automático al ocultar/cerrar la página (no perder el lote pendiente). */
|
|
527
564
|
private setupAnalyticsFlush;
|
package/dist/react-native.js
CHANGED
|
@@ -4124,10 +4124,13 @@ init_tracking_manager();
|
|
|
4124
4124
|
|
|
4125
4125
|
// src/analytics/analytics-manager.ts
|
|
4126
4126
|
function createDryRunSink(log = console.log) {
|
|
4127
|
-
return (payload) =>
|
|
4128
|
-
|
|
4129
|
-
|
|
4130
|
-
|
|
4127
|
+
return (payload, meta) => {
|
|
4128
|
+
if (meta?.resetSession) return;
|
|
4129
|
+
log(
|
|
4130
|
+
"[DeepdotsAnalytics] (dry-run \xB7 NOT sent \xB7 no init.analytics) POST /sdk/feedback \u2192",
|
|
4131
|
+
JSON.stringify(payload, null, 2)
|
|
4132
|
+
);
|
|
4133
|
+
};
|
|
4131
4134
|
}
|
|
4132
4135
|
var dryRunSink = createDryRunSink();
|
|
4133
4136
|
var AnalyticsManager = class {
|
|
@@ -4194,6 +4197,19 @@ var AnalyticsManager = class {
|
|
|
4194
4197
|
this.exitMiniService(name);
|
|
4195
4198
|
}
|
|
4196
4199
|
}
|
|
4200
|
+
/**
|
|
4201
|
+
* Olvida la sesión en curso SIN emitir nada: vacía el buffer y los mini-services activos
|
|
4202
|
+
* (sin `mini_service_exit`). Para una sesión que el backend ya cerró por inactividad: lo
|
|
4203
|
+
* que quedara pendiente pertenecía a ella y no debe llegar con la sesión nueva.
|
|
4204
|
+
*/
|
|
4205
|
+
discardSession(identity) {
|
|
4206
|
+
this.events = [];
|
|
4207
|
+
this.activeMiniServices.clear();
|
|
4208
|
+
try {
|
|
4209
|
+
void this.sink({ ...this.buildPayload(identity), events: [] }, { resetSession: true });
|
|
4210
|
+
} catch {
|
|
4211
|
+
}
|
|
4212
|
+
}
|
|
4197
4213
|
/**
|
|
4198
4214
|
* Olvida lo que pertenecía al usuario anterior (user attributes + métricas) al cambiar de
|
|
4199
4215
|
* usuario. NO toca el buffer de eventos: el cierre de sesión ya lo vació con la identidad
|
|
@@ -4403,6 +4419,12 @@ function createFeedbackSink(options) {
|
|
|
4403
4419
|
}
|
|
4404
4420
|
};
|
|
4405
4421
|
return async (envelope, meta) => {
|
|
4422
|
+
if (meta?.resetSession) {
|
|
4423
|
+
feedbackSessionId = void 0;
|
|
4424
|
+
firstPostInFlight = null;
|
|
4425
|
+
options.onSessionReset?.();
|
|
4426
|
+
return;
|
|
4427
|
+
}
|
|
4406
4428
|
const final = meta?.final === true;
|
|
4407
4429
|
const sessionEnd = meta?.sessionEnd === true;
|
|
4408
4430
|
if (!feedbackSessionId && firstPostInFlight && !final) {
|
|
@@ -4469,6 +4491,14 @@ var NavigationObserver = class {
|
|
|
4469
4491
|
this.closeCurrent();
|
|
4470
4492
|
this.currentScreen = null;
|
|
4471
4493
|
}
|
|
4494
|
+
/**
|
|
4495
|
+
* Olvida la pantalla actual SIN emitir su visita. Para una sesión que el backend ya dio
|
|
4496
|
+
* por cerrada: su visita no tiene dónde ir, y mandarla con la sesión nueva la contaría
|
|
4497
|
+
* donde no ocurrió. Después, `restart()` vuelve a empezar en la pantalla actual.
|
|
4498
|
+
*/
|
|
4499
|
+
discard() {
|
|
4500
|
+
this.currentScreen = null;
|
|
4501
|
+
}
|
|
4472
4502
|
/**
|
|
4473
4503
|
* Retoma el seguimiento en la pantalla actual tras un `stop()`, cuando se abre una sesión
|
|
4474
4504
|
* nueva sin navegar (cambio de usuario, vuelta de la bfcache). No-op si nunca se instaló
|
|
@@ -5002,6 +5032,10 @@ var EXIT_QUEUE_STORAGE_KEY = "__deepdots_exit_popup_queue__";
|
|
|
5002
5032
|
var DAY_IN_MS = 24 * 60 * 60 * 1e3;
|
|
5003
5033
|
var ANALYTICS_MAX_BATCH_SIZE = 20;
|
|
5004
5034
|
var ANALYTICS_FLUSH_INTERVAL_MS = 3e4;
|
|
5035
|
+
var ANALYTICS_HEARTBEAT_MS = 5 * 6e4;
|
|
5036
|
+
var ANALYTICS_SESSION_TIMEOUT_MS = 30 * 6e4;
|
|
5037
|
+
var ANALYTICS_SERVER_IDLE_MS = 60 * 6e4;
|
|
5038
|
+
var ANALYTICS_SESSION_DISCARD_MS = ANALYTICS_SERVER_IDLE_MS - 10 * 6e4;
|
|
5005
5039
|
var RESERVED_EVENT_PREFIX = "deepdots_";
|
|
5006
5040
|
var CUSTOM_EVENT_PREFIX = "deepdots_event_";
|
|
5007
5041
|
var DeepdotsPopups = class {
|
|
@@ -5065,11 +5099,21 @@ var DeepdotsPopups = class {
|
|
|
5065
5099
|
* nueva al volver a foreground o al conceder el consentimiento más tarde.
|
|
5066
5100
|
*/
|
|
5067
5101
|
this.sessionOpen = false;
|
|
5102
|
+
/** Último `user_engagement` emitido (ms epoch): marca el latido. */
|
|
5103
|
+
this.lastEngagementAt = 0;
|
|
5104
|
+
/** Cuándo se ocultó la pestaña por última vez (ms epoch); null si está visible. */
|
|
5105
|
+
this.hiddenAt = null;
|
|
5068
5106
|
/**
|
|
5069
5107
|
* Idioma resuelto en init() (explícito > navigator.language > Intl). Única fuente de
|
|
5070
5108
|
* verdad para el context de analytics Y para la segmentación por idioma de los popups.
|
|
5071
5109
|
*/
|
|
5072
5110
|
this.language = void 0;
|
|
5111
|
+
/** `geolocation` del init: si es false no se usa ni la caché ni el lookup. */
|
|
5112
|
+
this.geoEnabled = true;
|
|
5113
|
+
/** Solo se consulta a terceros si el país/ciudad se va a enviar (analytics configurado). */
|
|
5114
|
+
this.geoWanted = false;
|
|
5115
|
+
/** Evita más de un lookup por instancia (el consentimiento puede ir y venir). */
|
|
5116
|
+
this.geoLookupStarted = false;
|
|
5073
5117
|
}
|
|
5074
5118
|
/** Initialize the SDK with configuration */
|
|
5075
5119
|
init(config) {
|
|
@@ -5155,15 +5199,9 @@ var DeepdotsPopups = class {
|
|
|
5155
5199
|
if (this.tracking?.isTrackingEnabled()) {
|
|
5156
5200
|
this.crashReporter.install();
|
|
5157
5201
|
}
|
|
5158
|
-
|
|
5159
|
-
|
|
5160
|
-
|
|
5161
|
-
if (geo) {
|
|
5162
|
-
this.analytics?.updateDevice(geo);
|
|
5163
|
-
writeCachedGeo(storage, geo, Date.now());
|
|
5164
|
-
}
|
|
5165
|
-
}).catch(() => {
|
|
5166
|
-
});
|
|
5202
|
+
this.geoEnabled = config.geolocation ?? true;
|
|
5203
|
+
this.geoWanted = this.geoEnabled && !!config.analytics;
|
|
5204
|
+
this.resolveGeo();
|
|
5167
5205
|
this.navObserver = new NavigationObserver();
|
|
5168
5206
|
this.navObserver.onVisit((v) => this.track("deepdots_page_view", { screen: v.screen, duration_seconds: v.durationSeconds }));
|
|
5169
5207
|
this.navObserver.install();
|
|
@@ -5205,6 +5243,7 @@ var DeepdotsPopups = class {
|
|
|
5205
5243
|
if (!enabled) this.closeSession("tracking_disabled");
|
|
5206
5244
|
this.tracking?.setTrackingEnabled(enabled);
|
|
5207
5245
|
if (enabled) this.openSession();
|
|
5246
|
+
if (enabled) this.resolveGeo();
|
|
5208
5247
|
this.log("tracking \xB7 setTrackingEnabled:", enabled, "\xB7 session_id:", this.tracking?.getSessionId() ?? null);
|
|
5209
5248
|
}
|
|
5210
5249
|
// ───────── Analytics (canal separado del feedback, vinculado por user_id) ─────────
|
|
@@ -5401,6 +5440,7 @@ var DeepdotsPopups = class {
|
|
|
5401
5440
|
if (this.sessionOpen) return;
|
|
5402
5441
|
if (!this.tracking?.isTrackingEnabled()) return;
|
|
5403
5442
|
this.sessionOpen = true;
|
|
5443
|
+
this.lastEngagementAt = Date.now();
|
|
5404
5444
|
this.track("deepdots_session_start", {});
|
|
5405
5445
|
this.navObserver?.restart();
|
|
5406
5446
|
if (this.isDocumentVisible()) this.engagement?.resume();
|
|
@@ -5431,7 +5471,76 @@ var DeepdotsPopups = class {
|
|
|
5431
5471
|
flushEngagement() {
|
|
5432
5472
|
if (!this.tracking?.isTrackingEnabled()) return;
|
|
5433
5473
|
const ms = this.engagement?.consume() ?? 0;
|
|
5434
|
-
if (ms > 0)
|
|
5474
|
+
if (ms > 0) {
|
|
5475
|
+
this.track("deepdots_user_engagement", { engagement_time_msec: ms });
|
|
5476
|
+
this.lastEngagementAt = Date.now();
|
|
5477
|
+
}
|
|
5478
|
+
}
|
|
5479
|
+
/** Tick del flush periódico: latido de engagement si toca, y envío de lo acumulado. */
|
|
5480
|
+
onAnalyticsFlushTick() {
|
|
5481
|
+
if (this.sessionOpen && this.isDocumentVisible() && Date.now() - this.lastEngagementAt >= ANALYTICS_HEARTBEAT_MS) {
|
|
5482
|
+
this.flushEngagement();
|
|
5483
|
+
}
|
|
5484
|
+
this.flushAnalytics();
|
|
5485
|
+
}
|
|
5486
|
+
/**
|
|
5487
|
+
* La pestaña vuelve a verse. Tras más de ANALYTICS_SESSION_TIMEOUT_MS oculta, la sesión
|
|
5488
|
+
* anterior termina y empieza otra: seguir con el mismo sessionId mezclaba dos visitas y,
|
|
5489
|
+
* si el backend ya la había cerrado por inactividad, la partía en dos feedbacks.
|
|
5490
|
+
* - Oculta menos de ANALYTICS_SESSION_DISCARD_MS: el backend aún la tiene abierta → se
|
|
5491
|
+
* cierra con normalidad (page_view de la pantalla, session_end `idle_timeout`, completed).
|
|
5492
|
+
* - Más: ya la cerró el backend → se descarta sin enviar nada.
|
|
5493
|
+
*/
|
|
5494
|
+
onDocumentVisible() {
|
|
5495
|
+
const hiddenFor = this.hiddenAt === null ? 0 : Date.now() - this.hiddenAt;
|
|
5496
|
+
this.hiddenAt = null;
|
|
5497
|
+
if (!this.sessionOpen) return;
|
|
5498
|
+
if (hiddenFor < ANALYTICS_SESSION_TIMEOUT_MS) {
|
|
5499
|
+
this.engagement?.resume();
|
|
5500
|
+
return;
|
|
5501
|
+
}
|
|
5502
|
+
if (hiddenFor < ANALYTICS_SESSION_DISCARD_MS) {
|
|
5503
|
+
this.closeSession("idle_timeout");
|
|
5504
|
+
} else {
|
|
5505
|
+
this.discardSession();
|
|
5506
|
+
}
|
|
5507
|
+
this.openSession();
|
|
5508
|
+
}
|
|
5509
|
+
/** Olvida la sesión abierta sin enviar nada (ver onDocumentVisible). */
|
|
5510
|
+
discardSession() {
|
|
5511
|
+
this.sessionOpen = false;
|
|
5512
|
+
this.navObserver?.discard();
|
|
5513
|
+
this.analytics?.discardSession(this.analyticsIdentity());
|
|
5514
|
+
this.engagement?.consume();
|
|
5515
|
+
this.engagement?.pause();
|
|
5516
|
+
this.analyticsFeedbackSessionId = void 0;
|
|
5517
|
+
this.tracking?.setSessionId(null);
|
|
5518
|
+
this.log("tracking \xB7 session discarded after", ANALYTICS_SESSION_DISCARD_MS / 6e4, "min hidden");
|
|
5519
|
+
}
|
|
5520
|
+
/**
|
|
5521
|
+
* Geolocalización por IP (país/ciudad para analytics). La caché persistente es local y se
|
|
5522
|
+
* aplica siempre que `geolocation` no esté desactivado. El lookup a terceros (ipapi.co →
|
|
5523
|
+
* ipwho.is → ipinfo.io, fallback con timeout) solo se hace si el dato se va a ENVIAR:
|
|
5524
|
+
* analytics configurado + tracking activo + caché ausente o caducada. Una vez por instancia.
|
|
5525
|
+
*/
|
|
5526
|
+
resolveGeo() {
|
|
5527
|
+
const storage = this.storage;
|
|
5528
|
+
if (!this.geoEnabled || !storage || !this.analytics) return;
|
|
5529
|
+
const cachedGeo = readCachedGeo(storage, Date.now());
|
|
5530
|
+
if (cachedGeo) {
|
|
5531
|
+
this.analytics.updateDevice(cachedGeo);
|
|
5532
|
+
return;
|
|
5533
|
+
}
|
|
5534
|
+
if (!this.geoWanted || this.geoLookupStarted) return;
|
|
5535
|
+
if (!this.tracking?.isTrackingEnabled()) return;
|
|
5536
|
+
this.geoLookupStarted = true;
|
|
5537
|
+
fetchGeo().then((geo) => {
|
|
5538
|
+
if (geo) {
|
|
5539
|
+
this.analytics?.updateDevice(geo);
|
|
5540
|
+
writeCachedGeo(storage, geo, Date.now());
|
|
5541
|
+
}
|
|
5542
|
+
}).catch(() => {
|
|
5543
|
+
});
|
|
5435
5544
|
}
|
|
5436
5545
|
analyticsIdentity() {
|
|
5437
5546
|
return {
|
|
@@ -5441,8 +5550,8 @@ var DeepdotsPopups = class {
|
|
|
5441
5550
|
}
|
|
5442
5551
|
/** Flush automático al ocultar/cerrar la página (no perder el lote pendiente). */
|
|
5443
5552
|
setupAnalyticsFlush() {
|
|
5444
|
-
if (typeof document === "undefined" || typeof window === "undefined") return;
|
|
5445
5553
|
this.startAnalyticsFlushTimer();
|
|
5554
|
+
if (typeof document === "undefined" || typeof window === "undefined") return;
|
|
5446
5555
|
window.addEventListener("pagehide", () => {
|
|
5447
5556
|
clearInterval(this.analyticsFlushTimer);
|
|
5448
5557
|
this.closeSession("page_hide");
|
|
@@ -5457,14 +5566,15 @@ var DeepdotsPopups = class {
|
|
|
5457
5566
|
this.flushEngagement();
|
|
5458
5567
|
this.engagement?.pause();
|
|
5459
5568
|
this.flushAnalytics();
|
|
5569
|
+
this.hiddenAt = Date.now();
|
|
5460
5570
|
} else if (document.visibilityState === "visible") {
|
|
5461
|
-
|
|
5571
|
+
this.onDocumentVisible();
|
|
5462
5572
|
}
|
|
5463
5573
|
});
|
|
5464
5574
|
}
|
|
5465
5575
|
startAnalyticsFlushTimer() {
|
|
5466
5576
|
clearInterval(this.analyticsFlushTimer);
|
|
5467
|
-
this.analyticsFlushTimer = setInterval(() => this.
|
|
5577
|
+
this.analyticsFlushTimer = setInterval(() => this.onAnalyticsFlushTick(), ANALYTICS_FLUSH_INTERVAL_MS);
|
|
5468
5578
|
}
|
|
5469
5579
|
/** Enable auto-launch functionality with configured triggers */
|
|
5470
5580
|
autoLaunch() {
|