@wireai/activation 0.12.2 → 0.13.2
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/AGENTS.md +3 -1
- package/CHANGELOG.md +259 -1
- package/README.md +87 -3
- package/dist/analytics/index.d.mts +2 -2
- package/dist/analytics/index.d.ts +2 -2
- package/dist/analytics/index.js +174 -36
- package/dist/analytics/index.js.map +1 -1
- package/dist/analytics/index.mjs +174 -37
- package/dist/analytics/index.mjs.map +1 -1
- package/dist/{currentSession-BlCeDP0f.d.mts → currentSession-ClkLjcJ0.d.mts} +456 -19
- package/dist/{currentSession-BxEB37xt.d.ts → currentSession-DOVZEWJl.d.ts} +456 -19
- package/dist/index.d.mts +197 -16
- package/dist/index.d.ts +197 -16
- package/dist/index.js +1056 -390
- package/dist/index.js.map +1 -1
- package/dist/index.mjs +836 -193
- package/dist/index.mjs.map +1 -1
- package/dist/questionnaire/index.js.map +1 -1
- package/dist/questionnaire/index.mjs.map +1 -1
- package/dist/reviews/index.js +20 -7
- package/dist/reviews/index.js.map +1 -1
- package/dist/reviews/index.mjs +20 -7
- package/dist/reviews/index.mjs.map +1 -1
- package/package.json +1 -1
- package/src/OnboardingFlow.tsx +141 -3
- package/src/WireOnboarding.tsx +178 -34
- package/src/activation/wireActivation.ts +13 -7
- package/src/analytics/analyticsEvent.ts +16 -1
- package/src/analytics/analyticsFacade.ts +11 -10
- package/src/analytics/currentSession.ts +6 -20
- package/src/analytics/eventQueue.ts +71 -1
- package/src/analytics/index.ts +1 -1
- package/src/analytics/reportClientEvent.ts +157 -38
- package/src/cards/PermissionCard.tsx +438 -0
- package/src/cards/index.ts +7 -0
- package/src/config/wireConfigFromEnv.ts +1 -10
- package/src/context/deviceId.ts +77 -16
- package/src/context/userContext.ts +4 -15
- package/src/identity/identityRecord.ts +123 -0
- package/src/identity/userIdentity.ts +45 -9
- package/src/illustrations/defaultIllustrations.tsx +44 -3
- package/src/index.ts +44 -4
- package/src/permissions/index.ts +64 -0
- package/src/permissions/permissionCopy.ts +87 -0
- package/src/permissions/permissionEvents.ts +76 -0
- package/src/permissions/permissionMemory.ts +88 -0
- package/src/permissions/placement.ts +88 -0
- package/src/permissions/types.ts +131 -0
- package/src/session/persistedSession.ts +10 -3
- package/src/session-analytics/useLifecycleEvents.ts +10 -1
- package/src/types.ts +77 -1
- package/src/utils/deriveAnswers.ts +6 -2
- package/src/utils/readProgress.ts +4 -0
- package/src/utils/warnInDev.ts +33 -0
- package/src/components/DoneBlock.tsx +0 -37
package/dist/analytics/index.js
CHANGED
|
@@ -402,39 +402,63 @@ var init_Constants = __esm({
|
|
|
402
402
|
|
|
403
403
|
// src/analytics/reportClientEvent.ts
|
|
404
404
|
var makeSessionId = () => `wire_${Date.now().toString(36)}_${Math.random().toString(36).slice(2, 10)}`;
|
|
405
|
+
var toWireEvents = (events) => events.map((event) => {
|
|
406
|
+
if (typeof event.ts !== "number") return event;
|
|
407
|
+
const { ts, ...rest } = event;
|
|
408
|
+
if (!Number.isFinite(ts)) return rest;
|
|
409
|
+
try {
|
|
410
|
+
return { ...rest, ts: new Date(ts).toISOString() };
|
|
411
|
+
} catch {
|
|
412
|
+
return rest;
|
|
413
|
+
}
|
|
414
|
+
});
|
|
405
415
|
var buildEventsRequest = (target, events) => {
|
|
406
416
|
if (!(target == null ? void 0 : target.serverUrl) || events.length === 0) return null;
|
|
407
417
|
try {
|
|
408
418
|
const url = `${target.serverUrl.replace(/\/$/, "")}/v1/events`;
|
|
409
419
|
const headers = { "Content-Type": "application/json" };
|
|
410
420
|
if (target.apiKey) headers.Authorization = `Bearer ${target.apiKey}`;
|
|
411
|
-
|
|
421
|
+
const body = JSON.stringify({ events: toWireEvents(events) });
|
|
422
|
+
return { url, init: { method: "POST", headers, body } };
|
|
412
423
|
} catch {
|
|
413
424
|
return null;
|
|
414
425
|
}
|
|
415
426
|
};
|
|
416
|
-
var
|
|
417
|
-
if (typeof __DEV__ === "undefined" || !__DEV__) return;
|
|
418
|
-
if (typeof console === "undefined" || !console.warn) return;
|
|
427
|
+
var readEventsAck = async (res) => {
|
|
419
428
|
try {
|
|
420
429
|
const json = res == null ? void 0 : res.json;
|
|
421
|
-
if (typeof json !== "function") return;
|
|
422
|
-
|
|
423
|
-
|
|
424
|
-
|
|
425
|
-
|
|
426
|
-
|
|
427
|
-
|
|
428
|
-
|
|
429
|
-
|
|
430
|
+
if (typeof json !== "function") return void 0;
|
|
431
|
+
const body = await Promise.resolve(json.call(res));
|
|
432
|
+
const skipped = body == null ? void 0 : body.skipped;
|
|
433
|
+
if (typeof skipped !== "number" || !Number.isFinite(skipped)) return void 0;
|
|
434
|
+
const reasons = Array.isArray(body == null ? void 0 : body.errors) ? body.errors.map((e) => {
|
|
435
|
+
const entry = e;
|
|
436
|
+
const reason = entry == null ? void 0 : entry.reason;
|
|
437
|
+
if (typeof reason !== "string") return void 0;
|
|
438
|
+
const field = entry == null ? void 0 : entry.field;
|
|
439
|
+
return typeof field === "string" && field.length > 0 ? `${reason} (field: ${field})` : reason;
|
|
440
|
+
}).filter((r) => typeof r === "string") : [];
|
|
441
|
+
return { written: typeof (body == null ? void 0 : body.written) === "number" ? body.written : void 0, skipped, reasons };
|
|
430
442
|
} catch {
|
|
443
|
+
return void 0;
|
|
431
444
|
}
|
|
432
445
|
};
|
|
446
|
+
var describeDiscarded = (ack) => `[wireai] the server ACCEPTED the /v1/events POST but DISCARDED ${ack.skipped} event(s) (skipped in the response body) \u2014 they are gone, not retried. The server reported: skipped=${ack.skipped}${ack.written !== void 0 ? `, written=${ack.written}` : ""}` + (ack.reasons.length > 0 ? `, reasons: ${ack.reasons.join(", ")}.` : ". It gave no reason (the endpoint folds every rejection into one count), so check the server's ingest log for this request rather than guessing.");
|
|
447
|
+
var warnOnSkippedEvents = (res) => {
|
|
448
|
+
if (typeof __DEV__ === "undefined" || !__DEV__) return;
|
|
449
|
+
if (typeof console === "undefined" || !console.warn) return;
|
|
450
|
+
void readEventsAck(res).then((ack) => {
|
|
451
|
+
if (!ack || ack.skipped <= 0) return;
|
|
452
|
+
console.warn(describeDiscarded(ack));
|
|
453
|
+
});
|
|
454
|
+
};
|
|
433
455
|
var reportClientEvents = (target, events) => {
|
|
434
456
|
try {
|
|
435
457
|
const req = buildEventsRequest(target, events);
|
|
436
458
|
if (!req) return;
|
|
437
|
-
void fetch(req.url, req.init).
|
|
459
|
+
void fetch(req.url, req.init).then((res) => {
|
|
460
|
+
warnOnSkippedEvents(res);
|
|
461
|
+
}).catch(() => {
|
|
438
462
|
});
|
|
439
463
|
} catch {
|
|
440
464
|
}
|
|
@@ -445,13 +469,28 @@ var reportClientEventsAwait = async (target, events) => {
|
|
|
445
469
|
const req = buildEventsRequest(target, events);
|
|
446
470
|
if (!req) return false;
|
|
447
471
|
const res = await fetch(req.url, req.init);
|
|
448
|
-
|
|
472
|
+
if (!res || !res.ok) return false;
|
|
473
|
+
const ack = await readEventsAck(res);
|
|
474
|
+
if (!ack || ack.skipped <= 0) return true;
|
|
475
|
+
if (typeof __DEV__ !== "undefined" && __DEV__ && typeof console !== "undefined" && console.warn) {
|
|
476
|
+
console.warn(describeDiscarded(ack));
|
|
477
|
+
}
|
|
478
|
+
return false;
|
|
449
479
|
} catch {
|
|
450
480
|
return false;
|
|
451
481
|
}
|
|
452
482
|
};
|
|
453
483
|
var reportClientEventAwait = (target, event) => reportClientEventsAwait(target, [event]);
|
|
454
484
|
|
|
485
|
+
// src/utils/warnInDev.ts
|
|
486
|
+
var warnInDev = (message) => {
|
|
487
|
+
if (typeof __DEV__ !== "undefined" && __DEV__ && typeof console !== "undefined" && console.warn) {
|
|
488
|
+
console.warn(message);
|
|
489
|
+
return true;
|
|
490
|
+
}
|
|
491
|
+
return false;
|
|
492
|
+
};
|
|
493
|
+
|
|
455
494
|
// src/analytics/currentSession.ts
|
|
456
495
|
var CURRENT_SESSION_ID_SLOT = /* @__PURE__ */ Symbol.for(
|
|
457
496
|
"@wireai/activation:currentSessionId"
|
|
@@ -466,13 +505,6 @@ var getCurrentSessionId = () => globalSlot[CURRENT_SESSION_ID_SLOT];
|
|
|
466
505
|
var resetCurrentSessionId = () => {
|
|
467
506
|
globalSlot[CURRENT_SESSION_ID_SLOT] = void 0;
|
|
468
507
|
};
|
|
469
|
-
var warnInDev = (message) => {
|
|
470
|
-
if (typeof __DEV__ !== "undefined" && __DEV__ && typeof console !== "undefined" && console.warn) {
|
|
471
|
-
console.warn(message);
|
|
472
|
-
return true;
|
|
473
|
-
}
|
|
474
|
-
return false;
|
|
475
|
-
};
|
|
476
508
|
var MINT_WARNING = "[wireai] No app-open session was registered, so a session id was minted for this event (the server drops an event that has no session_id, and still answers 200). Mount useLifecycleEvents at your app root so events correlate to a real app-open.";
|
|
477
509
|
var MINT_WARNED_SLOT = /* @__PURE__ */ Symbol.for(
|
|
478
510
|
"@wireai/activation:currentSessionIdMintWarned"
|
|
@@ -583,6 +615,43 @@ var useScreenTracking = (navigationRef, options = {}) => {
|
|
|
583
615
|
}, [navigationRef]);
|
|
584
616
|
};
|
|
585
617
|
|
|
618
|
+
// src/permissions/permissionEvents.ts
|
|
619
|
+
var WIRE_PERMISSION_EVENTS = {
|
|
620
|
+
/** The priming screen became visible. The denominator for every rate below. */
|
|
621
|
+
screenShown: "wire_permission_screen_shown",
|
|
622
|
+
/** The user tapped the primary, so the OS dialog is about to open. The rationale worked. */
|
|
623
|
+
primerAccepted: "wire_permission_primer_accepted",
|
|
624
|
+
/** The OS granted it. */
|
|
625
|
+
granted: "wire_permission_granted",
|
|
626
|
+
/** The OS refused it (a permanently blocked answer reports here too, with `status: "blocked"`). */
|
|
627
|
+
denied: "wire_permission_denied",
|
|
628
|
+
/** The user took the secondary. The one native prompt was NOT spent. */
|
|
629
|
+
skipped: "wire_permission_skipped",
|
|
630
|
+
/** A blocked user was redirected to the OS settings page. */
|
|
631
|
+
settingsOpened: "wire_permission_settings_opened"
|
|
632
|
+
};
|
|
633
|
+
var permissionEventName = (stage) => {
|
|
634
|
+
switch (stage) {
|
|
635
|
+
case "shown":
|
|
636
|
+
return WIRE_PERMISSION_EVENTS.screenShown;
|
|
637
|
+
case "accepted":
|
|
638
|
+
return WIRE_PERMISSION_EVENTS.primerAccepted;
|
|
639
|
+
case "granted":
|
|
640
|
+
return WIRE_PERMISSION_EVENTS.granted;
|
|
641
|
+
case "denied":
|
|
642
|
+
return WIRE_PERMISSION_EVENTS.denied;
|
|
643
|
+
case "skipped":
|
|
644
|
+
return WIRE_PERMISSION_EVENTS.skipped;
|
|
645
|
+
case "settings":
|
|
646
|
+
return WIRE_PERMISSION_EVENTS.settingsOpened;
|
|
647
|
+
default: {
|
|
648
|
+
const _exhaustive = stage;
|
|
649
|
+
return _exhaustive;
|
|
650
|
+
}
|
|
651
|
+
}
|
|
652
|
+
};
|
|
653
|
+
var permissionEventProps = (permission, status) => status ? { permission, status } : { permission };
|
|
654
|
+
|
|
586
655
|
// src/analytics/analyticsEvent.ts
|
|
587
656
|
var WIRE_ONBOARDING_EVENTS = {
|
|
588
657
|
started: "wire_onboarding_started",
|
|
@@ -615,6 +684,11 @@ var toAnalyticsEvent = (event) => {
|
|
|
615
684
|
};
|
|
616
685
|
case "fallback":
|
|
617
686
|
return { name: WIRE_ONBOARDING_EVENTS.fallback, params: { reason: event.reason } };
|
|
687
|
+
case "permission":
|
|
688
|
+
return {
|
|
689
|
+
name: permissionEventName(event.stage),
|
|
690
|
+
params: permissionEventProps(event.permission, event.status)
|
|
691
|
+
};
|
|
618
692
|
default: {
|
|
619
693
|
const _exhaustive = event;
|
|
620
694
|
return _exhaustive;
|
|
@@ -820,6 +894,31 @@ var DEFAULTS = {
|
|
|
820
894
|
maxRetries: 6
|
|
821
895
|
};
|
|
822
896
|
var READ_TIMEOUT_MS = 1500;
|
|
897
|
+
var QUEUE_KEY_SLOT = /* @__PURE__ */ Symbol.for("@wireai/activation:eventQueueKeys");
|
|
898
|
+
var queueKeyGlobal = globalThis;
|
|
899
|
+
var claimedQueueKeys = () => {
|
|
900
|
+
const existing = queueKeyGlobal[QUEUE_KEY_SLOT];
|
|
901
|
+
if (existing) return existing;
|
|
902
|
+
const created = /* @__PURE__ */ new Set();
|
|
903
|
+
queueKeyGlobal[QUEUE_KEY_SLOT] = created;
|
|
904
|
+
return created;
|
|
905
|
+
};
|
|
906
|
+
var claimQueueKey = (preferred, explicit) => {
|
|
907
|
+
const claimed = claimedQueueKeys();
|
|
908
|
+
if (explicit || !claimed.has(preferred)) {
|
|
909
|
+
claimed.add(preferred);
|
|
910
|
+
return preferred;
|
|
911
|
+
}
|
|
912
|
+
let ordinal = 2;
|
|
913
|
+
while (claimed.has(`${preferred}#${ordinal}`)) ordinal++;
|
|
914
|
+
const key = `${preferred}#${ordinal}`;
|
|
915
|
+
claimed.add(key);
|
|
916
|
+
warnInDev(
|
|
917
|
+
`[wireai] a second event queue was created for the same appId, and "${preferred}" is already claimed by a live one. Two queues sharing one storage slot overwrite each other's backlog, delete each other's pending events when one drains to empty, and double-send on relaunch, so this queue was given "${key}" instead. Prefer ONE analytics instance per app; if you really need two, pass an explicit \`storageKey\` to each so the slots are yours to reason about.`
|
|
918
|
+
);
|
|
919
|
+
return key;
|
|
920
|
+
};
|
|
921
|
+
var resetEventQueueKeys = () => claimedQueueKeys().clear();
|
|
823
922
|
var withTimeout = (p, ms) => {
|
|
824
923
|
let timer;
|
|
825
924
|
const timeout = new Promise((resolve) => {
|
|
@@ -851,7 +950,8 @@ var createEventQueue = (options) => {
|
|
|
851
950
|
var _a2, _b, _c, _d, _e, _f, _g;
|
|
852
951
|
const target = options.target;
|
|
853
952
|
const storage = options.storage;
|
|
854
|
-
const
|
|
953
|
+
const defaultKey = (_b = options.storageKey) != null ? _b : `wireai:evtq:${(_a2 = options.appId) != null ? _a2 : "default"}`;
|
|
954
|
+
const key = storage ? claimQueueKey(defaultKey, options.storageKey !== void 0) : defaultKey;
|
|
855
955
|
const maxSize = (_c = options.maxSize) != null ? _c : DEFAULTS.maxSize;
|
|
856
956
|
const batchSize = (_d = options.batchSize) != null ? _d : DEFAULTS.batchSize;
|
|
857
957
|
const baseBackoffMs = (_e = options.baseBackoffMs) != null ? _e : DEFAULTS.baseBackoffMs;
|
|
@@ -1102,6 +1202,29 @@ var resolveUserContext = (ctx = {}, opts = {}) => {
|
|
|
1102
1202
|
return result;
|
|
1103
1203
|
};
|
|
1104
1204
|
|
|
1205
|
+
// src/identity/identityRecord.ts
|
|
1206
|
+
var IDENTITY_PROVENANCE_SLOT = /* @__PURE__ */ Symbol.for("@wireai/activation:identityProvenance");
|
|
1207
|
+
var provenanceGlobal = globalThis;
|
|
1208
|
+
var provenanceRegistry = () => {
|
|
1209
|
+
const existing = provenanceGlobal[IDENTITY_PROVENANCE_SLOT];
|
|
1210
|
+
if (existing) return existing;
|
|
1211
|
+
const created = { host: /* @__PURE__ */ new Map() };
|
|
1212
|
+
provenanceGlobal[IDENTITY_PROVENANCE_SLOT] = created;
|
|
1213
|
+
return created;
|
|
1214
|
+
};
|
|
1215
|
+
var provenanceKey = (space, scope) => `${space}:${scope != null ? scope : "default"}`;
|
|
1216
|
+
var resolveIdentity = (input) => {
|
|
1217
|
+
var _a2;
|
|
1218
|
+
if (typeof input.value !== "string") return void 0;
|
|
1219
|
+
const value = input.value.trim();
|
|
1220
|
+
if (!value) return void 0;
|
|
1221
|
+
const durable = (_a2 = input.durable) != null ? _a2 : input.source === "host";
|
|
1222
|
+
{
|
|
1223
|
+
provenanceRegistry().host.set(provenanceKey(input.space, input.scope), value);
|
|
1224
|
+
}
|
|
1225
|
+
return { value, space: input.space, source: input.source, durable };
|
|
1226
|
+
};
|
|
1227
|
+
|
|
1105
1228
|
// src/context/deviceId.ts
|
|
1106
1229
|
var AUTO_DEVICE_ID_PREFIX = "wdev_";
|
|
1107
1230
|
var deviceIdStorageKey = (appId) => `wireai:analytics:deviceKey:${appId != null ? appId : "default"}`;
|
|
@@ -1124,24 +1247,37 @@ var startHydration = (registry, appId, storage, minted) => {
|
|
|
1124
1247
|
const existing = registry.pending.get(appId);
|
|
1125
1248
|
if (existing) return existing;
|
|
1126
1249
|
const slot = deviceIdStorageKey(appId);
|
|
1127
|
-
const
|
|
1250
|
+
const degraded = () => {
|
|
1128
1251
|
var _a2;
|
|
1129
|
-
return (_a2 = registry.keys.get(appId)) != null ? _a2 : minted;
|
|
1252
|
+
return { value: (_a2 = registry.keys.get(appId)) != null ? _a2 : minted, durable: false };
|
|
1130
1253
|
};
|
|
1254
|
+
const adopted = (value) => ({ value, durable: true });
|
|
1131
1255
|
let run;
|
|
1132
1256
|
try {
|
|
1133
1257
|
run = Promise.resolve(storage.getItem(slot)).then((saved) => {
|
|
1134
1258
|
const persisted = typeof saved === "string" && saved.trim() ? saved.trim() : void 0;
|
|
1135
1259
|
if (persisted) {
|
|
1136
1260
|
registry.keys.set(appId, persisted);
|
|
1137
|
-
return persisted;
|
|
1261
|
+
return adopted(persisted);
|
|
1138
1262
|
}
|
|
1139
|
-
return Promise.resolve(storage.setItem(slot, minted)).then(
|
|
1140
|
-
|
|
1263
|
+
return Promise.resolve(storage.setItem(slot, minted)).then(
|
|
1264
|
+
() => {
|
|
1265
|
+
var _a2;
|
|
1266
|
+
return adopted((_a2 = registry.keys.get(appId)) != null ? _a2 : minted);
|
|
1267
|
+
},
|
|
1268
|
+
degraded
|
|
1269
|
+
);
|
|
1270
|
+
}).catch(degraded);
|
|
1141
1271
|
} catch {
|
|
1142
|
-
run = Promise.resolve(
|
|
1272
|
+
run = Promise.resolve(degraded());
|
|
1143
1273
|
}
|
|
1144
1274
|
registry.pending.set(appId, run);
|
|
1275
|
+
void run.then((outcome) => {
|
|
1276
|
+
var _a2;
|
|
1277
|
+
if (outcome.durable) return;
|
|
1278
|
+
(_a2 = registry.pending) == null ? void 0 : _a2.delete(appId);
|
|
1279
|
+
registry.hydrating.delete(appId);
|
|
1280
|
+
});
|
|
1145
1281
|
return run;
|
|
1146
1282
|
};
|
|
1147
1283
|
var resolveAutoDeviceKey = (opts = {}) => {
|
|
@@ -1169,11 +1305,6 @@ var resetAutoDeviceKeys = () => {
|
|
|
1169
1305
|
};
|
|
1170
1306
|
|
|
1171
1307
|
// src/analytics/analyticsFacade.ts
|
|
1172
|
-
var warnInDev2 = (message) => {
|
|
1173
|
-
if (typeof __DEV__ !== "undefined" && __DEV__ && typeof console !== "undefined" && console.warn) {
|
|
1174
|
-
console.warn(message);
|
|
1175
|
-
}
|
|
1176
|
-
};
|
|
1177
1308
|
var createAnalytics = (config, options = {}) => {
|
|
1178
1309
|
var _a2, _b, _c;
|
|
1179
1310
|
const resolveSessionId = () => {
|
|
@@ -1181,13 +1312,19 @@ var createAnalytics = (config, options = {}) => {
|
|
|
1181
1312
|
return (_a3 = config.sessionId) != null ? _a3 : ensureCurrentSessionId();
|
|
1182
1313
|
};
|
|
1183
1314
|
if (config.sessionId) {
|
|
1184
|
-
|
|
1315
|
+
warnInDev(
|
|
1185
1316
|
"[wireai] createAnalytics({ sessionId }) PINS every event from this instance to that one frozen id and opts out of the live per-open session (app.session_started) \u2014 lifecycle analytics collapse onto a single device-scoped id. Remove it unless your host runs its own session lifecycle."
|
|
1186
1317
|
);
|
|
1187
1318
|
}
|
|
1188
1319
|
const detectedAppVersion = detectAppVersion();
|
|
1189
1320
|
let userContext = { ...(_a2 = config.userContext) != null ? _a2 : {} };
|
|
1190
1321
|
const hostDeviceKeyAtInit = typeof ((_b = config.userContext) == null ? void 0 : _b.deviceKey) === "string" && config.userContext.deviceKey.trim() ? config.userContext.deviceKey.trim() : void 0;
|
|
1322
|
+
resolveIdentity({
|
|
1323
|
+
value: hostDeviceKeyAtInit,
|
|
1324
|
+
space: "device",
|
|
1325
|
+
source: "host",
|
|
1326
|
+
scope: config.appId
|
|
1327
|
+
});
|
|
1191
1328
|
const autoDeviceKeyOptions = {
|
|
1192
1329
|
appId: config.appId,
|
|
1193
1330
|
// A host-supplied deviceKey opts out of minting AND persisting (unchanged contract).
|
|
@@ -1233,7 +1370,7 @@ var createAnalytics = (config, options = {}) => {
|
|
|
1233
1370
|
};
|
|
1234
1371
|
const guardUserId = (clean) => {
|
|
1235
1372
|
if (config.allowEmailAsUserId || !looksLikeEmail(clean)) return clean;
|
|
1236
|
-
|
|
1373
|
+
warnInDev(
|
|
1237
1374
|
"[wireai] identify() was called with an email-shaped id. A raw email must NOT be the opaque user_id (PII leak) \u2014 pass it as userContext.userEmail instead. Binding was skipped. Set allowEmailAsUserId:true on createAnalytics if your user id genuinely is an email."
|
|
1238
1375
|
);
|
|
1239
1376
|
return void 0;
|
|
@@ -1354,6 +1491,7 @@ exports.reportClientEvents = reportClientEvents;
|
|
|
1354
1491
|
exports.reportClientEventsAwait = reportClientEventsAwait;
|
|
1355
1492
|
exports.resetAutoDeviceKeys = resetAutoDeviceKeys;
|
|
1356
1493
|
exports.resetCurrentSessionId = resetCurrentSessionId;
|
|
1494
|
+
exports.resetEventQueueKeys = resetEventQueueKeys;
|
|
1357
1495
|
exports.resolveAutoDeviceKey = resolveAutoDeviceKey;
|
|
1358
1496
|
exports.screenTrackingHandler = screenTrackingHandler;
|
|
1359
1497
|
exports.setCurrentSessionId = setCurrentSessionId;
|