@useinsider/guido 3.16.0-beta.c615198 → 3.16.0-beta.ff4f1bd

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (76) hide show
  1. package/README.md +1 -0
  2. package/dist/@types/config/schemas.js +12 -6
  3. package/dist/components/Guido.vue.js +6 -6
  4. package/dist/components/Guido.vue2.js +31 -30
  5. package/dist/components/organisms/extensions/recommendation/AssignStrategyDrawer.vue.js +18 -0
  6. package/dist/components/organisms/extensions/recommendation/AssignStrategyDrawer.vue2.js +61 -0
  7. package/dist/composables/useRecommendation.js +49 -43
  8. package/dist/config/migrator/recommendationMigrator.js +6 -4
  9. package/dist/enums/extensions/recommendationBlock.js +25 -23
  10. package/dist/extensions/Blocks/Recommendation/constants/defaultConfig.js +13 -11
  11. package/dist/extensions/Blocks/Recommendation/controls/main/algorithm.js +26 -37
  12. package/dist/extensions/Blocks/Recommendation/controls/main/index.js +120 -98
  13. package/dist/extensions/Blocks/Recommendation/controls/main/strategy.js +106 -0
  14. package/dist/extensions/Blocks/Recommendation/store/recommendation.js +186 -52
  15. package/dist/guido.css +1 -1
  16. package/dist/node_modules/@useinsider/design-system-organisms/dist/index-5JHlb8rM.js +524 -0
  17. package/dist/node_modules/@useinsider/design-system-organisms/dist/index.js +8450 -0
  18. package/dist/node_modules/@useinsider/design-system-organisms/node_modules/@useinsider/design-system-vue/dist/InAccordion.js +174 -0
  19. package/dist/node_modules/@useinsider/design-system-organisms/node_modules/@useinsider/design-system-vue/dist/InBasicTextInput.js +381 -0
  20. package/dist/node_modules/@useinsider/design-system-organisms/node_modules/@useinsider/design-system-vue/dist/InBox.js +236 -0
  21. package/dist/node_modules/@useinsider/design-system-organisms/node_modules/@useinsider/design-system-vue/dist/InBulkActions.js +70 -0
  22. package/dist/node_modules/@useinsider/design-system-organisms/node_modules/@useinsider/design-system-vue/dist/InButton.js +350 -0
  23. package/dist/node_modules/@useinsider/design-system-organisms/node_modules/@useinsider/design-system-vue/dist/InButtonV2.js +371 -0
  24. package/dist/node_modules/@useinsider/design-system-organisms/node_modules/@useinsider/design-system-vue/dist/InCheckBox.js +152 -0
  25. package/dist/node_modules/@useinsider/design-system-organisms/node_modules/@useinsider/design-system-vue/dist/InChips.js +141 -0
  26. package/dist/node_modules/@useinsider/design-system-organisms/node_modules/@useinsider/design-system-vue/dist/InCustomDropDown.js +1047 -0
  27. package/dist/node_modules/@useinsider/design-system-organisms/node_modules/@useinsider/design-system-vue/dist/InDataTableV2.js +96050 -0
  28. package/dist/node_modules/@useinsider/design-system-organisms/node_modules/@useinsider/design-system-vue/dist/InDatePicker.js +2042 -0
  29. package/dist/node_modules/@useinsider/design-system-organisms/node_modules/@useinsider/design-system-vue/dist/InDrawer.js +166 -0
  30. package/dist/node_modules/@useinsider/design-system-organisms/node_modules/@useinsider/design-system-vue/dist/InDropDown.js +1098 -0
  31. package/dist/node_modules/@useinsider/design-system-organisms/node_modules/@useinsider/design-system-vue/dist/InIcons.js +55 -0
  32. package/dist/node_modules/@useinsider/design-system-organisms/node_modules/@useinsider/design-system-vue/dist/InInfoBox.js +265 -0
  33. package/dist/node_modules/@useinsider/design-system-organisms/node_modules/@useinsider/design-system-vue/dist/InLinks.js +184 -0
  34. package/dist/node_modules/@useinsider/design-system-organisms/node_modules/@useinsider/design-system-vue/dist/InLoading.js +50 -0
  35. package/dist/node_modules/@useinsider/design-system-organisms/node_modules/@useinsider/design-system-vue/dist/InModals.js +453 -0
  36. package/dist/node_modules/@useinsider/design-system-organisms/node_modules/@useinsider/design-system-vue/dist/InNoData.js +145 -0
  37. package/dist/node_modules/@useinsider/design-system-organisms/node_modules/@useinsider/design-system-vue/dist/InOnPageMessage.js +176 -0
  38. package/dist/node_modules/@useinsider/design-system-organisms/node_modules/@useinsider/design-system-vue/dist/InProgress.js +266 -0
  39. package/dist/node_modules/@useinsider/design-system-organisms/node_modules/@useinsider/design-system-vue/dist/InRadioButton.js +114 -0
  40. package/dist/node_modules/@useinsider/design-system-organisms/node_modules/@useinsider/design-system-vue/dist/InSegments.js +200 -0
  41. package/dist/node_modules/@useinsider/design-system-organisms/node_modules/@useinsider/design-system-vue/dist/InSelect.js +451 -0
  42. package/dist/node_modules/@useinsider/design-system-organisms/node_modules/@useinsider/design-system-vue/dist/InSkeleton.js +49 -0
  43. package/dist/node_modules/@useinsider/design-system-organisms/node_modules/@useinsider/design-system-vue/dist/InStatusText.js +119 -0
  44. package/dist/node_modules/@useinsider/design-system-organisms/node_modules/@useinsider/design-system-vue/dist/InTabs.js +4309 -0
  45. package/dist/node_modules/@useinsider/design-system-organisms/node_modules/@useinsider/design-system-vue/dist/InTagsText.js +129 -0
  46. package/dist/node_modules/@useinsider/design-system-organisms/node_modules/@useinsider/design-system-vue/dist/InTextInput.js +503 -0
  47. package/dist/node_modules/@useinsider/design-system-organisms/node_modules/@useinsider/design-system-vue/dist/InToasts.js +253 -0
  48. package/dist/node_modules/@useinsider/design-system-organisms/node_modules/@useinsider/design-system-vue/dist/InToggle.js +107 -0
  49. package/dist/node_modules/@useinsider/design-system-organisms/node_modules/@useinsider/design-system-vue/dist/InTooltip.js +134 -0
  50. package/dist/node_modules/@useinsider/design-system-organisms/node_modules/@useinsider/design-system-vue/dist/InTooltipV2.js +464 -0
  51. package/dist/node_modules/@useinsider/design-system-organisms/node_modules/@useinsider/design-system-vue/dist/chunks/_commonjsHelpers.BItOPCY9.js +28 -0
  52. package/dist/node_modules/@useinsider/design-system-organisms/node_modules/@useinsider/design-system-vue/dist/chunks/_plugin-vue2_normalizer.WQT2Fc8L.js +23 -0
  53. package/dist/node_modules/@useinsider/design-system-organisms/node_modules/@useinsider/design-system-vue/dist/chunks/clickOutside.qP9M0QCm.js +29 -0
  54. package/dist/node_modules/@useinsider/design-system-organisms/node_modules/@useinsider/design-system-vue/dist/chunks/helpers.CgHNyjAJ.js +109 -0
  55. package/dist/node_modules/@useinsider/design-system-organisms/node_modules/@useinsider/design-system-vue/dist/chunks/index.Bw_06igr.js +2339 -0
  56. package/dist/node_modules/@useinsider/design-system-organisms/node_modules/@useinsider/design-system-vue/dist/chunks/localLocalesMixin.DYMhydo2.js +16 -0
  57. package/dist/node_modules/@useinsider/design-system-organisms/node_modules/@useinsider/design-system-vue/dist/chunks/useLocalLocales.Ckuhy7d-.js +17 -0
  58. package/dist/node_modules/@useinsider/design-system-organisms/node_modules/@useinsider/design-system-vue/dist/chunks/vue-property-decorator.BtlM7Epa.js +188 -0
  59. package/dist/services/recommendationApi.js +77 -28
  60. package/dist/src/@types/config/schemas.d.ts +12 -0
  61. package/dist/src/components/organisms/extensions/recommendation/AssignStrategyDrawer.vue.d.ts +3 -0
  62. package/dist/src/components/wrappers/WpModal.vue.d.ts +1 -1
  63. package/dist/src/composables/useConfig.d.ts +2 -0
  64. package/dist/src/composables/useRecommendation.d.ts +1 -0
  65. package/dist/src/enums/extensions/recommendationBlock.d.ts +2 -0
  66. package/dist/src/extensions/Blocks/Recommendation/controls/main/index.d.ts +6 -3
  67. package/dist/src/extensions/Blocks/Recommendation/controls/main/strategy.d.ts +26 -0
  68. package/dist/src/extensions/Blocks/Recommendation/store/recommendation.d.ts +199 -10
  69. package/dist/src/extensions/Blocks/Recommendation/types/nodeConfig.d.ts +6 -0
  70. package/dist/src/mock/api/recommendation-strategies.d.ts +41 -0
  71. package/dist/src/services/recommendationApi.d.ts +4 -1
  72. package/dist/src/stores/config.d.ts +18 -0
  73. package/dist/utils/templatePreparation.js +37 -34
  74. package/package.json +2 -1
  75. package/dist/extensions/Blocks/Recommendation/utils/productIds.js +0 -6
  76. package/dist/src/extensions/Blocks/Recommendation/utils/productIds.d.ts +0 -6
