@useinsider/guido 3.18.2-beta.8ef3138 → 3.18.2-beta.eedafd2
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 +1 -0
- package/dist/@types/config/schemas.js +28 -26
- package/dist/components/Guido.vue.js +8 -8
- package/dist/components/Guido.vue2.js +53 -51
- package/dist/components/organisms/AutoSaveController.vue2.js +9 -8
- package/dist/components/organisms/header/EditorActions.vue.js +2 -2
- package/dist/components/organisms/header/EditorActions.vue2.js +86 -56
- package/dist/components/organisms/header/LeftSlot.vue.js +5 -5
- package/dist/components/organisms/header/LeftSlot.vue2.js +16 -12
- package/dist/components/organisms/validation/ValidationErrorDrawer.vue.js +20 -0
- package/dist/components/organisms/validation/ValidationErrorDrawer.vue2.js +48 -0
- package/dist/components/wrappers/WpDrawer.vue.js +9 -7
- package/dist/components/wrappers/WpDrawer.vue2.js +1 -1
- package/dist/composables/useHtmlCompiler.js +37 -26
- package/dist/composables/useHtmlValidator.js +2 -0
- package/dist/composables/useSave.js +90 -45
- package/dist/composables/useSaveValidation.js +279 -0
- package/dist/composables/useSaveValidationRollout.js +9 -0
- package/dist/composables/validators/useCouponBlockValidator.js +24 -21
- package/dist/composables/validators/useUnsubscribeBlockValidator.js +34 -27
- package/dist/enums/save-validation.js +4 -0
- package/dist/extensions/Blocks/Recommendation/store/recommendation.js +43 -36
- package/dist/guido.css +1 -1
- package/dist/src/@types/config/schemas.d.ts +4 -0
- package/dist/src/@types/save-validation.d.ts +19 -0
- package/dist/src/components/Guido.vue.d.ts +17 -1
- package/dist/src/components/organisms/header/EditorActions.vue.d.ts +17 -1
- package/dist/src/components/organisms/header/HeaderWrapper.vue.d.ts +17 -1
- package/dist/src/components/organisms/header/RightSlot.vue.d.ts +17 -1
- package/dist/src/components/organisms/validation/ValidationErrorDrawer.vue.d.ts +2 -0
- package/dist/src/components/wrappers/WpDrawer.vue.d.ts +4 -3
- package/dist/src/composables/useConfig.d.ts +2 -0
- package/dist/src/composables/useHtmlValidator.d.ts +21 -0
- package/dist/src/composables/useSave.d.ts +6 -1
- package/dist/src/composables/useSaveValidation.d.ts +6 -0
- package/dist/src/composables/useSaveValidationRollout.d.ts +3 -0
- package/dist/src/composables/validators/useCouponBlockValidator.d.ts +3 -0
- package/dist/src/composables/validators/useUnsubscribeBlockValidator.d.ts +10 -0
- package/dist/src/enums/save-validation.d.ts +27 -0
- package/dist/src/extensions/Blocks/Recommendation/store/recommendation.d.ts +5 -0
- package/dist/src/stores/config.d.ts +30 -0
- package/dist/src/stores/save-validation.d.ts +22 -0
- package/dist/src/utils/liquidDynamicContent.d.ts +20 -0
- package/dist/src/utils/templatePreparation.d.ts +30 -0
- package/dist/stores/config.js +39 -22
- package/dist/stores/save-validation.js +30 -0
- package/dist/utils/genericUtil.js +64 -61
- package/dist/utils/liquidDynamicContent.js +15 -0
- package/dist/utils/templatePreparation.js +28 -25
- package/package.json +1 -1
|
@@ -0,0 +1,279 @@
|
|
|
1
|
+
import { getIgnoredRecommendationBlockIds as B } from "../config/compiler/utils/recommendationIgnoreUtils.js";
|
|
2
|
+
import { CanNotMakeAnyChangesForRunningKey as k, DISPLAY_CONDITIONS_REGEX as Y, DISPLAY_CONDITIONS_EXCEPTIONS_REGEX as x } from "../enums/html-validator.js";
|
|
3
|
+
import { SaveValidationRule as o } from "../enums/save-validation.js";
|
|
4
|
+
import { ToasterTypeOptions as r } from "../enums/toaster.js";
|
|
5
|
+
import { BLOCK_ROOT_SELECTOR as U } from "../extensions/Blocks/Checkbox/constants/selectors.js";
|
|
6
|
+
import { itemsBlockDynamicVariables as M } from "../extensions/Blocks/Items/enums/productEnums.js";
|
|
7
|
+
import { BLOCK_ROOT_SELECTOR as P } from "../extensions/Blocks/RadioButton/constants/selectors.js";
|
|
8
|
+
import { useRecommendationExtensionStore as W } from "../extensions/Blocks/Recommendation/store/recommendation.js";
|
|
9
|
+
import { RecommendationRequiredFieldsKey as G } from "../extensions/Blocks/Recommendation/validation/requiredFields.js";
|
|
10
|
+
import { useConfigStore as q } from "../stores/config.js";
|
|
11
|
+
import { useDynamicContentStore as H } from "../stores/dynamic-content.js";
|
|
12
|
+
import { useRecommendationStore as V } from "../stores/recommendation.js";
|
|
13
|
+
import { base64EncodeWithSpecialChars as T } from "../utils/base64.js";
|
|
14
|
+
import { useTemplatePreparation as X } from "../utils/templatePreparation.js";
|
|
15
|
+
import { useActionsApi as j } from "./useActionsApi.js";
|
|
16
|
+
import { useConfig as z } from "./useConfig.js";
|
|
17
|
+
import { useHtmlCompiler as $ } from "./useHtmlCompiler.js";
|
|
18
|
+
import { buildPartnerAttributeNameSet as Q, getInvalidDynamicContentTags as Z, getRecommendationBlockIds as J, findInvalidCustomFields as tt } from "./useHtmlValidator.js";
|
|
19
|
+
import { useHttp as et } from "./useHttp.js";
|
|
20
|
+
import { useTranslations as nt } from "./useTranslations.js";
|
|
21
|
+
import { findInvalidCouponBlocks as it, COUPON_TAG_MODIFIED_KEY as ot } from "./validators/useCouponBlockValidator.js";
|
|
22
|
+
import { findDuplicateUnsubPageTypes as rt, countUnsubBlocksWithoutPage as st, EMPTY_BLOCK_KEY as at } from "./validators/useUnsubscribeBlockValidator.js";
|
|
23
|
+
const ct = "newsletter.html-content-is-empty", lt = "custom-fields.missing-closing-braces", ut = "custom-fields.missing-opening-braces", I = "custom-fields.invalid-custom-fields", mt = "newsletter.display-conditions-invalid-syntax", dt = "custom-conditions.wrong-equality-operators", pt = "custom-conditions.missing-if-endif-tag", gt = "custom-conditions.no-space-after-braces", ft = "custom-conditions.no-braces-inside-if-tag", yt = "newsletter.fill-all-necessary-fields", Et = "newsletter.invalid-image-type", It = "unsubscribe-templates.select-checkbox-groups", St = "unsubscribe-templates.select-radio-button-groups", Ct = "newsletter.invalid-url-link-for-toaster", F = "journey-builder.liquid-validation-failed", _t = "/newsletter/template-library/check-template-html-body", ht = /src="[^"]*\.(svg|pst)"/gm, R = /({%(.*?)%})/g, kt = ["if", "endif", "else", "elif", "now"], Tt = (e) => !kt.includes(e.toLowerCase()), Ft = (e) => ["if", "endif"].includes(e.toLowerCase());
|
|
24
|
+
function Ot(e) {
|
|
25
|
+
return it(e).map((i) => ({
|
|
26
|
+
rule: o.CouponTagModified,
|
|
27
|
+
type: r.Warning,
|
|
28
|
+
key: ot,
|
|
29
|
+
detail: i
|
|
30
|
+
}));
|
|
31
|
+
}
|
|
32
|
+
function Rt(e) {
|
|
33
|
+
return rt(e).map((i) => ({
|
|
34
|
+
rule: o.DuplicateUnsubBlock,
|
|
35
|
+
type: r.Error,
|
|
36
|
+
key: i.messageKey
|
|
37
|
+
}));
|
|
38
|
+
}
|
|
39
|
+
function Lt(e) {
|
|
40
|
+
return Array.from({ length: st(e) }, () => ({
|
|
41
|
+
rule: o.UnsubBlockMissingTemplate,
|
|
42
|
+
type: r.Warning,
|
|
43
|
+
key: at
|
|
44
|
+
}));
|
|
45
|
+
}
|
|
46
|
+
function Nt(e, i) {
|
|
47
|
+
const n = e.match(R);
|
|
48
|
+
if (!n)
|
|
49
|
+
return [];
|
|
50
|
+
const a = [];
|
|
51
|
+
return n.forEach((u) => {
|
|
52
|
+
const s = u.slice(2, -2).trim().match(/(".*?"|[^"\s]+)(?=\s*|\s*$)/g);
|
|
53
|
+
if (s && s.length > 0) {
|
|
54
|
+
const [m] = s;
|
|
55
|
+
Tt(m) && !i.includes(m) && a.push({
|
|
56
|
+
rule: o.CustomFieldScript,
|
|
57
|
+
type: r.Warning,
|
|
58
|
+
key: I,
|
|
59
|
+
detail: m
|
|
60
|
+
});
|
|
61
|
+
}
|
|
62
|
+
}), a;
|
|
63
|
+
}
|
|
64
|
+
function bt(e) {
|
|
65
|
+
return e.length > 0 ? [] : [{ rule: o.EmptyHtml, type: r.Warning, key: ct }];
|
|
66
|
+
}
|
|
67
|
+
function At(e) {
|
|
68
|
+
const i = (e.match(/{/gm) || []).length, n = (e.match(/}/gm) || []).length;
|
|
69
|
+
return i > n ? [{
|
|
70
|
+
rule: o.MismatchedBraces,
|
|
71
|
+
type: r.Warning,
|
|
72
|
+
key: lt
|
|
73
|
+
}] : i < n ? [{
|
|
74
|
+
rule: o.MismatchedBraces,
|
|
75
|
+
type: r.Warning,
|
|
76
|
+
key: ut
|
|
77
|
+
}] : [];
|
|
78
|
+
}
|
|
79
|
+
function Dt(e) {
|
|
80
|
+
return Z(e).map((i) => ({
|
|
81
|
+
rule: o.InvalidDynamicTag,
|
|
82
|
+
type: r.Warning,
|
|
83
|
+
key: I,
|
|
84
|
+
detail: i
|
|
85
|
+
}));
|
|
86
|
+
}
|
|
87
|
+
function vt(e, i, n, a) {
|
|
88
|
+
const u = J(e);
|
|
89
|
+
return tt(e, i, u, n, a).map((s) => ({
|
|
90
|
+
rule: o.InvalidCustomField,
|
|
91
|
+
type: r.Error,
|
|
92
|
+
key: I,
|
|
93
|
+
detail: s
|
|
94
|
+
}));
|
|
95
|
+
}
|
|
96
|
+
function Kt(e) {
|
|
97
|
+
const i = e.match(/{%(.*?)%}/g), n = [], a = [];
|
|
98
|
+
if (i && i.forEach((u) => {
|
|
99
|
+
const s = u.match(Y), m = u.match(x), y = (s == null ? void 0 : s.join("")) || "";
|
|
100
|
+
(!s || u !== y) && !m && a.push({
|
|
101
|
+
rule: o.ConditionsSyntax,
|
|
102
|
+
type: r.Error,
|
|
103
|
+
key: mt,
|
|
104
|
+
detail: u
|
|
105
|
+
}), s && s.forEach((g) => {
|
|
106
|
+
g.trim() === "=" && a.push({
|
|
107
|
+
rule: o.WrongEqualityOperator,
|
|
108
|
+
type: r.Error,
|
|
109
|
+
key: dt
|
|
110
|
+
}), (g.match(/^[a-zA-Z]*$/g) ?? []).forEach((f) => {
|
|
111
|
+
Ft(f) && n.push(f);
|
|
112
|
+
});
|
|
113
|
+
});
|
|
114
|
+
}), n.length) {
|
|
115
|
+
const u = n.filter((m) => m === "if").length, s = n.filter((m) => m === "endif").length;
|
|
116
|
+
u !== s && a.push({
|
|
117
|
+
rule: o.MissingIfEndif,
|
|
118
|
+
type: r.Error,
|
|
119
|
+
key: pt
|
|
120
|
+
});
|
|
121
|
+
}
|
|
122
|
+
return a;
|
|
123
|
+
}
|
|
124
|
+
function wt(e) {
|
|
125
|
+
const i = (e.match(/{% /gm) || []).length, n = (e.match(/ %}/gm) || []).length;
|
|
126
|
+
return i === n ? [] : [{
|
|
127
|
+
rule: o.ConditionTagSpacing,
|
|
128
|
+
type: r.Warning,
|
|
129
|
+
key: gt
|
|
130
|
+
}];
|
|
131
|
+
}
|
|
132
|
+
function Bt(e) {
|
|
133
|
+
return (e.match(R) || []).filter((n) => n.includes("if")).map((n) => (n.match(/{{.*}}/gm) || []).length).reduce((n, a) => n + a, 0) === 0 ? [] : [{
|
|
134
|
+
rule: o.BracesInsideIfTag,
|
|
135
|
+
type: r.Warning,
|
|
136
|
+
key: ft
|
|
137
|
+
}];
|
|
138
|
+
}
|
|
139
|
+
function Yt(e) {
|
|
140
|
+
return (e.match(ht) ?? []).map((i) => ({
|
|
141
|
+
rule: o.InvalidImageType,
|
|
142
|
+
type: r.Error,
|
|
143
|
+
key: Et,
|
|
144
|
+
detail: i
|
|
145
|
+
}));
|
|
146
|
+
}
|
|
147
|
+
function O(e, i, n, a) {
|
|
148
|
+
const u = new DOMParser().parseFromString(e, "text/html");
|
|
149
|
+
return Array.from(u.querySelectorAll(i)).filter((s) => {
|
|
150
|
+
var m;
|
|
151
|
+
return !((m = s.id) != null && m.trim());
|
|
152
|
+
}).map(() => ({ rule: n, type: r.Error, key: a }));
|
|
153
|
+
}
|
|
154
|
+
const ae = () => {
|
|
155
|
+
const { config: e, isFeatureEnabled: i } = z(), n = nt(), { post: a } = et(), { getCompiledEmail: u, getTemplateData: s } = j(), { compileHtml: m } = $(), { hydrateRecommendationStore: y } = X(), g = H(), f = V(), E = W(), L = q(), N = (t) => ({
|
|
156
|
+
rule: t.rule,
|
|
157
|
+
type: t.type,
|
|
158
|
+
detail: t.detail,
|
|
159
|
+
message: "key" in t ? n(t.key) : t.message
|
|
160
|
+
}), b = async (t) => {
|
|
161
|
+
if (t.size === 0)
|
|
162
|
+
return /* @__PURE__ */ new Set();
|
|
163
|
+
try {
|
|
164
|
+
await E.fetchRecommendationFilters();
|
|
165
|
+
} catch {
|
|
166
|
+
return null;
|
|
167
|
+
}
|
|
168
|
+
return Q(E.filterList);
|
|
169
|
+
}, A = async (t) => {
|
|
170
|
+
try {
|
|
171
|
+
const l = await a(_t, { html: T(t) }), { status: c, message: d } = l.data, p = [];
|
|
172
|
+
return c || p.push({
|
|
173
|
+
rule: o.InvalidLinks,
|
|
174
|
+
type: r.Error,
|
|
175
|
+
// status===undefined means a bare message instead of a boolean; surface it,
|
|
176
|
+
// but fall back to the canned key when it's missing so a malformed body
|
|
177
|
+
// never renders a literal 'undefined' row (SD-147430).
|
|
178
|
+
...c === void 0 && d ? { message: d } : { key: Ct }
|
|
179
|
+
}), d === n(k) && p.push({
|
|
180
|
+
rule: o.LinkCheckInProgress,
|
|
181
|
+
type: r.Error,
|
|
182
|
+
key: k
|
|
183
|
+
}), p;
|
|
184
|
+
} catch (l) {
|
|
185
|
+
return console.warn("Link-check collector failed; skipping the link rule.", l), [];
|
|
186
|
+
}
|
|
187
|
+
}, D = async (t) => {
|
|
188
|
+
try {
|
|
189
|
+
const l = await a("/newsletter/contents/validate-syntax", [{
|
|
190
|
+
identifier: "default",
|
|
191
|
+
syntax: "liquid",
|
|
192
|
+
contents: {
|
|
193
|
+
subject: null,
|
|
194
|
+
preheader: null,
|
|
195
|
+
html: T(t),
|
|
196
|
+
ampHtml: null
|
|
197
|
+
}
|
|
198
|
+
}]);
|
|
199
|
+
if (!Array.isArray(l.data)) {
|
|
200
|
+
const d = l.data;
|
|
201
|
+
return [{
|
|
202
|
+
rule: o.LiquidSyntax,
|
|
203
|
+
type: r.Warning,
|
|
204
|
+
message: d.message ?? n(F)
|
|
205
|
+
}];
|
|
206
|
+
}
|
|
207
|
+
const [c] = l.data;
|
|
208
|
+
return Object.values((c == null ? void 0 : c.errors) ?? {}).map((d) => ({
|
|
209
|
+
rule: o.LiquidSyntax,
|
|
210
|
+
type: r.Warning,
|
|
211
|
+
message: d.replace(/^line \d+:\s*/, "")
|
|
212
|
+
}));
|
|
213
|
+
} catch {
|
|
214
|
+
return [{
|
|
215
|
+
rule: o.LiquidSyntax,
|
|
216
|
+
type: r.Error,
|
|
217
|
+
message: n(F)
|
|
218
|
+
}];
|
|
219
|
+
}
|
|
220
|
+
}, v = () => {
|
|
221
|
+
const t = E.invalidBlockIds().map((c) => ({
|
|
222
|
+
rule: o.RecommendationRequiredFields,
|
|
223
|
+
type: r.Error,
|
|
224
|
+
key: G,
|
|
225
|
+
detail: c
|
|
226
|
+
})), l = (f.recommendationConfigs ?? []).filter((c) => c.filters.some((d) => d.value === "")).map(() => ({
|
|
227
|
+
rule: o.RecommendationFilters,
|
|
228
|
+
type: r.Error,
|
|
229
|
+
key: yt
|
|
230
|
+
}));
|
|
231
|
+
return [...t, ...l];
|
|
232
|
+
}, K = async (t, l) => {
|
|
233
|
+
var _, h;
|
|
234
|
+
const c = [
|
|
235
|
+
...l.map((w) => w.value),
|
|
236
|
+
...M,
|
|
237
|
+
...((h = (_ = e.value) == null ? void 0 : _.template) == null ? void 0 : h.customFieldAttributes) ?? []
|
|
238
|
+
], d = B(t), p = await b(d), { isTransactional: C } = L;
|
|
239
|
+
return [
|
|
240
|
+
...await A(t),
|
|
241
|
+
...C ? [] : Nt(t, c),
|
|
242
|
+
...bt(t),
|
|
243
|
+
...At(t),
|
|
244
|
+
...Dt(t),
|
|
245
|
+
...C ? [] : vt(t, c, d, p),
|
|
246
|
+
...Kt(t),
|
|
247
|
+
...wt(t),
|
|
248
|
+
...Bt(t),
|
|
249
|
+
...v(),
|
|
250
|
+
...Yt(t),
|
|
251
|
+
...O(
|
|
252
|
+
t,
|
|
253
|
+
U,
|
|
254
|
+
o.CheckboxUnsubGroup,
|
|
255
|
+
It
|
|
256
|
+
),
|
|
257
|
+
...O(
|
|
258
|
+
t,
|
|
259
|
+
P,
|
|
260
|
+
o.RadioButtonUnsubGroup,
|
|
261
|
+
St
|
|
262
|
+
)
|
|
263
|
+
];
|
|
264
|
+
}, S = async (t, l) => [
|
|
265
|
+
...Ot(t),
|
|
266
|
+
...Rt(t),
|
|
267
|
+
...Lt(t),
|
|
268
|
+
...i("liquidSyntax") ? await D(t) : await K(t, l)
|
|
269
|
+
].map(N);
|
|
270
|
+
return { collectSaveValidationErrors: S, validateCurrentTemplate: async () => {
|
|
271
|
+
const { html: t } = await s();
|
|
272
|
+
await y(t);
|
|
273
|
+
const { html: l } = await u({ minimize: !0, resetDataSavedFlag: !1 }), { compiledHtml: c } = m(l);
|
|
274
|
+
return S(c, g.getSelectedDynamicContentList);
|
|
275
|
+
} };
|
|
276
|
+
};
|
|
277
|
+
export {
|
|
278
|
+
ae as useSaveValidation
|
|
279
|
+
};
|
|
@@ -0,0 +1,9 @@
|
|
|
1
|
+
import { useConfigStore as t } from "../stores/config.js";
|
|
2
|
+
import { computed as o } from "vue";
|
|
3
|
+
const n = ["newsletteruatcamp", "newsletterqacamp"], c = () => {
|
|
4
|
+
const e = t();
|
|
5
|
+
return { isEnabled: o(() => n.includes(e.partnerName)) };
|
|
6
|
+
};
|
|
7
|
+
export {
|
|
8
|
+
c as useSaveValidationRollout
|
|
9
|
+
};
|
|
@@ -1,24 +1,27 @@
|
|
|
1
|
-
import { ToasterTypeOptions as
|
|
2
|
-
import { COUPON_PLACEHOLDER_DEFAULT as
|
|
3
|
-
import { useToaster as
|
|
4
|
-
import { useTranslations as
|
|
5
|
-
const
|
|
6
|
-
|
|
7
|
-
|
|
8
|
-
]),
|
|
9
|
-
|
|
10
|
-
|
|
11
|
-
|
|
12
|
-
|
|
13
|
-
|
|
14
|
-
|
|
15
|
-
|
|
16
|
-
|
|
17
|
-
|
|
18
|
-
|
|
19
|
-
|
|
20
|
-
|
|
1
|
+
import { ToasterTypeOptions as n } from "../../enums/toaster.js";
|
|
2
|
+
import { COUPON_PLACEHOLDER_DEFAULT as s, COUPON_PLACEHOLDER_LIQUID as a } from "../../extensions/Blocks/CouponBlock/template.js";
|
|
3
|
+
import { useToaster as i } from "../useToaster.js";
|
|
4
|
+
import { useTranslations as l } from "../useTranslations.js";
|
|
5
|
+
const c = /* @__PURE__ */ new Set([
|
|
6
|
+
s,
|
|
7
|
+
a
|
|
8
|
+
]), p = "newsletter.coupon-tag-modified";
|
|
9
|
+
function u(r) {
|
|
10
|
+
const e = new DOMParser().parseFromString(r, "text/html");
|
|
11
|
+
return Array.from(e.querySelectorAll(".coupon-block")).map((o) => {
|
|
12
|
+
var t;
|
|
13
|
+
return ((t = o.textContent) == null ? void 0 : t.trim()) ?? "";
|
|
14
|
+
}).filter((o) => !c.has(o));
|
|
15
|
+
}
|
|
16
|
+
const T = () => {
|
|
17
|
+
const { showToaster: r } = i(), e = l();
|
|
18
|
+
return { validateCouponBlockTags: (t) => u(t).length > 0 ? (r({
|
|
19
|
+
type: n.Warning,
|
|
20
|
+
message: e(p)
|
|
21
|
+
}), !1) : !0 };
|
|
21
22
|
};
|
|
22
23
|
export {
|
|
23
|
-
|
|
24
|
+
p as COUPON_TAG_MODIFIED_KEY,
|
|
25
|
+
u as findInvalidCouponBlocks,
|
|
26
|
+
T as useCouponBlockValidator
|
|
24
27
|
};
|
|
@@ -1,8 +1,8 @@
|
|
|
1
|
-
import { ToasterTypeOptions as
|
|
1
|
+
import { ToasterTypeOptions as c } from "../../enums/toaster.js";
|
|
2
2
|
import { PAGE_TYPES as u } from "../../enums/unsubscribe.js";
|
|
3
|
-
import { UNSUBSCRIBE_BLOCK_SELECTOR as
|
|
4
|
-
import { useToaster as
|
|
5
|
-
import { useTranslations as
|
|
3
|
+
import { UNSUBSCRIBE_BLOCK_SELECTOR as i, DATA_ATTRIBUTES as a } from "../../extensions/Blocks/Unsubscribe/utils/constants.js";
|
|
4
|
+
import { useToaster as p } from "../useToaster.js";
|
|
5
|
+
import { useTranslations as l } from "../useTranslations.js";
|
|
6
6
|
const T = [
|
|
7
7
|
{
|
|
8
8
|
pageType: u.GLOBAL_UNSUBSCRIBE,
|
|
@@ -12,30 +12,37 @@ const T = [
|
|
|
12
12
|
pageType: u.SUBSCRIPTION_PREFERENCE_CENTER,
|
|
13
13
|
messageKey: "unsubscription-preference.duplicate-pref-center"
|
|
14
14
|
}
|
|
15
|
-
], g = "unsubscription-preference.duplicate-both",
|
|
16
|
-
|
|
17
|
-
|
|
18
|
-
|
|
19
|
-
|
|
20
|
-
|
|
21
|
-
|
|
22
|
-
|
|
23
|
-
|
|
24
|
-
|
|
25
|
-
|
|
26
|
-
|
|
15
|
+
], g = "unsubscription-preference.duplicate-both", E = "unsubscription-preference.select-page-to-continue";
|
|
16
|
+
function m(r) {
|
|
17
|
+
const s = new DOMParser().parseFromString(r, "text/html"), t = /* @__PURE__ */ new Map();
|
|
18
|
+
return s.querySelectorAll(i).forEach((n) => {
|
|
19
|
+
const e = Number(n.getAttribute(a.PAGE_TYPE));
|
|
20
|
+
t.set(e, (t.get(e) ?? 0) + 1);
|
|
21
|
+
}), T.filter((n) => (t.get(n.pageType) ?? 0) > 1);
|
|
22
|
+
}
|
|
23
|
+
function b(r) {
|
|
24
|
+
const s = new DOMParser().parseFromString(r, "text/html");
|
|
25
|
+
return Array.from(s.querySelectorAll(i)).filter((t) => {
|
|
26
|
+
const n = t.getAttribute(a.PAGE_TYPE), e = t.getAttribute(a.PAGE_LIST);
|
|
27
|
+
return !n || !e;
|
|
28
|
+
}).length;
|
|
29
|
+
}
|
|
30
|
+
const y = () => {
|
|
31
|
+
const { showToaster: r } = p(), s = l();
|
|
32
|
+
return { validateUnsubscribeBlockUniqueness: (e) => {
|
|
33
|
+
const o = m(e);
|
|
34
|
+
return o.length ? (r({
|
|
35
|
+
type: c.Error,
|
|
36
|
+
message: s(o.length > 1 ? g : o[0].messageKey)
|
|
27
37
|
}), !1) : !0;
|
|
28
|
-
}, validateUnsubscribeBlockHasTemplate: (
|
|
29
|
-
|
|
30
|
-
|
|
31
|
-
|
|
32
|
-
return !e || !s;
|
|
33
|
-
}) ? (c({
|
|
34
|
-
type: i.Warning,
|
|
35
|
-
message: p(b)
|
|
36
|
-
}), !1) : !0;
|
|
37
|
-
} };
|
|
38
|
+
}, validateUnsubscribeBlockHasTemplate: (e) => b(e) === 0 ? !0 : (r({
|
|
39
|
+
type: c.Warning,
|
|
40
|
+
message: s(E)
|
|
41
|
+
}), !1) };
|
|
38
42
|
};
|
|
39
43
|
export {
|
|
40
|
-
|
|
44
|
+
E as EMPTY_BLOCK_KEY,
|
|
45
|
+
b as countUnsubBlocksWithoutPage,
|
|
46
|
+
m as findDuplicateUnsubPageTypes,
|
|
47
|
+
y as useUnsubscribeBlockValidator
|
|
41
48
|
};
|
|
@@ -0,0 +1,4 @@
|
|
|
1
|
+
var n = /* @__PURE__ */ ((s) => (s.CouponTagModified = "coupon-tag-modified", s.DuplicateUnsubBlock = "duplicate-unsub-block", s.UnsubBlockMissingTemplate = "unsub-block-missing-template", s.LiquidSyntax = "liquid-syntax", s.InvalidLinks = "invalid-links", s.LinkCheckInProgress = "link-check-in-progress", s.CustomFieldScript = "custom-field-script", s.EmptyHtml = "empty-html", s.MismatchedBraces = "mismatched-braces", s.InvalidDynamicTag = "invalid-dynamic-tag", s.InvalidCustomField = "invalid-custom-field", s.ConditionsSyntax = "conditions-syntax", s.WrongEqualityOperator = "wrong-equality-operator", s.MissingIfEndif = "missing-if-endif", s.ConditionTagSpacing = "condition-tag-spacing", s.BracesInsideIfTag = "braces-inside-if-tag", s.RecommendationRequiredFields = "recommendation-required-fields", s.RecommendationFilters = "recommendation-filters", s.InvalidImageType = "invalid-image-type", s.CheckboxUnsubGroup = "checkbox-unsub-group", s.RadioButtonUnsubGroup = "radio-button-unsub-group", s))(n || {});
|
|
2
|
+
export {
|
|
3
|
+
n as SaveValidationRule
|
|
4
|
+
};
|
|
@@ -1,22 +1,22 @@
|
|
|
1
|
-
import { getRecommendationFeedSourceMaps as
|
|
2
|
-
import { useRecommendationApi as
|
|
3
|
-
import { useConfigStore as
|
|
4
|
-
import { defineStore as
|
|
1
|
+
import { getRecommendationFeedSourceMaps as I, getOperatorOptions as G, PriceAttributes as D } from "../../../../enums/extensions/recommendationBlock.js";
|
|
2
|
+
import { useRecommendationApi as F } from "../../../../services/recommendationApi.js";
|
|
3
|
+
import { useConfigStore as P } from "../../../../stores/config.js";
|
|
4
|
+
import { defineStore as _ } from "pinia";
|
|
5
5
|
import "../constants/selectors.js";
|
|
6
|
-
import { DEFAULT_MOBILE_CARDS_IN_ROW as
|
|
7
|
-
import { DEFAULT_NODE_CONFIG as
|
|
8
|
-
import { getDefaultProducts as
|
|
9
|
-
import { generateCompleteFilterQuery as
|
|
10
|
-
import { getPartnerRecommendationParams as
|
|
6
|
+
import { DEFAULT_MOBILE_CARDS_IN_ROW as U, DEFAULT_CARDS_IN_ROW as N } from "../constants/layout.js";
|
|
7
|
+
import { DEFAULT_NODE_CONFIG as L, EXCLUDED_ALGORITHM_IDS as x } from "../constants/defaultConfig.js";
|
|
8
|
+
import { getDefaultProducts as k } from "../templates/utils.js";
|
|
9
|
+
import { generateCompleteFilterQuery as R } from "../utils/filterUtil.js";
|
|
10
|
+
import { getPartnerRecommendationParams as B } from "../utils/partnerCustomizations.js";
|
|
11
11
|
import { sanitizeProductIds as A } from "../utils/productIds.js";
|
|
12
|
-
import { isFilterValid as
|
|
13
|
-
import { isConfigValid as
|
|
14
|
-
const u =
|
|
12
|
+
import { isFilterValid as M } from "../validation/filterSchema.js";
|
|
13
|
+
import { isConfigValid as C } from "../validation/requiredFields.js";
|
|
14
|
+
const u = F();
|
|
15
15
|
let f = null, g = null, h = null, S = null;
|
|
16
16
|
const p = /* @__PURE__ */ new Map();
|
|
17
|
-
function
|
|
17
|
+
function v() {
|
|
18
18
|
return {
|
|
19
|
-
cardsInRow:
|
|
19
|
+
cardsInRow: N,
|
|
20
20
|
currencySettings: {
|
|
21
21
|
name: "USD",
|
|
22
22
|
value: "USD",
|
|
@@ -30,7 +30,7 @@ function w() {
|
|
|
30
30
|
productIds: [],
|
|
31
31
|
id: 1,
|
|
32
32
|
language: "en_US",
|
|
33
|
-
mobileCardsInRow:
|
|
33
|
+
mobileCardsInRow: U,
|
|
34
34
|
mobileLayoutEnabled: !1,
|
|
35
35
|
orientation: "grid",
|
|
36
36
|
recommendedProducts: [],
|
|
@@ -46,9 +46,9 @@ function w() {
|
|
|
46
46
|
priceHideIfSameAsDiscounted: !1
|
|
47
47
|
};
|
|
48
48
|
}
|
|
49
|
-
function
|
|
49
|
+
function w() {
|
|
50
50
|
return {
|
|
51
|
-
recommendationConfigs:
|
|
51
|
+
recommendationConfigs: v(),
|
|
52
52
|
recommendationProducts: [],
|
|
53
53
|
filterStatus: !1,
|
|
54
54
|
filterSelectionDrawerStatus: !1,
|
|
@@ -60,7 +60,7 @@ function C() {
|
|
|
60
60
|
syncedConfigFingerprint: null
|
|
61
61
|
};
|
|
62
62
|
}
|
|
63
|
-
const
|
|
63
|
+
const O = () => ({
|
|
64
64
|
recommendationCampaignUrls: {},
|
|
65
65
|
activePredictiveAlgorithms: [],
|
|
66
66
|
languages: {},
|
|
@@ -72,8 +72,8 @@ const z = () => ({
|
|
|
72
72
|
blockStates: {},
|
|
73
73
|
currentRecommendationId: null,
|
|
74
74
|
configVersion: 0
|
|
75
|
-
}), Y =
|
|
76
|
-
state: () =>
|
|
75
|
+
}), Y = _("guidoRecommendationExtension", {
|
|
76
|
+
state: () => O(),
|
|
77
77
|
getters: {
|
|
78
78
|
// ====================================================================
|
|
79
79
|
// Proxy Getters — Backward Compatible Access to Current Block State
|
|
@@ -83,7 +83,7 @@ const z = () => ({
|
|
|
83
83
|
* This allows all existing code that reads `store.recommendationConfigs` to work unchanged.
|
|
84
84
|
*/
|
|
85
85
|
recommendationConfigs(t) {
|
|
86
|
-
return t.currentRecommendationId !== null && t.blockStates[t.currentRecommendationId] ? t.blockStates[t.currentRecommendationId].recommendationConfigs :
|
|
86
|
+
return t.currentRecommendationId !== null && t.blockStates[t.currentRecommendationId] ? t.blockStates[t.currentRecommendationId].recommendationConfigs : v();
|
|
87
87
|
},
|
|
88
88
|
/**
|
|
89
89
|
* Proxy getter: delegates to blockStates[currentRecommendationId].recommendationProducts
|
|
@@ -138,8 +138,8 @@ const z = () => ({
|
|
|
138
138
|
return [...new Set(t.map((e) => e.filterGroup))].sort((e, r) => e - r);
|
|
139
139
|
},
|
|
140
140
|
getActivePredictiveAlgorithms: (t) => {
|
|
141
|
-
const e =
|
|
142
|
-
return t.activePredictiveAlgorithms.filter((n) => !
|
|
141
|
+
const e = I(), r = [];
|
|
142
|
+
return t.activePredictiveAlgorithms.filter((n) => !x.includes(n)).forEach((n) => {
|
|
143
143
|
r.push(...e.filter((s) => s.id === n));
|
|
144
144
|
}), r.map((n) => ({
|
|
145
145
|
text: n.name,
|
|
@@ -157,7 +157,7 @@ const z = () => ({
|
|
|
157
157
|
getFilterList() {
|
|
158
158
|
return Object.values(this.filterList).filter((t) => t.isFilterable !== 0 && t.isFilterable !== !1).map((t) => {
|
|
159
159
|
let e;
|
|
160
|
-
return t.type === "productAttribute" ? e = `product_attributes.${t.attributeName}` :
|
|
160
|
+
return t.type === "productAttribute" ? e = `product_attributes.${t.attributeName}` : D.includes(t.attributeName) ? e = `${t.attributeName}.${this.recommendationConfigs.currencySettings.value}` : e = t.attributeName, {
|
|
161
161
|
text: t.displayName,
|
|
162
162
|
value: e,
|
|
163
163
|
type: t.attributeType
|
|
@@ -179,7 +179,7 @@ const z = () => ({
|
|
|
179
179
|
setCurrentBlock(t) {
|
|
180
180
|
this.blockStates[t] || (this.blockStates = {
|
|
181
181
|
...this.blockStates,
|
|
182
|
-
[t]:
|
|
182
|
+
[t]: w()
|
|
183
183
|
}), this.currentRecommendationId = t;
|
|
184
184
|
},
|
|
185
185
|
/**
|
|
@@ -247,7 +247,7 @@ const z = () => ({
|
|
|
247
247
|
decimalCount: String(e.currencyDecimalCount),
|
|
248
248
|
decimalSeparator: r(e.currencyDecimalSeparator, ","),
|
|
249
249
|
thousandSeparator: r(e.currencyThousandSeparator, ".")
|
|
250
|
-
}, s = !this.blockStates[t], i = s ?
|
|
250
|
+
}, s = !this.blockStates[t], i = s ? w() : this.blockStates[t];
|
|
251
251
|
i.recommendationConfigs = {
|
|
252
252
|
...i.recommendationConfigs,
|
|
253
253
|
strategy: e.strategy,
|
|
@@ -381,7 +381,7 @@ const z = () => ({
|
|
|
381
381
|
});
|
|
382
382
|
},
|
|
383
383
|
removeStrategy() {
|
|
384
|
-
this.patchCurrentBlockConfig({ strategyId: "", size:
|
|
384
|
+
this.patchCurrentBlockConfig({ strategyId: "", size: L.size });
|
|
385
385
|
},
|
|
386
386
|
// ====================================================================
|
|
387
387
|
// Shared Data Fetching (fetched once, used by all blocks)
|
|
@@ -453,7 +453,7 @@ const z = () => ({
|
|
|
453
453
|
const n = [...e.recommendationConfigs.filters];
|
|
454
454
|
n[r] = {
|
|
455
455
|
...t,
|
|
456
|
-
isValid:
|
|
456
|
+
isValid: M(t)
|
|
457
457
|
}, e.recommendationConfigs.filters = n;
|
|
458
458
|
}
|
|
459
459
|
},
|
|
@@ -491,7 +491,7 @@ const z = () => ({
|
|
|
491
491
|
}), e.recommendationConfigs.filters = r;
|
|
492
492
|
},
|
|
493
493
|
generateFilterQuery() {
|
|
494
|
-
return
|
|
494
|
+
return R(this.recommendationConfigs.filters);
|
|
495
495
|
},
|
|
496
496
|
/**
|
|
497
497
|
* Validation-only check invoked at save-CTA time. Defined as an action
|
|
@@ -499,7 +499,14 @@ const z = () => ({
|
|
|
499
499
|
* every block's recommendationConfigs across user edits.
|
|
500
500
|
*/
|
|
501
501
|
hasInvalidBlock() {
|
|
502
|
-
return Object.values(this.blockStates).some((t) => !
|
|
502
|
+
return Object.values(this.blockStates).some((t) => !C(t.recommendationConfigs, this));
|
|
503
|
+
},
|
|
504
|
+
/**
|
|
505
|
+
* Per-instance counterpart to `hasInvalidBlock`: the ids of every block
|
|
506
|
+
* that fails required-field validation, one drawer row each (SD-147430).
|
|
507
|
+
*/
|
|
508
|
+
invalidBlockIds() {
|
|
509
|
+
return Object.entries(this.blockStates).filter(([, t]) => !C(t.recommendationConfigs, this)).map(([t]) => t);
|
|
503
510
|
},
|
|
504
511
|
// ====================================================================
|
|
505
512
|
// Per-Block Product Fetching
|
|
@@ -520,12 +527,12 @@ const z = () => ({
|
|
|
520
527
|
},
|
|
521
528
|
async _doFetchProducts() {
|
|
522
529
|
var d;
|
|
523
|
-
const t = this.currentRecommendationId, e = this.blockStates[t], { recommendationConfigs: r } = e, n =
|
|
530
|
+
const t = this.currentRecommendationId, e = this.blockStates[t], { recommendationConfigs: r } = e, n = P();
|
|
524
531
|
if (r.strategyId && n.isFeatureEnabled("reusableRecommendationStrategy")) {
|
|
525
532
|
await this._doFetchStrategyProducts(t);
|
|
526
533
|
return;
|
|
527
534
|
}
|
|
528
|
-
const s = r.filters.filter((m) => m.isValid), i =
|
|
535
|
+
const s = r.filters.filter((m) => m.isValid), i = R(s), o = ((d = I().find((m) => m.key === r.strategy)) == null ? void 0 : d.path) || "", c = parseInt(r.size) || 6, a = {
|
|
529
536
|
locale: r.language,
|
|
530
537
|
currency: r.currencySettings.value,
|
|
531
538
|
partnerName: n.partnerName,
|
|
@@ -535,7 +542,7 @@ const z = () => ({
|
|
|
535
542
|
};
|
|
536
543
|
r.strategy === "manualMerchandising" ? a.productId = A(r.productIds) : r.strategy === "similarViewed" && (a.productId = "{itemId}"), r.strategy === "userBased" && (a.userId = "{user_id}"), i && (a.filter = i), r.shuffleProducts && (a.shuffle = !0), Object.assign(
|
|
537
544
|
a,
|
|
538
|
-
|
|
545
|
+
B(n.partnerName, r.strategy)
|
|
539
546
|
);
|
|
540
547
|
let l;
|
|
541
548
|
try {
|
|
@@ -557,7 +564,7 @@ const z = () => ({
|
|
|
557
564
|
);
|
|
558
565
|
if (i) {
|
|
559
566
|
s = parseInt(String(i.size ?? "")) || s;
|
|
560
|
-
const o = r.currencySettings.value, a = (await this.resolveStrategyUrlTemplate(i, o)).replaceAll("{locale}", r.language).replaceAll("{currency}", o), l = a.indexOf("?"), d = l === -1 ? a : a.slice(0, l), m = (l === -1 ? "" : a.slice(l + 1)).split("&").filter((
|
|
567
|
+
const o = r.currencySettings.value, a = (await this.resolveStrategyUrlTemplate(i, o)).replaceAll("{locale}", r.language).replaceAll("{currency}", o), l = a.indexOf("?"), d = l === -1 ? a : a.slice(0, l), m = (l === -1 ? "" : a.slice(l + 1)).split("&").filter((b) => b && !b.startsWith("user_id=")), y = m.length ? `${d}?${m.join("&")}` : d;
|
|
561
568
|
y && (n = await u.fetchRecommendationProductsByUrl(y));
|
|
562
569
|
}
|
|
563
570
|
} catch {
|
|
@@ -568,10 +575,10 @@ const z = () => ({
|
|
|
568
575
|
_setBlockProducts(t, e, r) {
|
|
569
576
|
if (!this.blockStates[t])
|
|
570
577
|
return;
|
|
571
|
-
const n = e.length > 0 ? e :
|
|
578
|
+
const n = e.length > 0 ? e : k(r);
|
|
572
579
|
this.blockStates[t].recommendationProducts = [
|
|
573
580
|
...n.slice(0, r),
|
|
574
|
-
...
|
|
581
|
+
...k(Math.max(0, r - n.length))
|
|
575
582
|
];
|
|
576
583
|
}
|
|
577
584
|
}
|
package/dist/guido.css
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
@charset "UTF-8";.gap-16[data-v-5553d071],.gap-16[data-v-0e1b0c54]{gap:16px}[data-v-
|
|
1
|
+
@charset "UTF-8";.gap-16[data-v-5553d071],.gap-16[data-v-0e1b0c54]{gap:16px}[data-v-b8f24f34] .in-button-v2__wrapper{line-height:0}[data-v-22226124] .in-segments-wrapper__button_selected,[data-v-22226124] .in-segments-wrapper__button_selected:hover{background-color:#dae1fb;color:#0010ac;border-color:#0010ac}[data-v-2cb418af] .in-progress-wrapper__progress p span:last-child{display:none!important}[data-v-2cb418af] .in-progress-description-status{display:none!important}.view-options-wrapper[data-v-87033101]{position:relative;display:inline-block}.new-tag[data-v-87033101]{position:absolute;top:-8px;right:-16px;z-index:10}[data-v-87033101] .guido__view-option-selection-desktop svg,[data-v-87033101] .guido__view-option-selection-mobile svg{margin:0 0 0 2px}[data-v-87033101] .in-segments-wrapper__button_selected,[data-v-87033101] .in-segments-wrapper__button_selected:hover{background-color:#dae1fb}[data-v-87033101] .in-tooltip-wrapper-v2__icon{cursor:pointer}.editor-toolbar[data-v-173c3a40]{gap:4px}.version-history-item[data-v-ee4b9c3f]{flex-basis:200px}.version-history[data-v-fad98586]{gap:8px}.version-history__toolbar[data-v-fad98586]{gap:4px}.view-options-wrapper[data-v-6ebabfe4]{position:relative;display:inline-block}.new-tag[data-v-6ebabfe4]{position:absolute;top:-8px;right:-16px;z-index:10}[data-v-6ebabfe4] .guido__verion-history-view-option-selection-desktop svg,[data-v-6ebabfe4] .guido__verion-history-view-option-selection-mobile svg{margin:0 0 0 2px}[data-v-6ebabfe4] .in-segments-wrapper__button_selected,[data-v-6ebabfe4] .in-segments-wrapper__button_selected:hover{background-color:#dae1fb}[data-v-6ebabfe4] .in-tooltip-wrapper-v2__icon{cursor:pointer}.auto-save-toggle[data-v-2c964af4]{position:relative}.auto-save-toggle__info-box[data-v-2c964af4]{position:absolute;top:100%;left:0;z-index:10;width:280px}.editor-actions[data-v-f938f128]{gap:4px}.header-wrapper[data-v-d11dd577]{min-width:1000px}.guido-loading__wrapper[data-v-07c4b2d8]{height:100%;top:75px!important;bottom:0!important}.validation-error-list[data-v-30d2e1f9]{gap:16px}.validation-error-row[data-v-30d2e1f9]{gap:8px;padding:24px;border:1px solid #E1E1E1;border-radius:8px}.validation-error-row__icon[data-v-30d2e1f9]{flex-shrink:0;font-size:24px;line-height:0}.validation-error-row__text[data-v-30d2e1f9]{font-size:13px;line-height:16px;color:#292929;word-break:break-word}.guido-editor__wrapper[data-v-584fdf72]{--ribbon-offset: 0px;position:relative;width:100%;height:calc(100vh - 128px - var(--ribbon-offset))}.guido-editor__container[data-v-584fdf72]{width:100%;height:calc(100vh - 128px - var(--ribbon-offset))}.guido-editor__no-header[data-v-584fdf72]{height:calc(100vh - 75px - var(--ribbon-offset))}[data-v-293f1c47] .in-breadcrumb-wrapper__links{cursor:pointer}.templates-wrapper[data-v-91a26acd]{gap:16px;grid-template-columns:repeat(3,1fr)}.templates-wrapper .template-wrapper[data-v-91a26acd]{cursor:pointer}.templates-wrapper .template-wrapper .template-container[data-v-91a26acd]{height:274px;padding:2px;transition:none}.templates-wrapper .template-wrapper .template-container.selected[data-v-91a26acd]{padding:1px}.templates-wrapper .template-wrapper .template-container .thumbnail[data-v-91a26acd]{object-fit:cover;transform:scale(1)}[data-v-b9a93c6e] .guido__verion-history-view-option-selection-desktop svg,[data-v-b9a93c6e] .guido__verion-history-view-option-selection-mobile svg{margin:0 0 0 2px}[data-v-b9a93c6e] .in-segments-wrapper__button_selected,[data-v-b9a93c6e] .in-segments-wrapper__button_selected:hover{background-color:#dae1fb}.error-list[data-v-c3fd5d4b]{gap:16px}.desktop-browser-header[data-v-d86c5af5]{height:79px;min-height:79px}.desktop-browser-header__left[data-v-d86c5af5]{-webkit-user-drag:none;height:79px;width:378px}.desktop-browser-header__center[data-v-d86c5af5]{height:79px;background-repeat:repeat-x;background-size:auto 100%;background-position:left top}.desktop-browser-header__right[data-v-d86c5af5]{-webkit-user-drag:none;height:79px;width:112px}.desktop-preview[data-v-cf946232]{min-width:602px;height:70vh;min-height:583px;border-radius:10px}.desktop-preview iframe[data-v-cf946232]{min-height:504px}.iframe-wrapper[data-v-f255b2bb]{width:258px}.iframe-scaled[data-v-f255b2bb]{width:320px;height:124.0310077519%;transform:scale(.80625);transform-origin:top left}.cropped-text[data-v-eb3d05d7]{width:220px;white-space:nowrap;overflow:hidden;text-overflow:ellipsis}.mobile-preview-wrapper__phone[data-v-3f472f96]{width:282px}.mobile-preview-wrapper__phone img[data-v-3f472f96]{object-fit:cover;border-radius:44px}.mobile-preview-wrapper__content[data-v-3f472f96]{width:258px;height:450px;left:12px}[data-v-6bcaca8a] .vueperslides__parallax-wrapper{padding-bottom:110px!important}[data-v-f16f20f8] .vueperslides__bullets{pointer-events:none!important}[data-v-f16f20f8] .vueperslides__parallax-wrapper{padding-bottom:110px!important}[data-v-bb3cca55] .vueperslides__bullets{pointer-events:none!important}[data-v-bb3cca55] .vueperslides__parallax-wrapper{height:110px!important;padding-bottom:110px!important}[data-v-b09e80c4] .vueperslides__bullets{pointer-events:none!important}[data-v-b09e80c4] .vueperslides__parallax-wrapper{height:110px!important;padding-bottom:110px!important}[data-v-9bdef600] .vueperslides__parallax-wrapper{padding-bottom:110px!important}.assign-strategy-drawer-content .assign-strategy-select[data-v-2580a7d9]{width:100%;max-width:none}.assign-strategy-drawer-content .assign-strategy-select[data-v-2580a7d9] .in-dropdown-box__container{width:413px}.assign-strategy-drawer .spaced-dot-sep{background-image:linear-gradient(90deg,#91949f 20%,#fff0 0);background-position:center bottom;background-repeat:repeat-x;background-size:5px 1px}.assign-strategy-drawer .spaced-dot-sep--top{background-position:center top}.assign-strategy-drawer .spaced-dot-sep--fc-n:first-child{background:none}
|