@useinsider/guido 3.9.0-beta.7791f66 → 3.9.0-beta.ba394b1

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.
Files changed (90) hide show
  1. package/dist/@types/config/schemas.js +70 -66
  2. package/dist/components/organisms/email-preview/desktop-preview/DesktopPreview.vue.js +8 -8
  3. package/dist/components/organisms/email-preview/desktop-preview/DesktopPreview.vue2.js +15 -12
  4. package/dist/components/organisms/email-preview/mobile-preview/ContentView.vue.js +5 -5
  5. package/dist/components/organisms/email-preview/mobile-preview/ContentView.vue2.js +16 -15
  6. package/dist/components/organisms/unsubscribe/UnsubscribePageSelection.vue.js +5 -5
  7. package/dist/components/organisms/unsubscribe/UnsubscribePageSelection.vue2.js +42 -37
  8. package/dist/components/organisms/unsubscribe/UnsubscribeTypeSelection.vue.js +3 -3
  9. package/dist/components/organisms/unsubscribe/UnsubscribeTypeSelection.vue2.js +40 -37
  10. package/dist/composables/useCustomInterfaceAppearance.js +16 -18
  11. package/dist/composables/useHtmlCompiler.js +13 -10
  12. package/dist/composables/usePreviewInteractionGuard.js +17 -0
  13. package/dist/composables/usePreviewMode.js +15 -14
  14. package/dist/composables/useRecommendationPreview.js +111 -0
  15. package/dist/composables/useSave.js +14 -14
  16. package/dist/composables/useStripo.js +39 -37
  17. package/dist/composables/useStripoNotifications.js +26 -0
  18. package/dist/composables/validators/useUnsubscribeBlockValidator.js +26 -17
  19. package/dist/config/compiler/htmlCompilerRules.js +38 -10
  20. package/dist/config/compiler/recommendationCompilerRules.js +84 -109
  21. package/dist/config/compiler/utils/recommendationCompilerUtils.js +88 -80
  22. package/dist/config/migrator/recommendation/htmlBuilder.js +53 -52
  23. package/dist/config/migrator/recommendation/settingsMapper.js +38 -33
  24. package/dist/enums/html-validator.js +6 -5
  25. package/dist/enums/toaster.js +2 -2
  26. package/dist/extensions/Blocks/Items/block.js +48 -29
  27. package/dist/extensions/Blocks/Items/utils/nodeConfigUtils.js +62 -45
  28. package/dist/extensions/Blocks/Recommendation/block.js +64 -42
  29. package/dist/extensions/Blocks/Recommendation/canvasPreview.css.js +16 -0
  30. package/dist/extensions/Blocks/Recommendation/constants/defaultConfig.js +41 -32
  31. package/dist/extensions/Blocks/Recommendation/controls/cardComposition/index.js +461 -363
  32. package/dist/extensions/Blocks/Recommendation/controls/main/index.js +99 -87
  33. package/dist/extensions/Blocks/Recommendation/controls/main/pricePlacement.js +133 -0
  34. package/dist/extensions/Blocks/Recommendation/controls/main/utils.js +160 -158
  35. package/dist/extensions/Blocks/Recommendation/extension.js +30 -29
  36. package/dist/extensions/Blocks/Recommendation/iconsRegistry.js +21 -7
  37. package/dist/extensions/Blocks/Recommendation/recommendation.css.js +64 -4
  38. package/dist/extensions/Blocks/Recommendation/store/recommendation.js +3 -1
  39. package/dist/extensions/Blocks/Recommendation/templates/grid/elementRenderer.js +130 -96
  40. package/dist/extensions/Blocks/Recommendation/templates/grid/template.js +43 -54
  41. package/dist/extensions/Blocks/Recommendation/templates/index.js +17 -14
  42. package/dist/extensions/Blocks/Recommendation/templates/list/elementRenderer.js +86 -80
  43. package/dist/extensions/Blocks/Recommendation/templates/list/template.js +31 -40
  44. package/dist/extensions/Blocks/Recommendation/templates/utils.js +155 -102
  45. package/dist/extensions/Blocks/Recommendation/useRecommendationBlockWarning.js +7 -7
  46. package/dist/extensions/Blocks/Unsubscribe/block.js +40 -37
  47. package/dist/extensions/Blocks/Unsubscribe/control.js +19 -16
  48. package/dist/extensions/Blocks/controlFactories.js +76 -57
  49. package/dist/guido.css +1 -1
  50. package/dist/services/templateLibraryApi.js +9 -8
  51. package/dist/src/@types/config/schemas.d.ts +16 -0
  52. package/dist/src/composables/useConfig.d.ts +4 -0
  53. package/dist/src/composables/usePreviewInteractionGuard.d.ts +3 -0
  54. package/dist/src/composables/useRecommendationPreview.d.ts +10 -0
  55. package/dist/src/composables/useStripoNotifications.d.ts +10 -0
  56. package/dist/src/composables/validators/useUnsubscribeBlockValidator.d.ts +1 -0
  57. package/dist/src/config/migrator/recommendation/settingsMapper.d.ts +1 -1
  58. package/dist/src/enums/toaster.d.ts +2 -2
  59. package/dist/src/extensions/Blocks/CouponBlock/controls/index.d.ts +1 -1
  60. package/dist/src/extensions/Blocks/Items/block.d.ts +8 -0
  61. package/dist/src/extensions/Blocks/Items/controls/index.d.ts +3 -3
  62. package/dist/src/extensions/Blocks/Items/utils/nodeConfigUtils.d.ts +1 -1
  63. package/dist/src/extensions/Blocks/Recommendation/block.d.ts +10 -0
  64. package/dist/src/extensions/Blocks/Recommendation/controls/cardComposition/index.d.ts +29 -3
  65. package/dist/src/extensions/Blocks/Recommendation/controls/index.d.ts +1 -1
  66. package/dist/src/extensions/Blocks/Recommendation/controls/main/index.d.ts +3 -1
  67. package/dist/src/extensions/Blocks/Recommendation/controls/main/pricePlacement.d.ts +59 -0
  68. package/dist/src/extensions/Blocks/Recommendation/controls/name/index.d.ts +1 -1
  69. package/dist/src/extensions/Blocks/Recommendation/controls/oldPrice/index.d.ts +1 -1
  70. package/dist/src/extensions/Blocks/Recommendation/controls/omnibusDiscount/index.d.ts +1 -1
  71. package/dist/src/extensions/Blocks/Recommendation/controls/omnibusPrice/index.d.ts +1 -1
  72. package/dist/src/extensions/Blocks/Recommendation/controls/price/index.d.ts +1 -1
  73. package/dist/src/extensions/Blocks/Recommendation/store/recommendation.d.ts +2 -0
  74. package/dist/src/extensions/Blocks/Recommendation/templates/grid/elementRenderer.d.ts +13 -1
  75. package/dist/src/extensions/Blocks/Recommendation/templates/grid/template.d.ts +4 -4
  76. package/dist/src/extensions/Blocks/Recommendation/templates/index.d.ts +1 -1
  77. package/dist/src/extensions/Blocks/Recommendation/templates/list/elementRenderer.d.ts +10 -1
  78. package/dist/src/extensions/Blocks/Recommendation/templates/list/template.d.ts +3 -3
  79. package/dist/src/extensions/Blocks/Recommendation/templates/utils.d.ts +51 -1
  80. package/dist/src/extensions/Blocks/Recommendation/types/nodeConfig.d.ts +15 -0
  81. package/dist/src/extensions/Blocks/controlFactories.d.ts +10 -1
  82. package/dist/src/stores/config.d.ts +36 -0
  83. package/dist/src/stores/toaster.d.ts +2 -3
  84. package/dist/src/stores/unsubscribe.d.ts +11 -1
  85. package/dist/src/utils/ampErrorFilter.d.ts +1 -0
  86. package/dist/stores/toaster.js +10 -10
  87. package/dist/stores/unsubscribe.js +8 -7
  88. package/dist/utils/ampErrorFilter.js +6 -5
  89. package/package.json +2 -2
  90. package/dist/static/styles/components/notification.css.js +0 -74
