@useinsider/guido 3.18.2-beta.ec25841 → 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 +6 -6
- package/dist/components/Guido.vue2.js +72 -70
- package/dist/components/organisms/AutoSaveController.vue2.js +9 -8
- package/dist/components/organisms/extensions/recommendation/AssignStrategyDrawer.vue.js +11 -13
- package/dist/components/organisms/extensions/recommendation/AssignStrategyDrawer.vue2.js +52 -70
- package/dist/components/organisms/extensions/recommendation/RemoveStrategyModal.vue2.js +37 -23
- 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/onboarding/OnboardingWrapper.vue2.js +18 -20
- package/dist/components/organisms/save-as-template/SaveAsTemplateDrawer.vue2.js +34 -34
- 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/useCustomInterfaceAppearance.js +46 -56
- package/dist/composables/useHtmlCompiler.js +37 -26
- package/dist/composables/useHtmlValidator.js +81 -84
- package/dist/composables/useHttp.js +24 -22
- package/dist/composables/useRecommendation.js +35 -40
- package/dist/composables/useSave.js +90 -45
- package/dist/composables/useSaveValidation.js +279 -0
- package/dist/composables/useSaveValidationRollout.js +9 -0
- package/dist/composables/useStripo.js +30 -30
- package/dist/composables/validators/useCouponBlockValidator.js +24 -21
- package/dist/composables/validators/useUnsubscribeBlockValidator.js +34 -27
- package/dist/enums/extensions/recommendationBlock.js +31 -38
- package/dist/enums/save-validation.js +4 -0
- package/dist/extensions/Blocks/Recommendation/block.js +39 -43
- package/dist/extensions/Blocks/Recommendation/constants/defaultConfig.js +20 -21
- package/dist/extensions/Blocks/Recommendation/controls/main/index.js +33 -38
- package/dist/extensions/Blocks/Recommendation/controls/main/strategy.js +52 -84
- package/dist/extensions/Blocks/Recommendation/store/recommendation.js +78 -168
- package/dist/extensions/Blocks/Recommendation/validation/requiredFields.js +12 -21
- package/dist/guido.css +1 -1
- package/dist/services/templateLibraryApi.js +17 -14
- 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/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/extensions/recommendationBlock.d.ts +0 -2
- package/dist/src/enums/save-validation.d.ts +27 -0
- package/dist/src/extensions/Blocks/Recommendation/constants/defaultConfig.d.ts +0 -1
- package/dist/src/extensions/Blocks/Recommendation/constants/index.d.ts +1 -1
- package/dist/src/extensions/Blocks/Recommendation/controls/main/index.d.ts +0 -2
- package/dist/src/extensions/Blocks/Recommendation/controls/main/strategy.d.ts +0 -9
- package/dist/src/extensions/Blocks/Recommendation/store/recommendation.d.ts +3 -73
- package/dist/src/extensions/Blocks/Recommendation/validation/requiredFields.d.ts +0 -4
- package/dist/src/stores/config.d.ts +30 -0
- package/dist/src/stores/onboarding.d.ts +0 -377
- package/dist/src/stores/save-validation.d.ts +22 -0
- package/dist/src/utils/genericUtil.d.ts +6 -0
- package/dist/src/utils/liquidDynamicContent.d.ts +20 -0
- package/dist/src/utils/templatePreparation.d.ts +30 -0
- package/dist/static/styles/components/recommendation-strategy.css.js +4 -34
- package/dist/stores/config.js +39 -22
- package/dist/stores/onboarding.js +36 -41
- package/dist/stores/save-validation.js +30 -0
- package/dist/utils/genericUtil.js +63 -54
- package/dist/utils/liquidDynamicContent.js +15 -0
- package/dist/utils/templatePreparation.js +63 -59
- package/package.json +1 -1
- package/dist/components/organisms/onboarding/RecommendationStrategyOnboarding.vue.js +0 -21
- package/dist/components/organisms/onboarding/RecommendationStrategyOnboarding.vue2.js +0 -47
- package/dist/extensions/Blocks/Recommendation/utils/strategyDetach.js +0 -19
- package/dist/src/extensions/Blocks/Recommendation/utils/strategyDetach.d.ts +0 -12
- package/dist/static/styles/components/skeleton.css.js +0 -23
- /package/dist/src/components/organisms/{onboarding/RecommendationStrategyOnboarding.vue.d.ts → validation/ValidationErrorDrawer.vue.d.ts} +0 -0
|
@@ -0,0 +1,20 @@
|
|
|
1
|
+
import type { BaseDynamicContent } from '@@/Types/generic';
|
|
2
|
+
export type DynamicContentFormat = NonNullable<BaseDynamicContent['format']>;
|
|
3
|
+
/** Format key the dynamic-content picker sends for a custom date/time format. */
|
|
4
|
+
export declare const TIME_FORMAT_KEY = "time-format";
|
|
5
|
+
/** Wraps a Liquid filter argument in whichever quote style the value itself does not use. */
|
|
6
|
+
export declare const quoteArgument: (value: string) => string | null;
|
|
7
|
+
/**
|
|
8
|
+
* `{ key: 'time-format', value: '%Y-%m-%d' }` -> `date: "%Y-%m-%d"`.
|
|
9
|
+
*
|
|
10
|
+
* Only a custom date/time strftime pattern has a Liquid equivalent. Anything else returns null so
|
|
11
|
+
* the caller emits a plain tag rather than one that silently lost — or literally printed — its
|
|
12
|
+
* format.
|
|
13
|
+
* @example formatToLiquidFilter({ key: 'time-format', value: '%b %-d, %Y' }) -> date: "%b %-d, %Y"
|
|
14
|
+
*/
|
|
15
|
+
export declare const formatToLiquidFilter: (format: DynamicContentFormat) => string | null;
|
|
16
|
+
/**
|
|
17
|
+
* Inverse of `formatToLiquidFilter` — reads the picker format back out of one filter segment, so a
|
|
18
|
+
* reopened tag restores its selection in the host's format dropdown.
|
|
19
|
+
*/
|
|
20
|
+
export declare const liquidFilterToFormat: (segment: string) => DynamicContentFormat | null;
|
|
@@ -15,6 +15,36 @@ import type { SavedTemplateDetails } from '@@/Types/stripo';
|
|
|
15
15
|
* same source), so it is reliably present regardless of how the block was added.
|
|
16
16
|
*/
|
|
17
17
|
export declare function getHtmlReferencedUnsubscribePages(html: string): number[];
|
|
18
|
+
/**
|
|
19
|
+
* Hydrates the recommendation extension store from the persisted `esd-ext-config`
|
|
20
|
+
* JSON blob on each `.recommendation-block-v2` element in the raw editor HTML.
|
|
21
|
+
*
|
|
22
|
+
* Why this runs before `compileHtml`:
|
|
23
|
+
* The HTML compiler's `prepareRecommendationBlocks` rule asks
|
|
24
|
+
* `useRecommendation.buildCampaignUrl(id)` to assemble each block's API URL
|
|
25
|
+
* from `blockStates[id].recommendationConfigs`. That Pinia entry is normally
|
|
26
|
+
* populated by `RecommendationBlockControl._syncNodeConfigToStore`, which
|
|
27
|
+
* only fires when the user *selects* the block. Saving without ever
|
|
28
|
+
* selecting a migrated block would otherwise build the URL from empty/
|
|
29
|
+
* default state and the campaign URL would not be saved.
|
|
30
|
+
*
|
|
31
|
+
* Why we read raw HTML, not compiled HTML:
|
|
32
|
+
* Stripo's `compileEmail()` strips editor-only attributes (`esd-*`) from the
|
|
33
|
+
* compiled output, so `esd-ext-config` is gone by the time the compiler
|
|
34
|
+
* pipeline sees the HTML. The raw HTML from `getTemplateData()` preserves
|
|
35
|
+
* the attribute as the migrator wrote it.
|
|
36
|
+
*
|
|
37
|
+
* Reference data pre-load:
|
|
38
|
+
* When the template has recommendation blocks, this also pre-loads the
|
|
39
|
+
* shared reference data (languages / currency list) so the save-time
|
|
40
|
+
* required-fields validator can check each block's locale and currency
|
|
41
|
+
* against the partner's real options. Best-effort — on a fetch failure the
|
|
42
|
+
* validator degrades to its empty-list guard (`requiredFields.ts`) instead
|
|
43
|
+
* of blocking the save or stranding the Save button.
|
|
44
|
+
*/
|
|
45
|
+
declare function hydrateRecommendationStoreFromRawHtml(rawHtml: string): Promise<void>;
|
|
18
46
|
export declare const useTemplatePreparation: () => {
|
|
19
47
|
prepareTemplateDetails: () => Promise<Omit<SavedTemplateDetails, "metadata">>;
|
|
48
|
+
hydrateRecommendationStore: typeof hydrateRecommendationStoreFromRawHtml;
|
|
20
49
|
};
|
|
50
|
+
export {};
|
|
@@ -49,8 +49,11 @@ const n = `.strategy-control-header {
|
|
|
49
49
|
white-space: nowrap;
|
|
50
50
|
}
|
|
51
51
|
|
|
52
|
-
.strategy-control-cta.primary > .button
|
|
52
|
+
.strategy-control-cta.primary > .button:disabled,
|
|
53
|
+
.strategy-control-cta.primary > .button.disabled {
|
|
54
|
+
opacity: 1;
|
|
53
55
|
color: var(--guido-color-gray-800);
|
|
56
|
+
cursor: default;
|
|
54
57
|
}
|
|
55
58
|
|
|
56
59
|
.strategy-control-name-band {
|
|
@@ -68,39 +71,6 @@ const n = `.strategy-control-header {
|
|
|
68
71
|
line-height: 24px;
|
|
69
72
|
}
|
|
70
73
|
|
|
71
|
-
/* Each skeleton mirrors the footprint of the element it stands in for, so retiring
|
|
72
|
-
the loading state does not shift the panel. */
|
|
73
|
-
.guido-skeleton--strategy-title {
|
|
74
|
-
width: 366px;
|
|
75
|
-
height: 38px;
|
|
76
|
-
}
|
|
77
|
-
|
|
78
|
-
.guido-skeleton--strategy-description {
|
|
79
|
-
width: 366px;
|
|
80
|
-
height: 48px;
|
|
81
|
-
}
|
|
82
|
-
|
|
83
|
-
.guido-skeleton--strategy-cta {
|
|
84
|
-
width: 175px;
|
|
85
|
-
height: 40px;
|
|
86
|
-
}
|
|
87
|
-
|
|
88
|
-
.guido-skeleton--strategy-name {
|
|
89
|
-
width: 398px;
|
|
90
|
-
height: 48px;
|
|
91
|
-
}
|
|
92
|
-
|
|
93
|
-
.strategy-control-skeleton-row {
|
|
94
|
-
display: flex;
|
|
95
|
-
gap: 16px;
|
|
96
|
-
padding: 0 16px 16px;
|
|
97
|
-
}
|
|
98
|
-
|
|
99
|
-
[data-strategy-loading-state] .guido-skeleton {
|
|
100
|
-
display: block;
|
|
101
|
-
}
|
|
102
|
-
|
|
103
|
-
|
|
104
74
|
.strategy-control-actions {
|
|
105
75
|
display: flex;
|
|
106
76
|
align-items: center;
|
package/dist/stores/config.js
CHANGED
|
@@ -1,8 +1,8 @@
|
|
|
1
|
-
import "../@types/config/schemas.js";
|
|
1
|
+
import { MessageType as r } from "../@types/config/schemas.js";
|
|
2
2
|
import "../@types/config/defaults.js";
|
|
3
3
|
import { parseConfig as o } from "../@types/config/validator.js";
|
|
4
|
-
import { defineStore as
|
|
5
|
-
const
|
|
4
|
+
import { defineStore as a } from "pinia";
|
|
5
|
+
const u = a("guido-config", {
|
|
6
6
|
state: () => ({
|
|
7
7
|
initialized: !1,
|
|
8
8
|
config: null
|
|
@@ -75,57 +75,74 @@ const f = r("guido-config", {
|
|
|
75
75
|
* Get the template ID
|
|
76
76
|
*/
|
|
77
77
|
templateId: (i) => {
|
|
78
|
-
var e,
|
|
79
|
-
return ((
|
|
78
|
+
var e, t;
|
|
79
|
+
return ((t = (e = i.config) == null ? void 0 : e.identity) == null ? void 0 : t.templateId) ?? "";
|
|
80
80
|
},
|
|
81
81
|
/**
|
|
82
82
|
* Get the user ID
|
|
83
83
|
*/
|
|
84
84
|
userId: (i) => {
|
|
85
|
-
var e,
|
|
86
|
-
return ((
|
|
85
|
+
var e, t;
|
|
86
|
+
return ((t = (e = i.config) == null ? void 0 : e.identity) == null ? void 0 : t.userId) ?? "";
|
|
87
87
|
},
|
|
88
88
|
/**
|
|
89
89
|
* Get the variation ID
|
|
90
90
|
*/
|
|
91
91
|
variationId: (i) => {
|
|
92
|
-
var e,
|
|
93
|
-
return ((
|
|
92
|
+
var e, t;
|
|
93
|
+
return ((t = (e = i.config) == null ? void 0 : e.identity) == null ? void 0 : t.variationId) ?? "";
|
|
94
94
|
},
|
|
95
95
|
/**
|
|
96
96
|
* Get the partner name
|
|
97
97
|
*/
|
|
98
98
|
partnerName: (i) => {
|
|
99
|
-
var e,
|
|
100
|
-
return ((
|
|
99
|
+
var e, t;
|
|
100
|
+
return ((t = (e = i.config) == null ? void 0 : e.partner) == null ? void 0 : t.name) ?? "";
|
|
101
101
|
},
|
|
102
102
|
/**
|
|
103
103
|
* Get the product type
|
|
104
104
|
*/
|
|
105
105
|
productType: (i) => {
|
|
106
|
-
var e,
|
|
107
|
-
return ((
|
|
106
|
+
var e, t;
|
|
107
|
+
return ((t = (e = i.config) == null ? void 0 : e.partner) == null ? void 0 : t.productType) ?? 60;
|
|
108
108
|
},
|
|
109
109
|
/**
|
|
110
110
|
* Get the message type
|
|
111
111
|
*/
|
|
112
112
|
messageType: (i) => {
|
|
113
|
-
var e,
|
|
114
|
-
return ((
|
|
113
|
+
var e, t;
|
|
114
|
+
return ((t = (e = i.config) == null ? void 0 : e.partner) == null ? void 0 : t.messageType) ?? 1;
|
|
115
|
+
},
|
|
116
|
+
/**
|
|
117
|
+
* Transactional campaigns keep the hard save block. Reactive getter, so
|
|
118
|
+
* consumers stay safe in setup where a raw config read snapshots null (SD-147945).
|
|
119
|
+
*/
|
|
120
|
+
isTransactional() {
|
|
121
|
+
return this.messageType === r.TRANSACTIONAL;
|
|
122
|
+
},
|
|
123
|
+
/**
|
|
124
|
+
* Soft-save policy: may the editor persist a template with validation errors?
|
|
125
|
+
* Default true (host sets features.allowSaveWithErrors=false for transactional +
|
|
126
|
+
* unsub). Reactive getter defaulting true — reading via isFeatureEnabled would
|
|
127
|
+
* floor to false pre-init and momentarily hide the soft-save option (SD-147430).
|
|
128
|
+
*/
|
|
129
|
+
allowSaveWithErrors() {
|
|
130
|
+
var i;
|
|
131
|
+
return ((i = this.features) == null ? void 0 : i.allowSaveWithErrors) ?? !0;
|
|
115
132
|
},
|
|
116
133
|
/**
|
|
117
134
|
* Get the username
|
|
118
135
|
*/
|
|
119
136
|
username: (i) => {
|
|
120
|
-
var e,
|
|
121
|
-
return ((
|
|
137
|
+
var e, t;
|
|
138
|
+
return ((t = (e = i.config) == null ? void 0 : e.partner) == null ? void 0 : t.username) ?? "Guido User";
|
|
122
139
|
},
|
|
123
140
|
/**
|
|
124
141
|
* Check if header should be shown
|
|
125
142
|
*/
|
|
126
143
|
showHeader: (i) => {
|
|
127
|
-
var e,
|
|
128
|
-
return ((
|
|
144
|
+
var e, t;
|
|
145
|
+
return ((t = (e = i.config) == null ? void 0 : e.ui) == null ? void 0 : t.showHeader) ?? !0;
|
|
129
146
|
},
|
|
130
147
|
/**
|
|
131
148
|
* Check if a specific feature is enabled.
|
|
@@ -134,8 +151,8 @@ const f = r("guido-config", {
|
|
|
134
151
|
*/
|
|
135
152
|
// eslint-disable-next-line @stylistic/max-len
|
|
136
153
|
isFeatureEnabled: (i) => (e) => {
|
|
137
|
-
var
|
|
138
|
-
return ((
|
|
154
|
+
var t, n;
|
|
155
|
+
return ((n = (t = i.config) == null ? void 0 : t.features) == null ? void 0 : n[e]) ?? !1;
|
|
139
156
|
}
|
|
140
157
|
},
|
|
141
158
|
actions: {
|
|
@@ -155,5 +172,5 @@ const f = r("guido-config", {
|
|
|
155
172
|
}
|
|
156
173
|
});
|
|
157
174
|
export {
|
|
158
|
-
|
|
175
|
+
u as useConfigStore
|
|
159
176
|
};
|
|
@@ -1,5 +1,5 @@
|
|
|
1
|
-
import { useOnboardingApi as
|
|
2
|
-
import { defineStore as
|
|
1
|
+
import { useOnboardingApi as s } from "../services/onboardingApi.js";
|
|
2
|
+
import { defineStore as e } from "pinia";
|
|
3
3
|
const t = () => ({
|
|
4
4
|
cardIndex: 0,
|
|
5
5
|
isActive: !1,
|
|
@@ -11,54 +11,49 @@ const t = () => ({
|
|
|
11
11
|
textBlockOnboarding: t(),
|
|
12
12
|
versionHistoryOnboarding: t(),
|
|
13
13
|
ampOnboarding: t(),
|
|
14
|
-
itemsOnboarding: t()
|
|
15
|
-
recommendationStrategyOnboarding: t()
|
|
14
|
+
itemsOnboarding: t()
|
|
16
15
|
},
|
|
17
16
|
userModalState: {},
|
|
18
17
|
isFetched: !1
|
|
19
|
-
}), c =
|
|
18
|
+
}), c = e("guidoOnboarding", {
|
|
20
19
|
state: () => a(),
|
|
21
20
|
getters: {
|
|
22
|
-
getOnboarding: (n) => (
|
|
23
|
-
isActive: (n) => (
|
|
24
|
-
getCurrentCard: (n) => (
|
|
25
|
-
const
|
|
26
|
-
return
|
|
21
|
+
getOnboarding: (n) => (i) => n.onboardings[i],
|
|
22
|
+
isActive: (n) => (i) => n.onboardings[i].isActive,
|
|
23
|
+
getCurrentCard: (n) => (i) => {
|
|
24
|
+
const o = n.onboardings[i];
|
|
25
|
+
return o.config[o.cardIndex];
|
|
27
26
|
},
|
|
28
27
|
getGenericCurrentCard: (n) => {
|
|
29
|
-
const { genericOnboarding:
|
|
30
|
-
return
|
|
28
|
+
const { genericOnboarding: i } = n.onboardings;
|
|
29
|
+
return i.config[i.cardIndex];
|
|
31
30
|
},
|
|
32
31
|
getTextBlockCurrentCard: (n) => {
|
|
33
|
-
const { textBlockOnboarding:
|
|
34
|
-
return
|
|
32
|
+
const { textBlockOnboarding: i } = n.onboardings;
|
|
33
|
+
return i.config[i.cardIndex];
|
|
35
34
|
},
|
|
36
35
|
getVersionHistoryCurrentCard: (n) => {
|
|
37
|
-
const { versionHistoryOnboarding:
|
|
38
|
-
return
|
|
36
|
+
const { versionHistoryOnboarding: i } = n.onboardings;
|
|
37
|
+
return i.config[i.cardIndex];
|
|
39
38
|
},
|
|
40
39
|
getAmpCurrentCard: (n) => {
|
|
41
|
-
const { ampOnboarding:
|
|
42
|
-
return
|
|
40
|
+
const { ampOnboarding: i } = n.onboardings;
|
|
41
|
+
return i.config[i.cardIndex];
|
|
43
42
|
},
|
|
44
43
|
getItemsCurrentCard: (n) => {
|
|
45
|
-
const { itemsOnboarding:
|
|
46
|
-
return
|
|
47
|
-
},
|
|
48
|
-
getRecommendationStrategyCurrentCard: (n) => {
|
|
49
|
-
const { recommendationStrategyOnboarding: o } = n.onboardings;
|
|
50
|
-
return o.config[o.cardIndex];
|
|
44
|
+
const { itemsOnboarding: i } = n.onboardings;
|
|
45
|
+
return i.config[i.cardIndex];
|
|
51
46
|
},
|
|
52
|
-
shouldShowOnboarding: (n) => (
|
|
53
|
-
const
|
|
54
|
-
return
|
|
47
|
+
shouldShowOnboarding: (n) => (i) => {
|
|
48
|
+
const o = n.userModalState.Guido;
|
|
49
|
+
return i === "newVersionPopup" && (o != null && o.genericOnboarding) ? !1 : o ? !o[i] : !0;
|
|
55
50
|
}
|
|
56
51
|
},
|
|
57
52
|
actions: {
|
|
58
53
|
closeOtherOnboardings(n) {
|
|
59
|
-
Object.keys(this.onboardings).forEach((
|
|
60
|
-
const
|
|
61
|
-
|
|
54
|
+
Object.keys(this.onboardings).forEach((i) => {
|
|
55
|
+
const o = i;
|
|
56
|
+
o !== n && this.onboardings[o].isActive && (this.onboardings[o].isActive = !1, this.onboardings[o].cardIndex = 0, this.onboardings[o].config = []);
|
|
62
57
|
});
|
|
63
58
|
},
|
|
64
59
|
start(n) {
|
|
@@ -76,12 +71,12 @@ const t = () => ({
|
|
|
76
71
|
previous(n) {
|
|
77
72
|
this.onboardings[n].cardIndex > 0 && this.onboardings[n].cardIndex--;
|
|
78
73
|
},
|
|
79
|
-
updateCardPosition(n,
|
|
80
|
-
const r = this.onboardings[n].config[
|
|
81
|
-
r && (r.top =
|
|
74
|
+
updateCardPosition(n, i, o) {
|
|
75
|
+
const r = this.onboardings[n].config[i];
|
|
76
|
+
r && (r.top = o.top, r.position = o.position);
|
|
82
77
|
},
|
|
83
|
-
setConfig(n,
|
|
84
|
-
this.onboardings[n].config =
|
|
78
|
+
setConfig(n, i) {
|
|
79
|
+
this.onboardings[n].config = i ?? [], this.onboardings[n].cardIndex >= this.onboardings[n].config.length && (this.onboardings[n].cardIndex = 0);
|
|
85
80
|
},
|
|
86
81
|
async onDiscoverNowClicked() {
|
|
87
82
|
await this.setUserModalState("newVersionPopup", "true", "Guido"), await this.setUserModalState("genericOnboarding", "true", "Guido"), this.start("genericOnboarding");
|
|
@@ -98,16 +93,16 @@ const t = () => ({
|
|
|
98
93
|
async fetchUserModalState() {
|
|
99
94
|
if (this.isFetched)
|
|
100
95
|
return;
|
|
101
|
-
const { fetchUserModalState: n } =
|
|
96
|
+
const { fetchUserModalState: n } = s();
|
|
102
97
|
try {
|
|
103
|
-
const
|
|
104
|
-
this.userModalState =
|
|
98
|
+
const i = await n();
|
|
99
|
+
this.userModalState = i, this.isFetched = !0;
|
|
105
100
|
} catch {
|
|
106
101
|
}
|
|
107
102
|
},
|
|
108
|
-
async setUserModalState(n,
|
|
109
|
-
const { setUserModalState: r } =
|
|
110
|
-
await r(n,
|
|
103
|
+
async setUserModalState(n, i, o) {
|
|
104
|
+
const { setUserModalState: r } = s();
|
|
105
|
+
await r(n, i, o), this.isFetched = !1, await this.fetchUserModalState();
|
|
111
106
|
}
|
|
112
107
|
}
|
|
113
108
|
});
|
|
@@ -0,0 +1,30 @@
|
|
|
1
|
+
import { defineStore as n } from "pinia";
|
|
2
|
+
function i(e) {
|
|
3
|
+
const t = /* @__PURE__ */ new Set();
|
|
4
|
+
return e.filter((r) => {
|
|
5
|
+
const s = JSON.stringify([r.rule, r.message, r.detail ?? ""]);
|
|
6
|
+
return t.has(s) ? !1 : (t.add(s), !0);
|
|
7
|
+
});
|
|
8
|
+
}
|
|
9
|
+
const o = n("guidoSaveValidation", {
|
|
10
|
+
state: () => ({
|
|
11
|
+
errors: [],
|
|
12
|
+
isDrawerOpen: !1,
|
|
13
|
+
intent: null
|
|
14
|
+
}),
|
|
15
|
+
getters: {
|
|
16
|
+
errorCount: (e) => e.errors.length
|
|
17
|
+
},
|
|
18
|
+
actions: {
|
|
19
|
+
open(e, t) {
|
|
20
|
+
this.errors = i(e), this.intent = t, this.isDrawerOpen = !0;
|
|
21
|
+
},
|
|
22
|
+
// Errors are retained so rows don't blank during the ~300ms close animation.
|
|
23
|
+
close() {
|
|
24
|
+
this.isDrawerOpen = !1;
|
|
25
|
+
}
|
|
26
|
+
}
|
|
27
|
+
});
|
|
28
|
+
export {
|
|
29
|
+
o as useSaveValidationStore
|
|
30
|
+
};
|
|
@@ -1,69 +1,78 @@
|
|
|
1
|
-
|
|
2
|
-
|
|
1
|
+
import { formatToLiquidFilter as b, quoteArgument as y, liquidFilterToFormat as h } from "./liquidDynamicContent.js";
|
|
2
|
+
const g = (t) => {
|
|
3
|
+
if (!t.includes("="))
|
|
4
|
+
return null;
|
|
5
|
+
const [r, e] = t.split("=");
|
|
6
|
+
return { key: r.trim(), value: e.trim() };
|
|
7
|
+
}, c = "default:", f = (t) => {
|
|
8
|
+
if (!t.startsWith(c))
|
|
9
|
+
return t;
|
|
10
|
+
const r = t.slice(c.length).trim(), e = (l) => r.length >= 2 && r.startsWith(l) && r.endsWith(l);
|
|
11
|
+
return e('"') || e("'") ? r.slice(1, -1) : r;
|
|
12
|
+
}, k = (t) => {
|
|
13
|
+
const e = t.value.match(/\{\{([^}]+)\}\}/)[1].split("|").map((a) => a.trim()), [l] = e, s = {
|
|
3
14
|
text: t.label,
|
|
4
|
-
value:
|
|
15
|
+
value: l || ""
|
|
5
16
|
};
|
|
6
|
-
if (
|
|
7
|
-
const [,
|
|
8
|
-
if (
|
|
9
|
-
|
|
10
|
-
|
|
11
|
-
|
|
12
|
-
|
|
13
|
-
n ? r.format = n : e || (r.fallback = l), e && (r.fallback = e);
|
|
17
|
+
if (e.length >= 2) {
|
|
18
|
+
const [, a, n] = e;
|
|
19
|
+
if (a.startsWith(c))
|
|
20
|
+
s.fallback = f(a);
|
|
21
|
+
else {
|
|
22
|
+
const o = h(a) ?? g(a);
|
|
23
|
+
o ? s.format = o : n || (s.fallback = a), n && (s.fallback = f(n));
|
|
14
24
|
}
|
|
15
25
|
}
|
|
16
|
-
return
|
|
17
|
-
},
|
|
18
|
-
|
|
19
|
-
|
|
20
|
-
|
|
21
|
-
|
|
22
|
-
};
|
|
23
|
-
if (c) {
|
|
24
|
-
if (!a.fallback)
|
|
25
|
-
return {
|
|
26
|
-
label: a.text,
|
|
27
|
-
value: `{{ ${a.value} }}`
|
|
28
|
-
};
|
|
29
|
-
const r = !Number.isNaN(Number(a.fallback)) && a.fallback.trim() !== "" ? a.fallback : `"${a.fallback}"`;
|
|
30
|
-
return {
|
|
31
|
-
label: `${a.text} | ${a.fallback}`,
|
|
32
|
-
value: `{{ ${a.value} | default: ${r} }}`
|
|
33
|
-
};
|
|
34
|
-
}
|
|
26
|
+
return s;
|
|
27
|
+
}, p = (t) => {
|
|
28
|
+
const e = !Number.isNaN(Number(t)) && t.trim() !== "" ? t : y(t);
|
|
29
|
+
return e === null ? null : `${c} ${e}`;
|
|
30
|
+
}, v = (t) => {
|
|
31
|
+
const r = t.format ? b(t.format) : null, e = t.fallback ? p(t.fallback) : null, l = [t.value, r, e].filter(Boolean);
|
|
35
32
|
return {
|
|
36
|
-
label:
|
|
37
|
-
value:
|
|
33
|
+
label: [t.text, r, e && t.fallback].filter(Boolean).join(" | "),
|
|
34
|
+
value: `{{ ${l.join(" | ")} }}`
|
|
38
35
|
};
|
|
39
|
-
}
|
|
40
|
-
|
|
41
|
-
|
|
42
|
-
|
|
43
|
-
|
|
44
|
-
|
|
36
|
+
}, i = (t, r = !1) => t.map((e) => r ? v(e) : e.format ? {
|
|
37
|
+
label: `${e.text} | ${e.format.key}=${e.format.value}`,
|
|
38
|
+
value: `{{${e.value}|${e.format.key}=${e.format.value}}}`
|
|
39
|
+
} : {
|
|
40
|
+
label: e.fallback ? `${e.text} | ${e.fallback}` : e.text,
|
|
41
|
+
value: e.fallback ? `{{${e.value}|${e.fallback}}}` : `{{${e.value}}}`
|
|
42
|
+
}), $ = (t) => {
|
|
43
|
+
const r = [], e = /* @__PURE__ */ new Set(), l = (a) => {
|
|
44
|
+
Array.isArray(a) && a.forEach((n) => {
|
|
45
|
+
const o = [...n.children ?? [], ...n.select_items ?? []];
|
|
46
|
+
if (o.length > 0) {
|
|
47
|
+
l(o);
|
|
45
48
|
return;
|
|
46
49
|
}
|
|
47
|
-
const u =
|
|
48
|
-
u &&
|
|
50
|
+
const u = n.text || n.tag_text;
|
|
51
|
+
u && n.value && !e.has(n.value) && (e.add(n.value), r.push({ text: u, value: n.value }));
|
|
49
52
|
});
|
|
50
|
-
}, [
|
|
51
|
-
return s
|
|
52
|
-
},
|
|
53
|
-
const
|
|
53
|
+
}, [s] = Object.values(t ?? {});
|
|
54
|
+
return l(s), r;
|
|
55
|
+
}, d = (t, r, e = !1) => {
|
|
56
|
+
const l = new Set(t.map((a) => a.value)), s = r.filter((a) => l.has(a.value) ? !1 : (l.add(a.value), !0));
|
|
54
57
|
return [
|
|
55
|
-
...
|
|
56
|
-
...
|
|
58
|
+
...i(t, e),
|
|
59
|
+
...i(s, e)
|
|
57
60
|
];
|
|
58
|
-
},
|
|
61
|
+
}, F = () => {
|
|
59
62
|
var t;
|
|
60
63
|
return ((t = document.head.querySelector('meta[name="csrf-token"]')) == null ? void 0 : t.getAttribute("content")) ?? "";
|
|
61
|
-
},
|
|
64
|
+
}, T = (t) => typeof t == "string" ? t : typeof t == "number" ? String(t) : "", x = (t) => {
|
|
65
|
+
if (t === null || typeof t != "object" || Array.isArray(t))
|
|
66
|
+
return !1;
|
|
67
|
+
const r = Object.getPrototypeOf(t);
|
|
68
|
+
return r === Object.prototype || r === null;
|
|
69
|
+
};
|
|
62
70
|
export {
|
|
63
|
-
|
|
64
|
-
|
|
65
|
-
|
|
66
|
-
|
|
67
|
-
|
|
68
|
-
|
|
71
|
+
T as asText,
|
|
72
|
+
d as buildMergeTagEntries,
|
|
73
|
+
i as dynamicContentToMergeTags,
|
|
74
|
+
$ as flattenDynamicContentList,
|
|
75
|
+
F as getCsrfToken,
|
|
76
|
+
x as isPlainObject,
|
|
77
|
+
k as mergeTagToDynamicContent
|
|
69
78
|
};
|
|
@@ -0,0 +1,15 @@
|
|
|
1
|
+
const E = "time-format", r = "date", u = new RegExp(`^${r}\\s*:\\s*(?:"([^"]*)"|'([^']*)')$`), s = /%[-_0^#]?\d*[a-zA-Z%]/, c = new RegExp(s, "g"), l = /\b(?:Y{2,4}|M{2,4}|D{1,4}|d{3,4}|H{2}|h{2}|m{2}|s{2}|S{1,3}|A|a)\b/, T = (t) => t.includes('"') ? t.includes("'") ? null : `'${t}'` : `"${t}"`, i = (t) => s.test(t) && !l.test(t.replace(c, "")), R = (t) => {
|
|
2
|
+
if (t.key !== E || !i(t.value ?? ""))
|
|
3
|
+
return null;
|
|
4
|
+
const n = T(t.value);
|
|
5
|
+
return n === null ? null : `${r}: ${n}`;
|
|
6
|
+
}, _ = (t) => {
|
|
7
|
+
const [, n, o] = t.match(u) ?? [], e = n ?? o;
|
|
8
|
+
return e ? { key: E, value: e } : null;
|
|
9
|
+
};
|
|
10
|
+
export {
|
|
11
|
+
E as TIME_FORMAT_KEY,
|
|
12
|
+
R as formatToLiquidFilter,
|
|
13
|
+
_ as liquidFilterToFormat,
|
|
14
|
+
T as quoteArgument
|
|
15
|
+
};
|