@useinsider/guido 3.21.2-beta.4c14c74 → 3.21.2-beta.5a809f7
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/dist/config/compiler/utils/recommendationCompilerUtils.js +22 -22
- package/dist/config/migrator/recommendation/compositionMapper.js +56 -49
- package/dist/config/migrator/recommendation/extractors.js +74 -26
- package/dist/config/migrator/recommendation/htmlBuilder.js +279 -202
- package/dist/config/migrator/recommendation/settingsMapper.js +37 -36
- package/dist/config/migrator/recommendationMigrator.js +65 -59
- package/dist/extensions/Blocks/Items/controls/button/link.js +17 -14
- package/dist/extensions/Blocks/Items/controls/cardComposition.js +17 -14
- package/dist/extensions/Blocks/Items/controls/image/link.js +17 -14
- package/dist/extensions/Blocks/Items/controls/name/trimming.js +10 -9
- package/dist/extensions/Blocks/Items/controls/price/currencyLocation.js +25 -24
- package/dist/extensions/Blocks/Items/controls/price/currencySymbol.js +13 -12
- package/dist/extensions/Blocks/Items/controls/price/formattedPrice.js +30 -29
- package/dist/extensions/Blocks/Items/controls/price/hideDiscount.js +16 -15
- package/dist/extensions/Blocks/Items/controls/price/priceOrientation.js +26 -25
- package/dist/extensions/Blocks/Items/controls/price/singlePrice.js +28 -27
- package/dist/extensions/Blocks/Items/controls/settingsControl.js +80 -75
- package/dist/extensions/Blocks/Recommendation/block.js +33 -24
- package/dist/extensions/Blocks/Recommendation/controls/cardBackground/index.js +3 -3
- package/dist/extensions/Blocks/Recommendation/controls/cardComposition/index.js +27 -26
- package/dist/extensions/Blocks/Recommendation/controls/customAttribute/textTrim.js +13 -13
- package/dist/extensions/Blocks/Recommendation/controls/main/index.js +216 -236
- package/dist/extensions/Blocks/Recommendation/controls/name/textTrim.js +5 -5
- package/dist/extensions/Blocks/Recommendation/controls/omnibusDiscount/textAfter.js +8 -8
- package/dist/extensions/Blocks/Recommendation/controls/omnibusDiscount/textBefore.js +15 -15
- package/dist/extensions/Blocks/Recommendation/controls/omnibusPrice/textAfter.js +12 -12
- package/dist/extensions/Blocks/Recommendation/controls/omnibusPrice/textBefore.js +10 -10
- package/dist/extensions/Blocks/Recommendation/controls/spacing/index.js +1 -1
- package/dist/extensions/Blocks/Recommendation/templates/grid/template.js +23 -22
- package/dist/extensions/Blocks/Recommendation/templates/list/template.js +19 -18
- package/dist/extensions/Blocks/Recommendation/templates/utils.js +82 -91
- package/dist/extensions/Blocks/Recommendation/utils/inlinePriceOrder.js +12 -0
- package/dist/extensions/Blocks/Recommendation/utils/legacyStrategyMap.js +3 -2
- package/dist/extensions/Blocks/common-control.js +55 -62
- package/dist/src/config/migrator/recommendation/compositionMapper.d.ts +3 -1
- package/dist/src/config/migrator/recommendation/extractors.d.ts +26 -0
- package/dist/src/extensions/Blocks/Items/controls/cardComposition.d.ts +1 -0
- package/dist/src/extensions/Blocks/Recommendation/block.d.ts +1 -0
- package/dist/src/extensions/Blocks/Recommendation/controls/main/index.d.ts +4 -11
- package/dist/src/extensions/Blocks/Recommendation/templates/utils.d.ts +1 -13
- package/dist/src/extensions/Blocks/Recommendation/utils/inlinePriceOrder.d.ts +9 -0
- package/dist/src/extensions/Blocks/Recommendation/utils/legacyStrategyMap.d.ts +2 -19
- package/dist/src/extensions/Blocks/common-control.d.ts +0 -2
- package/package.json +1 -1
|
@@ -1,79 +1,80 @@
|
|
|
1
|
-
var
|
|
2
|
-
var
|
|
3
|
-
var
|
|
4
|
-
import { useConfig as
|
|
5
|
-
import { ModificationDescription as
|
|
6
|
-
import { CommonControl as
|
|
7
|
-
import { RRS_CONFIG_VERSION as
|
|
8
|
-
import { RECOMMENDATION_ID_ATTR as
|
|
9
|
-
import { RecommendationConfigService as
|
|
10
|
-
import { useRecommendationExtensionStore as
|
|
11
|
-
import { refreshBlockOutsidePanel as
|
|
12
|
-
import {
|
|
1
|
+
var y = Object.defineProperty;
|
|
2
|
+
var P = (u, c, e) => c in u ? y(u, c, { enumerable: !0, configurable: !0, writable: !0, value: e }) : u[c] = e;
|
|
3
|
+
var r = (u, c, e) => P(u, typeof c != "symbol" ? c + "" : c, e);
|
|
4
|
+
import { useConfig as f } from "../../../../../composables/useConfig.js";
|
|
5
|
+
import { ModificationDescription as R } from "../../../../../node_modules/@stripoinc/ui-editor-extensions/dist/esm/index.js";
|
|
6
|
+
import { CommonControl as I } from "../../../common-control.js";
|
|
7
|
+
import { RRS_CONFIG_VERSION as k, DEFAULT_NODE_CONFIG as m } from "../../constants/defaultConfig.js";
|
|
8
|
+
import { RECOMMENDATION_ID_ATTR as S } from "../../constants/selectors.js";
|
|
9
|
+
import { RecommendationConfigService as d } from "../../services/configService.js";
|
|
10
|
+
import { useRecommendationExtensionStore as T } from "../../store/recommendation.js";
|
|
11
|
+
import { refreshBlockOutsidePanel as O } from "../../utils/blockRefresh.js";
|
|
12
|
+
import { mapLegacyStrategy as C } from "../../utils/legacyStrategyMap.js";
|
|
13
|
+
import { registerNodeConfigWriter as b, writeBlockConfigOutsidePanel as p, hasEditedConfigChange as B, pickConfigDescription as F, isProductIdsChange as D, PRODUCT_IDS_DESCRIPTION as L } from "../../utils/nodeConfigWriter.js";
|
|
13
14
|
import { AlgorithmControl as E } from "./algorithm.js";
|
|
14
|
-
import { ALGORITHM_CONTROL_ID as
|
|
15
|
-
import { CurrencyControl as
|
|
16
|
-
import { CURRENCY_CONTROL_ID as
|
|
17
|
-
import { FiltersControl as
|
|
18
|
-
import { FILTERS_CONTROL_ID as
|
|
19
|
-
import { LayoutOrientationControl as
|
|
20
|
-
import { LAYOUT_ORIENTATION_CONTROL_ID as
|
|
21
|
-
import { LocaleControl as
|
|
22
|
-
import { LOCALE_CONTROL_ID as
|
|
23
|
-
import { PricePlacementControl as
|
|
24
|
-
import { PRICE_PLACEMENT_CONTROL_ID as
|
|
25
|
-
import { ProductCountControl as
|
|
26
|
-
import { PRODUCT_COUNT_CONTROL_ID as
|
|
27
|
-
import { ProductLayoutControl as
|
|
28
|
-
import { PRODUCT_LAYOUT_CONTROL_ID as
|
|
29
|
-
import { ShuffleControl as
|
|
30
|
-
import { SHUFFLE_CONTROL_ID as
|
|
31
|
-
import { StrategyControl as
|
|
32
|
-
import { STRATEGY_CONTROL_ID as
|
|
33
|
-
import { setCurrencyAttributes as
|
|
34
|
-
import { adjustProductsToSize as
|
|
35
|
-
import { useDebounceFn as
|
|
36
|
-
const
|
|
37
|
-
class
|
|
15
|
+
import { ALGORITHM_CONTROL_ID as Pe } from "./algorithm.js";
|
|
16
|
+
import { CurrencyControl as U } from "./currency.js";
|
|
17
|
+
import { CURRENCY_CONTROL_ID as Ie } from "./currency.js";
|
|
18
|
+
import { FiltersControl as v } from "./filters.js";
|
|
19
|
+
import { FILTERS_CONTROL_ID as Se } from "./filters.js";
|
|
20
|
+
import { LayoutOrientationControl as w } from "./layoutOrientation.js";
|
|
21
|
+
import { LAYOUT_ORIENTATION_CONTROL_ID as Oe } from "./layoutOrientation.js";
|
|
22
|
+
import { LocaleControl as A } from "./locale.js";
|
|
23
|
+
import { LOCALE_CONTROL_ID as Be } from "./locale.js";
|
|
24
|
+
import { PricePlacementControl as V } from "./pricePlacement.js";
|
|
25
|
+
import { PRICE_PLACEMENT_CONTROL_ID as De } from "./pricePlacement.js";
|
|
26
|
+
import { ProductCountControl as W } from "./productCount.js";
|
|
27
|
+
import { PRODUCT_COUNT_CONTROL_ID as Ee } from "./productCount.js";
|
|
28
|
+
import { ProductLayoutControl as x } from "./productLayout.js";
|
|
29
|
+
import { PRODUCT_LAYOUT_CONTROL_ID as ve } from "./productLayout.js";
|
|
30
|
+
import { ShuffleControl as M } from "./shuffle.js";
|
|
31
|
+
import { SHUFFLE_CONTROL_ID as Ae } from "./shuffle.js";
|
|
32
|
+
import { StrategyControl as G } from "./strategy.js";
|
|
33
|
+
import { STRATEGY_CONTROL_ID as We } from "./strategy.js";
|
|
34
|
+
import { setCurrencyAttributes as z, getBlockElement as $, isPartnerManagedBlock as H, updateProductContentInPlace as Y, regenerateProductRowsWithStyles as j } from "./utils.js";
|
|
35
|
+
import { adjustProductsToSize as Me, formatProductPrice as Ge, getCardComposition as ze, getCurrentLayout as $e, getMainContainerTbody as He, regenerateMobileProductRows as Ye, updatePricesInPlace as je, updateSingleProductContent as qe } from "./utils.js";
|
|
36
|
+
import { useDebounceFn as _ } from "../../../../../node_modules/@vueuse/shared/index.js";
|
|
37
|
+
const h = "Update recommendation filters", q = "ui-elements-recommendation-block";
|
|
38
|
+
class _e extends I {
|
|
38
39
|
constructor() {
|
|
39
40
|
super(...arguments);
|
|
40
|
-
|
|
41
|
-
|
|
41
|
+
r(this, "store", T());
|
|
42
|
+
r(this, "storeUnsubscription", () => {
|
|
42
43
|
});
|
|
43
44
|
// A config change waiting to reach the node config. Deferred so it can ride the
|
|
44
45
|
// re-render's single apply() — one user action must cost one undo press.
|
|
45
|
-
|
|
46
|
-
|
|
46
|
+
r(this, "pendingNodeConfigWrite", null);
|
|
47
|
+
r(this, "pendingConfigFlushTimer", null);
|
|
47
48
|
// What the panel still owes the block it watches — finished outside the panel on teardown
|
|
48
49
|
// and block switch. A new generation tells debounced work queued for the old one to stand down.
|
|
49
|
-
|
|
50
|
-
|
|
51
|
-
|
|
52
|
-
|
|
53
|
-
|
|
50
|
+
r(this, "trackedBlockId", null);
|
|
51
|
+
r(this, "fetchedConfigVersion", 0);
|
|
52
|
+
r(this, "hasUnrenderedProducts", !1);
|
|
53
|
+
r(this, "panelGeneration", 0);
|
|
54
|
+
r(this, "isPanelAlive", !0);
|
|
54
55
|
// Sub-control instances for lifecycle management
|
|
55
|
-
|
|
56
|
-
|
|
57
|
-
|
|
58
|
-
|
|
59
|
-
|
|
60
|
-
|
|
61
|
-
|
|
62
|
-
|
|
63
|
-
|
|
64
|
-
|
|
65
|
-
|
|
56
|
+
r(this, "algorithmControl", null);
|
|
57
|
+
r(this, "localeControl", null);
|
|
58
|
+
r(this, "currencyControl", null);
|
|
59
|
+
r(this, "productCountControl", null);
|
|
60
|
+
r(this, "productLayoutControl", null);
|
|
61
|
+
r(this, "filtersControl", null);
|
|
62
|
+
r(this, "shuffleControl", null);
|
|
63
|
+
r(this, "pricePlacementControl", null);
|
|
64
|
+
r(this, "layoutOrientationControl", null);
|
|
65
|
+
r(this, "strategyControl", null);
|
|
66
|
+
r(this, "rrsEnabled", !1);
|
|
66
67
|
/**
|
|
67
68
|
* Debounced product fetch to prevent rapid API calls during config changes
|
|
68
69
|
*/
|
|
69
|
-
|
|
70
|
+
r(this, "_debouncedFetchProducts", _(async (e, t) => {
|
|
70
71
|
if (t !== this.panelGeneration)
|
|
71
72
|
return;
|
|
72
|
-
const
|
|
73
|
+
const o = this._getBlockConfigVersion(e);
|
|
73
74
|
try {
|
|
74
|
-
await (e === null ? this.store.fetchRecommendationProducts() : this.store.fetchRecommendationProductsForBlock(e)), t === this.panelGeneration && (this.fetchedConfigVersion = Math.max(this.fetchedConfigVersion,
|
|
75
|
+
await (e === null ? this.store.fetchRecommendationProducts() : this.store.fetchRecommendationProductsForBlock(e)), t === this.panelGeneration && (this.fetchedConfigVersion = Math.max(this.fetchedConfigVersion, o));
|
|
75
76
|
} finally {
|
|
76
|
-
t === this.panelGeneration &&
|
|
77
|
+
t === this.panelGeneration && o === this._getBlockConfigVersion(e) && this._scheduleConfigFlush();
|
|
77
78
|
}
|
|
78
79
|
}, 500));
|
|
79
80
|
/**
|
|
@@ -87,11 +88,11 @@ class me extends P {
|
|
|
87
88
|
* count. The store pads products to the configured size, so in-place only
|
|
88
89
|
* fails when the size actually changed.
|
|
89
90
|
*/
|
|
90
|
-
|
|
91
|
+
r(this, "_debouncedRegenerateWithProducts", _((e) => {
|
|
91
92
|
if (e !== this.panelGeneration || !this.currentNode || !this.api)
|
|
92
93
|
return;
|
|
93
|
-
const t = this._getRecommendationIdFromNode(this.currentNode),
|
|
94
|
-
if (t === null ||
|
|
94
|
+
const t = this._getRecommendationIdFromNode(this.currentNode), o = this.store.currentRecommendationId;
|
|
95
|
+
if (t === null || o === null || t === o || !this.store.blockStates[t]) {
|
|
95
96
|
this.hasUnrenderedProducts = !1, this._regenerateWithProducts();
|
|
96
97
|
return;
|
|
97
98
|
}
|
|
@@ -100,13 +101,13 @@ class me extends P {
|
|
|
100
101
|
try {
|
|
101
102
|
this._regenerateWithProducts();
|
|
102
103
|
} finally {
|
|
103
|
-
this.store.setCurrentBlock(
|
|
104
|
+
this.store.setCurrentBlock(o);
|
|
104
105
|
}
|
|
105
106
|
}
|
|
106
107
|
}, 100));
|
|
107
108
|
}
|
|
108
109
|
getId() {
|
|
109
|
-
return
|
|
110
|
+
return q;
|
|
110
111
|
}
|
|
111
112
|
get _subControls() {
|
|
112
113
|
return [
|
|
@@ -124,10 +125,10 @@ class me extends P {
|
|
|
124
125
|
}
|
|
125
126
|
getTemplate() {
|
|
126
127
|
var e;
|
|
127
|
-
return this.rrsEnabled =
|
|
128
|
-
var
|
|
129
|
-
return (
|
|
130
|
-
}), this.algorithmControl = new E(), this.localeControl = new
|
|
128
|
+
return this.rrsEnabled = f().isFeatureEnabled("reusableRecommendationStrategy"), this._subControls.forEach((t) => {
|
|
129
|
+
var o;
|
|
130
|
+
return (o = t == null ? void 0 : t.onDestroy) == null ? void 0 : o.call(t);
|
|
131
|
+
}), this.algorithmControl = new E(), this.localeControl = new A(), this.currencyControl = new U(), this.productCountControl = new W(), this.productLayoutControl = new x(), this.filtersControl = new v(), this.shuffleControl = new M(), this.pricePlacementControl = new V(), this.layoutOrientationControl = new w(), this.strategyControl = this.rrsEnabled ? new G() : null, this._subControls.forEach((t) => {
|
|
131
132
|
t && (t.api = this.api);
|
|
132
133
|
}), `
|
|
133
134
|
<div class="recommendation-controls-container">
|
|
@@ -145,29 +146,36 @@ class me extends P {
|
|
|
145
146
|
`;
|
|
146
147
|
}
|
|
147
148
|
_showControlsForBlock(e) {
|
|
148
|
-
var
|
|
149
|
-
const t = (
|
|
149
|
+
var s;
|
|
150
|
+
const t = (s = this.getContainer()) == null ? void 0 : s.querySelector(".recommendation-controls-container");
|
|
150
151
|
if (!t)
|
|
151
152
|
return;
|
|
152
|
-
const
|
|
153
|
-
t.classList.toggle("strategy-block",
|
|
153
|
+
const o = this._getRecommendationIdFromNode(e) === null ? null : d.getConfig(e), n = this.rrsEnabled && !!o && (!!(o != null && o.strategyId) || ((o == null ? void 0 : o.configVersion) ?? 0) >= k), i = this.rrsEnabled && !!o && !n;
|
|
154
|
+
t.classList.toggle("strategy-block", n), t.classList.toggle("legacy-strategy-block", i);
|
|
154
155
|
}
|
|
155
|
-
onRender() {
|
|
156
|
-
|
|
156
|
+
async onRender() {
|
|
157
|
+
var o;
|
|
158
|
+
b(this.api);
|
|
159
|
+
const e = this._getRecommendationIdFromNode(this.currentNode), t = e ?? this.store.currentRecommendationId;
|
|
160
|
+
if (t !== null && this.store.setCurrentBlock(t), e !== null && this._syncNodeConfigIfChanged(e), this._listenStateUpdates(), this._showControlsForBlock(this.currentNode), e !== null && this.strategyControl && (this.strategyControl.api = this.api, this.strategyControl.currentNode = this.currentNode, this.strategyControl.onRender()), t !== null && ((o = this.store.blockStates[t]) != null && o.isInitialized)) {
|
|
161
|
+
this._initializeSubControls();
|
|
162
|
+
return;
|
|
163
|
+
}
|
|
164
|
+
await this._fetchBlockData(t), this._initializeSubControls();
|
|
157
165
|
}
|
|
158
166
|
onTemplateNodeUpdated(e) {
|
|
159
|
-
var
|
|
167
|
+
var o;
|
|
160
168
|
super.onTemplateNodeUpdated(e);
|
|
161
169
|
const t = this._getRecommendationIdFromNode(e);
|
|
162
|
-
t !== null && t !== this.store.currentRecommendationId && this.store.setCurrentBlock(t), t !== null && this._syncNodeConfigIfChanged(t), this._showControlsForBlock(e),
|
|
170
|
+
t !== null && t !== this.store.currentRecommendationId && this.store.setCurrentBlock(t), t !== null && this._syncNodeConfigIfChanged(t), this._showControlsForBlock(e), t !== null && !((o = this.store.blockStates[t]) != null && o.isInitialized) && this._fetchBlockData(t).then(() => {
|
|
163
171
|
this._initializeSubControls();
|
|
164
|
-
}), this._subControls.forEach((
|
|
172
|
+
}), this._subControls.forEach((n) => {
|
|
165
173
|
var i;
|
|
166
|
-
|
|
174
|
+
n != null && n.api && (n.currentNode = e, (i = n.onTemplateNodeUpdated) == null || i.call(n, e));
|
|
167
175
|
});
|
|
168
176
|
}
|
|
169
177
|
onDestroy() {
|
|
170
|
-
this.panelGeneration++, this.isPanelAlive = !1, this.
|
|
178
|
+
this.panelGeneration++, this.isPanelAlive = !1, this.storeUnsubscription(), this._finishBlockOutsidePanel(), this.hasUnrenderedProducts = !1, this._subControls.forEach((e) => {
|
|
171
179
|
var t;
|
|
172
180
|
return (t = e == null ? void 0 : e.onDestroy) == null ? void 0 : t.call(e);
|
|
173
181
|
});
|
|
@@ -177,23 +185,11 @@ class me extends P {
|
|
|
177
185
|
* Each sub-control manages its own form values and event listeners
|
|
178
186
|
*/
|
|
179
187
|
_initializeSubControls() {
|
|
180
|
-
this.
|
|
188
|
+
this._subControls.forEach((e) => {
|
|
181
189
|
var t;
|
|
182
190
|
e && (e.api = this.api, e.currentNode = this.currentNode, (t = e.onRender) == null || t.call(e));
|
|
183
191
|
});
|
|
184
192
|
}
|
|
185
|
-
// The panel's own node, not the store's last focused block, decides what to render; the caller
|
|
186
|
-
// fetches an uninitialized block once its config is synced.
|
|
187
|
-
_renderWithPanelNode(e) {
|
|
188
|
-
var t;
|
|
189
|
-
if (!(!this.isAwaitingPanelNode || e === null)) {
|
|
190
|
-
if (this.isAwaitingPanelNode = !1, (t = this.store.blockStates[e]) != null && t.isInitialized) {
|
|
191
|
-
this._initializeSubControls();
|
|
192
|
-
return;
|
|
193
|
-
}
|
|
194
|
-
this.strategyControl && (this.strategyControl.api = this.api, this.strategyControl.currentNode = this.currentNode, this.strategyControl.onRender());
|
|
195
|
-
}
|
|
196
|
-
}
|
|
197
193
|
/**
|
|
198
194
|
* Syncs persisted node config into the Pinia store's block state.
|
|
199
195
|
*
|
|
@@ -224,13 +220,13 @@ class me extends P {
|
|
|
224
220
|
const t = this.store.blockStates[e];
|
|
225
221
|
if (!t)
|
|
226
222
|
return;
|
|
227
|
-
const
|
|
228
|
-
t.syncedConfigFingerprint =
|
|
223
|
+
const o = JSON.stringify(d.getConfig(this.currentNode)), n = t.syncedConfigFingerprint;
|
|
224
|
+
t.syncedConfigFingerprint = o, n !== o && ((i = this.pendingNodeConfigWrite) == null ? void 0 : i.blockId) !== e && this._syncNodeConfigToStore();
|
|
229
225
|
}
|
|
230
226
|
/** Whether the deferred write would move the node's strategyId — see the caller (SD-149916). */
|
|
231
227
|
_isPendingStrategyIdChange() {
|
|
232
228
|
const e = this.pendingNodeConfigWrite;
|
|
233
|
-
return e ?
|
|
229
|
+
return e ? d.getConfig(this.currentNode).strategyId !== e.updates.strategyId : !1;
|
|
234
230
|
}
|
|
235
231
|
_capturePendingNodeConfigWrite() {
|
|
236
232
|
const e = this.store.currentRecommendationId, t = e === null ? void 0 : this.store.blockStates[e];
|
|
@@ -245,15 +241,15 @@ class me extends P {
|
|
|
245
241
|
return !e || t !== null && e.blockId !== t ? null : e;
|
|
246
242
|
}
|
|
247
243
|
_getNodeConfigUpdates(e) {
|
|
248
|
-
const { filters: t, strategy:
|
|
244
|
+
const { filters: t, strategy: o, strategyId: n, size: i, productIds: s, nodeConfigVersion: l } = e, { partnerName: a } = f();
|
|
249
245
|
return {
|
|
250
246
|
filters: t,
|
|
251
|
-
strategy:
|
|
252
|
-
strategyId:
|
|
247
|
+
strategy: o,
|
|
248
|
+
strategyId: n,
|
|
253
249
|
size: i,
|
|
254
|
-
productIds:
|
|
255
|
-
configVersion:
|
|
256
|
-
...
|
|
250
|
+
productIds: s,
|
|
251
|
+
configVersion: l,
|
|
252
|
+
...a.value ? { partnerName: a.value } : {}
|
|
257
253
|
};
|
|
258
254
|
}
|
|
259
255
|
/**
|
|
@@ -268,7 +264,7 @@ class me extends P {
|
|
|
268
264
|
*/
|
|
269
265
|
_stagePendingNodeConfig(e) {
|
|
270
266
|
const t = this._pendingWriteForNode();
|
|
271
|
-
return !t || !this.currentNode ? !1 : (
|
|
267
|
+
return !t || !this.currentNode ? !1 : (d.stageConfig(e, this.currentNode, t.updates), !0);
|
|
272
268
|
}
|
|
273
269
|
/**
|
|
274
270
|
* Arms the guaranteed fallback write, once the product fetch has settled. The
|
|
@@ -292,15 +288,15 @@ class me extends P {
|
|
|
292
288
|
const e = this.pendingNodeConfigWrite;
|
|
293
289
|
if (this.pendingNodeConfigWrite = null, this._clearConfigFlush(), !(!e || !this.api)) {
|
|
294
290
|
if (e.blockId !== this.store.currentRecommendationId || !this.currentNode) {
|
|
295
|
-
const { blockId: t, updates:
|
|
296
|
-
!
|
|
291
|
+
const { blockId: t, updates: o } = e;
|
|
292
|
+
!p(t, o, h) && this.store.blockStates[t] && console.error("[recommendation] pending config write did not reach a node", { blockId: t });
|
|
297
293
|
return;
|
|
298
294
|
}
|
|
299
|
-
|
|
295
|
+
B(this.currentNode, e.updates) && d.updateConfig(
|
|
300
296
|
this.api,
|
|
301
297
|
this.currentNode,
|
|
302
298
|
e.updates,
|
|
303
|
-
|
|
299
|
+
F(this.currentNode, e.updates, h)
|
|
304
300
|
);
|
|
305
301
|
}
|
|
306
302
|
}
|
|
@@ -311,14 +307,14 @@ class me extends P {
|
|
|
311
307
|
/** The Product Ids label when the pending write moves the node's ids; the caller's default otherwise. */
|
|
312
308
|
_pendingDescription() {
|
|
313
309
|
const e = this._pendingWriteForNode();
|
|
314
|
-
if (!(!e || !this.currentNode || !
|
|
310
|
+
if (!(!e || !this.currentNode || !D(this.currentNode, e.updates)))
|
|
315
311
|
return L;
|
|
316
312
|
}
|
|
317
313
|
_syncNodeConfigToStore() {
|
|
318
|
-
var
|
|
319
|
-
const e =
|
|
314
|
+
var n;
|
|
315
|
+
const e = d.getConfig(this.currentNode), t = this.store.currentRecommendationId, o = t !== null && ((n = this.store.blockStates[t]) == null ? void 0 : n.isInitialized);
|
|
320
316
|
this.store.patchCurrentBlockConfig({
|
|
321
|
-
strategy: e.strategy,
|
|
317
|
+
strategy: C(e.strategy) ?? e.strategy,
|
|
322
318
|
strategyId: e.strategyId,
|
|
323
319
|
nodeConfigVersion: e.configVersion,
|
|
324
320
|
language: e.language,
|
|
@@ -331,7 +327,7 @@ class me extends P {
|
|
|
331
327
|
// Only sync filters from node config during initial load.
|
|
332
328
|
// After initialization, the Pinia store is the source of truth
|
|
333
329
|
// for filters (edited via the filter drawer).
|
|
334
|
-
...
|
|
330
|
+
...o ? {} : { filters: e.filters },
|
|
335
331
|
shuffleProducts: e.shuffleProducts,
|
|
336
332
|
priceMovedToNextLine: e.priceMovedToNextLine,
|
|
337
333
|
priceHideIfSameAsDiscounted: e.priceHideIfSameAsDiscounted,
|
|
@@ -352,90 +348,74 @@ class me extends P {
|
|
|
352
348
|
* 2. Smart defaults for new blocks (currency, algorithm) — sequential
|
|
353
349
|
* 3. Product data with correct defaults — sequential
|
|
354
350
|
*
|
|
355
|
-
*
|
|
351
|
+
* Shared by onRender() and onTemplateNodeUpdated() to avoid duplication.
|
|
356
352
|
* Marks the block as initialized to prevent redundant fetches on re-selection.
|
|
357
353
|
*/
|
|
358
354
|
async _fetchBlockData(e) {
|
|
359
355
|
if (e !== null && this.store.markBlockInitialized(e), (await Promise.allSettled([
|
|
360
356
|
this.store.fetchRecommendationCreateData(),
|
|
361
357
|
this.store.fetchRecommendationFilters()
|
|
362
|
-
])).forEach((
|
|
363
|
-
|
|
358
|
+
])).forEach((n, i) => {
|
|
359
|
+
n.status === "rejected" && console.warn(`Recommendation block: ${["fetchRecommendationCreateData", "fetchRecommendationFilters"][i]} failed`, n.reason);
|
|
364
360
|
}), e !== null && this.store.currentRecommendationId !== e) {
|
|
365
361
|
this._refreshOutsidePanel(e, !0);
|
|
366
362
|
return;
|
|
367
363
|
}
|
|
368
364
|
this._applySmartDefaults();
|
|
369
|
-
const
|
|
365
|
+
const o = this._getBlockConfigVersion(e);
|
|
370
366
|
try {
|
|
371
367
|
await this.store.fetchRecommendationProducts();
|
|
372
|
-
} catch (
|
|
373
|
-
console.warn("Recommendation block: fetchRecommendationProducts failed",
|
|
368
|
+
} catch (n) {
|
|
369
|
+
console.warn("Recommendation block: fetchRecommendationProducts failed", n);
|
|
374
370
|
}
|
|
375
|
-
e !== null && !this._isPanelOn(e) && this._refreshOutsidePanel(e, this._getBlockConfigVersion(e) !==
|
|
371
|
+
e !== null && !this._isPanelOn(e) && this._refreshOutsidePanel(e, this._getBlockConfigVersion(e) !== o);
|
|
376
372
|
}
|
|
377
373
|
_isPanelOn(e) {
|
|
378
374
|
return this.isPanelAlive && this.store.currentRecommendationId === e;
|
|
379
375
|
}
|
|
380
376
|
/**
|
|
381
|
-
*
|
|
382
|
-
*
|
|
383
|
-
* For new blocks (config still matches hardcoded defaults), validates that
|
|
384
|
-
* the default currency and algorithm are available from the API response.
|
|
385
|
-
* If not, falls back to the first available option.
|
|
386
|
-
*
|
|
387
|
-
* Saved templates with user-customized config are left unchanged because
|
|
388
|
-
* their values won't match the hardcoded defaults.
|
|
377
|
+
* Falls back to the first available option when the block's currency or locale is not offered (a new block on
|
|
378
|
+
* the hard-coded default, or a block copied from another account). Only the default strategy gets an algorithm.
|
|
389
379
|
*/
|
|
390
380
|
_applySmartDefaults() {
|
|
391
381
|
if (!this.currentNode || !this.api)
|
|
392
382
|
return;
|
|
393
|
-
const e =
|
|
394
|
-
let
|
|
395
|
-
|
|
396
|
-
|
|
397
|
-
|
|
398
|
-
|
|
399
|
-
|
|
400
|
-
|
|
401
|
-
|
|
402
|
-
|
|
403
|
-
|
|
404
|
-
|
|
405
|
-
if (e.strategy === a.strategy) {
|
|
406
|
-
const r = this.store.getActivePredictiveAlgorithms;
|
|
407
|
-
r.length > 0 && (r.some(
|
|
408
|
-
(d) => d.value === a.strategy
|
|
409
|
-
) || (o = r[0].value, t.strategy = o));
|
|
410
|
-
}
|
|
411
|
-
if (e.language === a.language) {
|
|
412
|
-
const r = this.store.getLanguages;
|
|
413
|
-
r.length > 0 && (r.some(
|
|
414
|
-
(d) => d.value === a.language
|
|
415
|
-
) || (i = r[0].value, t.language = i));
|
|
383
|
+
const e = d.getConfig(this.currentNode), t = {};
|
|
384
|
+
let o = null, n = null, i = null;
|
|
385
|
+
const { currencyList: s } = this.store;
|
|
386
|
+
if (s.length > 0 && !s.some((a) => a.value === `price.${e.currency.code}`) && (o = s[0].value.replace("price.", ""), t.currency = {
|
|
387
|
+
...e.currency,
|
|
388
|
+
code: o,
|
|
389
|
+
symbol: o
|
|
390
|
+
}), C(e.strategy) === m.strategy) {
|
|
391
|
+
const a = this.store.getActivePredictiveAlgorithms;
|
|
392
|
+
a.length > 0 && (a.some(
|
|
393
|
+
(N) => N.value === m.strategy
|
|
394
|
+
) || (n = a[0].value, t.strategy = n));
|
|
416
395
|
}
|
|
417
|
-
|
|
396
|
+
const l = this.store.getLanguages;
|
|
397
|
+
l.length > 0 && !l.some((a) => a.value === e.language) && (i = l[0].value, t.language = i), !(!o && !n && !i) && (d.updateConfig(
|
|
418
398
|
this.api,
|
|
419
399
|
this.currentNode,
|
|
420
400
|
t,
|
|
421
401
|
"Applied smart defaults"
|
|
422
|
-
),
|
|
402
|
+
), o && t.currency && z({
|
|
423
403
|
currentNode: this.currentNode,
|
|
424
404
|
documentModifier: this.api.getDocumentModifier(),
|
|
425
405
|
currency: t.currency
|
|
426
406
|
}), this.store.patchCurrentBlockConfig({
|
|
427
|
-
...
|
|
407
|
+
...o && t.currency ? {
|
|
428
408
|
currencySettings: {
|
|
429
|
-
name:
|
|
430
|
-
value:
|
|
431
|
-
symbol:
|
|
432
|
-
alignment:
|
|
433
|
-
decimalCount:
|
|
434
|
-
decimalSeparator:
|
|
435
|
-
thousandSeparator:
|
|
409
|
+
name: o,
|
|
410
|
+
value: o,
|
|
411
|
+
symbol: o,
|
|
412
|
+
alignment: t.currency.alignment === "before" ? "0" : "1",
|
|
413
|
+
decimalCount: t.currency.decimalCount.toString(),
|
|
414
|
+
decimalSeparator: t.currency.decimalSeparator,
|
|
415
|
+
thousandSeparator: t.currency.thousandSeparator
|
|
436
416
|
}
|
|
437
417
|
} : {},
|
|
438
|
-
...
|
|
418
|
+
...n ? { strategy: n } : {},
|
|
439
419
|
...i ? { language: i } : {}
|
|
440
420
|
}, { triggerRefetch: !1 }));
|
|
441
421
|
}
|
|
@@ -443,33 +423,33 @@ class me extends P {
|
|
|
443
423
|
* Reads the recommendation-id attribute from the block element within the node
|
|
444
424
|
*/
|
|
445
425
|
_getRecommendationIdFromNode(e) {
|
|
446
|
-
const t =
|
|
426
|
+
const t = $(e);
|
|
447
427
|
if (!t || !("getAttribute" in t))
|
|
448
428
|
return null;
|
|
449
|
-
const
|
|
450
|
-
if (!
|
|
429
|
+
const o = t.getAttribute(S);
|
|
430
|
+
if (!o)
|
|
451
431
|
return null;
|
|
452
|
-
const
|
|
453
|
-
return Number.isNaN(
|
|
432
|
+
const n = parseInt(o);
|
|
433
|
+
return Number.isNaN(n) ? null : n;
|
|
454
434
|
}
|
|
455
435
|
/**
|
|
456
436
|
* Lands what the panel still owes its block before it stops watching it: the config now, the
|
|
457
437
|
* products through a block-scoped refresh. Never throws — it runs from Stripo's teardown.
|
|
458
438
|
*/
|
|
459
|
-
_finishBlockOutsidePanel({ blockId: e, fetchedConfigVersion: t, hasUnrenderedProducts:
|
|
439
|
+
_finishBlockOutsidePanel({ blockId: e, fetchedConfigVersion: t, hasUnrenderedProducts: o } = this._trackedBlockSnapshot()) {
|
|
460
440
|
try {
|
|
461
441
|
this._flushPendingNodeConfig();
|
|
462
|
-
const
|
|
463
|
-
if (e === null || !
|
|
442
|
+
const n = e === null ? void 0 : this.store.blockStates[e];
|
|
443
|
+
if (e === null || !n)
|
|
464
444
|
return;
|
|
465
|
-
const i = t !==
|
|
466
|
-
i && !
|
|
445
|
+
const i = t !== n.configVersion;
|
|
446
|
+
i && !p(
|
|
467
447
|
e,
|
|
468
|
-
this._getNodeConfigUpdates(
|
|
469
|
-
|
|
470
|
-
) && console.error("[recommendation] config write outside the panel did not reach a node", { blockId: e }), (i ||
|
|
471
|
-
} catch (
|
|
472
|
-
console.error("[recommendation] finishing the block outside the panel failed",
|
|
448
|
+
this._getNodeConfigUpdates(n.recommendationConfigs),
|
|
449
|
+
h
|
|
450
|
+
) && console.error("[recommendation] config write outside the panel did not reach a node", { blockId: e }), (i || o) && this._refreshOutsidePanel(e, i);
|
|
451
|
+
} catch (n) {
|
|
452
|
+
console.error("[recommendation] finishing the block outside the panel failed", n);
|
|
473
453
|
}
|
|
474
454
|
}
|
|
475
455
|
_trackedBlockSnapshot() {
|
|
@@ -480,14 +460,14 @@ class me extends P {
|
|
|
480
460
|
};
|
|
481
461
|
}
|
|
482
462
|
_refreshOutsidePanel(e, t) {
|
|
483
|
-
|
|
484
|
-
pickUpdates: (
|
|
463
|
+
O(e, {
|
|
464
|
+
pickUpdates: (o) => this._getNodeConfigUpdates(o),
|
|
485
465
|
description: "Update recommendation configuration",
|
|
486
466
|
fetch: t
|
|
487
|
-
}).then((
|
|
488
|
-
!
|
|
489
|
-
}).catch((
|
|
490
|
-
console.error("[recommendation] refresh outside the panel failed",
|
|
467
|
+
}).then((o) => {
|
|
468
|
+
!o && this.store.blockStates[e] && console.error("[recommendation] refresh outside the panel did not reach a node", { blockId: e });
|
|
469
|
+
}).catch((o) => {
|
|
470
|
+
console.error("[recommendation] refresh outside the panel failed", o);
|
|
491
471
|
});
|
|
492
472
|
}
|
|
493
473
|
_getBlockConfigVersion(e) {
|
|
@@ -502,25 +482,25 @@ class me extends P {
|
|
|
502
482
|
this.hasUnrenderedProducts = !0;
|
|
503
483
|
return;
|
|
504
484
|
}
|
|
505
|
-
const e = this.store.recommendationProducts, t = this.api.getDocumentModifier(),
|
|
506
|
-
if (
|
|
507
|
-
|
|
508
|
-
new
|
|
485
|
+
const e = this.store.recommendationProducts, t = this.api.getDocumentModifier(), o = this._pendingDescription(), n = this._stagePendingNodeConfig(t);
|
|
486
|
+
if (H(this.currentNode)) {
|
|
487
|
+
n && (t.apply(
|
|
488
|
+
new R(o ?? "Update recommendation configuration")
|
|
509
489
|
), this._consumePendingNodeConfig());
|
|
510
490
|
return;
|
|
511
491
|
}
|
|
512
|
-
|
|
492
|
+
Y({
|
|
513
493
|
currentNode: this.currentNode,
|
|
514
494
|
documentModifier: t,
|
|
515
495
|
products: e,
|
|
516
|
-
description:
|
|
517
|
-
onApplied:
|
|
518
|
-
}) ||
|
|
496
|
+
description: o,
|
|
497
|
+
onApplied: n ? () => this._consumePendingNodeConfig() : void 0
|
|
498
|
+
}) || j({
|
|
519
499
|
currentNode: this.currentNode,
|
|
520
500
|
documentModifier: t,
|
|
521
501
|
products: e,
|
|
522
|
-
description:
|
|
523
|
-
}) &&
|
|
502
|
+
description: o
|
|
503
|
+
}) && n && this._consumePendingNodeConfig();
|
|
524
504
|
}
|
|
525
505
|
// Spent only once it landed with the cards (never when another block's write stayed unstaged):
|
|
526
506
|
// kept alive, it blocks the store resync an Undo needs and the flush writes the undone ids back.
|
|
@@ -542,55 +522,55 @@ class me extends P {
|
|
|
542
522
|
*/
|
|
543
523
|
_listenStateUpdates() {
|
|
544
524
|
const { store: e } = this;
|
|
545
|
-
let t = e.recommendationProducts,
|
|
546
|
-
this.panelGeneration++, this.isPanelAlive = !0, this.trackedBlockId = e.currentRecommendationId, this.fetchedConfigVersion =
|
|
547
|
-
const
|
|
548
|
-
if (
|
|
549
|
-
const
|
|
550
|
-
this.panelGeneration++, this.trackedBlockId =
|
|
525
|
+
let t = e.recommendationProducts, o = this._getBlockConfigVersion(e.currentRecommendationId);
|
|
526
|
+
this.panelGeneration++, this.isPanelAlive = !0, this.trackedBlockId = e.currentRecommendationId, this.fetchedConfigVersion = o, this.hasUnrenderedProducts = !1, this.storeUnsubscription = e.$subscribe(() => {
|
|
527
|
+
const n = e.currentRecommendationId;
|
|
528
|
+
if (n !== this.trackedBlockId) {
|
|
529
|
+
const g = this._trackedBlockSnapshot();
|
|
530
|
+
this.panelGeneration++, this.trackedBlockId = n, t = e.recommendationProducts, o = this._getBlockConfigVersion(n), this.fetchedConfigVersion = o, this.hasUnrenderedProducts = !1, this._finishBlockOutsidePanel(g);
|
|
551
531
|
return;
|
|
552
532
|
}
|
|
553
|
-
const i = this._getBlockConfigVersion(
|
|
554
|
-
i !==
|
|
555
|
-
const
|
|
556
|
-
|
|
533
|
+
const i = this._getBlockConfigVersion(n);
|
|
534
|
+
i !== o && (o = i, this._capturePendingNodeConfigWrite(), this._isPendingStrategyIdChange() && this._flushPendingNodeConfig(), this._debouncedFetchProducts(n, this.panelGeneration));
|
|
535
|
+
const s = e.recommendationProducts, l = s !== t, a = Array.isArray(s) && s.length > 0;
|
|
536
|
+
l && a && (t = s, this.hasUnrenderedProducts = !0, this._debouncedRegenerateWithProducts(this.panelGeneration));
|
|
557
537
|
});
|
|
558
538
|
}
|
|
559
539
|
}
|
|
560
540
|
export {
|
|
561
|
-
|
|
541
|
+
Pe as ALGORITHM_CONTROL_ID,
|
|
562
542
|
E as AlgorithmControl,
|
|
563
|
-
|
|
564
|
-
|
|
565
|
-
|
|
566
|
-
|
|
567
|
-
|
|
568
|
-
|
|
569
|
-
|
|
570
|
-
|
|
571
|
-
|
|
572
|
-
|
|
573
|
-
|
|
574
|
-
|
|
575
|
-
|
|
576
|
-
|
|
577
|
-
|
|
578
|
-
|
|
579
|
-
|
|
580
|
-
|
|
581
|
-
|
|
582
|
-
|
|
583
|
-
|
|
584
|
-
|
|
585
|
-
|
|
586
|
-
|
|
587
|
-
|
|
588
|
-
|
|
589
|
-
|
|
590
|
-
|
|
591
|
-
|
|
592
|
-
|
|
593
|
-
|
|
594
|
-
|
|
595
|
-
|
|
543
|
+
q as CONTROL_BLOCK_ID,
|
|
544
|
+
Ie as CURRENCY_CONTROL_ID,
|
|
545
|
+
U as CurrencyControl,
|
|
546
|
+
Se as FILTERS_CONTROL_ID,
|
|
547
|
+
v as FiltersControl,
|
|
548
|
+
Oe as LAYOUT_ORIENTATION_CONTROL_ID,
|
|
549
|
+
Be as LOCALE_CONTROL_ID,
|
|
550
|
+
w as LayoutOrientationControl,
|
|
551
|
+
A as LocaleControl,
|
|
552
|
+
De as PRICE_PLACEMENT_CONTROL_ID,
|
|
553
|
+
Ee as PRODUCT_COUNT_CONTROL_ID,
|
|
554
|
+
ve as PRODUCT_LAYOUT_CONTROL_ID,
|
|
555
|
+
V as PricePlacementControl,
|
|
556
|
+
W as ProductCountControl,
|
|
557
|
+
x as ProductLayoutControl,
|
|
558
|
+
_e as RecommendationBlockControl,
|
|
559
|
+
Ae as SHUFFLE_CONTROL_ID,
|
|
560
|
+
We as STRATEGY_CONTROL_ID,
|
|
561
|
+
M as ShuffleControl,
|
|
562
|
+
G as StrategyControl,
|
|
563
|
+
Me as adjustProductsToSize,
|
|
564
|
+
Ge as formatProductPrice,
|
|
565
|
+
$ as getBlockElement,
|
|
566
|
+
ze as getCardComposition,
|
|
567
|
+
$e as getCurrentLayout,
|
|
568
|
+
He as getMainContainerTbody,
|
|
569
|
+
H as isPartnerManagedBlock,
|
|
570
|
+
Ye as regenerateMobileProductRows,
|
|
571
|
+
j as regenerateProductRowsWithStyles,
|
|
572
|
+
z as setCurrencyAttributes,
|
|
573
|
+
je as updatePricesInPlace,
|
|
574
|
+
Y as updateProductContentInPlace,
|
|
575
|
+
qe as updateSingleProductContent
|
|
596
576
|
};
|