@@ -1,21 +1,20 @@
1
- import { getRecommendationFeedSourceMaps as g, getOperatorOptions as R, PriceAttributes as C } from "../../../../enums/extensions/recommendationBlock.js";
2
- import { useRecommendationApi as y } from "../../../../services/recommendationApi.js";
3
- import { useConfigStore as G } from "../../../../stores/config.js";
4
- import { defineStore as P } from "pinia";
1
+ import { getRecommendationFeedSourceMaps as p, getOperatorOptions as R, PriceAttributes as C } from "../../../../enums/extensions/recommendationBlock.js";
2
+ import { useRecommendationApi as w } from "../../../../services/recommendationApi.js";
3
+ import { useConfigStore as P } from "../../../../stores/config.js";
4
+ import { defineStore as G } from "pinia";
5
5
  import "../constants/selectors.js";
6
- import { DEFAULT_MOBILE_CARDS_IN_ROW as F, DEFAULT_CARDS_IN_ROW as D } from "../constants/layout.js";
7
- import { EXCLUDED_ALGORITHM_IDS as w } from "../constants/defaultConfig.js";
8
- import { getDefaultProducts as S } from "../templates/utils.js";
6
+ import { DEFAULT_MOBILE_CARDS_IN_ROW as D, DEFAULT_CARDS_IN_ROW as F } from "../constants/layout.js";
7
+ import { EXCLUDED_ALGORITHM_IDS as v } from "../constants/defaultConfig.js";
8
+ import { getDefaultProducts as y } from "../templates/utils.js";
9
9
  import { generateCompleteFilterQuery as b } from "../utils/filterUtil.js";