@@ -1,16 +1,16 @@
1
- import { defineComponent as v, ref as b, computed as f, watch as _ } from "vue";
1
+ import { defineComponent as _, ref as b, computed as f, watch as v } from "vue";
2
2
  import U from "../../wrappers/WpDrawer.vue.js";
3
- import { useToaster as N } from "../../../composables/useToaster.js";
4
- import { useTranslations as w } from "../../../composables/useTranslations.js";
3
+ import { useToaster as w } from "../../../composables/useToaster.js";
4
+ import { useTranslations as N } from "../../../composables/useTranslations.js";
5
5
  import { ACADEMY_LINKS as D } from "../../../enums/academy.js";
6
- import { ToasterTypeOptions as P } from "../../../enums/toaster.js";
7
- import { PAGE_TYPES as l, getTypeTranslations as R, UNSUBSCRIBE_PAGES_LINK as G } from "../../../enums/unsubscribe.js";
8
- import { useUnsubscribeStore as I } from "../../../stores/unsubscribe.js";
6
+ import { ToasterTypeOptions as I } from "../../../enums/toaster.js";
7
+ import { PAGE_TYPES as l, getTypeTranslations as R, UNSUBSCRIBE_PAGES_LINK as P } from "../../../enums/unsubscribe.js";
8
+ import { useUnsubscribeStore as G } from "../../../stores/unsubscribe.js";
9
9
  import { InSegments as L } from "@useinsider/design-system-vue";
