@active-reach/web-sdk 1.37.0 → 1.38.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/dist/aegis.min.js +1 -1
- package/dist/aegis.min.js.map +1 -1
- package/dist/{analytics-Qyzk8JaB.mjs → analytics-Cz1ZBOxH.mjs} +244 -110
- package/dist/analytics-Cz1ZBOxH.mjs.map +1 -0
- package/dist/core/analytics.d.ts +10 -0
- package/dist/core/analytics.d.ts.map +1 -1
- package/dist/core/prefetch-bundle-client.d.ts +1 -0
- package/dist/core/prefetch-bundle-client.d.ts.map +1 -1
- package/dist/core/queue.d.ts.map +1 -1
- package/dist/core/session.d.ts +12 -1
- package/dist/core/session.d.ts.map +1 -1
- package/dist/ecommerce/index.d.ts.map +1 -1
- package/dist/inapp/AegisInAppManager.d.ts +17 -1
- package/dist/inapp/AegisInAppManager.d.ts.map +1 -1
- package/dist/inapp/actions.d.ts +7 -0
- package/dist/inapp/actions.d.ts.map +1 -1
- package/dist/inapp/index.d.ts +1 -1
- package/dist/inapp/index.d.ts.map +1 -1
- package/dist/inapp/renderers/card-template.d.ts.map +1 -1
- package/dist/index.d.ts +1 -0
- package/dist/index.d.ts.map +1 -1
- package/dist/index.js +181 -32
- package/dist/index.js.map +1 -1
- package/dist/react.js +1 -1
- package/dist/triggers/TriggerEngine.d.ts +5 -0
- package/dist/triggers/TriggerEngine.d.ts.map +1 -1
- package/dist/utils/device.d.ts.map +1 -1
- package/dist/utils/meta-cookies.d.ts +7 -0
- package/dist/utils/meta-cookies.d.ts.map +1 -1
- package/dist/utils/redact-url.d.ts +56 -0
- package/dist/utils/redact-url.d.ts.map +1 -0
- package/dist/utils/url-parser.d.ts +38 -0
- package/dist/utils/url-parser.d.ts.map +1 -1
- package/dist/utils/visitor.d.ts +43 -0
- package/dist/utils/visitor.d.ts.map +1 -0
- package/dist/widgets/AegisWidgetManager.d.ts.map +1 -1
- package/package.json +1 -1
- package/dist/analytics-Qyzk8JaB.mjs.map +0 -1
package/dist/index.js
CHANGED
|
@@ -1,5 +1,5 @@
|
|
|
1
|
-
import { S as Storage, l as logger, A as Aegis } from "./analytics-
|
|
2
|
-
import { B, E, N, R, U, m } from "./analytics-
|
|
1
|
+
import { S as Storage, r as redactUrl, l as logger, A as Aegis } from "./analytics-Cz1ZBOxH.mjs";
|
|
2
|
+
import { B, E, N, R, U, m } from "./analytics-Cz1ZBOxH.mjs";
|
|
3
3
|
import { AegisWebPush } from "./push/AegisWebPush.js";
|
|
4
4
|
function debounce(func, wait) {
|
|
5
5
|
let timeoutId = null;
|
|
@@ -26,6 +26,13 @@ function throttle(func, limit) {
|
|
|
26
26
|
};
|
|
27
27
|
}
|
|
28
28
|
const PDP_SKU_RE = /\/p\/([^/?#]+)/;
|
|
29
|
+
function productPath(sku) {
|
|
30
|
+
const encoded = encodeURIComponent(sku).replace(
|
|
31
|
+
/[!'()*]/g,
|
|
32
|
+
(c) => `%${c.charCodeAt(0).toString(16).toUpperCase()}`
|
|
33
|
+
);
|
|
34
|
+
return `/p/${encoded}`;
|
|
35
|
+
}
|
|
29
36
|
function parseAction(actionUrl, meta) {
|
|
30
37
|
const url = (actionUrl ?? "").trim();
|
|
31
38
|
const m2 = meta ?? {};
|
|
@@ -61,7 +68,7 @@ function parseAction(actionUrl, meta) {
|
|
|
61
68
|
case "open-product":
|
|
62
69
|
case "product": {
|
|
63
70
|
const sku = params.get("sku") || m2.sku || void 0;
|
|
64
|
-
return { type: "open_product", sku, productId: m2.product_id, url: sku ?
|
|
71
|
+
return { type: "open_product", sku, productId: m2.product_id, url: sku ? productPath(sku) : void 0 };
|
|
65
72
|
}
|
|
66
73
|
default:
|
|
67
74
|
return { type: "custom", name: verb || "unknown", payload: Object.fromEntries(params) };
|
|
@@ -96,7 +103,7 @@ function parseAction(actionUrl, meta) {
|
|
|
96
103
|
}
|
|
97
104
|
return { type: "dismiss" };
|
|
98
105
|
}
|
|
99
|
-
function fallbackUrlForAction(a, productUrl =
|
|
106
|
+
function fallbackUrlForAction(a, productUrl = productPath) {
|
|
100
107
|
switch (a.type) {
|
|
101
108
|
case "navigate":
|
|
102
109
|
return a.url;
|
|
@@ -652,9 +659,11 @@ function appendRatingThanks(wrap, el2, ctx, fg, accent, isHigh) {
|
|
|
652
659
|
cta.textContent = el2.rating_high_cta || "Leave a review";
|
|
653
660
|
cta.style.cssText = `margin:4px auto 0;display:block;padding:9px 18px;border:none;border-radius:999px;background:${accent};color:#fff;font-size:13px;font-weight:800;cursor:pointer;`;
|
|
654
661
|
cta.addEventListener("click", () => {
|
|
662
|
+
var _a;
|
|
655
663
|
ctx.trackEvent(ctx.campaign.id, "clicked", {
|
|
656
664
|
meta: { element: "rating_input", cta: "high_review" }
|
|
657
665
|
});
|
|
666
|
+
void ((_a = ctx.submitResponse) == null ? void 0 : _a.call(ctx, "review_redirect", { cta: "high_review" }));
|
|
658
667
|
if (ctx.navigate) ctx.navigate(url, "cta");
|
|
659
668
|
else window.location.href = url;
|
|
660
669
|
});
|
|
@@ -821,6 +830,7 @@ function buildProductRatingListElement(el2, ctx, fg) {
|
|
|
821
830
|
const orderId = slot.getAttribute("data-order-id");
|
|
822
831
|
const billCode = slot.getAttribute("data-bill-code");
|
|
823
832
|
const token = slot.getAttribute("data-token");
|
|
833
|
+
const reviewsViaPage = Boolean(slot.getAttribute("data-reviews-url"));
|
|
824
834
|
const reviewsUrl = slot.getAttribute("data-reviews-url") || el2.rating_high_url || null;
|
|
825
835
|
const scale = typeof el2.rating_scale === "number" && el2.rating_scale >= 2 && el2.rating_scale <= 10 ? Math.floor(el2.rating_scale) : 5;
|
|
826
836
|
const showThumb = el2.show_thumbnail !== false && el2.rating_layout !== "compact";
|
|
@@ -1071,6 +1081,12 @@ function buildProductRatingListElement(el2, ctx, fg) {
|
|
|
1071
1081
|
a.href = ctx.sanitizeUrl(reviewsUrl) || "#";
|
|
1072
1082
|
a.textContent = el2.rating_high_cta || "Share a review";
|
|
1073
1083
|
a.style.cssText = `display:inline-block;margin-top:6px;font-size:12px;font-weight:700;color:${accent};text-decoration:none;`;
|
|
1084
|
+
if (!reviewsViaPage) {
|
|
1085
|
+
a.addEventListener("click", () => {
|
|
1086
|
+
var _a2;
|
|
1087
|
+
void ((_a2 = ctx.submitResponse) == null ? void 0 : _a2.call(ctx, "review_redirect", { cta: "item_rating_review" }));
|
|
1088
|
+
});
|
|
1089
|
+
}
|
|
1074
1090
|
ack.appendChild(a);
|
|
1075
1091
|
}
|
|
1076
1092
|
wrap.appendChild(ack);
|
|
@@ -1247,9 +1263,11 @@ function appendNpsThanks(wrap, el2, ctx, fg, accent, isPromoter) {
|
|
|
1247
1263
|
cta.textContent = el2.nps_promoter_cta || "Leave a review";
|
|
1248
1264
|
cta.style.cssText = `margin:4px auto 0;display:block;padding:9px 18px;border:none;border-radius:999px;background:${accent};color:#fff;font-size:13px;font-weight:800;cursor:pointer;`;
|
|
1249
1265
|
cta.addEventListener("click", () => {
|
|
1266
|
+
var _a;
|
|
1250
1267
|
ctx.trackEvent(ctx.campaign.id, "clicked", {
|
|
1251
1268
|
meta: { element: "nps", cta: "promoter_review" }
|
|
1252
1269
|
});
|
|
1270
|
+
void ((_a = ctx.submitResponse) == null ? void 0 : _a.call(ctx, "review_redirect", { cta: "promoter_review" }));
|
|
1253
1271
|
if (ctx.navigate) ctx.navigate(url, "cta");
|
|
1254
1272
|
else window.location.href = url;
|
|
1255
1273
|
});
|
|
@@ -4937,7 +4955,7 @@ class TriggerEngine {
|
|
|
4937
4955
|
this.exitIntentFired = true;
|
|
4938
4956
|
this.emit("exit_intent", {
|
|
4939
4957
|
client_y: event.clientY,
|
|
4940
|
-
page_url: window.location.href,
|
|
4958
|
+
page_url: redactUrl(window.location.href),
|
|
4941
4959
|
time_on_page: this.pageLoadTime ? (Date.now() - this.pageLoadTime) / 1e3 : 0
|
|
4942
4960
|
});
|
|
4943
4961
|
}
|
|
@@ -4958,7 +4976,7 @@ class TriggerEngine {
|
|
|
4958
4976
|
scroll_velocity: velocity,
|
|
4959
4977
|
scroll_distance: distance,
|
|
4960
4978
|
current_position: currentY,
|
|
4961
|
-
page_url: window.location.href,
|
|
4979
|
+
page_url: redactUrl(window.location.href),
|
|
4962
4980
|
time_on_page: this.pageLoadTime ? (Date.now() - this.pageLoadTime) / 1e3 : 0
|
|
4963
4981
|
});
|
|
4964
4982
|
this.scrollVelocityCooldownTimer = window.setTimeout(() => {
|
|
@@ -4972,12 +4990,12 @@ class TriggerEngine {
|
|
|
4972
4990
|
this.handleVisibilityChange = () => {
|
|
4973
4991
|
if (document.hidden) {
|
|
4974
4992
|
this.emit("visibility_hidden", {
|
|
4975
|
-
page_url: window.location.href,
|
|
4993
|
+
page_url: redactUrl(window.location.href),
|
|
4976
4994
|
time_on_page: this.pageLoadTime ? (Date.now() - this.pageLoadTime) / 1e3 : 0
|
|
4977
4995
|
});
|
|
4978
4996
|
} else {
|
|
4979
4997
|
this.emit("visibility_visible", {
|
|
4980
|
-
page_url: window.location.href
|
|
4998
|
+
page_url: redactUrl(window.location.href)
|
|
4981
4999
|
});
|
|
4982
5000
|
}
|
|
4983
5001
|
};
|
|
@@ -4988,7 +5006,7 @@ class TriggerEngine {
|
|
|
4988
5006
|
this.backButtonFired = true;
|
|
4989
5007
|
window.history.pushState(null, "", window.location.href);
|
|
4990
5008
|
this.emit("back_button", {
|
|
4991
|
-
page_url: window.location.href,
|
|
5009
|
+
page_url: redactUrl(window.location.href),
|
|
4992
5010
|
time_on_page: this.pageLoadTime ? (Date.now() - this.pageLoadTime) / 1e3 : 0
|
|
4993
5011
|
});
|
|
4994
5012
|
};
|
|
@@ -5016,7 +5034,7 @@ class TriggerEngine {
|
|
|
5016
5034
|
const timerId = window.setTimeout(() => {
|
|
5017
5035
|
this.emit(`time_on_page_${seconds}`, {
|
|
5018
5036
|
seconds,
|
|
5019
|
-
page_url: window.location.href
|
|
5037
|
+
page_url: redactUrl(window.location.href)
|
|
5020
5038
|
});
|
|
5021
5039
|
this.timeOnPageTargets.delete(seconds);
|
|
5022
5040
|
}, seconds * 1e3);
|
|
@@ -5936,6 +5954,54 @@ function renderReviewsOverlay(ctx, creds) {
|
|
|
5936
5954
|
document.body.appendChild(overlay);
|
|
5937
5955
|
renderReviewsInline(ctx, body, creds);
|
|
5938
5956
|
}
|
|
5957
|
+
const RETURNING_MARKER_KEY = "aegis_returning_user";
|
|
5958
|
+
const SESSION_VERDICT_KEY = "aegis_new_visitor_session";
|
|
5959
|
+
let cachedVerdict = null;
|
|
5960
|
+
function readSessionVerdict() {
|
|
5961
|
+
try {
|
|
5962
|
+
if (typeof sessionStorage === "undefined") return null;
|
|
5963
|
+
const stored = sessionStorage.getItem(SESSION_VERDICT_KEY);
|
|
5964
|
+
if (stored === "1") return true;
|
|
5965
|
+
if (stored === "0") return false;
|
|
5966
|
+
return null;
|
|
5967
|
+
} catch {
|
|
5968
|
+
return null;
|
|
5969
|
+
}
|
|
5970
|
+
}
|
|
5971
|
+
function writeSessionVerdict(verdict) {
|
|
5972
|
+
try {
|
|
5973
|
+
if (typeof sessionStorage === "undefined") return;
|
|
5974
|
+
sessionStorage.setItem(SESSION_VERDICT_KEY, verdict ? "1" : "0");
|
|
5975
|
+
} catch {
|
|
5976
|
+
}
|
|
5977
|
+
}
|
|
5978
|
+
function readMarkerVerdict() {
|
|
5979
|
+
try {
|
|
5980
|
+
if (typeof localStorage === "undefined") return false;
|
|
5981
|
+
return localStorage.getItem(RETURNING_MARKER_KEY) === null;
|
|
5982
|
+
} catch {
|
|
5983
|
+
return false;
|
|
5984
|
+
}
|
|
5985
|
+
}
|
|
5986
|
+
function isNewVisitor() {
|
|
5987
|
+
if (cachedVerdict !== null) return cachedVerdict;
|
|
5988
|
+
const sessionVerdict = readSessionVerdict();
|
|
5989
|
+
if (sessionVerdict !== null) {
|
|
5990
|
+
cachedVerdict = sessionVerdict;
|
|
5991
|
+
return cachedVerdict;
|
|
5992
|
+
}
|
|
5993
|
+
cachedVerdict = readMarkerVerdict();
|
|
5994
|
+
writeSessionVerdict(cachedVerdict);
|
|
5995
|
+
return cachedVerdict;
|
|
5996
|
+
}
|
|
5997
|
+
function markReturningVisitor() {
|
|
5998
|
+
isNewVisitor();
|
|
5999
|
+
try {
|
|
6000
|
+
if (typeof localStorage === "undefined") return;
|
|
6001
|
+
localStorage.setItem(RETURNING_MARKER_KEY, "1");
|
|
6002
|
+
} catch {
|
|
6003
|
+
}
|
|
6004
|
+
}
|
|
5939
6005
|
function readAnonIdFromStorage$1() {
|
|
5940
6006
|
if (typeof document === "undefined") return void 0;
|
|
5941
6007
|
try {
|
|
@@ -5945,6 +6011,11 @@ function readAnonIdFromStorage$1() {
|
|
|
5945
6011
|
return void 0;
|
|
5946
6012
|
}
|
|
5947
6013
|
}
|
|
6014
|
+
const JOURNEY_ACK_ACTION = {
|
|
6015
|
+
impression: "viewed",
|
|
6016
|
+
clicked: "clicked",
|
|
6017
|
+
dismissed: "dismissed"
|
|
6018
|
+
};
|
|
5948
6019
|
function svgNode(svg) {
|
|
5949
6020
|
try {
|
|
5950
6021
|
const doc = new DOMParser().parseFromString(svg, "image/svg+xml");
|
|
@@ -5956,6 +6027,7 @@ function svgNode(svg) {
|
|
|
5956
6027
|
}
|
|
5957
6028
|
}
|
|
5958
6029
|
const productIdentityCache = /* @__PURE__ */ new WeakMap();
|
|
6030
|
+
const UUID_SHAPE = /^[0-9a-f]{8}-[0-9a-f]{4}-[0-9a-f]{4}-[0-9a-f]{4}-[0-9a-f]{12}$/i;
|
|
5959
6031
|
function productIdentitiesFor(campaign) {
|
|
5960
6032
|
const ic = campaign == null ? void 0 : campaign.interactive_config;
|
|
5961
6033
|
const cards = ic && Array.isArray(ic.cards) ? ic.cards : [];
|
|
@@ -5966,11 +6038,18 @@ function productIdentitiesFor(campaign) {
|
|
|
5966
6038
|
const seen = /* @__PURE__ */ new Set();
|
|
5967
6039
|
for (const card of cards.slice(0, 24)) {
|
|
5968
6040
|
const meta = (card == null ? void 0 : card.metadata) || {};
|
|
5969
|
-
const
|
|
6041
|
+
const rawId = String(meta.product_id || "").trim();
|
|
6042
|
+
const rawSku = String(meta.sku || "").trim();
|
|
6043
|
+
const platformId = String(meta.platform_product_id || "").trim();
|
|
6044
|
+
const productId = UUID_SHAPE.test(rawId) ? rawId : "";
|
|
6045
|
+
const sku = rawSku && !UUID_SHAPE.test(rawSku) ? rawSku : rawId && !productId ? rawId : "";
|
|
6046
|
+
const identity = productId || sku || platformId;
|
|
5970
6047
|
if (!identity || seen.has(identity)) continue;
|
|
5971
6048
|
seen.add(identity);
|
|
5972
6049
|
items.push({
|
|
5973
|
-
product_id:
|
|
6050
|
+
...productId ? { product_id: productId } : {},
|
|
6051
|
+
...sku ? { sku } : {},
|
|
6052
|
+
...!productId && !sku && platformId ? { platform_product_id: platformId } : {},
|
|
5974
6053
|
name: String((card == null ? void 0 : card.title) || identity),
|
|
5975
6054
|
quantity: 1
|
|
5976
6055
|
});
|
|
@@ -5981,7 +6060,7 @@ function productIdentitiesFor(campaign) {
|
|
|
5981
6060
|
}
|
|
5982
6061
|
const _AegisInAppManager = class _AegisInAppManager {
|
|
5983
6062
|
constructor(config) {
|
|
5984
|
-
this.productUrl =
|
|
6063
|
+
this.productUrl = productPath;
|
|
5985
6064
|
this.campaigns = [];
|
|
5986
6065
|
this.displayedCampaigns = /* @__PURE__ */ new Set();
|
|
5987
6066
|
this._displaySizeMul = 1;
|
|
@@ -6007,6 +6086,8 @@ const _AegisInAppManager = class _AegisInAppManager {
|
|
|
6007
6086
|
this.slotUnfilledBeaconed = /* @__PURE__ */ new Set();
|
|
6008
6087
|
this.slotUnfilledSweepTimer = null;
|
|
6009
6088
|
this._pushOptInLoading = false;
|
|
6089
|
+
this.journeyStepByCampaign = /* @__PURE__ */ new Map();
|
|
6090
|
+
this.journeyAcks = /* @__PURE__ */ new Set();
|
|
6010
6091
|
this.writeKey = config.writeKey;
|
|
6011
6092
|
this.apiHost = config.apiHost || "https://api.aegis.ai";
|
|
6012
6093
|
this.userId = config.userId ?? readAnonIdFromStorage$1();
|
|
@@ -6112,13 +6193,13 @@ const _AegisInAppManager = class _AegisInAppManager {
|
|
|
6112
6193
|
this.log("AegisInApp already initialized");
|
|
6113
6194
|
return;
|
|
6114
6195
|
}
|
|
6115
|
-
|
|
6116
|
-
|
|
6117
|
-
|
|
6196
|
+
markReturningVisitor();
|
|
6197
|
+
try {
|
|
6198
|
+
if (typeof localStorage !== "undefined") {
|
|
6118
6199
|
const pv = parseInt(localStorage.getItem("aegis_pv_count") || "0", 10);
|
|
6119
6200
|
localStorage.setItem("aegis_pv_count", String(pv + 1));
|
|
6120
|
-
} catch {
|
|
6121
6201
|
}
|
|
6202
|
+
} catch {
|
|
6122
6203
|
}
|
|
6123
6204
|
ensureInAppFont();
|
|
6124
6205
|
await this.refreshCampaigns();
|
|
@@ -6495,9 +6576,11 @@ const _AegisInAppManager = class _AegisInAppManager {
|
|
|
6495
6576
|
try {
|
|
6496
6577
|
const context = new URLSearchParams({
|
|
6497
6578
|
device_type: this.detectDeviceType(),
|
|
6498
|
-
|
|
6579
|
+
// Credential params keep their key and lose their value, so a
|
|
6580
|
+
// `*placed=1*` / `*?step=cart*` rule still matches.
|
|
6581
|
+
page_url: typeof window !== "undefined" ? redactUrl(window.location.pathname + window.location.search) : "/"
|
|
6499
6582
|
});
|
|
6500
|
-
context.set("is_new_user",
|
|
6583
|
+
context.set("is_new_user", isNewVisitor() ? "true" : "false");
|
|
6501
6584
|
if (this.currentSurface) {
|
|
6502
6585
|
context.set("current_surface", this.currentSurface);
|
|
6503
6586
|
}
|
|
@@ -6579,28 +6662,29 @@ const _AegisInAppManager = class _AegisInAppManager {
|
|
|
6579
6662
|
if (/iPad|Tablet/i.test(ua)) return "tablet";
|
|
6580
6663
|
return "desktop";
|
|
6581
6664
|
}
|
|
6582
|
-
isNewUser() {
|
|
6583
|
-
if (typeof localStorage === "undefined") return true;
|
|
6584
|
-
return !localStorage.getItem("aegis_returning_user");
|
|
6585
|
-
}
|
|
6586
6665
|
// --- A/B Assignment Persistence (Critical Fix C) ---
|
|
6666
|
+
// Both A/B helpers sit on the campaign-fetch path, so blocked storage
|
|
6667
|
+
// (where even `typeof localStorage` throws) must not abort the fetch.
|
|
6587
6668
|
getABAssignments() {
|
|
6588
|
-
if (typeof localStorage === "undefined") return {};
|
|
6589
6669
|
try {
|
|
6670
|
+
if (typeof localStorage === "undefined") return {};
|
|
6590
6671
|
return JSON.parse(localStorage.getItem("aegis_ab_assignments") || "{}");
|
|
6591
6672
|
} catch {
|
|
6592
6673
|
return {};
|
|
6593
6674
|
}
|
|
6594
6675
|
}
|
|
6595
6676
|
processABAssignments(campaigns) {
|
|
6596
|
-
if (typeof localStorage === "undefined") return;
|
|
6597
6677
|
const stored = this.getABAssignments();
|
|
6598
6678
|
for (const campaign of campaigns) {
|
|
6599
6679
|
if (campaign.assigned_variant_id) {
|
|
6600
6680
|
stored[campaign.id] = campaign.assigned_variant_id;
|
|
6601
6681
|
}
|
|
6602
6682
|
}
|
|
6603
|
-
|
|
6683
|
+
try {
|
|
6684
|
+
if (typeof localStorage === "undefined") return;
|
|
6685
|
+
localStorage.setItem("aegis_ab_assignments", JSON.stringify(stored));
|
|
6686
|
+
} catch {
|
|
6687
|
+
}
|
|
6604
6688
|
}
|
|
6605
6689
|
getVariantId(campaignId) {
|
|
6606
6690
|
const assignments = this.getABAssignments();
|
|
@@ -11864,6 +11948,67 @@ const _AegisInAppManager = class _AegisInAppManager {
|
|
|
11864
11948
|
} catch (error) {
|
|
11865
11949
|
this.log(`Error tracking event: ${error}`, "error");
|
|
11866
11950
|
}
|
|
11951
|
+
const step = (trackedCampaign == null ? void 0 : trackedCampaign.journey_step_execution_id) || this.journeyStepByCampaign.get(campaignId);
|
|
11952
|
+
const ackAction = JOURNEY_ACK_ACTION[eventType];
|
|
11953
|
+
if (step) {
|
|
11954
|
+
this.journeyStepByCampaign.set(campaignId, step);
|
|
11955
|
+
if (ackAction) void this.ackJourneyQueueItem(step, ackAction);
|
|
11956
|
+
}
|
|
11957
|
+
}
|
|
11958
|
+
/**
|
|
11959
|
+
* POST /v1/in-app/widgets/{step}/ack — the canonical writer of a queue row's
|
|
11960
|
+
* seen-state (the same endpoint the Android and iOS SDKs call). Fail-soft by
|
|
11961
|
+
* construction: it runs after the render, is never awaited by it, and never
|
|
11962
|
+
* throws. A network error or 5xx is retried once; if that also fails the key
|
|
11963
|
+
* is released, so the next render of the (still re-served) message tries
|
|
11964
|
+
* again. A 4xx is the server's answer and is not retried. The server side is
|
|
11965
|
+
* idempotent — a repeated action is answered `late_arrival` and writes
|
|
11966
|
+
* nothing — so a duplicate ack is harmless.
|
|
11967
|
+
*/
|
|
11968
|
+
async ackJourneyQueueItem(step, action, attempt = 0) {
|
|
11969
|
+
const key = `${step}:${action}`;
|
|
11970
|
+
if (attempt === 0) {
|
|
11971
|
+
if (this.journeyAcks.has(key)) return;
|
|
11972
|
+
this.journeyAcks.add(key);
|
|
11973
|
+
}
|
|
11974
|
+
const headers = {
|
|
11975
|
+
"Content-Type": "application/json",
|
|
11976
|
+
"X-Aegis-Write-Key": this.writeKey
|
|
11977
|
+
};
|
|
11978
|
+
if (this.organizationId) headers["X-Organization-ID"] = this.organizationId;
|
|
11979
|
+
if (this.userId) headers["X-User-ID"] = this.userId;
|
|
11980
|
+
if (this.contactId) headers["X-Contact-ID"] = this.contactId;
|
|
11981
|
+
let retryable = true;
|
|
11982
|
+
try {
|
|
11983
|
+
const response = await fetch(
|
|
11984
|
+
`${this.apiHost}/v1/in-app/widgets/${encodeURIComponent(step)}/ack`,
|
|
11985
|
+
{
|
|
11986
|
+
method: "POST",
|
|
11987
|
+
headers,
|
|
11988
|
+
body: JSON.stringify({ action }),
|
|
11989
|
+
credentials: "include",
|
|
11990
|
+
// A click usually navigates away at once; keepalive lets the ack
|
|
11991
|
+
// outlive the page instead of being cancelled with it.
|
|
11992
|
+
keepalive: true
|
|
11993
|
+
}
|
|
11994
|
+
);
|
|
11995
|
+
if (response.ok) {
|
|
11996
|
+
this.log(`Acknowledged queued message ${step}: ${action}`);
|
|
11997
|
+
return;
|
|
11998
|
+
}
|
|
11999
|
+
retryable = response.status >= 500 || response.status === 408 || response.status === 429;
|
|
12000
|
+
this.log(`Queue ack ${action} for ${step} failed: HTTP ${response.status}`, "warn");
|
|
12001
|
+
} catch (error) {
|
|
12002
|
+
this.log(`Queue ack ${action} for ${step} failed: ${error}`, "warn");
|
|
12003
|
+
}
|
|
12004
|
+
if (!retryable) return;
|
|
12005
|
+
if (attempt === 0) {
|
|
12006
|
+
setTimeout(() => {
|
|
12007
|
+
void this.ackJourneyQueueItem(step, action, 1);
|
|
12008
|
+
}, _AegisInAppManager.JOURNEY_ACK_RETRY_MS);
|
|
12009
|
+
return;
|
|
12010
|
+
}
|
|
12011
|
+
this.journeyAcks.delete(key);
|
|
11867
12012
|
}
|
|
11868
12013
|
log(message, level = "log") {
|
|
11869
12014
|
if (this.debugMode) {
|
|
@@ -11914,6 +12059,7 @@ _AegisInAppManager.KNOWN_SURFACES = /* @__PURE__ */ new Set([
|
|
|
11914
12059
|
"external_mobile_screen"
|
|
11915
12060
|
]);
|
|
11916
12061
|
_AegisInAppManager.SERVED_DEDUP_PREFIX = "aegis_served_fired:";
|
|
12062
|
+
_AegisInAppManager.JOURNEY_ACK_RETRY_MS = 2e3;
|
|
11917
12063
|
let AegisInAppManager = _AegisInAppManager;
|
|
11918
12064
|
function renderPreview(config, opts) {
|
|
11919
12065
|
document.querySelectorAll(
|
|
@@ -12632,9 +12778,10 @@ class PrefetchBundleClient {
|
|
|
12632
12778
|
const ctx = this.contextProvider();
|
|
12633
12779
|
const qs = new URLSearchParams();
|
|
12634
12780
|
if (ctx.device_type) qs.set("device_type", ctx.device_type);
|
|
12635
|
-
if (ctx.page_url) qs.set("page_url", ctx.page_url);
|
|
12781
|
+
if (ctx.page_url) qs.set("page_url", redactUrl(ctx.page_url));
|
|
12636
12782
|
if (ctx.geo) qs.set("geo", ctx.geo);
|
|
12637
|
-
|
|
12783
|
+
const isNewUser = ctx.is_new_user ?? isNewVisitor();
|
|
12784
|
+
qs.set("is_new_user", isNewUser ? "true" : "false");
|
|
12638
12785
|
const url = `${this.apiHost}/v1/sdk/prefetch-bundle?${qs.toString()}`;
|
|
12639
12786
|
const headers = {
|
|
12640
12787
|
"X-Aegis-Write-Key": this.writeKey,
|
|
@@ -13516,8 +13663,8 @@ class AegisWidgetManager {
|
|
|
13516
13663
|
cart_items: this.cartData.cart_items,
|
|
13517
13664
|
user_email: this.userId,
|
|
13518
13665
|
abandoned_at: (/* @__PURE__ */ new Date()).toISOString(),
|
|
13519
|
-
page_url: window.location.href,
|
|
13520
|
-
referrer: document.referrer
|
|
13666
|
+
page_url: redactUrl(window.location.href),
|
|
13667
|
+
referrer: redactUrl(document.referrer)
|
|
13521
13668
|
};
|
|
13522
13669
|
const beaconUrl = `${this.apiHost}/v1/widgets/beacon/cart-abandoned`;
|
|
13523
13670
|
if (navigator.sendBeacon) {
|
|
@@ -14021,7 +14168,9 @@ class AegisWidgetManager {
|
|
|
14021
14168
|
cart_total: ((_c = data.cart) == null ? void 0 : _c.cart_total) || 0,
|
|
14022
14169
|
cart_currency: ((_d = data.cart) == null ? void 0 : _d.cart_currency) || "USD",
|
|
14023
14170
|
cart_items: ((_e = data.cart) == null ? void 0 : _e.cart_items) || [],
|
|
14024
|
-
|
|
14171
|
+
// Redacted: a stored cart URL is re-sent later as a recovery link, and a
|
|
14172
|
+
// credential in it (`?t=` / `?k=`) must not outlive this page view.
|
|
14173
|
+
cart_url: redactUrl(window.location.href),
|
|
14025
14174
|
platform: "web",
|
|
14026
14175
|
geo_region: geoRegion,
|
|
14027
14176
|
device_type: deviceType,
|
|
@@ -15137,7 +15286,7 @@ const _AegisMessageRuntime = class _AegisMessageRuntime {
|
|
|
15137
15286
|
var _a;
|
|
15138
15287
|
this.initialized = false;
|
|
15139
15288
|
{
|
|
15140
|
-
const v = "1.
|
|
15289
|
+
const v = "1.38.0";
|
|
15141
15290
|
try {
|
|
15142
15291
|
globalThis.__AEGIS_SDK_VERSION__ = v;
|
|
15143
15292
|
} catch {
|