10
- import { getPartnerRecommendationParams as v } from "../utils/partnerCustomizations.js";
11
- import { sanitizeProductIds as N } from "../utils/productIds.js";
12
- import { isFilterValid as x } from "../validation/filterSchema.js";
10
+ import { getPartnerRecommendationParams as U } from "../utils/partnerCustomizations.js";
11
+ import { isFilterValid as _ } from "../validation/filterSchema.js";
13
12
  import { isConfigValid as L } from "../validation/requiredFields.js";
14
- const h = y();
15
- let m = null, u = null, d = null;
13
+ const l = w();
14
+ let m = null, u = null, d = null, f = null;
16
15
  function k() {
17
16
  return {
18
- cardsInRow: D,
17
+ cardsInRow: F,
19
18
  currencySettings: {
20
19
  name: "USD",
21
20
  value: "USD",
@@ -29,13 +28,14 @@ function k() {
29
28
  productIds: [],
30
29
  id: 1,
31
30
  language: "en_US",
32
- mobileCardsInRow: F,
31
+ mobileCardsInRow: D,
33
32
  mobileLayoutEnabled: !1,
34
33
  orientation: "grid",
35
34
  recommendedProducts: [],
36
35
  sendProductRequestFlag: !1,
37
36
  shuffleProducts: !1,
38
37
  strategy: "mostPopular",
38
+ strategyId: "",
39
39
  textTrimming: !0,
40
40
  unresponsive: !1,
41
41
  size: "6",
@@ -50,22 +50,26 @@ function I() {
50
50
  recommendationProducts: [],
51
51
  filterStatus: !1,
52
52
  filterSelectionDrawerStatus: !1,
53
+ assignStrategyDrawerStatus: !1,
53
54
  filterGroup: 1,
54
55
  isInitialized: !1,
55
56
  filterSnapshot: null
56
57
  };
57
58
  }
58
- const U = () => ({
59
+ const N = () => ({
59
60
  recommendationCampaignUrls: {},
60
61
  activePredictiveAlgorithms: [],
61
62
  languages: {},
62
63
  currencyList: [],
63
64
  filterList: {},
65
+ strategies: [],
66
+ strategiesLoading: !1,
67
+ strategyUrlTemplates: {},
64
68
  blockStates: {},
65
69
  currentRecommendationId: null,
66
70
  configVersion: 0
67
- }), H = P("guidoRecommendationExtension", {
68
- state: () => U(),
71
+ }), q = G("guidoRecommendationExtension", {
72
+ state: () => N(),
69
73
  getters: {
70
74
  // ====================================================================
71
75
  // Proxy Getters — Backward Compatible Access to Current Block State
@@ -89,6 +93,20 @@ const U = () => ({
89
93
  filterSelectionDrawerStatus(t) {
90
94
  return t.currentRecommendationId !== null && t.blockStates[t.currentRecommendationId] ? t.blockStates[t.currentRecommendationId].filterSelectionDrawerStatus : !1;
91
95
  },
96
+ /**
97
+ * Proxy getter: delegates to blockStates[currentRecommendationId].assignStrategyDrawerStatus
98
+ */
99
+ assignStrategyDrawerStatus(t) {
100
+ return t.currentRecommendationId !== null && t.blockStates[t.currentRecommendationId] ? t.blockStates[t.currentRecommendationId].assignStrategyDrawerStatus : !1;
101
+ },
102
+ /**
103
+ * The current block's assigned strategy record from the listing,
104
+ * or null when nothing is assigned / the strategy is no longer listed.
105
+ */
106
+ assignedStrategy(t) {
107
+ const { strategyId: e } = this.recommendationConfigs;
108
+ return e ? t.strategies.find((r) => String(r.strategy_id) === e) ?? null : null;
109
+ },
92
110
  /**
93
111
  * Proxy getter: delegates to blockStates[currentRecommendationId].filterStatus
94
112
  */
@@ -120,9 +138,9 @@ const U = () => ({
120
138
  return [...new Set(t.map((e) => e.filterGroup))].sort((e, r) => e - r);
121
139
  },
122
140
  getActivePredictiveAlgorithms: (t) => {
123
- const e = g(), r = [];
124
- return t.activePredictiveAlgorithms.filter((n) => !w.includes(n)).forEach((n) => {
125
- r.push(...e.filter((c) => c.id === n));
141
+ const e = p(), r = [];
142
+ return t.activePredictiveAlgorithms.filter((n) => !v.includes(n)).forEach((n) => {
143
+ r.push(...e.filter((s) => s.id === n));
126
144
  }), r.map((n) => ({
127
145
  text: n.name,
128
146
  value: n.key
@@ -193,10 +211,10 @@ const U = () => ({
193
211
  [e]: o
194
212
  };
195
213
  }
196
- const n = t.toString(), c = e.toString(), i = this.recommendationCampaignUrls[n];
214
+ const n = t.toString(), s = e.toString(), i = this.recommendationCampaignUrls[n];
197
215
  i && (this.recommendationCampaignUrls = {
198
216
  ...this.recommendationCampaignUrls,
199
- [c]: i
217
+ [s]: i
200
218
  });
201
219
  },
202
220
  /**
@@ -221,7 +239,7 @@ const U = () => ({
221
239
  * `isInitialized`) alone.
222
240
  */
223
241
  seedBlockUrlConfig(t, e) {
224
- const r = (o, s) => o === "." || o === "," || o === " " ? o : s, n = {
242
+ const r = (o, a) => o === "." || o === "," || o === " " ? o : a, n = {
225
243
  name: e.currencyCode,
226
244
  value: e.currencyCode,
227
245
  symbol: e.currencyCode,
@@ -229,17 +247,18 @@ const U = () => ({
229
247
  decimalCount: String(e.currencyDecimalCount),
230
248
  decimalSeparator: r(e.currencyDecimalSeparator, ","),
231
249
  thousandSeparator: r(e.currencyThousandSeparator, ".")
232
- }, c = !this.blockStates[t], i = c ? I() : this.blockStates[t];
250
+ }, s = !this.blockStates[t], i = s ? I() : this.blockStates[t];
233
251
  i.recommendationConfigs = {
234
252
  ...i.recommendationConfigs,
235
253
  strategy: e.strategy,
254
+ strategyId: e.strategyId,
236
255
  language: e.language,
237
256
  size: e.size,
238
257
  productIds: e.productIds,
239
258
  filters: e.filters,
240
259
  shuffleProducts: e.shuffleProducts,
241
260
  currencySettings: n
242
- }, c && (this.blockStates = {
261
+ }, s && (this.blockStates = {
243
262
  ...this.blockStates,
244
263
  [t]: i
245
264
  });
@@ -315,6 +334,78 @@ const U = () => ({
315
334
  t.filterSnapshot !== null && (t.recommendationConfigs.filters = t.filterSnapshot, t.filterSnapshot = null), t.filterSelectionDrawerStatus = !1;
316
335
  },
317
336
  // ====================================================================
337
+ // Reusable Recommendation Strategy (SD-149105)
338
+ // ====================================================================
339
+ /**
340
+ * Opens the Assign Strategy drawer for the current block.
341
+ * Selection state lives in the drawer component until Assign is
342
+ * pressed, so closing without assigning needs no snapshot/revert.
343
+ */
344
+ openAssignStrategyDrawer() {
345
+ this.currentRecommendationId === null || !this.blockStates[this.currentRecommendationId] || (this.blockStates[this.currentRecommendationId].assignStrategyDrawerStatus = !0);
346
+ },
347
+ closeAssignStrategyDrawer() {
348
+ this.currentRecommendationId === null || !this.blockStates[this.currentRecommendationId] || (this.blockStates[this.currentRecommendationId].assignStrategyDrawerStatus = !1);
349
+ },
350
+ /**
351
+ * Fetches the active + EMAIL strategy listing. Always fetches fresh
352
+ * (dead-strategy detection and post-create refresh need freshness);
353
+ * only concurrent in-flight calls share one request.
354
+ */
355
+ async fetchStrategies() {
356
+ if (f) {
357
+ await f;
358
+ return;
359
+ }
360
+ f = (async () => {
361
+ this.strategiesLoading = !0;
362
+ try {
363
+ this.strategies = await l.fetchRecommendationStrategies();
364
+ } finally {
365
+ this.strategiesLoading = !1;
366
+ }
367
+ })();
368
+ try {
369
+ await f;
370
+ } finally {
371
+ f = null;
372
+ }
373
+ },
374
+ /**
375
+ * Resolves a strategy's recommendation endpoint template via
376
+ * endpoint-generate, cached per strategy id. Failures throw and are
377
+ * NOT cached, so the next attempt retries.
378
+ */
379
+ async resolveStrategyUrlTemplate(t) {
380
+ const e = String(t.strategy_id), r = this.strategyUrlTemplates[e];
381
+ if (r)
382
+ return r;
383
+ const { full_path: n } = await l.generateStrategyEndpoint(t);
384
+ return this.strategyUrlTemplates = {
385
+ ...this.strategyUrlTemplates,
386
+ [e]: n
387
+ }, n;
388
+ },
389
+ /**
390
+ * Assigns a strategy to the current block. The config write is
391
+ * synchronous (before any await) so a block switch cannot misdirect
392
+ * it; the configVersion bump persists it to node config and triggers
393
+ * the product refetch via the coordinator control's subscription.
394
+ */
395
+ assignStrategy(t) {
396
+ this.patchCurrentBlockConfig({
397
+ strategyId: String(t.strategy_id),
398
+ ...t.size !== void 0 ? { size: String(t.size) } : {}
399
+ });
400
+ },
401
+ /**
402
+ * Clears the current block's strategy; it falls back to the
403
+ * per-block algorithm settings.
404
+ */
405
+ removeStrategy() {
406
+ this.patchCurrentBlockConfig({ strategyId: "" });
407
+ },
408
+ // ====================================================================
318
409
  // Shared Data Fetching (fetched once, used by all blocks)
319
410
  // ====================================================================
320
411
  async fetchRecommendationCreateData() {
@@ -328,7 +419,7 @@ const U = () => ({
328
419
  activePredictiveAlgorithms: t,
329
420
  languages: e,
330
421
  currencies: r
331
- } = await h.fetchRecommendationCreateData();
422
+ } = await l.fetchRecommendationCreateData();
332
423
  if (this.activePredictiveAlgorithms = t, this.languages = e, this.currentRecommendationId !== null && this.blockStates[this.currentRecommendationId]) {
333
424
  const n = this.blockStates[this.currentRecommendationId];
334
425
  n.filterStatus = !!n.recommendationConfigs.filters.length;
@@ -349,7 +440,7 @@ const U = () => ({
349
440
  return;
350
441
  }
351
442
  u = (async () => {
352
- const t = await h.fetchRecommendationFilters();
443
+ const t = await l.fetchRecommendationFilters();
353
444
  this.filterList = t;
354
445
  })();
355
446
  try {
@@ -370,10 +461,10 @@ const U = () => ({
370
461
  deleteFilterGroup(t) {
371
462
  if (this.currentRecommendationId === null || !this.blockStates[this.currentRecommendationId])
372
463
  return;
373
- const e = this.blockStates[this.currentRecommendationId], r = e.recommendationConfigs.filters.filter((i) => i.filterGroup !== t), n = [...new Set(r.map((i) => i.filterGroup))].sort((i, o) => i - o), c = new Map(n.map((i, o) => [i, o + 1]));
464
+ const e = this.blockStates[this.currentRecommendationId], r = e.recommendationConfigs.filters.filter((i) => i.filterGroup !== t), n = [...new Set(r.map((i) => i.filterGroup))].sort((i, o) => i - o), s = new Map(n.map((i, o) => [i, o + 1]));
374
465
  e.recommendationConfigs.filters = r.map((i) => ({
375
466
  ...i,
376
- filterGroup: c.get(i.filterGroup) ?? i.filterGroup
467
+ filterGroup: s.get(i.filterGroup) ?? i.filterGroup
377
468
  }));
378
469
  },
379
470
  updateFilter(t) {
@@ -384,7 +475,7 @@ const U = () => ({
384
475
  const n = [...e.recommendationConfigs.filters];
385
476
  n[r] = {
386
477
  ...t,
387
- isValid: x(t)
478
+ isValid: _(t)
388
479
  }, e.recommendationConfigs.filters = n;
389
480
  }
390
481
  },
@@ -398,10 +489,10 @@ const U = () => ({
398
489
  let i = 1;
399
490
  n = n.map((o) => o.filterGroup === t.filterGroup ? { ...o, filterNumber: i++ } : o);
400
491
  } else {
401
- const i = [...new Set(n.map((s) => s.filterGroup))].sort((s, a) => s - a), o = new Map(i.map((s, a) => [s, a + 1]));
402
- n = n.map((s) => ({
403
- ...s,
404
- filterGroup: o.get(s.filterGroup) ?? s.filterGroup
492
+ const i = [...new Set(n.map((a) => a.filterGroup))].sort((a, c) => a - c), o = new Map(i.map((a, c) => [a, c + 1]));
493
+ n = n.map((a) => ({
494
+ ...a,
495
+ filterGroup: o.get(a.filterGroup) ?? a.filterGroup
405
496
  }));
406
497
  }
407
498
  e.recommendationConfigs.filters = n;
@@ -410,15 +501,15 @@ const U = () => ({
410
501
  addFilter(t) {
411
502
  if (this.currentRecommendationId === null || !this.blockStates[this.currentRecommendationId])
412
503
  return;
413
- const e = this.blockStates[this.currentRecommendationId], r = [...e.recommendationConfigs.filters], c = r.filter(
504
+ const e = this.blockStates[this.currentRecommendationId], r = [...e.recommendationConfigs.filters], s = r.filter(
414
505
  (o) => o.filterGroup === t.filterGroup
415
506
  ).length + 1, i = r.findLastIndex((o) => o.filterGroup === t.filterGroup);
416
507
  i !== -1 ? r.splice(i + 1, 0, {
417
508
  ...t,
418
- filterNumber: c
509
+ filterNumber: s
419
510
  }) : r.push({
420
511
  ...t,
421
- filterNumber: c
512
+ filterNumber: s
422
513
  }), e.recommendationConfigs.filters = r;
423
514
  },
424
515
  generateFilterQuery() {
@@ -450,8 +541,13 @@ const U = () => ({
450
541
  }
451
542
  },
452
543
  async _doFetchProducts() {
453
- var p;
454
- const t = this.currentRecommendationId, e = this.blockStates[t], { recommendationConfigs: r } = e, n = r.filters.filter((l) => l.isValid), c = b(n), i = ((p = g().find((l) => l.key === r.strategy)) == null ? void 0 : p.path) || "", o = G(), s = parseInt(r.size) || 6, a = {
544
+ var S;
545
+ const t = this.currentRecommendationId, e = this.blockStates[t], { recommendationConfigs: r } = e;
546
+ if (r.strategyId) {
547
+ await this._doFetchStrategyProducts(t);
548
+ return;
549
+ }
550
+ const n = r.filters.filter((h) => h.isValid), s = b(n), i = ((S = p().find((h) => h.key === r.strategy)) == null ? void 0 : S.path) || "", o = P(), a = parseInt(r.size) || 6, c = {
455
551
  locale: r.language,
456
552
  currency: r.currencySettings.value,
457
553
  partnerName: o.partnerName,
@@ -459,26 +555,64 @@ const U = () => ({
459
555
  details: !0,
460
556
  campaignId: o.variationId
461
557
  };
462
- r.strategy === "manualMerchandising" ? a.productId = N(r.productIds) : r.strategy === "similarViewed" && (a.productId = "{itemId}"), r.strategy === "userBased" && (a.userId = "{user_id}"), c && (a.filter = c), r.shuffleProducts && (a.shuffle = !0), Object.assign(
463
- a,
464
- v(o.partnerName, r.strategy)
558
+ r.strategy === "manualMerchandising" ? c.productId = r.productIds.join(",") : r.strategy === "similarViewed" && (c.productId = "{itemId}"), r.strategy === "userBased" && (c.userId = "{user_id}"), s && (c.filter = s), r.shuffleProducts && (c.shuffle = !0), Object.assign(
559
+ c,
560
+ U(o.partnerName, r.strategy)
465
561
  );
466
- let f;
562
+ let g;
467
563
  try {
468
- f = await h.fetchRecommendationProducts(i, a);
564
+ g = await l.fetchRecommendationProducts(i, c);
469
565
  } catch {
470
- f = [];
566
+ g = [];
471
567
  }
472
- if (this.blockStates[t]) {
473
- const l = f.length > 0 ? f : S(s);
474
- l.length < s ? this.blockStates[t].recommendationProducts = [
475
- ...l,
476
- ...S(s - l.length)
477
- ] : l.length > s ? this.blockStates[t].recommendationProducts = l.slice(0, s) : this.blockStates[t].recommendationProducts = l;
568
+ this._setBlockProducts(t, g, a);
569
+ },
570
+ /**
571
+ * Fetches products for a strategy-backed block: listing lookup →
572
+ * endpoint-generate template → fill {locale}/{currency}, drop
573
+ * {user_id} (resolved at send time) → fetch. Any failure (dead
574
+ * strategy, resolution error) falls back to placeholder products.
575
+ */
576
+ async _doFetchStrategyProducts(t) {
577
+ const { recommendationConfigs: e } = this.blockStates[t];
578
+ let r = [], n = parseInt(e.size) || 6;
579
+ try {
580
+ this.strategies.length || await this.fetchStrategies();
581
+ const s = this.strategies.find(
582
+ (i) => String(i.strategy_id) === e.strategyId
583
+ );
584
+ if (s) {
585
+ n = parseInt(String(s.size ?? "")) || n;
586
+ const i = await this.resolveStrategyUrlTemplate(s), o = new URL(
587
+ i.replaceAll("{locale}", e.language).replaceAll("{currency}", e.currencySettings.value)
588
+ );
589
+ o.searchParams.delete("user_id"), r = await l.fetchRecommendationProductsByUrl(o.toString());
590
+ }
591
+ } catch {
592
+ r = [];
478
593
  }
594
+ this._setBlockProducts(t, r, n);
595
+ },
596
+ /**
597
+ * Writes products to a block's state, padded/clipped to `size` so
598
+ * in-place content updates (which compare DOM element count vs
599
+ * products.length) succeed:
600
+ * - API returned nothing → fill entirely with defaults
601
+ * - fewer than requested → pad with dummies
602
+ * - more than requested → clip, preventing the renderer from extending
603
+ * its slot grid (which would reset migrator-applied styles).
604
+ */
605
+ _setBlockProducts(t, e, r) {
606
+ if (!this.blockStates[t])
607
+ return;
608
+ const n = e.length > 0 ? e : y(r);
609
+ n.length < r ? this.blockStates[t].recommendationProducts = [
610
+ ...n,
611
+ ...y(r - n.length)
612
+ ] : n.length > r ? this.blockStates[t].recommendationProducts = n.slice(0, r) : this.blockStates[t].recommendationProducts = n;
479
613
  }
480
614
  }
481
615
  });
482
616
  export {
483
- H as useRecommendationExtensionStore
617
+ q as useRecommendationExtensionStore
484
618
  };