10
- const W = /* @__PURE__ */ v({
10
+ const W = /* @__PURE__ */ _({
11
11
  __name: "UnsubscribeTypeSelection",
12
- setup(O) {
13
- const t = w(), { showToaster: d } = N(), e = I(), n = b(!1), i = b(!0), o = b(l.GLOBAL_UNSUBSCRIBE), T = t(
12
+ setup(k) {
13
+ const t = N(), { showToaster: d } = w(), e = G(), n = b(!1), o = b(!0), r = b(l.GLOBAL_UNSUBSCRIBE), T = t(
14
14
  "unsubscription-preference.select-unsubscribe-page-description",
15
15
  { action: `<a href="${D.GLOBAL_UNSUBSCRIBE}" target="_blank">${t("ds-rules.visit-academy")}</a>` }
16
16
  ), y = f(() => [
@@ -31,7 +31,7 @@ const W = /* @__PURE__ */ v({
31
31
  disable: e.isSubscriptionPreferencesCenterDisabled,
32
32
  tooltipText: e.isSubscriptionPreferencesCenterDisabled ? t("unsubscription-preference.pref-center-added") : ""
33
33
  }
34
- ]), S = f(
34
+ ]), g = f(
35
35
  () => e.isGlobalUnsubscribeDisabled && e.isSubscriptionPreferencesCenterDisabled
36
36
  ), C = f(() => ({
37
37
  primaryButton: {
@@ -41,8 +41,8 @@ const W = /* @__PURE__ */ v({
41
41
  n.value ? "unsubscription-preference.selecting-type" : "products.select-and-continue"
42
42
  ),
43
43
  loadingStatus: n.value,
44
- disabledStatus: S.value,
45
- skeletonStatus: i.value,
44
+ disabledStatus: g.value,
45
+ skeletonStatus: o.value,
46
46
  skeletonSizing: { width: 168, height: 40 }
47
47
  },
48
48
  cancelOrBackButton: {
@@ -50,59 +50,62 @@ const W = /* @__PURE__ */ v({
50
50
  type: "secondary",
51
51
  labelText: t("products.cancel"),
52
52
  disabledStatus: n.value,
53
- skeletonStatus: i.value,
53
+ skeletonStatus: o.value,
54
54
  skeletonSizing: { width: 78, height: 40 }
55
55
  }
56
- })), m = (s) => {
57
- e.typeSelectionDrawerStatus = !1, document.dispatchEvent(new CustomEvent("unsubscribe:cancel")), s && setTimeout(() => {
56
+ })), S = (s) => {
57
+ e.typeSelectionDrawerStatus = !1, document.dispatchEvent(new CustomEvent("unsubscribe:cancel", {
58
+ detail: { blockId: e.pendingBlockId }
59
+ })), s && setTimeout(() => {
58
60
  s();
59
61
  }, 500);
60
62
  }, E = (s) => {
61
- o.value = s;
62
- }, g = () => {
63
- const s = e.hasTemplatesByCollectionType, r = [];
64
- if (Object.entries(s).forEach(([c, p]) => {
65
- p || r.push(Number(c));
66
- }), r.length === 0)
63
+ r.value = s;
64
+ }, m = () => {
65
+ const s = e.hasTemplatesByCollectionType, a = [];
66
+ if (Object.entries(s).forEach(([i, p]) => {
67
+ p || a.push(Number(i));
68
+ }), a.length === 0)
67
69
  return !0;
68
- const B = R(), a = r.map((c) => B[c]);
70
+ const h = R(), c = a.map((i) => h[i]);
69
71
  let u = "";
70
- if (r.length === 1)
72
+ if (a.length === 1)
71
73
  u = t("unsubscription-preference.create-page-to-continue", {
72
- page: a[0]
74
+ page: c[0]
73
75
  });
74
- else if (r.length === 2)
76
+ else if (a.length === 2)
75
77
  u = t("unsubscription-preference.create-pages-to-continue", {
76
- page1: a[0],
77
- page2: a[1]
78
+ page1: c[0],
79
+ page2: c[1]
78
80
  });
79
81
  else {
80
- const c = a.pop() ?? "", p = a.join(", ");
82
+ const i = c.pop() ?? "", p = c.join(", ");
81
83
  u = t("unsubscription-preference.create-multiple-pages-to-continue", {
82
84
  pages: p,
83
- lastPage: c
85
+ lastPage: i
84
86
  });
85
87
  }
86
88
  return d({
87
- type: P.Warning,
89
+ type: I.Warning,
88
90
  message: u,
89
91
  actionButton: {
90
92
  text: "Go to Unsubscribe Pages",
91
93
  onClick: () => {
92
- window.location.href = G;
94
+ const i = new URL(P, window.location.origin).href;
95
+ window.open(i, "_blank", "noopener");
93
96
  }
94
97
  }
95
98
  }), !1;
96
- }, h = async () => {
97
- if (n.value = !0, await e.fetchTemplates(), e.setCollection(o.value), !g()) {
98
- n.value = !1, m();
99
+ }, B = async () => {
100
+ if (n.value = !0, await e.fetchTemplates(!0), e.setCollection(r.value), !m()) {
101
+ n.value = !1, S();
99
102
  return;
100
103
  }
101
104
  n.value = !1, e.typeSelectionDrawerStatus = !1, e.pageSelectionDrawerStatus = !0;
102
105
  };
103
- return _(() => e.typeSelectionDrawerStatus, (s) => {
104
- s && (i.value = !0, o.value = l.GLOBAL_UNSUBSCRIBE, e.isGlobalUnsubscribeDisabled && (o.value = e.isSubscriptionPreferencesCenterDisabled ? 0 : l.SUBSCRIPTION_PREFERENCE_CENTER), i.value = !1);
105
- }), { __sfc: !0, trans: t, showToaster: d, unsubscribeStore: e, isSelecting: n, skeletonStatus: i, selectedCollection: o, descriptionText: T, segmentList: y, hasNoSelectableType: S, footerButtonGroupOptions: C, closeModal: m, changeCollection: E, validateTemplates: g, selectCollection: h, WpDrawer: U, InSegments: L };
106
+ return v(() => e.typeSelectionDrawerStatus, (s) => {
107
+ s && (o.value = !0, r.value = l.GLOBAL_UNSUBSCRIBE, e.isGlobalUnsubscribeDisabled && (r.value = e.isSubscriptionPreferencesCenterDisabled ? 0 : l.SUBSCRIPTION_PREFERENCE_CENTER), o.value = !1);
108
+ }), { __sfc: !0, trans: t, showToaster: d, unsubscribeStore: e, isSelecting: n, skeletonStatus: o, selectedCollection: r, descriptionText: T, segmentList: y, hasNoSelectableType: g, footerButtonGroupOptions: C, closeModal: S, changeCollection: E, validateTemplates: m, selectCollection: B, WpDrawer: U, InSegments: L };
106
109
  }
107
110
  });
108
111
  export {
@@ -4,21 +4,20 @@ import e from "../static/styles/components/amp-block.css.js";
4
4
  import i from "../static/styles/components/base-input.css.js";
5
5
  import p from "../static/styles/components/button-group.css.js";
6
6
  import n from "../static/styles/components/button.css.js";
7
- import C from "../static/styles/components/combobox.css.js";
8
- import s from "../static/styles/components/counter.css.js";
7
+ import s from "../static/styles/components/combobox.css.js";
8
+ import C from "../static/styles/components/counter.css.js";
9
9
  import f from "../static/styles/components/dropdown-menu.css.js";
10
10
  import a from "../static/styles/components/loader.css.js";
11
11
  import u from "../static/styles/components/narrow-panel.css.js";
12
- import c from "../static/styles/components/notification.css.js";
13
- import d from "../static/styles/components/popup.css.js";
14
- import l from "../static/styles/components/switcher.css.js";
15
- import h from "../static/styles/components/tabs.css.js";
16
- import w from "../static/styles/components/tools.css.js";
17
- import y from "../static/styles/components/version-history.css.js";
18
- import B from "../static/styles/components/wide-panel.css.js";
19
- import b from "../static/styles/variables.css.js";
20
- const A = [
21
- b,
12
+ import c from "../static/styles/components/popup.css.js";
13
+ import d from "../static/styles/components/switcher.css.js";
14
+ import l from "../static/styles/components/tabs.css.js";
15
+ import h from "../static/styles/components/tools.css.js";
16
+ import w from "../static/styles/components/version-history.css.js";
17
+ import y from "../static/styles/components/wide-panel.css.js";
18
+ import B from "../static/styles/variables.css.js";
19
+ const b = [
20
+ B,
22
21
  // Must be on top
23
22
  S,
24
23
  // Must be on top
@@ -27,8 +26,8 @@ const A = [
27
26
  i,
28
27
  p,
29
28
  n,
30
- C,
31
29
  s,
30
+ C,
32
31
  f,
33
32
  a,
34
33
  u,
@@ -37,13 +36,12 @@ const A = [
37
36
  l,
38
37
  h,
39
38
  w,
40
- y,
41
- B
39
+ y
42
40
  ].join(`
43
41
 
44
- `), F = () => ({ importCss: () => {
42
+ `), v = () => ({ importCss: () => {
45
43
  const o = new CSSStyleSheet();
46
- o.replaceSync(A);
44
+ o.replaceSync(b);
47
45
  const r = document.querySelector("ui-editor");
48
46
  if (!r)
49
47
  return;
@@ -51,5 +49,5 @@ const A = [
51
49
  t && (t.adoptedStyleSheets = [o]);
52
50
  } });
53
51
  export {
54
- F as useCustomInterfaceAppearance
52
+ v as useCustomInterfaceAppearance
55
53
  };
@@ -26,24 +26,27 @@ const y = /* @__PURE__ */ new Set([
26
26
  "format-comment-braces",
27
27
  "add-universal-link-flags",
28
28
  // Coupon placeholder replacement (only present when liquidSyntax is enabled).
29
- "liquid-coupon-code"
29
+ "liquid-coupon-code",
30
+ // Editor-only attribute strip — AMP4EMAIL has no `contenteditable`, so leaving
31
+ // it in narrows/breaks rendering. Pure attribute removal, emits nothing.
32
+ "remove-contenteditable"
30
33
  ]), M = () => {
31
- var t, m, r;
32
- const { compiler: e, isFeatureEnabled: a, partner: n } = k(), p = ((t = e.value) == null ? void 0 : t.customRules) || [], l = [
33
- ...!!((m = e.value) != null && m.ignoreDefaultRules) ? [] : R,
34
+ var i, m, r;
35
+ const { compiler: o, isFeatureEnabled: n, partner: a } = k(), p = ((i = o.value) == null ? void 0 : i.customRules) || [], l = [
36
+ ...!!((m = o.value) != null && m.ignoreDefaultRules) ? [] : R,
34
37
  ...v,
35
38
  ...x,
36
39
  ...g,
37
40
  ...b,
38
41
  ...H,
39
- ...a("liquidSyntax") ? C : [],
40
- ...p.map((o, f) => ({
41
- ...o,
42
- priority: o.priority + 1e3 + f
42
+ ...n("liquidSyntax") ? C : [],
43
+ ...p.map((e, f) => ({
44
+ ...e,
45
+ priority: e.priority + 1e3 + f
43
46
  // Ensure additional rules run after default rules
44
47
  }))
45
- ], u = s(l), c = l.filter((o) => y.has(o.id)), d = s(c), i = (r = n.value) == null ? void 0 : r.fallbackFont;
46
- return { compileHtml: (o) => u.compile(o, void 0, i), compileAmpHtml: (o) => d.compile(o, void 0, i) };
48
+ ], u = s(l), c = l.filter((e) => y.has(e.id)), d = s(c), t = (r = a.value) == null ? void 0 : r.fallbackFont;
49
+ return { compileHtml: (e) => u.compile(e, void 0, t), compileAmpHtml: (e) => d.compile(e, void 0, t) };
47
50
  };
48
51
  export {
49
52
  M as useHtmlCompiler
@@ -0,0 +1,17 @@
1
+ const o = ["click", "auxclick", "submit"], c = (t) => {
2
+ t.preventDefault(), t.stopPropagation();
3
+ }, a = () => ({ blockPreviewInteractions: (r) => {
4
+ try {
5
+ const e = r.contentDocument;
6
+ if (!e)
7
+ return;
8
+ o.forEach((n) => {
9
+ e.addEventListener(n, c, !0);
10
+ });
11
+ } catch (e) {
12
+ console.warn("[usePreviewInteractionGuard] Could not guard preview iframe:", e);
13
+ }
14
+ } });
15
+ export {
16
+ a as usePreviewInteractionGuard
17
+ };
@@ -1,28 +1,29 @@
1
- import { useEditorStore as d } from "../stores/editor.js";
2
- import { usePreviewStore as n } from "../stores/preview.js";
3
- import { useActionsApi as p } from "./useActionsApi.js";
4
- import { useCodeEditorApi as c } from "./useCodeEditorApi.js";
5
- import { useHtmlCompiler as u } from "./useHtmlCompiler.js";
6
- const g = () => {
7
- const t = d(), e = n(), { closeCodeEditor: i } = c(), { getPreviewData: a, getCompiledEmail: s } = p(), { compileHtml: m } = u(), r = () => {
1
+ import { useEditorStore as n } from "../stores/editor.js";
2
+ import { usePreviewStore as p } from "../stores/preview.js";
3
+ import { useActionsApi as c } from "./useActionsApi.js";
4
+ import { useCodeEditorApi as u } from "./useCodeEditorApi.js";
5
+ import { useHtmlCompiler as v } from "./useHtmlCompiler.js";
6
+ import { useRecommendationPreview as w } from "./useRecommendationPreview.js";
7
+ const C = () => {
8
+ const t = n(), e = p(), { closeCodeEditor: a } = u(), { getPreviewData: m, getCompiledEmail: s } = c(), { compileHtml: l } = v(), { substituteRecommendationPreview: r } = w(), i = () => {
8
9
  t.isPreviewModeOpen = !1, e.$reset();
9
10
  };
10
11
  return {
11
- closePreviewMode: r,
12
+ closePreviewMode: i,
12
13
  openPreviewMode: () => {
13
- t.isCodeEditorOpen && i(), t.isPreviewModeOpen = !0;
14
+ t.isCodeEditorOpen && a(), t.isPreviewModeOpen = !0;
14
15
  },
15
16
  loadPreviewData: async () => {
16
17
  if (!(t.loadingStatus || e.isLoaded)) {
17
18
  t.loadingStatus = !0;
18
19
  try {
19
- const [o, l] = await Promise.all([
20
- a(),
20
+ const [o, d] = await Promise.all([
21
+ m(),
21
22
  s({ minimize: !0, resetDataSavedFlag: !1 })
22
23
  ]);
23
- e.templateHtml = o.html || "", e.ampHtml = o.ampHtml || "", e.ampErrors = o.ampErrors || [], e.setEmailFormat(o.ampHtml ? "AMP" : "html"), e.emailSizeKB = m(l.html).estimatedSizeKB, e.isLoaded = !0;
24
+ e.templateHtml = r(o.html || ""), e.ampHtml = r(o.ampHtml || ""), e.ampErrors = o.ampErrors || [], e.setEmailFormat(o.ampHtml ? "AMP" : "html"), e.emailSizeKB = l(d.html).estimatedSizeKB, e.isLoaded = !0;
24
25
  } catch (o) {
25
- console.error("Failed to load preview data:", o), r();
26
+ console.error("Failed to load preview data:", o), i();
26
27
  } finally {
27
28
  t.loadingStatus = !1;
28
29
  }
@@ -31,5 +32,5 @@ const g = () => {
31
32
  };
32
33
  };
33
34
  export {
34
- g as usePreviewMode
35
+ C as usePreviewMode
35
36
  };
@@ -0,0 +1,111 @@
1
+ import { BLOCK_ROOT_SELECTOR as S, CURRENCY_ATTR as p, CONTAINER_SELECTOR as O } from "../extensions/Blocks/Recommendation/constants/selectors.js";
2
+ import { useRecommendationExtensionStore as h } from "../extensions/Blocks/Recommendation/store/recommendation.js";
3
+ import { formatPrice as E } from "../extensions/Blocks/Recommendation/utils/priceFormatter.js";
4
+ const f = `${S}[recommendation-id]`, C = ".product-old-price", R = /\{\{(?:reco_)?(\d+_\d+_[a-zA-Z0-9_.]+)\}\}/g, T = new RegExp(
5
+ "\\{%\\s*if\\s+([\\s\\S]+?)\\s*%\\}([\\s\\S]*?)(?:\\{%\\s*else\\s*%\\}([\\s\\S]*?))?\\{%\\s*endif\\s*%\\}",
6
+ "g"
7
+ );
8
+ function b(e) {
9
+ return e.replaceAll("&", "&amp;").replaceAll("<", "&lt;").replaceAll(">", "&gt;").replaceAll('"', "&quot;").replaceAll("'", "&#39;");
10
+ }
11
+ function _(e) {
12
+ var s;
13
+ const n = (s = e.replace(/[\u0000-\u0020]+/g, "").toLowerCase().match(/^([a-z][a-z0-9+.-]*):/)) == null ? void 0 : s[1];
14
+ return n && n !== "http" && n !== "https" && n !== "mailto" ? "" : e;
15
+ }
16
+ function N(e) {
17
+ const t = e.getAttribute(p.CURRENCY) || "USD", n = e.getAttribute(p.DECIMAL_SEPARATOR) || ".", s = e.getAttribute(p.THOUSAND_SEPARATOR) || ",";
18
+ return {
19
+ code: t,
20
+ symbol: e.getAttribute(p.SYMBOL) || t,
21
+ alignment: e.getAttribute(p.ALIGNMENT) === "0" ? "before" : "after",
22
+ decimalCount: parseInt(e.getAttribute(p.DECIMAL_COUNT) || "2") || 2,
23
+ decimalSeparator: n,
24
+ thousandSeparator: s
25
+ };
26
+ }
27
+ function g(e, t) {
28
+ return (e == null ? void 0 : e[t]) ?? Object.values(e ?? {})[0] ?? 0;
29
+ }
30
+ function L(e, t) {
31
+ const n = g(e.original_price, t), s = g(e.price, t), o = n > 0 ? Math.round((n - s) / n * 100) : 0;
32
+ return o > 0 ? `${o}%` : "0%";
33
+ }
34
+ function P(e, t, n, s, o, a) {
35
+ s.forEach((i, c) => {
36
+ const r = (m) => `${n}_${c}_${m}`, u = E({ price: g(i.price, o.code), currency: o }), l = E({ price: g(i.original_price, o.code), currency: o }), d = L(i, o.code);
37
+ e.set(r("name"), i.name ?? ""), e.set(r("image_url"), _(i.image_url ?? "")), e.set(r("url"), _(i.url ?? "")), e.set(r("item_id"), i.item_id ?? ""), e.set(r("currency"), ""), e.set(r("price"), u), e.set(r("original_price"), l), e.set(r("discount"), d), e.set(r("omnibus_price"), l), e.set(r("omnibus_discount"), d), a && u === l && t.add(`${n}_${c}`), Object.entries(i.product_attributes ?? {}).forEach(([m, A]) => {
38
+ e.set(r(`product_attribute.${m}`), String(A)), e.set(r(m), String(A));
39
+ });
40
+ });
41
+ }
42
+ function $(e, t) {
43
+ const n = e.match(/^(.+?)\s*(!=|==)\s*"([^"]*)"$/);
44
+ if (!n)
45
+ return !0;
46
+ const [, s, o, a] = n, i = t.get(s.trim()) ?? "";
47
+ return o === "!=" ? i !== a : i === a;
48
+ }
49
+ function z(e, t) {
50
+ return e.replace(
51
+ T,
52
+ (n, s, o, a) => s.split(/\s+and\s+/).every((c) => $(c.trim(), t)) ? o : a ?? ""
53
+ );
54
+ }
55
+ function w(e) {
56
+ let t = e;
57
+ for (; t.children.length === 1; )
58
+ [t] = t.children;
59
+ return t;
60
+ }
61
+ function D(e, t) {
62
+ var i;
63
+ if (!t.size)
64
+ return e;
65
+ const n = e.replaceAll("{%", "<!--{%").replaceAll("%}", "%}-->"), s = new DOMParser().parseFromString(n, "text/html");
66
+ s.querySelectorAll(f).forEach((c) => {
67
+ const r = Number(c.getAttribute("recommendation-id"));
68
+ if (!Number.isFinite(r))
69
+ return;
70
+ const u = c.querySelectorAll(O);
71
+ (u.length ? Array.from(u) : [c]).forEach((d) => {
72
+ d.querySelectorAll(C).forEach((m, A) => {
73
+ t.has(`${r}_${A}`) && (w(m).textContent = "");
74
+ });
75
+ });
76
+ });
77
+ const o = (i = e.match(/<!DOCTYPE[^>]*>/i)) == null ? void 0 : i[0];
78
+ return ((o ? `${o}
79
+ ` : "") + s.documentElement.outerHTML).replaceAll("<!--{%", "{%").replaceAll("%}-->", "%}").replaceAll("&lt;!--{%", "{%").replaceAll("%}--&gt;", "%}");
80
+ }
81
+ function I(e) {
82
+ if (!e || !e.includes("recommendation-block-v2"))
83
+ return e;
84
+ const t = h(), n = new DOMParser().parseFromString(e, "text/html"), s = Array.from(n.querySelectorAll(f)), o = /* @__PURE__ */ new Map(), a = /* @__PURE__ */ new Set();
85
+ if (s.forEach((c) => {
86
+ var l;
87
+ const r = Number(c.getAttribute("recommendation-id"));
88
+ if (!Number.isFinite(r))
89
+ return;
90
+ const u = ((l = t.blockStates[r]) == null ? void 0 : l.recommendationProducts) ?? [];
91
+ u.length && P(
92
+ o,
93
+ a,
94
+ r,
95
+ u,
96
+ N(c),
97
+ c.getAttribute("hide-price") === "true"
98
+ );
99
+ }), !o.size)
100
+ return e;
101
+ let i = D(e, a);
102
+ return i = i.replace(
103
+ R,
104
+ (c, r) => o.has(r) ? b(o.get(r)) : c
105
+ ), i = z(i, o), i;
106
+ }
107
+ const q = () => ({ substituteRecommendationPreview: I });
108
+ export {
109
+ I as substituteRecommendationPreview,
110
+ q as useRecommendationPreview
111
+ };
@@ -1,32 +1,32 @@
1
- import { useActionsApi as x } from "./useActionsApi.js";
1
+ import { useActionsApi as H } from "./useActionsApi.js";
2
2
  import { useConfig as y } from "./useConfig.js";
3
- import { useSaveStart as w, useSaveComplete as H } from "./useGuidoActions.js";
3
+ import { useSaveStart as w, useSaveComplete as k } from "./useGuidoActions.js";
4
4
  import { useSyncModuleExtractor as q } from "./useSyncModuleExtractor.js";
5
5
  import { useStripoApi as C } from "../services/stripoApi.js";
6
6
  import { useTemplatePreparation as E } from "../utils/templatePreparation.js";
7
- import { useHtmlValidator as k } from "./useHtmlValidator.js";
7
+ import { useHtmlValidator as B } from "./useHtmlValidator.js";
8
8
  import { useCouponBlockValidator as L } from "./validators/useCouponBlockValidator.js";
9
9
  import { useLiquidValidator as P } from "./validators/useLiquidValidator.js";
10
- import { useUnsubscribeBlockValidator as B } from "./validators/useUnsubscribeBlockValidator.js";
11
- const J = () => {
12
- const o = w(), s = H(), { validateHtml: r } = k(), { validateLiquidSyntax: n } = P(), { validateCouponBlockTags: l } = L(), { validateUnsubscribeBlockUniqueness: d } = B(), { callbacks: i, isFeatureEnabled: u } = y(), { extractSyncModuleData: c } = q(), { setSyncModuleUnsubscriptionPages: m } = C(), { editorSave: p } = x();
13
- return { save: async (f = !1, v = !1) => {
10
+ import { useUnsubscribeBlockValidator as U } from "./validators/useUnsubscribeBlockValidator.js";
11
+ const K = () => {
12
+ const o = w(), s = k(), { validateHtml: r } = B(), { validateLiquidSyntax: l } = P(), { validateCouponBlockTags: n } = L(), { validateUnsubscribeBlockUniqueness: d, validateUnsubscribeBlockHasTemplate: c } = U(), { callbacks: i, isFeatureEnabled: u } = y(), { extractSyncModuleData: m } = q(), { setSyncModuleUnsubscriptionPages: p } = C(), { editorSave: v } = H();
13
+ return { save: async (f = !1, S = !1) => {
14
14
  var a;
15
15
  o();
16
- const { prepareTemplateDetails: S } = E(), t = await S();
17
- if (!l(t.compiledHtml) || !d(t.compiledHtml))
16
+ const { prepareTemplateDetails: V } = E(), t = await V();
17
+ if (!n(t.compiledHtml) || !d(t.compiledHtml) || !c(t.compiledHtml))
18
18
  return;
19
19
  if (u("liquidSyntax")) {
20
- if (!await n(t.compiledHtml))
20
+ if (!await l(t.compiledHtml))
21
21
  return;
22
22
  } else if (!await r(t.compiledHtml, t.dynamicContentList, !0))
23
23
  return;
24
- if ((a = i.value) != null && a.externalValidation && !await i.value.externalValidation(t) || !await p())
24
+ if ((a = i.value) != null && a.externalValidation && !await i.value.externalValidation(t) || !await v())
25
25
  return;
26
- const { unsubscribePayload: V, stripoModules: b } = c(t.rawHtml);
27
- return await m(V), t.modules = b, f || s({ ...t, silent: v }), t;
26
+ const { unsubscribePayload: b, stripoModules: x } = m(t.rawHtml);
27
+ return await p(b), t.modules = x, f || s({ ...t, silent: S }), t;
28
28
  } };
29
29
  };
30
30
  export {
31
- J as useSave
31
+ K as useSave
32
32
  };
@@ -1,29 +1,30 @@
1
- import { useActionsApi as I } from "./useActionsApi.js";
2
- import { useBlocksConfig as U } from "./useBlocksConfig.js";
3
- import { useConfig as R } from "./useConfig.js";
4
- import { useCustomInterfaceAppearance as x } from "./useCustomInterfaceAppearance.js";
5
- import { useFullStoryBridge as O } from "./useFullStoryBridge.js";
6
- import { useStripoEventHandler as q } from "./useStripoEventHandler.js";
7
- import { useToaster as H } from "./useToaster.js";
8
- import { localePatch as z } from "../config/i18n/index.js";
1
+ import { useActionsApi as U } from "./useActionsApi.js";
2
+ import { useBlocksConfig as R } from "./useBlocksConfig.js";
3
+ import { useConfig as x } from "./useConfig.js";
4
+ import { useCustomInterfaceAppearance as O } from "./useCustomInterfaceAppearance.js";
5
+ import { useFullStoryBridge as q } from "./useFullStoryBridge.js";
6
+ import { useStripoEventHandler as H } from "./useStripoEventHandler.js";
7
+ import { useStripoNotifications as N } from "./useStripoNotifications.js";
8
+ import { useToaster as z } from "./useToaster.js";
9
+ import { localePatch as L } from "../config/i18n/index.js";
9
10
  import { en as h } from "../config/i18n/en/index.js";
10
- import { ToasterTypeOptions as L } from "../enums/toaster.js";
11
- import { useStripoApi as $ } from "../services/stripoApi.js";
12
- import G from "../static/styles/customEditorStyle.css.js";
11
+ import { ToasterTypeOptions as $ } from "../enums/toaster.js";
12
+ import { useStripoApi as G } from "../services/stripoApi.js";
13
+ import J from "../static/styles/customEditorStyle.css.js";
13
14
  import { useEditorStore as C } from "../stores/editor.js";
14
- import { dynamicContentToMergeTags as J } from "../utils/genericUtil.js";
15
- import N from "../package.json.js";
16
- const ce = (E, l) => {
17
- const { features: c, template: w, isFeatureEnabled: u } = R(), { handleError: m, showToaster: b } = H(), { getToken: T, getCustomFonts: k, getSyncModulesStatus: B } = $(), { handleEvent: F } = q(), { getStripoBlocksConfig: v } = U(), V = async (s, r = [], i = !1) => {
15
+ import { dynamicContentToMergeTags as X } from "../utils/genericUtil.js";
16
+ import j from "../package.json.js";
17
+ const pe = (E, l) => {
18
+ const { features: c, template: w, isFeatureEnabled: u } = x(), { handleError: m, showToaster: b } = z(), { getToken: T, getCustomFonts: k, getSyncModulesStatus: B } = G(), { handleEvent: F } = H(), { getStripoBlocksConfig: v } = R(), { getStripoNotifications: V } = N(), _ = async (s, i = [], r = !1) => {
18
19
  var g, S, y;
19
- const e = C(), { html: p, css: a } = s, { baseBlocks: t, extensions: d } = await v(), f = ((g = c.value) == null ? void 0 : g.displayConditions) ?? !0, A = ((S = c.value) == null ? void 0 : S.modulesDisabled) ?? !1, M = ((y = w.value) == null ? void 0 : y.forceRecreate) ?? !1;
20
+ const e = C(), { html: p, css: a } = s, { baseBlocks: t, extensions: d } = await v(), f = ((g = c.value) == null ? void 0 : g.displayConditions) ?? !0, M = ((S = c.value) == null ? void 0 : S.modulesDisabled) ?? !1, P = ((y = w.value) == null ? void 0 : y.forceRecreate) ?? !1;
20
21
  await window.UIEditor.initEditor(
21
22
  document.querySelector("#guido-editor"),
22
23
  {
23
24
  metadata: E,
24
25
  html: p,
25
26
  css: a,
26
- forceRecreate: M,
27
+ forceRecreate: P,
27
28
  locale: "en",
28
29
  undoButtonSelector: "#guido__undo-button",
29
30
  redoButtonSelector: "#guido__redo-button",
@@ -33,12 +34,12 @@ const ce = (E, l) => {
33
34
  customAppearanceMergetags: !u("liquidSyntax"),
34
35
  customAppearanceMergetagsBorderColor: "#f1f3fe",
35
36
  customAppearanceMergetagsBackgroundColor: "#f1f3fe",
36
- customViewStyles: G,
37
+ customViewStyles: J,
37
38
  conditionsEnabled: f,
38
39
  customConditionsEnabled: f,
39
40
  enableXSSSecurity: !0,
40
- modulesDisabled: A,
41
- syncModulesEnabled: i,
41
+ modulesDisabled: M,
42
+ syncModulesEnabled: r,
42
43
  messageSettingsEnabled: !0,
43
44
  displayGmailAnnotations: !0,
44
45
  displayHiddenPreheader: !1,
@@ -51,11 +52,11 @@ const ce = (E, l) => {
51
52
  editorFonts: {
52
53
  showDefaultStandardFonts: !0,
53
54
  showDefaultNotStandardFonts: !0,
54
- customFonts: r
55
+ customFonts: i
55
56
  },
56
57
  mergeTags: [
57
58
  {
58
- entries: J(
59
+ entries: X(
59
60
  l.preselectedDynamicContentList,
60
61
  u("liquidSyntax")
61
62
  )
@@ -71,8 +72,8 @@ const ce = (E, l) => {
71
72
  },
72
73
  onTemplateLoaded() {
73
74
  try {
74
- const { importCss: o } = x(), { activateCustomViewStyles: n, updateTimerInClonedTemplate: P } = I(), { injectFullStory: D } = O();
75
- o(), n(), D(), P(), l.onReady(), e.isStripoInitialized = !0, e.loadingStatus = !1, setTimeout(() => {
75
+ const { importCss: o } = O(), { activateCustomViewStyles: n, updateTimerInClonedTemplate: D } = U(), { injectFullStory: I } = q();
76
+ o(), n(), I(), D(), l.onReady(), e.isStripoInitialized = !0, e.loadingStatus = !1, setTimeout(() => {
76
77
  e.hasChanges = !1;
77
78
  }, 1e3);
78
79
  } catch (o) {
@@ -92,41 +93,42 @@ const ce = (E, l) => {
92
93
  e.hasChanges = !0;
93
94
  },
94
95
  onEvent: F,
96
+ notifications: V(),
95
97
  ignoreClickOutsideSelectors: [
96
98
  "#guido-dynamic-content-modal",
97
99
  ".in-on-board-wrapper",
98
100
  ".in-drawer__container"
99
101
  ],
100
102
  extensions: d,
101
- localePatch: z
103
+ localePatch: L
102
104
  }
103
105
  );
104
- }, _ = (s) => new Promise((r, i) => {
106
+ }, A = (s) => new Promise((i, r) => {
105
107
  var d;
106
108
  if (document.getElementById("UiEditorScript")) {
107
- Promise.resolve(s()).then(r, i);
109
+ Promise.resolve(s()).then(i, r);
108
110
  return;
109
111
  }
110
- const e = N.guido, a = `https://email-static.useinsider.com/guido/${(d = e == null ? void 0 : e.stripo) == null ? void 0 : d.version}/UIEditor.js`, t = document.createElement("script");
112
+ const e = j.guido, a = `https://email-static.useinsider.com/guido/${(d = e == null ? void 0 : e.stripo) == null ? void 0 : d.version}/UIEditor.js`, t = document.createElement("script");
111
113
  t.id = "UiEditorScript", t.type = "module", t.src = a, t.onload = () => {
112
- Promise.resolve(s()).then(r, i);
114
+ Promise.resolve(s()).then(i, r);
113
115
  }, t.onerror = () => {
114
- i(new Error(`Failed to load Stripo UIEditor script from S3: ${a}`));
116
+ r(new Error(`Failed to load Stripo UIEditor script from S3: ${a}`));
115
117
  }, document.body.appendChild(t);
116
118
  });
117
119
  return { initPlugin: async (s) => {
118
- const r = C();
120
+ const i = C();
119
121
  try {
120
- await _(async () => {
121
- const [i, e] = await Promise.all([
122
+ await A(async () => {
123
+ const [r, e] = await Promise.all([
122
124
  k(),
123
125
  B()
124
126
  ]);
125
- r.syncModulesEnabled = e, await V(s, i, e);
127
+ i.syncModulesEnabled = e, await _(s, r, e);
126
128
  });
127
129
  } catch {
128
- r.loadingStatus = !1, b({
129
- type: L.Alert,
130
+ i.loadingStatus = !1, b({
131
+ type: $.Alert,
130
132
  message: h["An error has occurred. Please report the error code to support."],
131
133
  actionButton: {
132
134
  text: h["Reload page"],
@@ -137,5 +139,5 @@ const ce = (E, l) => {
137
139
  } };
138
140
  };
139
141
  export {
140
- ce as useStripo
142
+ pe as useStripo
141
143
  };
@@ -0,0 +1,26 @@
1
+ import { useToaster as d } from "./useToaster.js";
2
+ import { ToasterTypeOptions as c } from "../enums/toaster.js";
3
+ const g = () => {
4
+ const { showToaster: l, hideToaster: u } = d();
5
+ let s = null;
6
+ const n = (o, t, i, e, f = !0) => {
7
+ s = i;
8
+ const r = e != null && e.action ? { text: e.action.label, onClick: e.action.func } : void 0;
9
+ l({ type: o, message: t, actionButton: r, autoHide: (e == null ? void 0 : e.autoClose) ?? f });
10
+ };
11
+ return { getStripoNotifications: () => ({
12
+ info: (o, t, i) => n(c.Info, o, t, i),
13
+ success: (o, t, i) => n(c.Success, o, t, i),
14
+ warn: (o, t, i) => n(c.Warning, o, t, i),
15
+ error: (o, t, i) => n(c.Alert, o, t, i),
16
+ // A loader marks an in-progress operation; Stripo dismisses it via hide(id)
17
+ // when finished, so it must not auto-hide.
18
+ loader: (o, t, i) => n(c.Info, o, t, i, !1),
19
+ hide: (o) => {
20
+ s === o && (u(), s = null);
21
+ }
22
+ }) };
23
+ };
24
+ export {
25
+ g as useStripoNotifications
26
+ };