@rebuy/rebuy 3.29.0 → 3.30.0

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 (47) hide show
  1. package/dist/index.cjs +1543 -1346
  2. package/dist/index.mjs +1537 -1340
  3. package/dist/schema/index.d.ts +7 -0
  4. package/dist/schema/postPurchaseProductCollectionView.d.ts +8 -0
  5. package/dist/schema/postPurchaseProductDisplay.d.ts +59 -0
  6. package/dist/schema/postPurchaseProductGallery.d.ts +11 -0
  7. package/dist/schema/postPurchaseProductSettings.d.ts +117 -0
  8. package/dist/schema/postPurchaseProductSource.d.ts +65 -0
  9. package/dist/schema/postPurchaseVariantCatalog.d.ts +41 -0
  10. package/dist/schema/postPurchaseVariantDefault.d.ts +36 -0
  11. package/dist/schema/shopConfig.d.ts +2 -2
  12. package/dist/schema/userConfig.d.ts +2 -2
  13. package/dist/schema/widgetData.d.ts +2 -2
  14. package/dist/schema/widgets/checkout-and-beyond/banner.d.ts +29 -29
  15. package/dist/schema/widgets/checkout-and-beyond/carousel.d.ts +29 -29
  16. package/dist/schema/widgets/checkout-and-beyond/cartLine.d.ts +29 -29
  17. package/dist/schema/widgets/checkout-and-beyond/common.d.ts +5 -5
  18. package/dist/schema/widgets/checkout-and-beyond/offers.d.ts +29 -29
  19. package/dist/schema/widgets/checkout-and-beyond/progressBar.d.ts +29 -29
  20. package/dist/schema/widgets/checkout-and-beyond/root.d.ts +1 -1
  21. package/dist/schema/widgets/contentBlock.d.ts +4 -4
  22. package/dist/schema/widgets/post-purchase-offer/constants.d.ts +4 -4
  23. package/dist/schema/widgets/post-purchase-offer/postPurchaseBlocks.d.ts +2 -2
  24. package/dist/schema/widgets/post-purchase-offer/postPurchaseOffer.d.ts +2 -2
  25. package/dist/schema/widgets/post-purchase-offer/postPurchaseSettings.d.ts +2 -2
  26. package/dist/schema/widgets/post-purchase-offer/postPurchaseWidget.d.ts +2 -2
  27. package/dist/server/__fixtures__/postPurchaseProduct.d.ts +137 -0
  28. package/dist/server/__fixtures__/postPurchaseVariantDefaults.d.ts +26 -0
  29. package/dist/server/__fixtures__/postPurchaseVariants.d.ts +47 -0
  30. package/dist/server/index.cjs +6 -2
  31. package/dist/server/index.mjs +6 -2
  32. package/dist/server/matchPostPurchaseVariantDefault.d.ts +17 -0
  33. package/dist/server/normalizePostPurchaseCollection.d.ts +250 -0
  34. package/dist/server/normalizePostPurchaseProduct.d.ts +202 -0
  35. package/dist/server/postPurchasePrimaryImage.d.ts +6 -0
  36. package/dist/server/postPurchaseProductDisplay.d.ts +41 -0
  37. package/dist/server/postPurchaseProductEligibility.d.ts +8 -0
  38. package/dist/server/postPurchaseProductGallery.d.ts +5 -0
  39. package/dist/server/postPurchaseVariantAvailable.d.ts +12 -0
  40. package/dist/server/postPurchaseVariantCatalog.d.ts +3 -0
  41. package/dist/server/projectPostPurchaseProduct.d.ts +127 -0
  42. package/dist/server/resolvePostPurchaseVariantDefault.d.ts +10 -0
  43. package/dist/transforms/index.cjs +7 -3
  44. package/dist/transforms/index.mjs +7 -3
  45. package/dist/transforms/offerV1/offerTemplateSeed.d.ts +8 -5
  46. package/dist/transforms/postPurchase/imageContentSettings.d.ts +1 -1
  47. package/package.json +1 -1
package/dist/index.mjs CHANGED
@@ -41,8 +41,8 @@ function getIdFromGraphUrl(graphId, objectType) {
41
41
  }
42
42
  return id;
43
43
  }
44
- function variantAvailable(variant) {
45
- return !(variant.inventory_management && variant.inventory_policy === "deny" && variant.inventory_quantity <= 0);
44
+ function variantAvailable(variant2) {
45
+ return !(variant2.inventory_management && variant2.inventory_policy === "deny" && variant2.inventory_quantity <= 0);
46
46
  }
47
47
  function firstAvailableVariant(product) {
48
48
  let selectedVariant = product.variants[0];
@@ -76,7 +76,7 @@ function convertProductToStorefrontFormat(product) {
76
76
  const minVariantCompareAtPrice = variantMinMaxPriceObject(product, "compare_at_price", "min");
77
77
  const maxVariantCompareAtPrice = variantMinMaxPriceObject(product, "compare_at_price", "max");
78
78
  const selectedOptions = selectedVariantOptions(product, defaultVariant);
79
- const variants = product.variants.map((variant) => convertVariantToStorefrontFormat(product, variant));
79
+ const variants = product.variants.map((variant2) => convertVariantToStorefrontFormat(product, variant2));
80
80
  return {
81
81
  collections: null,
82
82
  compareAtPriceRange: {
@@ -119,15 +119,15 @@ function convertToNodes(arr) {
119
119
  ]
120
120
  };
121
121
  }
122
- function convertVariantToStorefrontFormat(product, variant) {
123
- const selectedOptions = selectedVariantOptions(product, variant);
124
- const image = productImageObject(product, variant.image_id);
122
+ function convertVariantToStorefrontFormat(product, variant2) {
123
+ const selectedOptions = selectedVariantOptions(product, variant2);
124
+ const image = productImageObject(product, variant2.image_id);
125
125
  return {
126
- availableForSale: variantAvailable(variant),
127
- compareAtPriceV2: variantPriceObject(variant, "compare_at_price"),
128
- id: `gid://shopify/ProductVariant/${variant.id}`,
126
+ availableForSale: variantAvailable(variant2),
127
+ compareAtPriceV2: variantPriceObject(variant2, "compare_at_price"),
128
+ id: `gid://shopify/ProductVariant/${variant2.id}`,
129
129
  image,
130
- priceV2: variantPriceObject(variant, "price"),
130
+ priceV2: variantPriceObject(variant2, "price"),
131
131
  product: {
132
132
  handle: product.handle,
133
133
  id: product.id,
@@ -135,8 +135,8 @@ function convertVariantToStorefrontFormat(product, variant) {
135
135
  vendor: product.vendor
136
136
  },
137
137
  selectedOptions: [selectedOptions],
138
- sku: variant.sku,
139
- title: variant.title
138
+ sku: variant2.sku,
139
+ title: variant2.title
140
140
  };
141
141
  }
142
142
  function variantMinMaxPriceObject(product, key = "price", operator = "min") {
@@ -153,25 +153,25 @@ function variantMinMaxPriceObject(product, key = "price", operator = "min") {
153
153
  }
154
154
  return priceObject;
155
155
  }
156
- function variantPriceObject(variant, key = "price") {
157
- if (variant[key] != null) {
156
+ function variantPriceObject(variant2, key = "price") {
157
+ if (variant2[key] != null) {
158
158
  return {
159
- amount: variant[key],
159
+ amount: variant2[key],
160
160
  currencyCode: "USD"
161
161
  };
162
162
  }
163
163
  return null;
164
164
  }
165
- function selectedVariantOptions(product, variant) {
165
+ function selectedVariantOptions(product, variant2) {
166
166
  const selectedOptions = {};
167
- if (variant.option1 != null) {
168
- selectedOptions[product.options[0].name] = variant.option1;
167
+ if (variant2.option1 != null) {
168
+ selectedOptions[product.options[0].name] = variant2.option1;
169
169
  }
170
- if (variant.option2 != null) {
171
- selectedOptions[product.options[1].name] = variant.option2;
170
+ if (variant2.option2 != null) {
171
+ selectedOptions[product.options[1].name] = variant2.option2;
172
172
  }
173
- if (variant.option3 != null) {
174
- selectedOptions[product.options[2].name] = variant.option3;
173
+ if (variant2.option3 != null) {
174
+ selectedOptions[product.options[2].name] = variant2.option3;
175
175
  }
176
176
  return selectedOptions;
177
177
  }
@@ -216,16 +216,16 @@ function utmObjectFromString(str) {
216
216
  }
217
217
  return Object.keys(matches).length > 0 ? matches : null;
218
218
  }
219
- function amountToCents(amount) {
219
+ function amountToCents(amount2) {
220
220
  let normalizedAmount = 0;
221
- if (typeof amount === "string") {
222
- if (amount.indexOf(".") !== -1) {
223
- normalizedAmount = Math.round(parseFloat(amount) * 100);
221
+ if (typeof amount2 === "string") {
222
+ if (amount2.indexOf(".") !== -1) {
223
+ normalizedAmount = Math.round(parseFloat(amount2) * 100);
224
224
  } else {
225
- normalizedAmount = parseInt(amount, 10);
225
+ normalizedAmount = parseInt(amount2, 10);
226
226
  }
227
- } else if (typeof amount === "number") {
228
- normalizedAmount = Math.round(amount * 100);
227
+ } else if (typeof amount2 === "number") {
228
+ normalizedAmount = Math.round(amount2 * 100);
229
229
  }
230
230
  if (isNaN(normalizedAmount)) {
231
231
  normalizedAmount = 0;
@@ -293,10 +293,10 @@ var stagingDomains = [
293
293
  "dash-ext-hoke.myshopify.com",
294
294
  "rebuy-checkout-e2e-staging.myshopify.com"
295
295
  ];
296
- var makeCall = async (key, method, path, data, origin, options = {}) => {
296
+ var makeCall = async (key, method, path, data, origin, options2 = {}) => {
297
297
  const url = `${origin}${path}`;
298
298
  const requestUrl = new URL(url);
299
- const fetchOptions = options?.fetch ?? {};
299
+ const fetchOptions = options2?.fetch ?? {};
300
300
  const requestData = {};
301
301
  if (typeof data == "object" && data != null) {
302
302
  Object.assign(requestData, data);
@@ -325,7 +325,7 @@ var makeCall = async (key, method, path, data, origin, options = {}) => {
325
325
  return response;
326
326
  };
327
327
  var Api = class {
328
- constructor(options) {
328
+ constructor(options2) {
329
329
  this.config = {
330
330
  /**
331
331
  * @deprecated Use `staticDomain` (same host) — `cdnDomain` remains only for legacy callers and goes away in the next major.
@@ -339,10 +339,10 @@ var Api = class {
339
339
  shop: null,
340
340
  staticDomain: "https://cdn.rebuyengine.com"
341
341
  };
342
- if (typeof options == "string") {
343
- this.config.key = options;
344
- } else if (typeof options == "object" && options != null) {
345
- Object.assign(this.config, options);
342
+ if (typeof options2 == "string") {
343
+ this.config.key = options2;
344
+ } else if (typeof options2 == "object" && options2 != null) {
345
+ Object.assign(this.config, options2);
346
346
  }
347
347
  for (const domain of stagingDomains) {
348
348
  if (typeof location === "object" && location?.host?.includes(domain)) {
@@ -355,23 +355,23 @@ var Api = class {
355
355
  }
356
356
  }
357
357
  }
358
- async callEvent(method, path, data, options) {
359
- return await makeCall(this.config.key, method, path, data, this.config.eventDomain, options);
358
+ async callEvent(method, path, data, options2) {
359
+ return await makeCall(this.config.key, method, path, data, this.config.eventDomain, options2);
360
360
  }
361
- async callShield(method, path, data, options) {
362
- return await makeCall(this.config.key, method, path, data, this.config.shieldDomain, options);
361
+ async callShield(method, path, data, options2) {
362
+ return await makeCall(this.config.key, method, path, data, this.config.shieldDomain, options2);
363
363
  }
364
- async callStatic(method, path, data, options) {
365
- return await makeCall(this.config.key, method, path, data, this.config.staticDomain, options);
364
+ async callStatic(method, path, data, options2) {
365
+ return await makeCall(this.config.key, method, path, data, this.config.staticDomain, options2);
366
366
  }
367
- async callGeo(method, path, data, options) {
368
- return await makeCall(this.config.key, method, path, data, this.config.geoDomain, options);
367
+ async callGeo(method, path, data, options2) {
368
+ return await makeCall(this.config.key, method, path, data, this.config.geoDomain, options2);
369
369
  }
370
- async callCdn(method, path, data, options) {
371
- return await makeCall(this.config.key, method, path, data, this.config.cdnDomain, options);
370
+ async callCdn(method, path, data, options2) {
371
+ return await makeCall(this.config.key, method, path, data, this.config.cdnDomain, options2);
372
372
  }
373
- async callApi(method, path, data, options) {
374
- return await makeCall(this.config.key, method, path, data, this.config.domain, options);
373
+ async callApi(method, path, data, options2) {
374
+ return await makeCall(this.config.key, method, path, data, this.config.domain, options2);
375
375
  }
376
376
  };
377
377
  var api_default = Api;
@@ -623,16 +623,16 @@ var trackEvent = async (config2, eventData) => {
623
623
  }
624
624
  return await config2.api.callEvent("POST", "/api/v1/analytics/event", eventData);
625
625
  };
626
- var makeShieldCall = async (config2, endpoint, params, format, options = {}) => {
627
- return await makeCall2(config2, endpoint, params, format, { ...options, shield: true });
626
+ var makeShieldCall = async (config2, endpoint, params, format, options2 = {}) => {
627
+ return await makeCall2(config2, endpoint, params, format, { ...options2, shield: true });
628
628
  };
629
- var makeStaticCall = async (config2, endpoint, params, format, options = {}) => {
630
- return await makeCall2(config2, endpoint, params, format, { ...options, static: true });
629
+ var makeStaticCall = async (config2, endpoint, params, format, options2 = {}) => {
630
+ return await makeCall2(config2, endpoint, params, format, { ...options2, static: true });
631
631
  };
632
- var makeCDNCall = async (config2, endpoint, params, format, options = {}) => {
633
- return await makeCall2(config2, endpoint, params, format, { ...options, cdn: true });
632
+ var makeCDNCall = async (config2, endpoint, params, format, options2 = {}) => {
633
+ return await makeCall2(config2, endpoint, params, format, { ...options2, cdn: true });
634
634
  };
635
- var makeCall2 = async (config2, endpoint, params, format, options = {}) => {
635
+ var makeCall2 = async (config2, endpoint, params, format, options2 = {}) => {
636
636
  const query = {};
637
637
  if (config2.defaultParameters != null) {
638
638
  Object.assign(query, config2.defaultParameters);
@@ -643,15 +643,15 @@ var makeCall2 = async (config2, endpoint, params, format, options = {}) => {
643
643
  if (typeof params == "object" && params != null) {
644
644
  Object.assign(query, params);
645
645
  }
646
- if (typeof options != "object" || options == null) {
647
- console.warn("Unsupported fetch options provided.", options);
648
- options = {};
646
+ if (typeof options2 != "object" || options2 == null) {
647
+ console.warn("Unsupported fetch options provided.", options2);
648
+ options2 = {};
649
649
  }
650
650
  if (config2.identity && config2.identity.visitorId()) {
651
651
  query.uuid = config2.identity.visitorId();
652
652
  }
653
- const source = options.cdn ? "callCdn" : options.shield ? "callShield" : options.static ? "callStatic" : "callApi";
654
- const response = await config2.api[source]("GET", endpoint, query, options);
653
+ const source = options2.cdn ? "callCdn" : options2.shield ? "callShield" : options2.static ? "callStatic" : "callApi";
654
+ const response = await config2.api[source]("GET", endpoint, query, options2);
655
655
  if (response.data && format === "storefront") {
656
656
  for (let i = 0; i < response.data.length; i++) {
657
657
  response.data[i] = convertProductToStorefrontFormat(response.data[i]);
@@ -691,20 +691,20 @@ var RebuyClient = class {
691
691
  this.config.contextParameters = contextParameters;
692
692
  }
693
693
  }
694
- async getData(endpoint, params, options = {}) {
695
- return await makeCall2(this.config, endpoint, params, null, options);
694
+ async getData(endpoint, params, options2 = {}) {
695
+ return await makeCall2(this.config, endpoint, params, null, options2);
696
696
  }
697
- async getDataFromCDN(endpoint, params, options = {}) {
698
- return await makeCDNCall(this.config, endpoint, params, null, options);
697
+ async getDataFromCDN(endpoint, params, options2 = {}) {
698
+ return await makeCDNCall(this.config, endpoint, params, null, options2);
699
699
  }
700
- async getShieldedAsset(endpoint, params, options = {}) {
701
- return await makeShieldCall(this.config, endpoint, params, null, options);
700
+ async getShieldedAsset(endpoint, params, options2 = {}) {
701
+ return await makeShieldCall(this.config, endpoint, params, null, options2);
702
702
  }
703
- async getStaticAsset(endpoint, params, options = {}) {
704
- return await makeStaticCall(this.config, endpoint, params, null, options);
703
+ async getStaticAsset(endpoint, params, options2 = {}) {
704
+ return await makeStaticCall(this.config, endpoint, params, null, options2);
705
705
  }
706
- async getStorefrontData(endpoint, params, options = {}) {
707
- return await makeCall2(this.config, endpoint, params, "storefront", options);
706
+ async getStorefrontData(endpoint, params, options2 = {}) {
707
+ return await makeCall2(this.config, endpoint, params, "storefront", options2);
708
708
  }
709
709
  async trackProductViewed(data) {
710
710
  const requiredKeys = ["shopify_product_id", "shopify_product_handle"];
@@ -1318,207 +1318,120 @@ var SessionPolicySchema = TimingSettingsSchema.extend({
1318
1318
  }
1319
1319
  );
1320
1320
 
1321
- // src/schema/postPurchaseSelection.ts
1321
+ // src/schema/postPurchaseProductCollectionView.ts
1322
+ import { z as z12 } from "zod";
1323
+
1324
+ // src/schema/postPurchaseProductSource.ts
1322
1325
  import { z as z11 } from "zod";
1323
- var SelectionClaimsSchema = DecideRequestSchema.extend({
1324
- appId: PostPurchaseAppIdSchema,
1325
- entry: DecisionEntrySchema,
1326
- iss: z11.literal("rebuy-api"),
1327
- purpose: z11.literal("post-purchase-selection")
1326
+ var PostPurchaseAmount = z11.string().regex(/^\d+(?:\.\d+)?$/).refine((value) => Number.isFinite(Number(value)));
1327
+ var PostPurchaseProductId = z11.number().int().positive();
1328
+ var PostPurchaseVariantId = z11.number().int().positive();
1329
+ var ProductBase = OfferProduct.pick({ description: true, id: true, image: true, title: true }).extend({
1330
+ description: OfferProduct.shape.description.nullable(),
1331
+ id: PostPurchaseProductId
1328
1332
  });
1329
- var SessionStartRequestSchema = DecideRequestSchema.extend({
1330
- selectionToken: z11.string().min(1).max(8192).optional()
1331
- }).strict();
1332
-
1333
- // src/schema/postPurchaseSession.ts
1334
- import { z as z12 } from "zod";
1335
- var SessionIdentitySchema = DecideRequestSchema.extend({ appId: PostPurchaseAppIdSchema });
1336
- var SessionOrderTimingSchema = z12.object({
1337
- nativeDeadline: PostPurchaseTimestampSchema,
1338
- orderCreatedAt: PostPurchaseTimestampSchema,
1339
- orderId: PostPurchaseOrderIdSchema,
1340
- timingSource: z12.literal("shopify-order-created-at")
1333
+ var SourceVariant = OfferProduct.shape.variants.element.pick({ id: true, title: true }).extend({
1334
+ compareAtPrice: PostPurchaseAmount.nullable(),
1335
+ id: PostPurchaseVariantId,
1336
+ imageId: z11.number().int().nonnegative().nullish(),
1337
+ inventoryManagement: z11.string().nullable(),
1338
+ inventoryPolicy: z11.string(),
1339
+ inventoryQuantity: z11.number(),
1340
+ option1: z11.unknown().optional(),
1341
+ option2: z11.unknown().optional(),
1342
+ option3: z11.unknown().optional(),
1343
+ price: PostPurchaseAmount,
1344
+ productId: PostPurchaseProductId,
1345
+ sellingPlanAllocations: z11.unknown().optional()
1341
1346
  });
1342
- var ReadySessionTimingSchema = SessionOrderTimingSchema.extend({
1343
- deadline: PostPurchaseTimestampSchema,
1344
- entry: DecisionEntrySchema,
1345
- policySnapshot: SessionPolicySchema,
1346
- startedAt: PostPurchaseTimestampSchema
1347
- }).refine((session) => session.orderCreatedAt <= session.startedAt, {
1348
- message: "startedAt must not precede orderCreatedAt",
1349
- path: ["startedAt"]
1350
- }).refine((session) => session.startedAt <= session.deadline, {
1351
- message: "deadline must not precede startedAt",
1352
- path: ["deadline"]
1353
- }).refine((session) => session.deadline <= session.nativeDeadline, {
1354
- message: "deadline must not exceed nativeDeadline",
1355
- path: ["deadline"]
1347
+ var Product2 = ProductBase.extend({
1348
+ images: z11.array(
1349
+ z11.object({ alt: z11.string().optional().catch(void 0), id: z11.number().int().positive(), src: z11.string() })
1350
+ ).nullish(),
1351
+ metadata: z11.object({
1352
+ productQuantity: z11.union([
1353
+ z11.number().int().positive(),
1354
+ z11.string().regex(/^[1-9]\d*$/).transform(Number)
1355
+ ]).optional()
1356
+ }).optional(),
1357
+ metafields: z11.unknown().optional(),
1358
+ options: z11.unknown().optional(),
1359
+ productGroupVariants: z11.array(z11.unknown()).default([]),
1360
+ selectedVariant: z11.unknown().optional(),
1361
+ sellingPlanGroups: z11.array(
1362
+ OfferProduct.shape.sellingPlanGroups.unwrap().element.extend({
1363
+ discountAmount: z11.unknown().optional(),
1364
+ discountType: z11.unknown().optional(),
1365
+ id: z11.unknown().optional(),
1366
+ sellingPlans: z11.unknown().optional()
1367
+ })
1368
+ ).optional(),
1369
+ variants: z11.array(SourceVariant)
1356
1370
  });
1357
- var SessionStartResponseSchema = z12.object({
1358
- data: z12.object({
1359
- phase: z12.literal("render"),
1360
- serverNow: PostPurchaseTimestampSchema,
1361
- session: ReadySessionTimingSchema,
1362
- workflowPhase: z12.literal("start")
1363
- }),
1364
- successful: z12.literal(true)
1371
+ var PostPurchaseProductSource = z11.object({
1372
+ data: z11.array(Product2),
1373
+ metadata: z11.object({ widget: z11.record(z11.string(), z11.unknown()).default({}) }).default({ widget: {} })
1365
1374
  });
1366
1375
 
1367
- // src/schema/postPurchaseSessionClose.ts
1368
- import { z as z13 } from "zod";
1369
- var SessionClosureSchema = z13.object({ closedAt: PostPurchaseTimestampSchema, status: z13.literal("closed") });
1370
- var SessionCloseRequestSchema = DecideRequestSchema.strict();
1371
- var SessionCloseResponseSchema = z13.object({ data: SessionClosureSchema, successful: z13.literal(true) });
1372
-
1373
- // src/schema/postPurchaseShadow.ts
1374
- import { z as z14 } from "zod";
1375
- var PostPurchaseShadowSelectionSchema = z14.discriminatedUnion("verdict", [
1376
- z14.object({ entry: DecisionEntrySchema, verdict: z14.literal("render") }),
1377
- z14.object({ verdict: z14.literal("skip") })
1378
- ]);
1379
- var PostPurchaseShadowReportFields = z14.object({
1380
- differences: z14.array(z14.enum(["verdict", "entry", "targeting", "incomplete-capture", "unsupported-configuration"])).refine((differences) => new Set(differences).size === differences.length, {
1381
- message: "differences must not contain duplicate entries"
1382
- }),
1383
- legacySelection: PostPurchaseShadowSelectionSchema,
1384
- phase: z14.literal("shouldRender"),
1385
- sampleId: z14.string(),
1386
- serverSelection: PostPurchaseShadowSelectionSchema.optional(),
1387
- status: z14.enum(["match", "diverged", "incomplete"]),
1388
- targetingFlowIds: z14.array(z14.number().int().positive()),
1389
- workflowPhase: z14.literal("decide")
1390
- });
1391
- var PostPurchaseShadowReportSchema = PostPurchaseShadowReportFields.refine(
1392
- (report) => report.status !== "match" || report.differences.length === 0,
1393
- { message: "status 'match' requires an empty differences array", path: ["status"] }
1394
- ).refine((report) => report.status !== "diverged" || report.differences.length > 0, {
1395
- message: "status 'diverged' requires a non-empty differences array",
1396
- path: ["status"]
1397
- }).refine((report) => report.status !== "diverged" || report.serverSelection !== void 0, {
1398
- message: "status 'diverged' requires a serverSelection to diverge from",
1399
- path: ["status"]
1400
- });
1376
+ // src/schema/postPurchaseProductCollectionView.ts
1377
+ var PostPurchaseExcludedProductIds = z12.array(PostPurchaseProductId).default([]);
1401
1378
 
1402
- // src/schema/postPurchaseSkipTrace.ts
1403
- import { z as z15 } from "zod";
1404
- var POST_PURCHASE_SKIP_LIMIT = 32;
1405
- var PostPurchaseSkipTraceSchema = z15.array(
1406
- z15.object({
1407
- entry: DecisionEntrySchema,
1408
- reason: PostPurchaseSkipReasonSchema
1409
- })
1410
- ).max(POST_PURCHASE_SKIP_LIMIT);
1379
+ // src/schema/postPurchaseProductDisplay.ts
1380
+ import { z as z21 } from "zod";
1411
1381
 
1412
- // src/schema/shopConfig.ts
1413
- import { z as z16 } from "zod";
1414
- var ShopConfig = z16.object({
1415
- activeExperiments: z16.array(
1416
- z16.object({
1417
- data: z16.array(
1418
- z16.object({
1419
- aliasName: z16.string(),
1420
- cssInput: z16.string().nullish(),
1421
- elementId: z16.coerce.number(),
1422
- id: z16.coerce.number(),
1423
- javascriptInput: z16.string().nullish(),
1424
- traffic: z16.coerce.number()
1425
- })
1426
- ),
1427
- id: z16.coerce.number(),
1428
- name: z16.string(),
1429
- pageTarget: z16.string().nullable(),
1430
- pageTargetUrl: z16.string().nullable(),
1431
- placeholderId: z16.coerce.number().nullable(),
1432
- type: z16.string()
1433
- })
1434
- ),
1435
- activePackages: z16.array(
1436
- z16.object({
1437
- cancelledAt: z16.string().nullable(),
1438
- id: z16.number(),
1439
- installedAt: z16.string().nullable(),
1440
- isActive: z16.boolean(),
1441
- isBillable: z16.boolean(),
1442
- packageId: z16.number(),
1443
- packageName: z16.string(),
1444
- shortName: z16.string(),
1445
- trialDays: z16.number(),
1446
- uninstalledAt: z16.string().nullable()
1382
+ // src/schema/postPurchaseProductGallery.ts
1383
+ import { z as z13 } from "zod";
1384
+ var PostPurchaseProductGallery = z13.object({
1385
+ images: z13.array(
1386
+ z13.object({
1387
+ description: z13.string(),
1388
+ id: z13.number().int().positive(),
1389
+ source: z13.string(),
1390
+ thumbnail: z13.string()
1447
1391
  })
1448
1392
  ),
1449
- apiKey: z16.string(),
1450
- billingVersion: z16.string().nullable(),
1451
- cacheKey: z16.coerce.number(),
1452
- carousel: z16.enum(["flickity", "splide"]),
1453
- currency: z16.string(),
1454
- currencySymbol: z16.string(),
1455
- domain: z16.string(),
1456
- enabledJquery: z16.boolean(),
1457
- enabledPresentmentCurrencies: z16.array(z16.string()),
1458
- hasSmartCollectionsEnabled: z16.boolean(),
1459
- hasSmartSearchEnabled: z16.boolean(),
1460
- id: z16.coerce.number(),
1461
- integrations: z16.record(
1462
- z16.enum([
1463
- "attentive",
1464
- "judgeme",
1465
- "junip",
1466
- "klaviyo",
1467
- "loox",
1468
- "okendo",
1469
- "opinew",
1470
- "recharge",
1471
- "reviewsio",
1472
- "stamped",
1473
- "yotpo"
1474
- ]),
1475
- z16.union([z16.boolean(), z16.unknown()])
1476
- ),
1477
- markets: z16.object({
1478
- enabled: z16.boolean()
1479
- }),
1480
- monetize: z16.object({
1481
- publisherKey: z16.string().nullable()
1482
- }).nullish(),
1483
- moneyFormat: z16.string(),
1484
- myshopifyDomain: z16.string(),
1485
- primaryLocale: z16.string(),
1486
- productGroupsEnabled: z16.enum(["no", "yes"]).transform((value) => value === "yes"),
1487
- rechargeCustomDomain: z16.string().nullable(),
1488
- sellingPlansEnabled: z16.boolean(),
1489
- shopId: z16.number(),
1490
- shopifySellingPlansEnabled: z16.boolean(),
1491
- shopName: z16.string(),
1492
- storefrontAccessToken: z16.string().nullable(),
1493
- useRebuyIcons: z16.boolean()
1393
+ selectedImageId: z13.number().int().positive().optional()
1494
1394
  });
1495
1395
 
1496
- // src/schema/userConfig.ts
1497
- import { z as z17 } from "zod";
1498
- var UserConfig = z17.object({
1499
- shop: ShopConfig,
1500
- /**
1501
- * `.catch(undefined)` is the safety bar: smart-cart shape drift can NEVER fail `fetchUserConfig`,
1502
- * which resolves the apiKey for every offers/monetize/analytics/gift request.
1503
- */
1504
- smartCart: SmartCartConfig.nullish().catch(void 0),
1505
- smartFlows: z17.array(z17.unknown())
1506
- });
1396
+ // src/schema/widgets/post-purchase-offer/postPurchaseSettings.ts
1397
+ import { z as z20 } from "zod";
1507
1398
 
1508
- // src/schema/widgetData.ts
1509
- import { z as z48 } from "zod";
1399
+ // src/schema/widgets/post-purchase-offer/common.ts
1400
+ import { replace, toNumber, toString } from "es-toolkit/compat";
1401
+ import { z as z14 } from "zod";
1402
+ var strictNumber = z14.union([
1403
+ z14.number(),
1404
+ z14.string().transform((value) => toNumber(replace(toString(value), /[^0-9.]/g, "")) || 0),
1405
+ z14.unknown().transform(() => 0)
1406
+ ]);
1510
1407
 
1511
- // src/schema/widgets/abTestingPlaceholder.ts
1512
- import { z as z18 } from "zod";
1513
- var ABTestingPlaceholder = z18.looseObject({
1514
- type: z18.literal("placeholder")
1515
- });
1408
+ // src/schema/widgets/post-purchase-offer/constants.ts
1409
+ import { z as z15 } from "zod";
1410
+ var blockTypes = [
1411
+ "callout_banner",
1412
+ "image",
1413
+ "image_content",
1414
+ "pay_button",
1415
+ "product_information",
1416
+ "separator",
1417
+ "text",
1418
+ "timer"
1419
+ ];
1420
+ var blockType = z15.enum(blockTypes);
1421
+ var BlockType = blockType.enum;
1516
1422
 
1517
- // src/schema/widgets/checkout-and-beyond/constants.ts
1518
- import { uniqBy } from "es-toolkit";
1423
+ // src/schema/widgets/post-purchase-offer/postPurchaseBlocks.ts
1424
+ import { get as get3, isEqual } from "es-toolkit/compat";
1425
+ import { v4 as uuidv42 } from "uuid";
1426
+ import { z as z19 } from "zod";
1427
+
1428
+ // src/schema/widgets/checkout-and-beyond/text.ts
1429
+ import { forEach, isString as isString2 } from "es-toolkit/compat";
1430
+ import { v7 as uuidv7 } from "uuid";
1431
+ import { z as z18 } from "zod";
1519
1432
 
1520
1433
  // src/schema/widgets/checkout-and-beyond/common.ts
1521
- var freezeEnum = (values) => Object.freeze(Object.fromEntries(values.map((v) => [v, v])));
1434
+ var freezeEnum = (values2) => Object.freeze(Object.fromEntries(values2.map((v) => [v, v])));
1522
1435
  var bannerColors = ["info", "success", "warning", "critical"];
1523
1436
  var BannerColor = freezeEnum(bannerColors);
1524
1437
  var borderRadii = ["none", "small", "base", "large", "fullyRounded"];
@@ -1723,82 +1636,6 @@ var widgetTypes = [
1723
1636
  ];
1724
1637
  var WidgetType = freezeEnum(widgetTypes);
1725
1638
 
1726
- // src/schema/widgets/checkout-and-beyond/constants.ts
1727
- var DEFAULT_ENDPOINTS = [
1728
- { label: "Recommended (AI)", value: "/products/recommended" },
1729
- { label: "Top Sellers", value: "/products/top_sellers" },
1730
- { label: "Buy It Again", value: "/products/purchased" },
1731
- { label: "Recently Viewed", value: "/products/viewed" },
1732
- { label: "Products Search", value: "/products/search" },
1733
- { label: "Collection Products", value: "/products/collections" },
1734
- { label: "Similar Products (AI)", value: "/products/similar_products" }
1735
- ];
1736
- var STATIC_ENDPOINTS = [
1737
- { label: "Recommended (AI)", value: "/products/recommended" },
1738
- { label: "Top Sellers", value: "/products/top_sellers" },
1739
- { label: "Trending Products", value: "/products/trending_products" },
1740
- { label: "Buy It Again", value: "/products/purchased" },
1741
- { label: "Collection Products", value: "/products/collections" },
1742
- { label: "Recently Viewed", value: "/products/viewed" },
1743
- { label: "Static Products", value: "/products/static" },
1744
- { label: "Products Search", value: "/products/search" },
1745
- { label: "Similar Products (AI)", value: "/products/similar_products" }
1746
- ];
1747
- var COMBINED_ENDPOINTS = uniqBy([...DEFAULT_ENDPOINTS, ...STATIC_ENDPOINTS], (item) => item.value);
1748
- var targetAreas = {
1749
- [EditorMode.checkoutExtension]: [
1750
- { icon: "splitscreen_top", label: "Header Area", width: "984px" },
1751
- { icon: "splitscreen_left", label: "Main Column", width: "503px" },
1752
- { icon: "splitscreen_right", label: "Summary Column", width: "404px" }
1753
- ],
1754
- [EditorMode.postPurchaseOffer]: null,
1755
- [EditorMode.thankYouPage]: [
1756
- { icon: "splitscreen_top", label: "Header Area", width: "984px" },
1757
- { icon: "splitscreen_left", label: "Main Column", width: "503px" },
1758
- { icon: "splitscreen_right", label: "Summary Column", width: "404px" }
1759
- ],
1760
- [EditorMode.orderStatusPage]: [
1761
- // { fill: true, flip: 'vertical', icon: 'bottom_navigation', label: 'Announcement Bar' },
1762
- { icon: "splitscreen_top", label: "Header Area", width: "1124px" },
1763
- { fill: true, icon: "view_column_2", label: "Main Area", width: "646px" },
1764
- { icon: "splitscreen_bottom", label: "Footer Area", width: "1124px" }
1765
- ],
1766
- [EditorMode.ordersIndexPage]: [
1767
- // { fill: true, flip: 'vertical', icon: 'bottom_navigation', label: 'Announcement Bar' },
1768
- { icon: "splitscreen_top", label: "Main Area", width: "1124px" }
1769
- ],
1770
- [EditorMode.customerProfilePage]: [
1771
- // { fill: true, flip: 'vertical', icon: 'bottom_navigation', label: 'Announcement Bar' },
1772
- { icon: "splitscreen_top", label: "Main Area", width: "1124px" }
1773
- ]
1774
- };
1775
-
1776
- // src/schema/widgets/checkoutExtension.ts
1777
- import { z as z19 } from "zod";
1778
- var CheckoutExtension = z19.looseObject({
1779
- type: z19.literal(WidgetType.shopify_checkout_extension).default(WidgetType.shopify_checkout_extension)
1780
- });
1781
-
1782
- // src/schema/widgets/contentBlock.ts
1783
- import { z as z42 } from "zod";
1784
-
1785
- // src/schema/widgets/checkout-and-beyond/root.ts
1786
- import { z as z41 } from "zod";
1787
-
1788
- // src/schema/widgets/checkout-and-beyond/layout.ts
1789
- import { v7 as uuidv713 } from "uuid";
1790
- import { z as z40 } from "zod";
1791
-
1792
- // src/schema/widgets/checkout-and-beyond/shared.ts
1793
- import { z as z39 } from "zod";
1794
-
1795
- // src/schema/widgets/checkout-and-beyond/banner.ts
1796
- import { z as z20 } from "zod";
1797
-
1798
- // src/schema/widgets/checkout-and-beyond/utils.ts
1799
- import { isPlainObject as isPlainObject2 } from "es-toolkit";
1800
- import { get as get2, isString } from "es-toolkit/compat";
1801
-
1802
1639
  // src/schema/widgets/checkout-and-beyond/regex.ts
1803
1640
  var ARRAY_INDEX_STRING = /^(0|[1-9]\d*)$/;
1804
1641
  var DYNAMIC_TOKEN_REGEX = /^\{\{\s*[A-Za-z]+\s*\}\}$/;
@@ -1807,6 +1644,10 @@ var HEX_COLOR_REGEX = /^#([0-9a-fA-F]{3}|[0-9a-fA-F]{6})$/;
1807
1644
  var ROOT_RELATIVE_PATH_REGEX = /^\/(?!\/)/;
1808
1645
  var HTML_TAGS_REGEX = /<\/?[a-zA-Z][^>]*>/g;
1809
1646
 
1647
+ // src/schema/widgets/checkout-and-beyond/utils.ts
1648
+ import { isPlainObject as isPlainObject2 } from "es-toolkit";
1649
+ import { get as get2, isString } from "es-toolkit/compat";
1650
+
1810
1651
  // src/transforms/convertNumericObjects.ts
1811
1652
  import { isPlainObject } from "es-toolkit";
1812
1653
  var ARRAY_INDEX_STRING2 = /^(?:0|[1-9]\d*)$/;
@@ -1870,57 +1711,979 @@ var isReviewsType = isSectionType(SectionType.reviews);
1870
1711
  var isTextType = isSectionType(SectionType.text);
1871
1712
  var isVariantsType = isSectionType(SectionType.variants);
1872
1713
 
1873
- // src/schema/widgets/checkout-and-beyond/banner.ts
1874
- var CABBannerSection = z20.lazy(
1875
- () => CABLayoutSection.omit({ sectionType: true }).extend({
1876
- buttonField: z20.enum(buttonFields).optional(),
1877
- color: z20.enum(bannerColors).default("info"),
1878
- dismissible: z20.boolean().default(true),
1879
- /**
1880
- * The `s-banner` heading — localized content (a buyer can see a merchant-composed banner). Absent OR
1881
- * blank ⇒ no heading; the renderer emits no heading slot for `''` rather than an empty one.
1882
- *
1883
- * Merchant-composed buyer-facing plain text, so it rejects HTML at the boundary the same way
1884
- * `CABImageSection.altText` and `CABTextSection.content` do (the unchecked localized records elsewhere —
1885
- * `progressBar`'s gift labels, `reviews`' plurals — are converter/constant-sourced, not merchant input).
1886
- *
1887
- * The refinement is a last-resort ASSERTION, not the normalization boundary: `normalizeTextContent` only
1888
- * rewrites `sectionType: 'text'` nodes' `content`, so nothing strips markup or canonicalizes `{token}`
1889
- * here. A producer must strip upstream the way `composeOffer` does for `altText`. Get it wrong and
1890
- * `salvageSections` stubs the whole banner (children included) with a drift report — degraded, reported,
1891
- * not a 500. Nothing emits `heading` yet; the first converter that maps merchant banner copy into it
1892
- * either strips first or teaches `normalizeTextContent` to strip this field.
1893
- */
1894
- heading: z20.record(z20.string(), z20.string().refine(checkForHTML, NO_HTML)).optional(),
1895
- sectionType: z20.literal(SectionType.banner).default(SectionType.banner)
1896
- })
1897
- );
1898
-
1899
- // src/schema/widgets/checkout-and-beyond/button.ts
1900
- import { v7 as uuidv73 } from "uuid";
1901
- import { z as z25 } from "zod";
1902
-
1903
- // src/schema/widgets/checkout-and-beyond/image.ts
1904
- import { v7 as uuidv7 } from "uuid";
1905
- import { z as z23 } from "zod";
1714
+ // src/schema/widgets/checkout-and-beyond/variables.ts
1715
+ import { z as z17 } from "zod";
1906
1716
 
1907
- // src/schema/widgets/checkout-and-beyond/icons.ts
1908
- var iconNames = [
1909
- "alert-circle",
1910
- "alert-triangle",
1911
- "alert-triangle-filled",
1912
- "arrow-down",
1913
- "arrow-left",
1914
- "arrow-right",
1915
- "arrow-up",
1916
- "arrow-up-right",
1917
- "bag",
1918
- "bullet",
1919
- "calendar",
1920
- "camera",
1921
- "caret-down",
1922
- "cart",
1923
- "cash-dollar",
1717
+ // src/schema/widgets/checkout-and-beyond/rule.ts
1718
+ import { z as z16 } from "zod";
1719
+ var ruleTypes = [
1720
+ "cart",
1721
+ "cart_count",
1722
+ "cart_item_count",
1723
+ "cart_line_count",
1724
+ "cart_subtotal",
1725
+ "collection",
1726
+ "customer",
1727
+ "customer_order_count",
1728
+ "customer_tag",
1729
+ "customer_total_spent",
1730
+ "date",
1731
+ "product",
1732
+ "product_tag",
1733
+ "product_title",
1734
+ "product_type",
1735
+ "product_vendor"
1736
+ ];
1737
+ var ruleType = z16.enum(ruleTypes);
1738
+ var RuleType = ruleType.enum;
1739
+ var ruleOperators = [
1740
+ "after",
1741
+ "anything",
1742
+ "before",
1743
+ "contains",
1744
+ "contains_any",
1745
+ "does_not_contain",
1746
+ "does_not_contain_any",
1747
+ "equals",
1748
+ "does_not_equal",
1749
+ "greater_than",
1750
+ "less_than"
1751
+ ];
1752
+ var ruleOperator = z16.enum(ruleOperators);
1753
+ var RuleOperator = ruleOperator.enum;
1754
+ var RuleCondition = z16.object({
1755
+ operator: z16.enum(ruleOperators).default(RuleOperator.anything),
1756
+ products: z16.union([z16.array(z16.unknown()), z16.strictObject({}).transform(() => [])]).default(() => []),
1757
+ type: z16.enum(ruleTypes).default(RuleType.cart_subtotal),
1758
+ value: z16.coerce.string().default("")
1759
+ });
1760
+ var RuleLogicBlock = z16.object({
1761
+ rules: z16.array(RuleCondition).default(() => [])
1762
+ });
1763
+ var CABRulesetEntry = z16.object({
1764
+ exitIfMatched: z16.boolean().default(true),
1765
+ logic: z16.array(RuleLogicBlock).default(() => []),
1766
+ output: z16.array(
1767
+ z16.object({
1768
+ key: z16.string().default("should_show"),
1769
+ type: z16.literal("data_json").default("data_json"),
1770
+ value: z16.string().default("true")
1771
+ })
1772
+ ).default(() => [{ key: "should_show", type: "data_json", value: "true" }])
1773
+ });
1774
+ var CABRuleset = z16.union([z16.array(CABRulesetEntry), z16.strictObject({}).transform(() => [])]).default(() => []);
1775
+
1776
+ // src/schema/widgets/checkout-and-beyond/variables.ts
1777
+ var variableEffect = z17.enum(variableEffects);
1778
+ var CABVariableSeed = z17.object({
1779
+ dataSourceId: z17.number().nullable().default(null),
1780
+ ruleset: CABRuleset
1781
+ });
1782
+ var CABBooleanVariable = z17.object({
1783
+ /**
1784
+ * Holds until the first seed verdict lands (and forever, for unseeded variables). Omitted, it derives
1785
+ * from seededness — `false` with a `seed` (visibility is EARNED), `true` without — via the transform
1786
+ * below; a cross-field default has no `.default()` spelling. An explicit value always wins.
1787
+ */
1788
+ defaultValue: z17.boolean().optional(),
1789
+ name: z17.string().min(1),
1790
+ seed: CABVariableSeed.optional(),
1791
+ /** Defaulted so every stored declaration (all boolean before `text` existed) parses unchanged. */
1792
+ type: z17.literal(VariableType.boolean).default(VariableType.boolean)
1793
+ });
1794
+ var CABTextVariable = z17.object({
1795
+ defaultValue: z17.string(),
1796
+ name: z17.string().min(1),
1797
+ seed: z17.never().optional(),
1798
+ type: z17.literal(VariableType.text)
1799
+ });
1800
+ var CABNumberVariable = z17.object({
1801
+ defaultValue: z17.number(),
1802
+ name: z17.string().min(1),
1803
+ seed: z17.never().optional(),
1804
+ type: z17.literal(VariableType.number)
1805
+ });
1806
+ var CABVariable = z17.union([CABTextVariable, CABNumberVariable, CABBooleanVariable]).transform(
1807
+ (variable) => variable.type === VariableType.boolean ? { ...variable, defaultValue: variable.defaultValue ?? variable.seed === void 0 } : variable
1808
+ );
1809
+ var CABVariableEffect = z17.object({
1810
+ effect: variableEffect.default(VariableEffect.toggle),
1811
+ variable: z17.string().min(1)
1812
+ });
1813
+ var CABVisibility = z17.object({
1814
+ variable: z17.string().min(1),
1815
+ visibleWhen: z17.boolean().default(true)
1816
+ });
1817
+ var contentOperator = z17.enum(contentOperators);
1818
+ var resultCountOperator = z17.enum(resultCountOperators);
1819
+ var resultTagOperator = z17.enum(resultTagOperators);
1820
+ var mutatorEvent = z17.enum(mutatorEvents);
1821
+ var CABContentTrigger = z17.object({
1822
+ operator: contentOperator.default(ContentOperator.is_empty),
1823
+ type: z17.literal("content")
1824
+ });
1825
+ var CABResultCountTrigger = z17.object({
1826
+ operator: resultCountOperator.default(ResultCountOperator.equals),
1827
+ type: z17.literal("result_count"),
1828
+ value: z17.number().default(0)
1829
+ });
1830
+ var CABResultTagTrigger = z17.object({
1831
+ operator: resultTagOperator.default(ResultTagOperator.contains),
1832
+ type: z17.literal("result_tag"),
1833
+ value: z17.string().min(1)
1834
+ });
1835
+ var CABEventTrigger = z17.object({
1836
+ event: mutatorEvent,
1837
+ type: z17.literal("event")
1838
+ });
1839
+ var CABVariableTrigger = z17.discriminatedUnion("type", [
1840
+ CABContentTrigger,
1841
+ CABEventTrigger,
1842
+ CABResultCountTrigger,
1843
+ CABResultTagTrigger
1844
+ ]);
1845
+ var CABVariableMutator = z17.object({
1846
+ effect: variableEffect.default(VariableEffect.set_false),
1847
+ variable: z17.string().min(1),
1848
+ when: CABVariableTrigger
1849
+ });
1850
+ var CABVariableFields = {
1851
+ mutators: z17.array(CABVariableMutator).optional(),
1852
+ variables: z17.array(CABVariable).refine((variables) => new Set(variables.map(({ name }) => name)).size === variables.length, {
1853
+ message: "variable names must be unique within a section"
1854
+ }).optional(),
1855
+ visibility: CABVisibility.optional()
1856
+ };
1857
+
1858
+ // src/schema/widgets/checkout-and-beyond/text.ts
1859
+ var enumOrOmit = (...vals) => z18.string().transform((val) => vals.includes(val) ? val : void 0).optional();
1860
+ var TiptapText = z18.object({
1861
+ marks: z18.union([
1862
+ z18.array(
1863
+ z18.discriminatedUnion("type", [
1864
+ z18.object({ type: z18.literal("bold") }),
1865
+ z18.object({ type: z18.literal("italic") }),
1866
+ z18.object({
1867
+ attrs: z18.object({
1868
+ class: z18.string().nullable(),
1869
+ href: z18.union([
1870
+ z18.url(),
1871
+ z18.literal("#"),
1872
+ z18.string().regex(DYNAMIC_TOKEN_REGEX),
1873
+ z18.string().regex(ROOT_RELATIVE_PATH_REGEX)
1874
+ ]),
1875
+ rel: z18.string().default("noopener noreferrer nofollow"),
1876
+ target: z18.string().default("_blank")
1877
+ }),
1878
+ type: z18.literal("link")
1879
+ }),
1880
+ z18.object({ type: z18.literal("strike") }),
1881
+ z18.object({
1882
+ attrs: z18.object({
1883
+ color: enumOrOmit(...textColorNames).default(TextColorName.base),
1884
+ fontSize: enumOrOmit(...textSizeNames).default(TextSizeName.base)
1885
+ }),
1886
+ type: z18.literal("textStyle")
1887
+ })
1888
+ ])
1889
+ ),
1890
+ z18.strictObject({}).transform(() => [])
1891
+ ]).optional(),
1892
+ text: z18.string().default(""),
1893
+ type: z18.literal("text").default("text")
1894
+ });
1895
+ var TiptapParagraph = z18.object({
1896
+ attrs: z18.object({
1897
+ textAlign: enumOrOmit(...textAlignments)
1898
+ }).default({ textAlign: TextAlignment.start }),
1899
+ content: z18.union([z18.array(TiptapText), z18.strictObject({}).transform(() => [])]).default(() => []),
1900
+ type: z18.literal("paragraph").default("paragraph")
1901
+ });
1902
+ var TiptapDocument = z18.object({
1903
+ attrs: z18.object({
1904
+ blockSpacing: enumOrOmit(...spacings)
1905
+ }).default({ blockSpacing: Spacing.base }),
1906
+ content: z18.union([z18.array(TiptapParagraph), z18.strictObject({}).transform(() => [])]).default(() => [TiptapParagraph.parse({})]),
1907
+ type: z18.literal("doc").default("doc")
1908
+ });
1909
+ var CABTextTier = z18.object({
1910
+ threshold: z18.number().int().nonnegative(),
1911
+ thresholds: z18.record(z18.string(), z18.number().int().nonnegative()).default(() => ({})),
1912
+ tierId: z18.string().optional(),
1913
+ tierType: z18.enum(progressTierTypes).default(ProgressTierType.shipping)
1914
+ });
1915
+ var CABTextSection = z18.object({
1916
+ ...CABVariableFields,
1917
+ buttonField: z18.enum(buttonFields).optional(),
1918
+ content: z18.record(z18.string(), z18.union([z18.string(), TiptapDocument]).refine(checkForHTML, NO_HTML).optional()).default({ en: TiptapDocument.parse({}) }).optional(),
1919
+ name: z18.string().optional(),
1920
+ optionId: z18.number().optional(),
1921
+ sectionId: z18.uuid().default(() => uuidv7()),
1922
+ sectionType: z18.literal(SectionType.text).default(SectionType.text),
1923
+ tier: CABTextTier.optional()
1924
+ }).superRefine(({ buttonField, content }, ctx) => {
1925
+ if (buttonField === ButtonField.destinationUrl && content) {
1926
+ forEach(content, (value, lang) => {
1927
+ if (value && isString2(value)) {
1928
+ if (DYNAMIC_TOKEN_REGEX.test(value)) return;
1929
+ try {
1930
+ new URL(value);
1931
+ } catch {
1932
+ ctx.addIssue({
1933
+ code: "custom",
1934
+ message: "Invalid URL",
1935
+ path: ["content", lang]
1936
+ });
1937
+ }
1938
+ }
1939
+ });
1940
+ }
1941
+ });
1942
+
1943
+ // src/schema/widgets/post-purchase-offer/postPurchaseBlocks.ts
1944
+ var TextAlignment2 = z19.union([z19.enum(["leading", "center", "trailing"]), z19.unknown().transform(() => "leading")]);
1945
+ var TextSize = z19.union([
1946
+ z19.enum(["xsmall", "small", "base", "default", "medium", "large", "xlarge"]),
1947
+ z19.unknown().transform(() => "medium")
1948
+ ]);
1949
+ var CalloutBannerBlock = z19.object({
1950
+ id: z19.string().optional().default(() => uuidv42()),
1951
+ name: z19.string().optional(),
1952
+ settings: z19.object({
1953
+ superTitle: z19.union([z19.string(), TiptapDocument]).default(() => "Limited-time Offer"),
1954
+ title: z19.union([z19.string(), TiptapDocument]).default(() => "Add this customer favorite to your order")
1955
+ }),
1956
+ styles: z19.object({
1957
+ superTitleEmphasized: z19.boolean().default(false),
1958
+ superTitleSize: TextSize.default("large"),
1959
+ textAlignment: TextAlignment2.default("center"),
1960
+ titleEmphasized: z19.boolean().default(true),
1961
+ titleSize: TextSize.default("large")
1962
+ }),
1963
+ type: z19.literal(BlockType.callout_banner).default(BlockType.callout_banner)
1964
+ });
1965
+ var ImageBlock = z19.object({
1966
+ id: z19.string().optional().default(() => uuidv42()),
1967
+ name: z19.string().optional(),
1968
+ settings: z19.union([
1969
+ z19.object({
1970
+ /** This isn't used in the post-purchase offer widget */
1971
+ alt: z19.string().optional().default(""),
1972
+ image: z19.union([z19.literal(""), z19.url()]).default(""),
1973
+ imageSize: z19.number().default(20),
1974
+ imageType: z19.enum(["URL", "UPLOAD"]).default("URL")
1975
+ }),
1976
+ z19.array(z19.never()).transform(() => ({}))
1977
+ ]),
1978
+ type: z19.literal(BlockType.image).default(BlockType.image)
1979
+ });
1980
+ var ImageContentBlock = z19.object({
1981
+ id: z19.string().optional().default(() => uuidv42()),
1982
+ name: z19.string().optional(),
1983
+ settings: z19.object({
1984
+ alt: z19.string().optional().default(""),
1985
+ description: z19.union([z19.string(), TiptapDocument, z19.null()]).default(
1986
+ "Lorem ipsum dolor sit amet, consectetur adipiscing elit, sed do eiusmod tempor incididunt ut labore et dolore magna aliqua. Ut enim ad minim veniam, quis nostrud exercitation ullamco laboris nisi ut aliquip ex ea commodo consequat. Duis aute irure dolor in reprehenderit in voluptate velit esse cillum dolore eu fugiat nulla pariatur. Excepteur sint occaecat cupidatat non proident, sunt in culpa qui officia deserunt mollit anim id est laborum."
1987
+ ),
1988
+ descriptionSize: TextSize.default("medium"),
1989
+ horizontalAlignment: TextAlignment2.default("leading"),
1990
+ image: z19.union([z19.literal(""), z19.url()]).default(""),
1991
+ imagePlacement: z19.enum(["bottom", "left", "right", "top"]).optional().default("left"),
1992
+ imageSize: z19.number().default(20),
1993
+ superTitle: z19.union([z19.string(), TiptapDocument]).default("Lorem Ipsum!"),
1994
+ superTitleSize: TextSize.default("medium"),
1995
+ /** This isn't configurable in the admin-nextjs editor */
1996
+ swapContent: z19.boolean().optional().default(false),
1997
+ title: z19.union([z19.string(), TiptapDocument]).nullable().default("Lorem ipsum dolor sit amet"),
1998
+ titleSize: TextSize.default("medium")
1999
+ }),
2000
+ type: z19.literal(BlockType.image_content).default(BlockType.image_content)
2001
+ });
2002
+ var PayButtonBlock = z19.object({
2003
+ id: z19.string().optional().default(() => uuidv42()),
2004
+ name: z19.string().optional(),
2005
+ settings: z19.union([
2006
+ z19.object({
2007
+ label: z19.string().default("Pay Now")
2008
+ }),
2009
+ z19.array(z19.never()).transform(() => ({
2010
+ label: "Pay Now"
2011
+ }))
2012
+ ]),
2013
+ styles: z19.union([
2014
+ z19.object({
2015
+ buttonWidth: z19.number().min(10).max(100).default(50)
2016
+ }),
2017
+ z19.array(z19.never()).transform(() => ({
2018
+ buttonWidth: 50
2019
+ }))
2020
+ ]),
2021
+ type: z19.literal(BlockType.pay_button).default(BlockType.pay_button)
2022
+ });
2023
+ var ProductInformationBlock = z19.object({
2024
+ /** This isn't configurable in the admin-nextjs editor */
2025
+ hideProductImage: z19.boolean().optional().default(false),
2026
+ id: z19.string().optional().default(() => uuidv42()),
2027
+ name: z19.string().optional(),
2028
+ type: z19.literal(BlockType.product_information).default(BlockType.product_information)
2029
+ });
2030
+ var SeparatorBlock = z19.object({
2031
+ id: z19.string().optional().default(() => uuidv42()),
2032
+ name: z19.string().optional(),
2033
+ type: z19.literal(BlockType.separator).default(BlockType.separator)
2034
+ });
2035
+ var TextBlock = z19.object({
2036
+ id: z19.string().optional().default(() => uuidv42()),
2037
+ name: z19.string().optional(),
2038
+ settings: z19.object({
2039
+ description: z19.union([z19.string(), TiptapDocument]).optional().default(
2040
+ "Lorem ipsum dolor sit amet, consectetur adipiscing elit, sed do eiusmod tempor incididunt ut labore et dolore magna aliqua. Ut enim ad minim veniam, quis nostrud exercitation ullamco laboris nisi ut aliquip ex ea commodo consequat. Duis aute irure dolor in reprehenderit in voluptate velit esse cillum dolore eu fugiat nulla pariatur. Excepteur sint occaecat cupidatat non proident, sunt in culpa qui officia deserunt mollit anim id est laborum."
2041
+ ),
2042
+ /** This isn't used in the post-purchase offer widget */
2043
+ descriptionSize: TextSize.default("medium"),
2044
+ horizontalAlignment: TextAlignment2.default("leading"),
2045
+ superTitle: z19.union([z19.string(), TiptapDocument]).default("Super Title"),
2046
+ /** This isn't used in the post-purchase offer widget */
2047
+ superTitleSize: TextSize.default("medium"),
2048
+ title: z19.union([z19.string(), TiptapDocument]).nullable().default("Lorem ipsum dolor sit amet."),
2049
+ /** This isn't used in the post-purchase offer widget */
2050
+ titleSize: TextSize.default("medium")
2051
+ }),
2052
+ type: z19.literal(BlockType.text).default(BlockType.text)
2053
+ });
2054
+ var TimerBlock = z19.object({
2055
+ id: z19.string().optional().default(() => uuidv42()),
2056
+ name: z19.string().optional(),
2057
+ settings: z19.object({
2058
+ durationMinutes: z19.number().min(0).default(10),
2059
+ durationSeconds: z19.union([z19.number().min(0), z19.unknown().transform(() => 0)]).default(0),
2060
+ endOffer: z19.boolean().default(true),
2061
+ title: z19.union([z19.string(), TiptapDocument]).default("Hurry \u2014 your special offer ends in:")
2062
+ }),
2063
+ styles: z19.object({
2064
+ textAlignment: TextAlignment2.default("center"),
2065
+ timerBackgroundColor: z19.enum(["info", "warning", "success", "critical"]).default("warning"),
2066
+ timerEmphasized: z19.union([z19.boolean(), z19.unknown().transform(() => true)]).default(true),
2067
+ timerSize: TextSize.default("medium"),
2068
+ timerWidth: z19.number().min(10).max(100).optional().default(100),
2069
+ titleEmphasized: z19.union([z19.boolean(), z19.unknown().transform(() => true)]).default(false),
2070
+ titleSize: TextSize.default("medium")
2071
+ }),
2072
+ type: z19.literal(BlockType.timer).default(BlockType.timer)
2073
+ });
2074
+ var PostPurchaseBlock = z19.discriminatedUnion("type", [
2075
+ CalloutBannerBlock,
2076
+ ImageBlock,
2077
+ ImageContentBlock,
2078
+ PayButtonBlock,
2079
+ ProductInformationBlock,
2080
+ SeparatorBlock,
2081
+ TextBlock,
2082
+ TimerBlock
2083
+ ]);
2084
+ var isCalloutBannerBlock = (block) => isEqual(get3(block, "type"), BlockType.callout_banner);
2085
+ var isImageBlock = (block) => isEqual(get3(block, "type"), BlockType.image);
2086
+ var isImageContentBlock = (block) => isEqual(get3(block, "type"), BlockType.image_content);
2087
+ var isPayButtonBlock = (block) => isEqual(get3(block, "type"), BlockType.pay_button);
2088
+ var isProductInformationBlock = (block) => isEqual(get3(block, "type"), BlockType.product_information);
2089
+ var isSeparatorBlock = (block) => isEqual(get3(block, "type"), BlockType.separator);
2090
+ var isTextBlock = (block) => isEqual(get3(block, "type"), BlockType.text);
2091
+ var isTimerBlock = (block) => isEqual(get3(block, "type"), BlockType.timer);
2092
+
2093
+ // src/schema/widgets/post-purchase-offer/postPurchaseSettings.ts
2094
+ var PostPurchaseSettings = z20.object({
2095
+ advance: z20.object({ removePartialOrder: z20.boolean().default(true) }).optional().default(() => ({ removePartialOrder: true })),
2096
+ blocks: z20.union([z20.array(PostPurchaseBlock), z20.unknown().transform(() => [])]).default(() => [
2097
+ PostPurchaseBlock.parse({ settings: {}, styles: {}, type: BlockType.timer }),
2098
+ PostPurchaseBlock.parse({ settings: {}, styles: {}, type: BlockType.callout_banner }),
2099
+ PostPurchaseBlock.parse({ type: BlockType.product_information })
2100
+ ]),
2101
+ columnLayout: z20.boolean().optional(),
2102
+ discount: z20.object({
2103
+ amount: strictNumber.default(30),
2104
+ shouldShowSavingText: z20.boolean().optional().default(true),
2105
+ type: z20.enum(["none", "fixed_amount", "percentage"]).default("none")
2106
+ }),
2107
+ discountedFrom: z20.enum(["price", "compare_at_price"]).optional().default("price"),
2108
+ endpoint: z20.string().optional(),
2109
+ integrations: z20.object({
2110
+ judgeme: z20.boolean().default(false),
2111
+ junip: z20.boolean().optional().default(false),
2112
+ klaviyo: z20.boolean().default(false),
2113
+ loox: z20.boolean().default(false),
2114
+ okendo: z20.boolean().default(false),
2115
+ opinew: z20.boolean().optional().default(false),
2116
+ reviewsio: z20.boolean().optional().default(false),
2117
+ stamped: z20.boolean().default(false),
2118
+ yotpo: z20.boolean().default(false)
2119
+ }),
2120
+ key: z20.string().optional(),
2121
+ language: z20.object({
2122
+ description: z20.union([z20.string(), z20.unknown().transform(() => "")]).default(""),
2123
+ descriptionEnabled: z20.boolean().optional().default(false),
2124
+ descriptionRte: z20.object({
2125
+ content: z20.array(z20.unknown()),
2126
+ type: z20.string()
2127
+ }).optional(),
2128
+ descriptionSpacing: z20.enum(["none", "xtight", "tight", "default", "loose", "xloose"]).optional(),
2129
+ displayCtaPrice: z20.boolean().default(true),
2130
+ global: z20.object({
2131
+ declineAll: z20.string().optional().default("Decline All"),
2132
+ declineThisOffer: z20.string().default("Decline this offer"),
2133
+ free: z20.string().optional().default("Free"),
2134
+ notAvailable: z20.string().optional().default("Not available"),
2135
+ payNow: z20.string().default("Pay Now"),
2136
+ payNowUpgradeToSubscription: z20.string().optional().default("Upgrade to Subscription"),
2137
+ quantity: z20.string().default("Quantity"),
2138
+ /** This isn't configurable in the admin-nextjs editor */
2139
+ recurringShipping: z20.string().optional().default("Recurring shipping"),
2140
+ recurringSubtotal: z20.string().default("Recurring subtotal"),
2141
+ reviewsPlural: z20.string().optional().default("Reviews"),
2142
+ reviewsSingular: z20.string().optional().default("Review"),
2143
+ save: z20.union([z20.string(), z20.unknown().transform(() => "Save")]).optional().default("Save"),
2144
+ shipping: z20.string().default("Shipping"),
2145
+ subscriptionOption: z20.string().optional().default("Subscribe and Save"),
2146
+ subtotal: z20.string().default("Subtotal"),
2147
+ taxes: z20.string().default("Taxes"),
2148
+ total: z20.string().default("Total")
2149
+ }).optional().default(() => ({
2150
+ declineAll: "Decline All",
2151
+ declineThisOffer: "Decline this offer",
2152
+ free: "Free",
2153
+ notAvailable: "Not available",
2154
+ payNow: "Pay Now",
2155
+ payNowUpgradeToSubscription: "Upgrade to Subscription",
2156
+ quantity: "Quantity",
2157
+ /** This isn't configurable in the admin-nextjs editor */
2158
+ recurringShipping: "Recurring shipping",
2159
+ recurringSubtotal: "Recurring subtotal",
2160
+ reviewsPlural: "Reviews",
2161
+ reviewsSingular: "Review",
2162
+ save: "Save",
2163
+ shipping: "Shipping",
2164
+ subscriptionOption: "Subscribe and Save",
2165
+ subtotal: "Subtotal",
2166
+ taxes: "Taxes",
2167
+ total: "Total"
2168
+ })),
2169
+ globalTranslation: z20.string().optional().default("english")
2170
+ }),
2171
+ metafields: z20.boolean().default(false),
2172
+ /** This isn't configurable in the admin-nextjs editor */
2173
+ offer: z20.object({
2174
+ count: z20.number().default(1)
2175
+ }),
2176
+ offersLayout: z20.object({
2177
+ itemsPerPage: z20.number().optional(),
2178
+ type: z20.enum(["list", "grid", "carousel"]).default("list")
2179
+ }).optional().default({
2180
+ type: "list"
2181
+ }),
2182
+ /** This isn't configurable in the admin-nextjs editor */
2183
+ previewMode: z20.boolean().default(false),
2184
+ productLimit: z20.number().optional().default(1),
2185
+ productOptions: z20.object({
2186
+ /** This isn't configurable in the admin-nextjs editor */
2187
+ hideOutOfStockVariants: z20.boolean().optional().default(false),
2188
+ matchVariant: z20.boolean().optional().default(true),
2189
+ showDeclineAll: z20.enum(["above", "below", "both", "none"]).optional(),
2190
+ showShipping: z20.boolean().optional().default(true),
2191
+ showSubtotal: z20.boolean().optional().default(true),
2192
+ showTaxes: z20.boolean().optional().default(true),
2193
+ showTotal: z20.boolean().optional().default(true),
2194
+ showVariantSelectors: z20.boolean().optional().default(true),
2195
+ variantSelectorDisplayMode: z20.enum(["separate", "single"]).optional().default("separate")
2196
+ }),
2197
+ productType: z20.union([z20.enum(["one-time", "subscription", "both"]), z20.literal("").transform(() => "one-time")]).default("one-time"),
2198
+ productTypeSelector: z20.enum(["dropdown", "radio"]).optional().default("radio"),
2199
+ quantityInputs: z20.object({
2200
+ defaultQuantity: z20.union([z20.number(), z20.null().transform(() => 1)]).default(1),
2201
+ enabled: z20.boolean().default(true),
2202
+ maxValue: z20.union([z20.number(), z20.null().transform(() => 15)]).default(15),
2203
+ minValue: z20.union([z20.number().min(0), z20.unknown().transform(() => 0)]).default(1)
2204
+ }),
2205
+ shipping: z20.object({
2206
+ amount: strictNumber.default(10),
2207
+ /** This isn't configurable in the admin-nextjs editor */
2208
+ enabled: z20.boolean().default(true),
2209
+ title: z20.string().optional().default("Shipping Fees"),
2210
+ type: z20.enum(["free", "fixed_amount"]).default("free")
2211
+ }),
2212
+ styles: z20.object({
2213
+ starColor: z20.string().optional().default("#fadb14"),
2214
+ starSize: z20.union([z20.enum(["small", "medium", "large"]), z20.unknown().transform(() => "large")]).optional().default("large"),
2215
+ starStrokeColor: z20.string().optional().default("#fadb14"),
2216
+ strokeWidth: z20.string().optional().default("1")
2217
+ }).optional(),
2218
+ subImages: z20.number().nullish().default(8),
2219
+ subscription: z20.object({
2220
+ discount: z20.object({
2221
+ amount: strictNumber.default(30),
2222
+ shouldShowSavingText: z20.boolean().optional().default(true),
2223
+ type: z20.enum(["none", "fixed_amount", "percentage"]).default("none")
2224
+ }),
2225
+ shipping: z20.object({
2226
+ amount: strictNumber.default(1),
2227
+ /** This isn't configurable in the admin-nextjs editor */
2228
+ enabled: z20.boolean().default(true),
2229
+ /** This isn't configurable in the admin-nextjs editor */
2230
+ recurringAmount: strictNumber.default(2),
2231
+ shippingTitle: z20.string().default("Shipping Fees"),
2232
+ type: z20.enum(["free", "fixed_amount"]).default("free")
2233
+ })
2234
+ }).optional().default({
2235
+ discount: {
2236
+ amount: 30,
2237
+ shouldShowSavingText: true,
2238
+ type: "none"
2239
+ },
2240
+ shipping: {
2241
+ amount: 1,
2242
+ /** This isn't configurable in the admin-nextjs editor */
2243
+ enabled: true,
2244
+ /** This isn't configurable in the admin-nextjs editor */
2245
+ recurringAmount: 2,
2246
+ shippingTitle: "Shipping Fees",
2247
+ type: "free"
2248
+ }
2249
+ }),
2250
+ subscriptionIsDefault: z20.boolean().optional(),
2251
+ /** This isn't configurable in the admin-nextjs editor */
2252
+ template: z20.string().optional().default(""),
2253
+ type: z20.literal("shopify_post_purchase_extension").default("shopify_post_purchase_extension"),
2254
+ upgradeToSubscription: z20.object({
2255
+ acceptButtonText: z20.string().optional().default("Upgrade"),
2256
+ allow: z20.boolean().optional().default(false),
2257
+ emailRefundNotice: z20.boolean().optional().default(false),
2258
+ errorBannerText: z20.string().optional().default("This subscription cannot be added - limit one per order")
2259
+ }).optional().default(() => ({
2260
+ acceptButtonText: "Upgrade",
2261
+ allow: false,
2262
+ emailRefundNotice: false,
2263
+ errorBannerText: "This subscription cannot be added - limit one per order"
2264
+ }))
2265
+ });
2266
+
2267
+ // src/schema/postPurchaseProductDisplay.ts
2268
+ var language = PostPurchaseSettings.shape.language;
2269
+ var PostPurchasePrimaryImageSource = z21.string().default(
2270
+ "https://cdn.shopify.com/shopifycloud/shopify/assets/no-image-2048-5e88c1b20e087fb7bbe9a3771824e743c244f437e4f8ba93bbf7b11b53f7824c.gif"
2271
+ );
2272
+ var PostPurchaseProductDisplay = z21.object({
2273
+ discountedFrom: PostPurchaseSettings.shape.discountedFrom,
2274
+ gallery: PostPurchaseProductGallery.optional(),
2275
+ language: language.pick({
2276
+ description: true,
2277
+ descriptionEnabled: true,
2278
+ descriptionRte: true,
2279
+ descriptionSpacing: true
2280
+ }),
2281
+ primaryImage: z21.object({ description: z21.string(), source: z21.string() }),
2282
+ productOptions: PostPurchaseSettings.shape.productOptions.pick({
2283
+ showDeclineAll: true,
2284
+ showShipping: true,
2285
+ showSubtotal: true,
2286
+ showTaxes: true,
2287
+ showTotal: true,
2288
+ showVariantSelectors: true
2289
+ }),
2290
+ responseDescription: language.shape.description,
2291
+ shouldShowSavingText: PostPurchaseSettings.shape.discount.shape.shouldShowSavingText
2292
+ });
2293
+
2294
+ // src/schema/postPurchaseProductSettings.ts
2295
+ import { z as z22 } from "zod";
2296
+ var amount = z22.union([z22.number().nonnegative(), PostPurchaseAmount.transform(Number)]);
2297
+ var PostPurchaseProductSettings = PostPurchaseSettings.pick({
2298
+ discountedFrom: true,
2299
+ language: true,
2300
+ productLimit: true,
2301
+ productOptions: true,
2302
+ productType: true,
2303
+ productTypeSelector: true,
2304
+ quantityInputs: true,
2305
+ subscriptionIsDefault: true,
2306
+ upgradeToSubscription: true
2307
+ }).extend({
2308
+ advance: z22.unknown().default({}),
2309
+ blocks: z22.array(z22.unknown()).optional(),
2310
+ discount: PostPurchaseSettings.shape.discount.extend({ amount: amount.default(30) }),
2311
+ integrations: z22.unknown().default({}),
2312
+ shipping: PostPurchaseSettings.shape.shipping.extend({ amount: amount.default(10) }),
2313
+ styles: z22.unknown().default({}),
2314
+ subImages: PostPurchaseSettings.shape.subImages.catch(null),
2315
+ subscription: z22.unknown().default(PostPurchaseSettings.shape.subscription.parse(void 0))
2316
+ });
2317
+
2318
+ // src/schema/postPurchaseSelection.ts
2319
+ import { z as z23 } from "zod";
2320
+ var SelectionClaimsSchema = DecideRequestSchema.extend({
2321
+ appId: PostPurchaseAppIdSchema,
2322
+ entry: DecisionEntrySchema,
2323
+ iss: z23.literal("rebuy-api"),
2324
+ purpose: z23.literal("post-purchase-selection")
2325
+ });
2326
+ var SessionStartRequestSchema = DecideRequestSchema.extend({
2327
+ selectionToken: z23.string().min(1).max(8192).optional()
2328
+ }).strict();
2329
+
2330
+ // src/schema/postPurchaseSession.ts
2331
+ import { z as z24 } from "zod";
2332
+ var SessionIdentitySchema = DecideRequestSchema.extend({ appId: PostPurchaseAppIdSchema });
2333
+ var SessionOrderTimingSchema = z24.object({
2334
+ nativeDeadline: PostPurchaseTimestampSchema,
2335
+ orderCreatedAt: PostPurchaseTimestampSchema,
2336
+ orderId: PostPurchaseOrderIdSchema,
2337
+ timingSource: z24.literal("shopify-order-created-at")
2338
+ });
2339
+ var ReadySessionTimingSchema = SessionOrderTimingSchema.extend({
2340
+ deadline: PostPurchaseTimestampSchema,
2341
+ entry: DecisionEntrySchema,
2342
+ policySnapshot: SessionPolicySchema,
2343
+ startedAt: PostPurchaseTimestampSchema
2344
+ }).refine((session) => session.orderCreatedAt <= session.startedAt, {
2345
+ message: "startedAt must not precede orderCreatedAt",
2346
+ path: ["startedAt"]
2347
+ }).refine((session) => session.startedAt <= session.deadline, {
2348
+ message: "deadline must not precede startedAt",
2349
+ path: ["deadline"]
2350
+ }).refine((session) => session.deadline <= session.nativeDeadline, {
2351
+ message: "deadline must not exceed nativeDeadline",
2352
+ path: ["deadline"]
2353
+ });
2354
+ var SessionStartResponseSchema = z24.object({
2355
+ data: z24.object({
2356
+ phase: z24.literal("render"),
2357
+ serverNow: PostPurchaseTimestampSchema,
2358
+ session: ReadySessionTimingSchema,
2359
+ workflowPhase: z24.literal("start")
2360
+ }),
2361
+ successful: z24.literal(true)
2362
+ });
2363
+
2364
+ // src/schema/postPurchaseSessionClose.ts
2365
+ import { z as z25 } from "zod";
2366
+ var SessionClosureSchema = z25.object({ closedAt: PostPurchaseTimestampSchema, status: z25.literal("closed") });
2367
+ var SessionCloseRequestSchema = DecideRequestSchema.strict();
2368
+ var SessionCloseResponseSchema = z25.object({ data: SessionClosureSchema, successful: z25.literal(true) });
2369
+
2370
+ // src/schema/postPurchaseShadow.ts
2371
+ import { z as z26 } from "zod";
2372
+ var PostPurchaseShadowSelectionSchema = z26.discriminatedUnion("verdict", [
2373
+ z26.object({ entry: DecisionEntrySchema, verdict: z26.literal("render") }),
2374
+ z26.object({ verdict: z26.literal("skip") })
2375
+ ]);
2376
+ var PostPurchaseShadowReportFields = z26.object({
2377
+ differences: z26.array(z26.enum(["verdict", "entry", "targeting", "incomplete-capture", "unsupported-configuration"])).refine((differences) => new Set(differences).size === differences.length, {
2378
+ message: "differences must not contain duplicate entries"
2379
+ }),
2380
+ legacySelection: PostPurchaseShadowSelectionSchema,
2381
+ phase: z26.literal("shouldRender"),
2382
+ sampleId: z26.string(),
2383
+ serverSelection: PostPurchaseShadowSelectionSchema.optional(),
2384
+ status: z26.enum(["match", "diverged", "incomplete"]),
2385
+ targetingFlowIds: z26.array(z26.number().int().positive()),
2386
+ workflowPhase: z26.literal("decide")
2387
+ });
2388
+ var PostPurchaseShadowReportSchema = PostPurchaseShadowReportFields.refine(
2389
+ (report) => report.status !== "match" || report.differences.length === 0,
2390
+ { message: "status 'match' requires an empty differences array", path: ["status"] }
2391
+ ).refine((report) => report.status !== "diverged" || report.differences.length > 0, {
2392
+ message: "status 'diverged' requires a non-empty differences array",
2393
+ path: ["status"]
2394
+ }).refine((report) => report.status !== "diverged" || report.serverSelection !== void 0, {
2395
+ message: "status 'diverged' requires a serverSelection to diverge from",
2396
+ path: ["status"]
2397
+ });
2398
+
2399
+ // src/schema/postPurchaseSkipTrace.ts
2400
+ import { z as z27 } from "zod";
2401
+ var POST_PURCHASE_SKIP_LIMIT = 32;
2402
+ var PostPurchaseSkipTraceSchema = z27.array(
2403
+ z27.object({
2404
+ entry: DecisionEntrySchema,
2405
+ reason: PostPurchaseSkipReasonSchema
2406
+ })
2407
+ ).max(POST_PURCHASE_SKIP_LIMIT);
2408
+
2409
+ // src/schema/postPurchaseVariantCatalog.ts
2410
+ import { z as z28 } from "zod";
2411
+ var PostPurchaseVariantSelector = z28.object({ variantId: PostPurchaseVariantId }).strict();
2412
+ var PostPurchaseVariantOption = OfferProduct.shape.options.element.extend({
2413
+ id: z28.number().int().positive(),
2414
+ position: z28.number().int().min(1).max(3)
2415
+ });
2416
+ var PostPurchaseVariantValues = OfferProduct.shape.variants.element.pick({
2417
+ option1: true,
2418
+ option2: true,
2419
+ option3: true
2420
+ });
2421
+ var PostPurchaseVariantCatalog = z28.object({
2422
+ displayMode: PostPurchaseSettings.shape.productOptions.shape.variantSelectorDisplayMode,
2423
+ options: z28.array(PostPurchaseVariantOption),
2424
+ productId: PostPurchaseProductId,
2425
+ showSelectors: PostPurchaseSettings.shape.productOptions.shape.showVariantSelectors,
2426
+ variants: z28.array(
2427
+ PostPurchaseVariantValues.partial().extend({
2428
+ available: z28.boolean(),
2429
+ id: PostPurchaseVariantId,
2430
+ imageId: z28.number().int().nonnegative().nullish(),
2431
+ title: OfferProduct.shape.variants.element.shape.title
2432
+ })
2433
+ )
2434
+ });
2435
+
2436
+ // src/schema/postPurchaseVariantDefault.ts
2437
+ import { z as z29 } from "zod";
2438
+ var values = PostPurchaseVariantValues.partial().extend({
2439
+ option1: PostPurchaseVariantValues.shape.option1.nullish()
2440
+ });
2441
+ var variant = values.extend({
2442
+ id: PostPurchaseVariantId,
2443
+ inventoryManagement: z29.string().nullable(),
2444
+ inventoryPolicy: z29.string(),
2445
+ inventoryQuantity: z29.number()
2446
+ });
2447
+ var options = z29.array(PostPurchaseVariantOption.pick({ name: true, values: true }));
2448
+ var PostPurchaseVariantDefaultProduct = z29.object({
2449
+ id: PostPurchaseProductId,
2450
+ options,
2451
+ selectedVariant: variant.optional(),
2452
+ variants: z29.array(variant)
2453
+ });
2454
+ var PostPurchaseVariantDefaultSettings = PostPurchaseSettings.shape.productOptions.pick({
2455
+ hideOutOfStockVariants: true,
2456
+ matchVariant: true
2457
+ });
2458
+ var PostPurchaseOrderAttributes = z29.record(z29.string(), z29.array(z29.string())).default({});
2459
+
2460
+ // src/schema/shopConfig.ts
2461
+ import { z as z30 } from "zod";
2462
+ var ShopConfig = z30.object({
2463
+ activeExperiments: z30.array(
2464
+ z30.object({
2465
+ data: z30.array(
2466
+ z30.object({
2467
+ aliasName: z30.string(),
2468
+ cssInput: z30.string().nullish(),
2469
+ elementId: z30.coerce.number(),
2470
+ id: z30.coerce.number(),
2471
+ javascriptInput: z30.string().nullish(),
2472
+ traffic: z30.coerce.number()
2473
+ })
2474
+ ),
2475
+ id: z30.coerce.number(),
2476
+ name: z30.string(),
2477
+ pageTarget: z30.string().nullable(),
2478
+ pageTargetUrl: z30.string().nullable(),
2479
+ placeholderId: z30.coerce.number().nullable(),
2480
+ type: z30.string()
2481
+ })
2482
+ ),
2483
+ activePackages: z30.array(
2484
+ z30.object({
2485
+ cancelledAt: z30.string().nullable(),
2486
+ id: z30.number(),
2487
+ installedAt: z30.string().nullable(),
2488
+ isActive: z30.boolean(),
2489
+ isBillable: z30.boolean(),
2490
+ packageId: z30.number(),
2491
+ packageName: z30.string(),
2492
+ shortName: z30.string(),
2493
+ trialDays: z30.number(),
2494
+ uninstalledAt: z30.string().nullable()
2495
+ })
2496
+ ),
2497
+ apiKey: z30.string(),
2498
+ billingVersion: z30.string().nullable(),
2499
+ cacheKey: z30.coerce.number(),
2500
+ carousel: z30.enum(["flickity", "splide"]),
2501
+ currency: z30.string(),
2502
+ currencySymbol: z30.string(),
2503
+ domain: z30.string(),
2504
+ enabledJquery: z30.boolean(),
2505
+ enabledPresentmentCurrencies: z30.array(z30.string()),
2506
+ hasSmartCollectionsEnabled: z30.boolean(),
2507
+ hasSmartSearchEnabled: z30.boolean(),
2508
+ id: z30.coerce.number(),
2509
+ integrations: z30.record(
2510
+ z30.enum([
2511
+ "attentive",
2512
+ "judgeme",
2513
+ "junip",
2514
+ "klaviyo",
2515
+ "loox",
2516
+ "okendo",
2517
+ "opinew",
2518
+ "recharge",
2519
+ "reviewsio",
2520
+ "stamped",
2521
+ "yotpo"
2522
+ ]),
2523
+ z30.union([z30.boolean(), z30.unknown()])
2524
+ ),
2525
+ markets: z30.object({
2526
+ enabled: z30.boolean()
2527
+ }),
2528
+ monetize: z30.object({
2529
+ publisherKey: z30.string().nullable()
2530
+ }).nullish(),
2531
+ moneyFormat: z30.string(),
2532
+ myshopifyDomain: z30.string(),
2533
+ primaryLocale: z30.string(),
2534
+ productGroupsEnabled: z30.enum(["no", "yes"]).transform((value) => value === "yes"),
2535
+ rechargeCustomDomain: z30.string().nullable(),
2536
+ sellingPlansEnabled: z30.boolean(),
2537
+ shopId: z30.number(),
2538
+ shopifySellingPlansEnabled: z30.boolean(),
2539
+ shopName: z30.string(),
2540
+ storefrontAccessToken: z30.string().nullable(),
2541
+ useRebuyIcons: z30.boolean()
2542
+ });
2543
+
2544
+ // src/schema/userConfig.ts
2545
+ import { z as z31 } from "zod";
2546
+ var UserConfig = z31.object({
2547
+ shop: ShopConfig,
2548
+ /**
2549
+ * `.catch(undefined)` is the safety bar: smart-cart shape drift can NEVER fail `fetchUserConfig`,
2550
+ * which resolves the apiKey for every offers/monetize/analytics/gift request.
2551
+ */
2552
+ smartCart: SmartCartConfig.nullish().catch(void 0),
2553
+ smartFlows: z31.array(z31.unknown())
2554
+ });
2555
+
2556
+ // src/schema/widgetData.ts
2557
+ import { z as z59 } from "zod";
2558
+
2559
+ // src/schema/widgets/abTestingPlaceholder.ts
2560
+ import { z as z32 } from "zod";
2561
+ var ABTestingPlaceholder = z32.looseObject({
2562
+ type: z32.literal("placeholder")
2563
+ });
2564
+
2565
+ // src/schema/widgets/checkout-and-beyond/constants.ts
2566
+ import { uniqBy } from "es-toolkit";
2567
+ var DEFAULT_ENDPOINTS = [
2568
+ { label: "Recommended (AI)", value: "/products/recommended" },
2569
+ { label: "Top Sellers", value: "/products/top_sellers" },
2570
+ { label: "Buy It Again", value: "/products/purchased" },
2571
+ { label: "Recently Viewed", value: "/products/viewed" },
2572
+ { label: "Products Search", value: "/products/search" },
2573
+ { label: "Collection Products", value: "/products/collections" },
2574
+ { label: "Similar Products (AI)", value: "/products/similar_products" }
2575
+ ];
2576
+ var STATIC_ENDPOINTS = [
2577
+ { label: "Recommended (AI)", value: "/products/recommended" },
2578
+ { label: "Top Sellers", value: "/products/top_sellers" },
2579
+ { label: "Trending Products", value: "/products/trending_products" },
2580
+ { label: "Buy It Again", value: "/products/purchased" },
2581
+ { label: "Collection Products", value: "/products/collections" },
2582
+ { label: "Recently Viewed", value: "/products/viewed" },
2583
+ { label: "Static Products", value: "/products/static" },
2584
+ { label: "Products Search", value: "/products/search" },
2585
+ { label: "Similar Products (AI)", value: "/products/similar_products" }
2586
+ ];
2587
+ var COMBINED_ENDPOINTS = uniqBy([...DEFAULT_ENDPOINTS, ...STATIC_ENDPOINTS], (item) => item.value);
2588
+ var targetAreas = {
2589
+ [EditorMode.checkoutExtension]: [
2590
+ { icon: "splitscreen_top", label: "Header Area", width: "984px" },
2591
+ { icon: "splitscreen_left", label: "Main Column", width: "503px" },
2592
+ { icon: "splitscreen_right", label: "Summary Column", width: "404px" }
2593
+ ],
2594
+ [EditorMode.postPurchaseOffer]: null,
2595
+ [EditorMode.thankYouPage]: [
2596
+ { icon: "splitscreen_top", label: "Header Area", width: "984px" },
2597
+ { icon: "splitscreen_left", label: "Main Column", width: "503px" },
2598
+ { icon: "splitscreen_right", label: "Summary Column", width: "404px" }
2599
+ ],
2600
+ [EditorMode.orderStatusPage]: [
2601
+ // { fill: true, flip: 'vertical', icon: 'bottom_navigation', label: 'Announcement Bar' },
2602
+ { icon: "splitscreen_top", label: "Header Area", width: "1124px" },
2603
+ { fill: true, icon: "view_column_2", label: "Main Area", width: "646px" },
2604
+ { icon: "splitscreen_bottom", label: "Footer Area", width: "1124px" }
2605
+ ],
2606
+ [EditorMode.ordersIndexPage]: [
2607
+ // { fill: true, flip: 'vertical', icon: 'bottom_navigation', label: 'Announcement Bar' },
2608
+ { icon: "splitscreen_top", label: "Main Area", width: "1124px" }
2609
+ ],
2610
+ [EditorMode.customerProfilePage]: [
2611
+ // { fill: true, flip: 'vertical', icon: 'bottom_navigation', label: 'Announcement Bar' },
2612
+ { icon: "splitscreen_top", label: "Main Area", width: "1124px" }
2613
+ ]
2614
+ };
2615
+
2616
+ // src/schema/widgets/checkoutExtension.ts
2617
+ import { z as z33 } from "zod";
2618
+ var CheckoutExtension = z33.looseObject({
2619
+ type: z33.literal(WidgetType.shopify_checkout_extension).default(WidgetType.shopify_checkout_extension)
2620
+ });
2621
+
2622
+ // src/schema/widgets/contentBlock.ts
2623
+ import { z as z53 } from "zod";
2624
+
2625
+ // src/schema/widgets/checkout-and-beyond/root.ts
2626
+ import { z as z52 } from "zod";
2627
+
2628
+ // src/schema/widgets/checkout-and-beyond/layout.ts
2629
+ import { v7 as uuidv713 } from "uuid";
2630
+ import { z as z51 } from "zod";
2631
+
2632
+ // src/schema/widgets/checkout-and-beyond/shared.ts
2633
+ import { z as z50 } from "zod";
2634
+
2635
+ // src/schema/widgets/checkout-and-beyond/banner.ts
2636
+ import { z as z34 } from "zod";
2637
+ var CABBannerSection = z34.lazy(
2638
+ () => CABLayoutSection.omit({ sectionType: true }).extend({
2639
+ buttonField: z34.enum(buttonFields).optional(),
2640
+ color: z34.enum(bannerColors).default("info"),
2641
+ dismissible: z34.boolean().default(true),
2642
+ /**
2643
+ * The `s-banner` heading — localized content (a buyer can see a merchant-composed banner). Absent OR
2644
+ * blank ⇒ no heading; the renderer emits no heading slot for `''` rather than an empty one.
2645
+ *
2646
+ * Merchant-composed buyer-facing plain text, so it rejects HTML at the boundary the same way
2647
+ * `CABImageSection.altText` and `CABTextSection.content` do (the unchecked localized records elsewhere —
2648
+ * `progressBar`'s gift labels, `reviews`' plurals — are converter/constant-sourced, not merchant input).
2649
+ *
2650
+ * The refinement is a last-resort ASSERTION, not the normalization boundary: `normalizeTextContent` only
2651
+ * rewrites `sectionType: 'text'` nodes' `content`, so nothing strips markup or canonicalizes `{token}`
2652
+ * here. A producer must strip upstream the way `composeOffer` does for `altText`. Get it wrong and
2653
+ * `salvageSections` stubs the whole banner (children included) with a drift report — degraded, reported,
2654
+ * not a 500. Nothing emits `heading` yet; the first converter that maps merchant banner copy into it
2655
+ * either strips first or teaches `normalizeTextContent` to strip this field.
2656
+ */
2657
+ heading: z34.record(z34.string(), z34.string().refine(checkForHTML, NO_HTML)).optional(),
2658
+ sectionType: z34.literal(SectionType.banner).default(SectionType.banner)
2659
+ })
2660
+ );
2661
+
2662
+ // src/schema/widgets/checkout-and-beyond/button.ts
2663
+ import { v7 as uuidv73 } from "uuid";
2664
+ import { z as z36 } from "zod";
2665
+
2666
+ // src/schema/widgets/checkout-and-beyond/image.ts
2667
+ import { v7 as uuidv72 } from "uuid";
2668
+ import { z as z35 } from "zod";
2669
+
2670
+ // src/schema/widgets/checkout-and-beyond/icons.ts
2671
+ var iconNames = [
2672
+ "alert-circle",
2673
+ "alert-triangle",
2674
+ "alert-triangle-filled",
2675
+ "arrow-down",
2676
+ "arrow-left",
2677
+ "arrow-right",
2678
+ "arrow-up",
2679
+ "arrow-up-right",
2680
+ "bag",
2681
+ "bullet",
2682
+ "calendar",
2683
+ "camera",
2684
+ "caret-down",
2685
+ "cart",
2686
+ "cash-dollar",
1924
2687
  "categories",
1925
2688
  "check",
1926
2689
  "check-circle",
@@ -1988,162 +2751,18 @@ var IconSize = freezeEnum(iconSizes);
1988
2751
  var iconTones = ["auto", "critical", "custom", "info", "neutral", "success", "warning"];
1989
2752
  var IconTone = freezeEnum(iconTones);
1990
2753
 
1991
- // src/schema/widgets/checkout-and-beyond/variables.ts
1992
- import { z as z22 } from "zod";
1993
-
1994
- // src/schema/widgets/checkout-and-beyond/rule.ts
1995
- import { z as z21 } from "zod";
1996
- var ruleTypes = [
1997
- "cart",
1998
- "cart_count",
1999
- "cart_item_count",
2000
- "cart_line_count",
2001
- "cart_subtotal",
2002
- "collection",
2003
- "customer",
2004
- "customer_order_count",
2005
- "customer_tag",
2006
- "customer_total_spent",
2007
- "date",
2008
- "product",
2009
- "product_tag",
2010
- "product_title",
2011
- "product_type",
2012
- "product_vendor"
2013
- ];
2014
- var ruleType = z21.enum(ruleTypes);
2015
- var RuleType = ruleType.enum;
2016
- var ruleOperators = [
2017
- "after",
2018
- "anything",
2019
- "before",
2020
- "contains",
2021
- "contains_any",
2022
- "does_not_contain",
2023
- "does_not_contain_any",
2024
- "equals",
2025
- "does_not_equal",
2026
- "greater_than",
2027
- "less_than"
2028
- ];
2029
- var ruleOperator = z21.enum(ruleOperators);
2030
- var RuleOperator = ruleOperator.enum;
2031
- var RuleCondition = z21.object({
2032
- operator: z21.enum(ruleOperators).default(RuleOperator.anything),
2033
- products: z21.union([z21.array(z21.unknown()), z21.strictObject({}).transform(() => [])]).default(() => []),
2034
- type: z21.enum(ruleTypes).default(RuleType.cart_subtotal),
2035
- value: z21.coerce.string().default("")
2036
- });
2037
- var RuleLogicBlock = z21.object({
2038
- rules: z21.array(RuleCondition).default(() => [])
2039
- });
2040
- var CABRulesetEntry = z21.object({
2041
- exitIfMatched: z21.boolean().default(true),
2042
- logic: z21.array(RuleLogicBlock).default(() => []),
2043
- output: z21.array(
2044
- z21.object({
2045
- key: z21.string().default("should_show"),
2046
- type: z21.literal("data_json").default("data_json"),
2047
- value: z21.string().default("true")
2048
- })
2049
- ).default(() => [{ key: "should_show", type: "data_json", value: "true" }])
2050
- });
2051
- var CABRuleset = z21.union([z21.array(CABRulesetEntry), z21.strictObject({}).transform(() => [])]).default(() => []);
2052
-
2053
- // src/schema/widgets/checkout-and-beyond/variables.ts
2054
- var variableEffect = z22.enum(variableEffects);
2055
- var CABVariableSeed = z22.object({
2056
- dataSourceId: z22.number().nullable().default(null),
2057
- ruleset: CABRuleset
2058
- });
2059
- var CABBooleanVariable = z22.object({
2060
- /**
2061
- * Holds until the first seed verdict lands (and forever, for unseeded variables). Omitted, it derives
2062
- * from seededness — `false` with a `seed` (visibility is EARNED), `true` without — via the transform
2063
- * below; a cross-field default has no `.default()` spelling. An explicit value always wins.
2064
- */
2065
- defaultValue: z22.boolean().optional(),
2066
- name: z22.string().min(1),
2067
- seed: CABVariableSeed.optional(),
2068
- /** Defaulted so every stored declaration (all boolean before `text` existed) parses unchanged. */
2069
- type: z22.literal(VariableType.boolean).default(VariableType.boolean)
2070
- });
2071
- var CABTextVariable = z22.object({
2072
- defaultValue: z22.string(),
2073
- name: z22.string().min(1),
2074
- seed: z22.never().optional(),
2075
- type: z22.literal(VariableType.text)
2076
- });
2077
- var CABNumberVariable = z22.object({
2078
- defaultValue: z22.number(),
2079
- name: z22.string().min(1),
2080
- seed: z22.never().optional(),
2081
- type: z22.literal(VariableType.number)
2082
- });
2083
- var CABVariable = z22.union([CABTextVariable, CABNumberVariable, CABBooleanVariable]).transform(
2084
- (variable) => variable.type === VariableType.boolean ? { ...variable, defaultValue: variable.defaultValue ?? variable.seed === void 0 } : variable
2085
- );
2086
- var CABVariableEffect = z22.object({
2087
- effect: variableEffect.default(VariableEffect.toggle),
2088
- variable: z22.string().min(1)
2089
- });
2090
- var CABVisibility = z22.object({
2091
- variable: z22.string().min(1),
2092
- visibleWhen: z22.boolean().default(true)
2093
- });
2094
- var contentOperator = z22.enum(contentOperators);
2095
- var resultCountOperator = z22.enum(resultCountOperators);
2096
- var resultTagOperator = z22.enum(resultTagOperators);
2097
- var mutatorEvent = z22.enum(mutatorEvents);
2098
- var CABContentTrigger = z22.object({
2099
- operator: contentOperator.default(ContentOperator.is_empty),
2100
- type: z22.literal("content")
2101
- });
2102
- var CABResultCountTrigger = z22.object({
2103
- operator: resultCountOperator.default(ResultCountOperator.equals),
2104
- type: z22.literal("result_count"),
2105
- value: z22.number().default(0)
2106
- });
2107
- var CABResultTagTrigger = z22.object({
2108
- operator: resultTagOperator.default(ResultTagOperator.contains),
2109
- type: z22.literal("result_tag"),
2110
- value: z22.string().min(1)
2111
- });
2112
- var CABEventTrigger = z22.object({
2113
- event: mutatorEvent,
2114
- type: z22.literal("event")
2115
- });
2116
- var CABVariableTrigger = z22.discriminatedUnion("type", [
2117
- CABContentTrigger,
2118
- CABEventTrigger,
2119
- CABResultCountTrigger,
2120
- CABResultTagTrigger
2121
- ]);
2122
- var CABVariableMutator = z22.object({
2123
- effect: variableEffect.default(VariableEffect.set_false),
2124
- variable: z22.string().min(1),
2125
- when: CABVariableTrigger
2126
- });
2127
- var CABVariableFields = {
2128
- mutators: z22.array(CABVariableMutator).optional(),
2129
- variables: z22.array(CABVariable).refine((variables) => new Set(variables.map(({ name }) => name)).size === variables.length, {
2130
- message: "variable names must be unique within a section"
2131
- }).optional(),
2132
- visibility: CABVisibility.optional()
2133
- };
2134
-
2135
2754
  // src/schema/widgets/checkout-and-beyond/image.ts
2136
- var CABImageSectionFields = z23.object({
2755
+ var CABImageSectionFields = z35.object({
2137
2756
  ...CABVariableFields,
2138
- altText: z23.string().refine(checkForHTML, NO_HTML).default(""),
2757
+ altText: z35.string().refine(checkForHTML, NO_HTML).default(""),
2139
2758
  /**
2140
2759
  * Image width÷height (e.g. `46` for the progress-bar fill); `null` renders at natural size. Any POSITIVE
2141
2760
  * ratio — never limited to 1, but never `0`/negative either: a renderer dividing by it would get `Infinity`,
2142
2761
  * and CSS `aspect-ratio` drops a negative value and silently reverts to natural size.
2143
2762
  */
2144
- aspectRatio: z23.number().positive().nullable().default(null),
2145
- border: z23.lazy(() => CABBorder),
2146
- buttonField: z23.enum(buttonFields).optional(),
2763
+ aspectRatio: z35.number().positive().nullable().default(null),
2764
+ border: z35.lazy(() => CABBorder),
2765
+ buttonField: z35.enum(buttonFields).optional(),
2147
2766
  /**
2148
2767
  * `icon` renders `source` as a single `s-icon` by name (the uber-image path covers icons too), reading
2149
2768
  * `iconSize`/`iconTone`. The other values are a harmless informational holdover from the previous
@@ -2162,165 +2781,77 @@ var CABImageSectionFields = z23.object({
2162
2781
  * behavior degraded gracefully and told us about it. The client-assembled half of the invariant was never
2163
2782
  * the risky half.
2164
2783
  */
2165
- category: z23.enum(["gallery", "icon", "icons", "payment-methods", "secure-checkout"]).nullable().default(null),
2784
+ category: z35.enum(["gallery", "icon", "icons", "payment-methods", "secure-checkout"]).nullable().default(null),
2166
2785
  /** `icon`-mode only: the `s-icon` `size`; `null` ⇒ the component default (`base`). Ignored by image treatments. */
2167
- iconSize: z23.enum(iconSizes).nullable().default(null),
2786
+ iconSize: z35.enum(iconSizes).nullable().default(null),
2168
2787
  /** `icon`-mode only: the `s-icon` `tone`; `null` ⇒ the component default (`auto`). Ignored by image treatments. */
2169
- iconTone: z23.enum(iconTones).nullable().default(null),
2170
- name: z23.string().optional(),
2171
- naturalHeight: z23.number().default(0),
2172
- naturalWidth: z23.number().default(0),
2788
+ iconTone: z35.enum(iconTones).nullable().default(null),
2789
+ name: z35.string().optional(),
2790
+ naturalHeight: z35.number().default(0),
2791
+ naturalWidth: z35.number().default(0),
2173
2792
  /**
2174
2793
  * `contain` (the component default): dimensionless images render in s-image's 1/1 default frame, and
2175
2794
  * `cover` would crop non-square art (payment badges lost their edges — 15993); `contain` letterboxes.
2176
2795
  */
2177
- objectFit: z23.enum(objectFits).default(ObjectFit.contain),
2178
- sectionId: z23.uuid().default(() => uuidv7()),
2179
- sectionType: z23.literal(SectionType.image).default(SectionType.image),
2796
+ objectFit: z35.enum(objectFits).default(ObjectFit.contain),
2797
+ sectionId: z35.uuid().default(() => uuidv72()),
2798
+ sectionType: z35.literal(SectionType.image).default(SectionType.image),
2180
2799
  /**
2181
2800
  * An image URL or dynamic token, an empty default, or — when `category: 'icon'` — an icon NAME. Icon mode
2182
2801
  * takes a name or `''` only, NOT a token: no renderer resolves a token to an icon today, so accepting one
2183
2802
  * would promise a capability that doesn't exist. Widen the refine's carve-out to `DYNAMIC_TOKEN_REGEX` when a
2184
- * server-chosen tier icon actually needs it.
2185
- */
2186
- source: z23.union([z23.url(), z23.literal(""), z23.string().regex(DYNAMIC_TOKEN_REGEX), z23.enum(iconNames)]).default(""),
2187
- width: z23.number().default(100)
2188
- });
2189
- var iconNameSet = new Set(iconNames);
2190
- var isIconName = (source) => iconNameSet.has(source);
2191
- var CABImageSection = CABImageSectionFields.superRefine(({ category, source }, ctx) => {
2192
- if (category === "icon" && source !== "" && !isIconName(source))
2193
- ctx.addIssue({
2194
- code: "custom",
2195
- message: "icon-mode source must be an icon name",
2196
- path: ["source"]
2197
- });
2198
- if (category !== "icon" && isIconName(source))
2199
- ctx.addIssue({
2200
- code: "custom",
2201
- message: "source must be a URL or dynamic token unless category is `icon`",
2202
- path: ["source"]
2203
- });
2204
- });
2205
-
2206
- // src/schema/widgets/checkout-and-beyond/text.ts
2207
- import { forEach, isString as isString2 } from "es-toolkit/compat";
2208
- import { v7 as uuidv72 } from "uuid";
2209
- import { z as z24 } from "zod";
2210
- var enumOrOmit = (...vals) => z24.string().transform((val) => vals.includes(val) ? val : void 0).optional();
2211
- var TiptapText = z24.object({
2212
- marks: z24.union([
2213
- z24.array(
2214
- z24.discriminatedUnion("type", [
2215
- z24.object({ type: z24.literal("bold") }),
2216
- z24.object({ type: z24.literal("italic") }),
2217
- z24.object({
2218
- attrs: z24.object({
2219
- class: z24.string().nullable(),
2220
- href: z24.union([
2221
- z24.url(),
2222
- z24.literal("#"),
2223
- z24.string().regex(DYNAMIC_TOKEN_REGEX),
2224
- z24.string().regex(ROOT_RELATIVE_PATH_REGEX)
2225
- ]),
2226
- rel: z24.string().default("noopener noreferrer nofollow"),
2227
- target: z24.string().default("_blank")
2228
- }),
2229
- type: z24.literal("link")
2230
- }),
2231
- z24.object({ type: z24.literal("strike") }),
2232
- z24.object({
2233
- attrs: z24.object({
2234
- color: enumOrOmit(...textColorNames).default(TextColorName.base),
2235
- fontSize: enumOrOmit(...textSizeNames).default(TextSizeName.base)
2236
- }),
2237
- type: z24.literal("textStyle")
2238
- })
2239
- ])
2240
- ),
2241
- z24.strictObject({}).transform(() => [])
2242
- ]).optional(),
2243
- text: z24.string().default(""),
2244
- type: z24.literal("text").default("text")
2245
- });
2246
- var TiptapParagraph = z24.object({
2247
- attrs: z24.object({
2248
- textAlign: enumOrOmit(...textAlignments)
2249
- }).default({ textAlign: TextAlignment.start }),
2250
- content: z24.union([z24.array(TiptapText), z24.strictObject({}).transform(() => [])]).default(() => []),
2251
- type: z24.literal("paragraph").default("paragraph")
2252
- });
2253
- var TiptapDocument = z24.object({
2254
- attrs: z24.object({
2255
- blockSpacing: enumOrOmit(...spacings)
2256
- }).default({ blockSpacing: Spacing.base }),
2257
- content: z24.union([z24.array(TiptapParagraph), z24.strictObject({}).transform(() => [])]).default(() => [TiptapParagraph.parse({})]),
2258
- type: z24.literal("doc").default("doc")
2259
- });
2260
- var CABTextTier = z24.object({
2261
- threshold: z24.number().int().nonnegative(),
2262
- thresholds: z24.record(z24.string(), z24.number().int().nonnegative()).default(() => ({})),
2263
- tierId: z24.string().optional(),
2264
- tierType: z24.enum(progressTierTypes).default(ProgressTierType.shipping)
2803
+ * server-chosen tier icon actually needs it.
2804
+ */
2805
+ source: z35.union([z35.url(), z35.literal(""), z35.string().regex(DYNAMIC_TOKEN_REGEX), z35.enum(iconNames)]).default(""),
2806
+ width: z35.number().default(100)
2265
2807
  });
2266
- var CABTextSection = z24.object({
2267
- ...CABVariableFields,
2268
- buttonField: z24.enum(buttonFields).optional(),
2269
- content: z24.record(z24.string(), z24.union([z24.string(), TiptapDocument]).refine(checkForHTML, NO_HTML).optional()).default({ en: TiptapDocument.parse({}) }).optional(),
2270
- name: z24.string().optional(),
2271
- optionId: z24.number().optional(),
2272
- sectionId: z24.uuid().default(() => uuidv72()),
2273
- sectionType: z24.literal(SectionType.text).default(SectionType.text),
2274
- tier: CABTextTier.optional()
2275
- }).superRefine(({ buttonField, content }, ctx) => {
2276
- if (buttonField === ButtonField.destinationUrl && content) {
2277
- forEach(content, (value, lang) => {
2278
- if (value && isString2(value)) {
2279
- if (DYNAMIC_TOKEN_REGEX.test(value)) return;
2280
- try {
2281
- new URL(value);
2282
- } catch {
2283
- ctx.addIssue({
2284
- code: "custom",
2285
- message: "Invalid URL",
2286
- path: ["content", lang]
2287
- });
2288
- }
2289
- }
2808
+ var iconNameSet = new Set(iconNames);
2809
+ var isIconName = (source) => iconNameSet.has(source);
2810
+ var CABImageSection = CABImageSectionFields.superRefine(({ category, source }, ctx) => {
2811
+ if (category === "icon" && source !== "" && !isIconName(source))
2812
+ ctx.addIssue({
2813
+ code: "custom",
2814
+ message: "icon-mode source must be an icon name",
2815
+ path: ["source"]
2816
+ });
2817
+ if (category !== "icon" && isIconName(source))
2818
+ ctx.addIssue({
2819
+ code: "custom",
2820
+ message: "source must be a URL or dynamic token unless category is `icon`",
2821
+ path: ["source"]
2290
2822
  });
2291
- }
2292
2823
  });
2293
2824
 
2294
2825
  // src/schema/widgets/checkout-and-beyond/button.ts
2295
- var CABButtonContent = z25.lazy(
2296
- () => z25.discriminatedUnion("sectionType", [CABImageSection, CABLayoutSection, CABTextSection])
2826
+ var CABButtonContent = z36.lazy(
2827
+ () => z36.discriminatedUnion("sectionType", [CABImageSection, CABLayoutSection, CABTextSection])
2297
2828
  );
2298
- var CABButtonSection = z25.object({
2829
+ var CABButtonSection = z36.object({
2299
2830
  ...CABVariableFields,
2300
- action: z25.union([z25.literal(""), z25.enum(buttonActions)]).default(""),
2301
- buttonStyle: z25.enum(buttonStyles).default(ButtonStyle.primary),
2302
- custom: z25.object({
2303
- color: z25.string().regex(HEX_COLOR_REGEX).default("#005bd3"),
2304
- height: z25.number().default(52),
2305
- width: z25.number().default(300)
2831
+ action: z36.union([z36.literal(""), z36.enum(buttonActions)]).default(""),
2832
+ buttonStyle: z36.enum(buttonStyles).default(ButtonStyle.primary),
2833
+ custom: z36.object({
2834
+ color: z36.string().regex(HEX_COLOR_REGEX).default("#005bd3"),
2835
+ height: z36.number().default(52),
2836
+ width: z36.number().default(300)
2306
2837
  }).default({
2307
2838
  color: "#005bd3",
2308
2839
  height: 52,
2309
2840
  width: 300
2310
2841
  }),
2311
- disableDowngrade: z25.boolean().default(false),
2312
- name: z25.string().optional(),
2313
- optionId: z25.number().optional(),
2314
- popover: z25.object({
2315
- alignment: z25.enum(textAlignments).default(TextAlignment.center),
2316
- position: z25.enum(popoverPositions).default(PopoverPosition.blockStart)
2842
+ disableDowngrade: z36.boolean().default(false),
2843
+ name: z36.string().optional(),
2844
+ optionId: z36.number().optional(),
2845
+ popover: z36.object({
2846
+ alignment: z36.enum(textAlignments).default(TextAlignment.center),
2847
+ position: z36.enum(popoverPositions).default(PopoverPosition.blockStart)
2317
2848
  }).optional().default(() => ({
2318
2849
  alignment: TextAlignment.center,
2319
2850
  position: PopoverPosition.blockStart
2320
2851
  })),
2321
- sectionId: z25.uuid().default(() => uuidv73()),
2322
- sections: z25.union([z25.array(CABButtonContent), z25.strictObject({}).transform(() => [])]).default(() => []),
2323
- sectionType: z25.literal(SectionType.button).default(SectionType.button),
2852
+ sectionId: z36.uuid().default(() => uuidv73()),
2853
+ sections: z36.union([z36.array(CABButtonContent), z36.strictObject({}).transform(() => [])]).default(() => []),
2854
+ sectionType: z36.literal(SectionType.button).default(SectionType.button),
2324
2855
  /**
2325
2856
  * The smart-cart tier this button acts on (`addGift`/`removeGift`): scopes the click to one tier's gift. The
2326
2857
  * client resolves the tier's gift (productId) from the progress-bar context by this `tierId` — the button node
@@ -2335,91 +2866,91 @@ var CABButtonSection = z25.object({
2335
2866
  * lookup finds no tier and the click resolves to nothing. Safe to bound — the field is new, so there are no
2336
2867
  * stored payloads to grandfather, and the producer is client code, not a merchant form.
2337
2868
  */
2338
- tier: z25.object({ tierId: z25.string().min(1) }).optional(),
2869
+ tier: z36.object({ tierId: z36.string().min(1) }).optional(),
2339
2870
  /** Fire-and-forget pixel POSTed when the button is clicked (e.g. a Monetize decline). */
2340
- trackingUrl: z25.string().optional(),
2871
+ trackingUrl: z36.string().optional(),
2341
2872
  /**
2342
2873
  * Secondary effects applied to in-scope variables on click, alongside (never instead of) the primary
2343
2874
  * `action` — an `addToOrder` button can also flip a variable. Applied in array order.
2344
2875
  */
2345
- variableEffects: z25.array(CABVariableEffect).optional()
2876
+ variableEffects: z36.array(CABVariableEffect).optional()
2346
2877
  });
2347
2878
 
2348
2879
  // src/schema/widgets/checkout-and-beyond/carousel.ts
2349
- import { z as z30 } from "zod";
2880
+ import { z as z41 } from "zod";
2350
2881
 
2351
2882
  // src/schema/widgets/checkout-and-beyond/offers.ts
2352
- import { z as z29 } from "zod";
2883
+ import { z as z40 } from "zod";
2353
2884
 
2354
2885
  // src/schema/widgets/checkout-and-beyond/dataSource.ts
2355
2886
  import { v7 as uuidv74 } from "uuid";
2356
- import { z as z26 } from "zod";
2357
- var CABDiscount = z26.object({
2358
- amount: z26.union([z26.number(), z26.string()]).catch(0),
2359
- discountedBy: z26.string().optional(),
2360
- discountedFrom: z26.enum(discountSources).optional().catch(void 0),
2361
- type: z26.enum(discountTypes).catch("none")
2362
- });
2363
- var CABIntegrations = z26.object({
2364
- judgeme: z26.boolean().default(false),
2365
- junip: z26.boolean().default(false),
2366
- klaviyo: z26.boolean().default(false),
2367
- loox: z26.boolean().default(false),
2368
- okendo: z26.boolean().default(false),
2369
- opinew: z26.boolean().default(false),
2370
- reviewsio: z26.boolean().default(false),
2371
- stamped: z26.boolean().default(false),
2372
- yotpo: z26.boolean().default(false)
2373
- });
2374
- var CABDataSourceSection = z26.object({
2375
- dataSourceId: z26.number().nullable().default(null),
2376
- dataSourcePath: z26.string().default(DEFAULT_ENDPOINTS[0].value),
2887
+ import { z as z37 } from "zod";
2888
+ var CABDiscount = z37.object({
2889
+ amount: z37.union([z37.number(), z37.string()]).catch(0),
2890
+ discountedBy: z37.string().optional(),
2891
+ discountedFrom: z37.enum(discountSources).optional().catch(void 0),
2892
+ type: z37.enum(discountTypes).catch("none")
2893
+ });
2894
+ var CABIntegrations = z37.object({
2895
+ judgeme: z37.boolean().default(false),
2896
+ junip: z37.boolean().default(false),
2897
+ klaviyo: z37.boolean().default(false),
2898
+ loox: z37.boolean().default(false),
2899
+ okendo: z37.boolean().default(false),
2900
+ opinew: z37.boolean().default(false),
2901
+ reviewsio: z37.boolean().default(false),
2902
+ stamped: z37.boolean().default(false),
2903
+ yotpo: z37.boolean().default(false)
2904
+ });
2905
+ var CABDataSourceSection = z37.object({
2906
+ dataSourceId: z37.number().nullable().default(null),
2907
+ dataSourcePath: z37.string().default(DEFAULT_ENDPOINTS[0].value),
2377
2908
  discount: CABDiscount.optional(),
2378
2909
  integrations: CABIntegrations.optional(),
2379
- limit: z26.number().default(1),
2380
- matchVariant: z26.boolean().default(false),
2381
- matchVariantOutOfStock: z26.boolean().default(false),
2382
- name: z26.string().default(DEFAULT_ENDPOINTS[0].label),
2383
- productType: z26.enum(productTypes).optional(),
2384
- sectionId: z26.uuid().default(() => uuidv74()),
2385
- sectionType: z26.literal(SectionType.dataSource).default(SectionType.dataSource),
2910
+ limit: z37.number().default(1),
2911
+ matchVariant: z37.boolean().default(false),
2912
+ matchVariantOutOfStock: z37.boolean().default(false),
2913
+ name: z37.string().default(DEFAULT_ENDPOINTS[0].label),
2914
+ productType: z37.enum(productTypes).optional(),
2915
+ sectionId: z37.uuid().default(() => uuidv74()),
2916
+ sectionType: z37.literal(SectionType.dataSource).default(SectionType.dataSource),
2386
2917
  /** Default subscribe-vs-one-time for `productType: both` (legacy `subscription_is_default`). */
2387
- subscriptionIsDefault: z26.boolean().default(false),
2388
- treatAsGwp: z26.boolean().default(false)
2918
+ subscriptionIsDefault: z37.boolean().default(false),
2919
+ treatAsGwp: z37.boolean().default(false)
2389
2920
  });
2390
2921
 
2391
2922
  // src/schema/widgets/checkout-and-beyond/products.ts
2392
2923
  import { v7 as uuidv76 } from "uuid";
2393
- import { z as z28 } from "zod";
2924
+ import { z as z39 } from "zod";
2394
2925
 
2395
2926
  // src/schema/widgets/checkout-and-beyond/product.ts
2396
2927
  import { v7 as uuidv75 } from "uuid";
2397
- import { z as z27 } from "zod";
2398
- var CABVariantContent = z27.lazy(
2399
- () => z27.discriminatedUnion("sectionType", [CABButtonSection, CABTextSection])
2928
+ import { z as z38 } from "zod";
2929
+ var CABVariantContent = z38.lazy(
2930
+ () => z38.discriminatedUnion("sectionType", [CABButtonSection, CABTextSection])
2400
2931
  );
2401
- var CABProductSection = z27.object({
2932
+ var CABProductSection = z38.object({
2402
2933
  ...CABVariableFields,
2403
- name: z27.string().optional(),
2404
- productId: z27.number().nullable().default(null),
2405
- sectionId: z27.uuid().default(() => uuidv75()),
2406
- sections: z27.union([z27.array(CABVariantContent), z27.strictObject({}).transform(() => [])]).default(() => []),
2407
- sectionType: z27.literal(SectionType.product).default(SectionType.product),
2408
- selectors: z27.record(z27.string(), z27.enum(variantSelectors).default(VariantSelector.menu)).default(() => ({})),
2409
- variantMode: z27.enum(variantModes).default(VariantMode.multiple)
2934
+ name: z38.string().optional(),
2935
+ productId: z38.number().nullable().default(null),
2936
+ sectionId: z38.uuid().default(() => uuidv75()),
2937
+ sections: z38.union([z38.array(CABVariantContent), z38.strictObject({}).transform(() => [])]).default(() => []),
2938
+ sectionType: z38.literal(SectionType.product).default(SectionType.product),
2939
+ selectors: z38.record(z38.string(), z38.enum(variantSelectors).default(VariantSelector.menu)).default(() => ({})),
2940
+ variantMode: z38.enum(variantModes).default(VariantMode.multiple)
2410
2941
  });
2411
2942
 
2412
2943
  // src/schema/widgets/checkout-and-beyond/products.ts
2413
- var CABProductsSection = z28.object({
2944
+ var CABProductsSection = z39.object({
2414
2945
  ...CABVariableFields,
2415
- name: z28.string().optional(),
2416
- sectionId: z28.uuid().default(() => uuidv76()),
2417
- sections: z28.union([z28.array(z28.lazy(() => CABProductSection)), z28.strictObject({}).transform(() => [])]).default(() => []),
2418
- sectionType: z28.literal(SectionType.products).default(SectionType.products)
2946
+ name: z39.string().optional(),
2947
+ sectionId: z39.uuid().default(() => uuidv76()),
2948
+ sections: z39.union([z39.array(z39.lazy(() => CABProductSection)), z39.strictObject({}).transform(() => [])]).default(() => []),
2949
+ sectionType: z39.literal(SectionType.products).default(SectionType.products)
2419
2950
  });
2420
2951
 
2421
2952
  // src/schema/widgets/checkout-and-beyond/offers.ts
2422
- var CABOffersSection = z29.lazy(
2953
+ var CABOffersSection = z40.lazy(
2423
2954
  () => CABLayoutSection.omit({ sections: true, sectionType: true }).extend({
2424
2955
  /**
2425
2956
  * A rule between consecutive cards in the vertical list — legacy checkout-offers' `<Divider />`,
@@ -2427,8 +2958,8 @@ var CABOffersSection = z29.lazy(
2427
2958
  * run of products). Optional, not defaulted: only the v1 converter sets it (REB-24265); a
2428
2959
  * hand-built tree keeps React CAB's dividerless rendering.
2429
2960
  */
2430
- divider: z29.boolean().optional(),
2431
- sections: z29.union([z29.array(z29.lazy(() => CABSection)), z29.strictObject({}).transform(() => [])]).default(() => [
2961
+ divider: z40.boolean().optional(),
2962
+ sections: z40.union([z40.array(z40.lazy(() => CABSection)), z40.strictObject({}).transform(() => [])]).default(() => [
2432
2963
  CABBannerSection.parse({
2433
2964
  buttonField: "undoAddToOrder",
2434
2965
  color: "success",
@@ -2442,77 +2973,77 @@ var CABOffersSection = z29.lazy(
2442
2973
  CABDataSourceSection.parse({}),
2443
2974
  CABProductsSection.parse({})
2444
2975
  ]),
2445
- sectionType: z29.literal(SectionType.offers).default(SectionType.offers)
2976
+ sectionType: z40.literal(SectionType.offers).default(SectionType.offers)
2446
2977
  })
2447
2978
  );
2448
2979
 
2449
2980
  // src/schema/widgets/checkout-and-beyond/carousel.ts
2450
- var CABCarouselSection = z30.lazy(
2981
+ var CABCarouselSection = z41.lazy(
2451
2982
  () => CABLayoutSection.omit({ sections: true, sectionType: true }).extend({
2452
- autoAdvanceInterval: z30.number().default(0),
2453
- itemsAtOnce: z30.number().min(1).default(1),
2983
+ autoAdvanceInterval: z41.number().default(0),
2984
+ itemsAtOnce: z41.number().min(1).default(1),
2454
2985
  /** Card arrangement for the offers child (`horizontal` = side-by-side) — NOT the carousel's own `direction`. */
2455
- offersDirection: z30.enum(offersDirections).default("vertical"),
2456
- sections: z30.union([z30.array(z30.lazy(() => CABSection)), z30.strictObject({}).transform(() => [])]).default(() => [CABOffersSection.parse({})]),
2457
- sectionType: z30.literal(SectionType.carousel).default(SectionType.carousel)
2986
+ offersDirection: z41.enum(offersDirections).default("vertical"),
2987
+ sections: z41.union([z41.array(z41.lazy(() => CABSection)), z41.strictObject({}).transform(() => [])]).default(() => [CABOffersSection.parse({})]),
2988
+ sectionType: z41.literal(SectionType.carousel).default(SectionType.carousel)
2458
2989
  })
2459
2990
  );
2460
2991
 
2461
2992
  // src/schema/widgets/checkout-and-beyond/cartLine.ts
2462
- import { z as z31 } from "zod";
2463
- var CABCartLineSection = z31.lazy(
2993
+ import { z as z42 } from "zod";
2994
+ var CABCartLineSection = z42.lazy(
2464
2995
  () => CABLayoutSection.omit({ sections: true, sectionType: true }).extend({
2465
- sections: z31.union([z31.array(z31.lazy(() => CABSection)), z31.strictObject({}).transform(() => [])]).default(() => [CABButtonSection.parse({ action: ButtonAction.switchToSubscription })]),
2466
- sectionType: z31.literal(SectionType.cartLine).default(SectionType.cartLine)
2996
+ sections: z42.union([z42.array(z42.lazy(() => CABSection)), z42.strictObject({}).transform(() => [])]).default(() => [CABButtonSection.parse({ action: ButtonAction.switchToSubscription })]),
2997
+ sectionType: z42.literal(SectionType.cartLine).default(SectionType.cartLine)
2467
2998
  })
2468
2999
  );
2469
3000
 
2470
3001
  // src/schema/widgets/checkout-and-beyond/discount.ts
2471
3002
  import { v7 as uuidv77 } from "uuid";
2472
- import { z as z32 } from "zod";
2473
- var CABDiscountSection = z32.object({
3003
+ import { z as z43 } from "zod";
3004
+ var CABDiscountSection = z43.object({
2474
3005
  ...CABVariableFields,
2475
- amount: z32.union([z32.number(), z32.string()]).catch(0),
2476
- discountedBy: z32.string().optional(),
2477
- discountedFrom: z32.enum(discountSources).optional().catch(void 0),
2478
- message: z32.string().optional(),
2479
- name: z32.string().optional(),
2480
- quantity: z32.number().default(1),
2481
- sectionId: z32.uuid().default(() => uuidv77()),
2482
- sectionType: z32.literal(SectionType.discount).default(SectionType.discount),
2483
- type: z32.enum(discountTypes).catch("none")
3006
+ amount: z43.union([z43.number(), z43.string()]).catch(0),
3007
+ discountedBy: z43.string().optional(),
3008
+ discountedFrom: z43.enum(discountSources).optional().catch(void 0),
3009
+ message: z43.string().optional(),
3010
+ name: z43.string().optional(),
3011
+ quantity: z43.number().default(1),
3012
+ sectionId: z43.uuid().default(() => uuidv77()),
3013
+ sectionType: z43.literal(SectionType.discount).default(SectionType.discount),
3014
+ type: z43.enum(discountTypes).catch("none")
2484
3015
  });
2485
3016
 
2486
3017
  // src/schema/widgets/checkout-and-beyond/monetize.ts
2487
3018
  import { v7 as uuidv78 } from "uuid";
2488
- import { z as z33 } from "zod";
2489
- var CABMonetizeAds = z33.object({
2490
- requestId: z33.string().optional(),
3019
+ import { z as z44 } from "zod";
3020
+ var CABMonetizeAds = z44.object({
3021
+ requestId: z44.string().optional(),
2491
3022
  /** Defaulted here, never in the beacon: absence of information is `ads` itself being absent. */
2492
- testing: z33.boolean().default(false)
3023
+ testing: z44.boolean().default(false)
2493
3024
  });
2494
- var CABMonetizeSection = z33.object({
3025
+ var CABMonetizeSection = z44.object({
2495
3026
  ...CABVariableFields,
2496
3027
  ads: CABMonetizeAds.optional(),
2497
- name: z33.string().optional(),
3028
+ name: z44.string().optional(),
2498
3029
  /**
2499
3030
  * Server-hydrated offer cards (inline hydration): when `/cab/sections` was asked with a `monetize`
2500
3031
  * context block, the composed cards ride the marker itself — `[]` means "hydrated, no fill" (render
2501
3032
  * nothing, skip the fetch); ABSENT means "not hydrated" (the client fetches via `/cab/monetize`).
2502
3033
  */
2503
- offers: z33.array(z33.lazy(() => CABSection)).optional(),
3034
+ offers: z44.array(z44.lazy(() => CABSection)).optional(),
2504
3035
  /** Privacy Policy footer href (the widget's `privacy_policy_url` setting); read server-side for hydration, relayed by the client only on the legacy `/cab/monetize` fallback. */
2505
- privacyPolicyUrl: z33.string().optional(),
2506
- sectionId: z33.uuid().default(() => uuidv78()),
2507
- sectionType: z33.literal(SectionType.monetize).default(SectionType.monetize),
3036
+ privacyPolicyUrl: z44.string().optional(),
3037
+ sectionId: z44.uuid().default(() => uuidv78()),
3038
+ sectionType: z44.literal(SectionType.monetize).default(SectionType.monetize),
2508
3039
  /** Ads-taxonomy sub-vertical id (the widget's `sub_vertical` setting); paired with `vertical`. */
2509
- subVertical: z33.string().optional(),
3040
+ subVertical: z44.string().optional(),
2510
3041
  /** Ads-taxonomy vertical id (the widget's `vertical` setting) — with `subVertical`, the admin Monetize editor's two configurables. */
2511
- vertical: z33.string().optional()
3042
+ vertical: z44.string().optional()
2512
3043
  });
2513
3044
 
2514
3045
  // src/schema/widgets/checkout-and-beyond/progressBar.ts
2515
- import { z as z34 } from "zod";
3046
+ import { z as z45 } from "zod";
2516
3047
 
2517
3048
  // src/schema/widgets/checkout-and-beyond/giftLabels.ts
2518
3049
  var GIFT_LABELS = {
@@ -2631,34 +3162,34 @@ var GIFT_LABELS = {
2631
3162
  };
2632
3163
 
2633
3164
  // src/schema/widgets/checkout-and-beyond/progressBar.ts
2634
- var CABProgressTierExclusion = z34.object({
2635
- collectionIds: z34.array(z34.number().int().positive()).default(() => []),
2636
- productIds: z34.array(z34.number().int().positive()).default(() => []),
2637
- tags: z34.array(z34.string().min(1)).default(() => []),
2638
- type: z34.enum(progressTierExclusionTypes)
3165
+ var CABProgressTierExclusion = z45.object({
3166
+ collectionIds: z45.array(z45.number().int().positive()).default(() => []),
3167
+ productIds: z45.array(z45.number().int().positive()).default(() => []),
3168
+ tags: z45.array(z45.string().min(1)).default(() => []),
3169
+ type: z45.enum(progressTierExclusionTypes)
2639
3170
  });
2640
- var CABProgressTier = z34.object({
3171
+ var CABProgressTier = z45.object({
2641
3172
  /**
2642
3173
  * Order-discount tiers only (onsite `discount`): the reward the order-discount Function applies at
2643
3174
  * cart time, carried so the client can resolve the `{{discountAmount}}` token in this tier's copy.
2644
3175
  * `fixedAmount`: shop-currency CENTS (FX-scaled by the client, like {@link CABProgressTier.threshold});
2645
3176
  * `percentage`: the whole-percent number rendered raw (`{n}%`). Absent on non-discount tiers.
2646
3177
  */
2647
- discount: z34.object({ amount: z34.number().nonnegative(), type: z34.enum(["fixedAmount", "percentage"]) }).optional(),
3178
+ discount: z45.object({ amount: z45.number().nonnegative(), type: z45.enum(["fixedAmount", "percentage"]) }).optional(),
2648
3179
  /**
2649
3180
  * Per-tier exclusion rules (onsite `exclusions` when `exclusions_enabled`): lines they match don't count
2650
3181
  * toward this tier. Empty (the default, and the converter's output for a disabled or ruleless tier) means
2651
3182
  * the tier measures the plain bar-level adjusted progress. Consumers read ONLY the list named by the rule's
2652
3183
  * `type` — the converter leaves the other two at `[]`, so a populated off-type list never reaches the tree.
2653
3184
  */
2654
- exclusions: z34.array(CABProgressTierExclusion).default(() => []),
3185
+ exclusions: z45.array(CABProgressTierExclusion).default(() => []),
2655
3186
  /**
2656
3187
  * Smart-cart product (gift) tiers only (onsite `filter_oos_variants`): when set, the client drops this
2657
3188
  * tier entirely once its gift has NO in-stock eligible variant — the milestone, fill slot and gift
2658
3189
  * controls all disappear, mirroring onsite removing the tier from `bar.tiers` before it renders. Absent
2659
3190
  * on shipping/discount/decorative tiers and left off by default (the tier renders regardless of stock).
2660
3191
  */
2661
- filterOosVariants: z34.boolean().default(false),
3192
+ filterOosVariants: z45.boolean().default(false),
2662
3193
  /**
2663
3194
  * Smart-cart product (gift) tiers only: the reward unlocked at this tier. The client enriches
2664
3195
  * `productId`/`variantIds` to live variants (availability, price) and adds the chosen one to the cart
@@ -2666,10 +3197,10 @@ var CABProgressTier = z34.object({
2666
3197
  * tiers and on tiers with no configured product. Cart add/remove is a later stage; carried here so the
2667
3198
  * tree is complete.
2668
3199
  */
2669
- gift: z34.object({
2670
- productId: z34.number().int().positive(),
2671
- title: z34.string().optional(),
2672
- variantIds: z34.array(z34.number().int().positive()).default(() => [])
3200
+ gift: z45.object({
3201
+ productId: z45.number().int().positive(),
3202
+ title: z45.string().optional(),
3203
+ variantIds: z45.array(z45.number().int().positive()).default(() => [])
2673
3204
  }).optional(),
2674
3205
  /**
2675
3206
  * The step-row icon's square size in PIXELS (onsite `product_tier_element_size`, an admin px string the
@@ -2689,7 +3220,7 @@ var CABProgressTier = z34.object({
2689
3220
  * renderer never spells a fallback), which also makes a tree authored before this field render at
2690
3221
  * React's size rather than the old hardcoded 20.
2691
3222
  */
2692
- iconSizePx: z34.number().int().min(1).max(64).default(18),
3223
+ iconSizePx: z45.number().int().min(1).max(64).default(18),
2693
3224
  /**
2694
3225
  * The step-row label at this tier's slot (onsite `getTierLabel`): the merchant custom label, else the
2695
3226
  * type default — 'Free Shipping' or '{n}% Discount'. A PRODUCT tier gets NO converter label: its name is
@@ -2699,35 +3230,35 @@ var CABProgressTier = z34.object({
2699
3230
  * turns a blank label into an absent key, and a client-authored blank means the same thing — the renderer
2700
3231
  * emits no caption slot rather than an empty one). Plain text — a compact icon+label.
2701
3232
  */
2702
- label: z34.record(z34.string(), z34.string()).optional(),
3233
+ label: z45.record(z45.string(), z45.string()).optional(),
2703
3234
  /**
2704
3235
  * Smart-cart product (gift) tiers only (onsite `product_tier_image`): show the gift's product image in
2705
3236
  * the step-row slot instead of the generic bag icon. The converter can't supply the image URL (config
2706
3237
  * carries only product IDs), so the client resolves it (authoritative Shopify featured image, React
2707
3238
  * parity) and falls back to the bag icon when the flag is off or no image resolves. Default false.
2708
3239
  */
2709
- productTierImage: z34.boolean().default(false),
3240
+ productTierImage: z45.boolean().default(false),
2710
3241
  /**
2711
3242
  * The tier's goal, measured per `unit`. `currency` (default): SHOP-currency cents — the canonical
2712
3243
  * fallback: when the buyer's presentment currency has no entry in `thresholds`, the client
2713
3244
  * multiplies this by the live FX rate (converter maps the v1 `unlock_price`, e.g. `75` → `7500`).
2714
3245
  * `item`: a raw item count — no cents, no FX, no `thresholds` overrides.
2715
3246
  */
2716
- threshold: z34.number().int().nonnegative(),
3247
+ threshold: z45.number().int().nonnegative(),
2717
3248
  /**
2718
3249
  * Per-presentment-currency goal overrides — lowercased ISO currency code → cents (e.g. `{ cad: 9900 }`).
2719
3250
  * When the buyer's currency has an entry, the client uses it verbatim INSTEAD of FX-converting
2720
3251
  * `threshold`, so merchants show intentional, clean per-market amounts (Shopify Markets) rather than a
2721
3252
  * converted base. Defaults to `{}` — no overrides means always fall back to `threshold`.
2722
3253
  */
2723
- thresholds: z34.record(z34.string(), z34.number().int().nonnegative()).default(() => ({})),
3254
+ thresholds: z45.record(z45.string(), z45.number().int().nonnegative()).default(() => ({})),
2724
3255
  /**
2725
3256
  * Smart-cart tier identifier, mirrored onto the gift cart line's `_tier` attribute so the client can
2726
3257
  * match an in-cart gift back to its tier (add on reach, remove on downgrade/decline). Absent on the
2727
3258
  * shipping bar (single unlabeled tier, no gift).
2728
3259
  */
2729
- tierId: z34.string().optional(),
2730
- tierType: z34.enum(progressTierTypes).default(ProgressTierType.shipping),
3260
+ tierId: z45.string().optional(),
3261
+ tierType: z45.enum(progressTierTypes).default(ProgressTierType.shipping),
2731
3262
  /**
2732
3263
  * What this tier's progress is measured in — PER TIER (onsite's `unlock_condition_type` model, NOT
2733
3264
  * the React port's bar-level `tiers[0]` shortcut). `currency` compares money cents against the
@@ -2738,9 +3269,9 @@ var CABProgressTier = z34.object({
2738
3269
  * count carries no injected noun (no English `item`/`items` inflection on localized copy); merchant
2739
3270
  * template text supplies grammatically-neutral wording around the token.
2740
3271
  */
2741
- unit: z34.enum(progressTierUnits).default(ProgressTierUnit.currency)
3272
+ unit: z45.enum(progressTierUnits).default(ProgressTierUnit.currency)
2742
3273
  });
2743
- var CABProgressBarSection = z34.lazy(
3274
+ var CABProgressBarSection = z45.lazy(
2744
3275
  () => CABLayoutSection.omit({ sectionType: true }).extend({
2745
3276
  /**
2746
3277
  * The onsite bar id (smart-cart TPB bars only). The client mirrors it to the cart's `_barId` attribute
@@ -2749,35 +3280,35 @@ var CABProgressBarSection = z34.lazy(
2749
3280
  * checkout reaches the extension without it, so the client writes it or the tier gift's 100% discount
2750
3281
  * (and any tier order discount) never applies. Absent on the v1 shipping bar (no gift tiers, no id).
2751
3282
  */
2752
- barId: z34.string().optional(),
3283
+ barId: z45.string().optional(),
2753
3284
  /** Empty = shown everywhere; otherwise uppercase ISO country codes. */
2754
- countryCodes: z34.array(z34.string().transform((code) => code.trim().toUpperCase())).default(() => []),
3285
+ countryCodes: z45.array(z45.string().transform((code) => code.trim().toUpperCase())).default(() => []),
2755
3286
  /**
2756
3287
  * Uppercase ISO codes where a higher-precedence geo bar applies, so this (default, non-geo) bar is
2757
3288
  * hidden there — replicates React `getbar`'s geo-match-over-default precedence. Empty = never excluded.
2758
3289
  */
2759
- excludeCountryCodes: z34.array(z34.string().transform((code) => code.trim().toUpperCase())).default(() => []),
3290
+ excludeCountryCodes: z45.array(z45.string().transform((code) => code.trim().toUpperCase())).default(() => []),
2760
3291
  /**
2761
3292
  * Measure progress against the PRE-discount subtotal (onsite `exclude_discount_in_subtotal`, and
2762
3293
  * forced on for bars with a discount tier so its own reward can't un-reach the tier). The client
2763
3294
  * adds the cart's discount allocations back to the live subtotal.
2764
3295
  */
2765
- excludeDiscountInSubtotal: z34.boolean().default(false),
3296
+ excludeDiscountInSubtotal: z45.boolean().default(false),
2766
3297
  /** Variant ids the client subtracts from the adjusted subtotal (React `bar.excluded_products`). */
2767
- excludedVariantIds: z34.array(z34.number().int().positive()).default(() => []),
3298
+ excludedVariantIds: z45.array(z45.number().int().positive()).default(() => []),
2768
3299
  /**
2769
3300
  * When the cart holds a subscription item, treat the bar as reached regardless of subtotal (React
2770
3301
  * `free_shipping_on_subscription(s)`). `freeShippingOnAll` is already a zero-threshold tier instead.
2771
3302
  */
2772
- freeShippingOnSubscription: z34.boolean().default(false),
3303
+ freeShippingOnSubscription: z45.boolean().default(false),
2773
3304
  /** Localized heading over the gift controls (onsite `gift_area_title`, default 'FREE GIFTS'). */
2774
- giftAreaTitle: z34.record(z34.string(), z34.string()).default(() => ({ en: "FREE GIFTS" })),
3305
+ giftAreaTitle: z45.record(z45.string(), z45.string()).default(() => ({ en: "FREE GIFTS" })),
2775
3306
  /** Localized gift-control labels (add/remove/heading); a tier's gift `title` beats `yourGift`. */
2776
- giftLabels: z34.object({
2777
- addGift: z34.record(z34.string(), z34.string()).default(() => ({ ...GIFT_LABELS.addGift })),
2778
- remove: z34.record(z34.string(), z34.string()).default(() => ({ ...GIFT_LABELS.remove })),
2779
- selectOptions: z34.record(z34.string(), z34.string()).default(() => ({ ...GIFT_LABELS.selectOptions })),
2780
- yourGift: z34.record(z34.string(), z34.string()).default(() => ({ ...GIFT_LABELS.yourGift }))
3307
+ giftLabels: z45.object({
3308
+ addGift: z45.record(z45.string(), z45.string()).default(() => ({ ...GIFT_LABELS.addGift })),
3309
+ remove: z45.record(z45.string(), z45.string()).default(() => ({ ...GIFT_LABELS.remove })),
3310
+ selectOptions: z45.record(z45.string(), z45.string()).default(() => ({ ...GIFT_LABELS.selectOptions })),
3311
+ yourGift: z45.record(z45.string(), z45.string()).default(() => ({ ...GIFT_LABELS.yourGift }))
2781
3312
  }).default(() => ({
2782
3313
  addGift: { ...GIFT_LABELS.addGift },
2783
3314
  remove: { ...GIFT_LABELS.remove },
@@ -2785,38 +3316,38 @@ var CABProgressBarSection = z34.lazy(
2785
3316
  yourGift: { ...GIFT_LABELS.yourGift }
2786
3317
  })),
2787
3318
  /** The bar's a11y label; the merchant names it in the editor, else this default (React parity). */
2788
- name: z34.string().default("Order progress"),
3319
+ name: z45.string().default("Order progress"),
2789
3320
  /**
2790
3321
  * Bar fill color. An explicit (widget-authored) value is used verbatim; when absent the server
2791
3322
  * fills it with the live shop theme's `buttonBackground` (React `useRebuyTheme` parity). Still
2792
3323
  * absent after that ⇒ the theme fetch failed and the client renders its platform-default bar —
2793
3324
  * optional, not defaulted, so "merchant chose no color" stays distinguishable from any real value.
2794
3325
  */
2795
- progressColor: z34.string().optional(),
2796
- sectionType: z34.literal(SectionType.progressBar).default(SectionType.progressBar),
3326
+ progressColor: z45.string().optional(),
3327
+ sectionType: z45.literal(SectionType.progressBar).default(SectionType.progressBar),
2797
3328
  /**
2798
3329
  * The bar's milestones in the merchant's CONFIGURED order — the renderer does NOT sort them (022
2799
3330
  * O-B2: sorting by resolved threshold reversed configured milestones on out-of-order or mixed-unit
2800
3331
  * count-vs-cents bars). Drives the fill (even slot per tier) and, for smart-cart product tiers, the
2801
3332
  * gift add/remove. The visual tier display lives in `sections` (composable), NOT here.
2802
3333
  */
2803
- tiers: z34.union([z34.array(CABProgressTier), z34.strictObject({}).transform(() => [])]).default(() => [])
3334
+ tiers: z45.union([z45.array(CABProgressTier), z45.strictObject({}).transform(() => [])]).default(() => [])
2804
3335
  })
2805
3336
  );
2806
3337
 
2807
3338
  // src/schema/widgets/checkout-and-beyond/quantity.ts
2808
3339
  import { v7 as uuidv79 } from "uuid";
2809
- import { z as z35 } from "zod";
2810
- var CABQuantitySection = z35.object({
3340
+ import { z as z46 } from "zod";
3341
+ var CABQuantitySection = z46.object({
2811
3342
  ...CABVariableFields,
2812
- errorMessages: z35.record(
2813
- z35.string(),
2814
- z35.object({
3343
+ errorMessages: z46.record(
3344
+ z46.string(),
3345
+ z46.object({
2815
3346
  /** `{{step}}` is interpolated at render — the off-increment message React never gave a merchant key. */
2816
- increment: z35.string().optional(),
2817
- max: z35.string().optional(),
2818
- min: z35.string().optional(),
2819
- neg: z35.string().optional()
3347
+ increment: z46.string().optional(),
3348
+ max: z46.string().optional(),
3349
+ min: z46.string().optional(),
3350
+ neg: z46.string().optional()
2820
3351
  })
2821
3352
  ).default({
2822
3353
  en: {
@@ -2826,18 +3357,18 @@ var CABQuantitySection = z35.object({
2826
3357
  neg: "Quantity cannot be negative"
2827
3358
  }
2828
3359
  }),
2829
- inputType: z35.enum(quantityInputs).default(QuantityInput.select),
2830
- max: z35.number().min(1).max(100).default(10),
2831
- min: z35.number().min(1).default(1),
3360
+ inputType: z46.enum(quantityInputs).default(QuantityInput.select),
3361
+ max: z46.number().min(1).max(100).default(10),
3362
+ min: z46.number().min(1).default(1),
2832
3363
  /** The a11y label for the quantity control; the merchant names it in the editor, else this default. */
2833
- name: z35.string().default("Quantity"),
2834
- sectionId: z35.uuid().default(() => uuidv79()),
2835
- sectionType: z35.literal(SectionType.quantity).default(SectionType.quantity)
3364
+ name: z46.string().default("Quantity"),
3365
+ sectionId: z46.uuid().default(() => uuidv79()),
3366
+ sectionType: z46.literal(SectionType.quantity).default(SectionType.quantity)
2836
3367
  });
2837
3368
 
2838
3369
  // src/schema/widgets/checkout-and-beyond/reviews.ts
2839
3370
  import { v7 as uuidv710 } from "uuid";
2840
- import { z as z36 } from "zod";
3371
+ import { z as z47 } from "zod";
2841
3372
 
2842
3373
  // src/schema/widgets/checkout-and-beyond/reviewLabels.ts
2843
3374
  var REVIEW_LABELS = {
@@ -2900,68 +3431,68 @@ var REVIEW_LABELS = {
2900
3431
  };
2901
3432
 
2902
3433
  // src/schema/widgets/checkout-and-beyond/reviews.ts
2903
- var CABReviewsSection = z36.object({
3434
+ var CABReviewsSection = z47.object({
2904
3435
  ...CABVariableFields,
2905
- color: z36.string().default("#fadb14"),
3436
+ color: z47.string().default("#fadb14"),
2906
3437
  /**
2907
3438
  * Localized review-count templates (`{{reviewCount}}`), one/other plural forms; the client picks the
2908
3439
  * form via `Intl.PluralRules`. Defaults here (schema-first) so every tree localizes without converter
2909
3440
  * or merchant work.
2910
3441
  */
2911
- countLabels: z36.object({
2912
- one: z36.record(z36.string(), z36.string()).default(() => ({ ...REVIEW_LABELS.one })),
2913
- other: z36.record(z36.string(), z36.string()).default(() => ({ ...REVIEW_LABELS.other }))
3442
+ countLabels: z47.object({
3443
+ one: z47.record(z47.string(), z47.string()).default(() => ({ ...REVIEW_LABELS.one })),
3444
+ other: z47.record(z47.string(), z47.string()).default(() => ({ ...REVIEW_LABELS.other }))
2914
3445
  }).default(() => ({ one: { ...REVIEW_LABELS.one }, other: { ...REVIEW_LABELS.other } })),
2915
- name: z36.string().optional(),
2916
- sectionId: z36.uuid().default(() => uuidv710()),
2917
- sectionType: z36.literal(SectionType.reviews).default(SectionType.reviews),
2918
- size: z36.enum(reviewsSizes).default(ReviewsSize.default),
3446
+ name: z47.string().optional(),
3447
+ sectionId: z47.uuid().default(() => uuidv710()),
3448
+ sectionType: z47.literal(SectionType.reviews).default(SectionType.reviews),
3449
+ size: z47.enum(reviewsSizes).default(ReviewsSize.default),
2919
3450
  /**
2920
3451
  * Star outline color, interpolated into a style by the renderer, so it is hex-constrained like
2921
3452
  * `CABButtonSection.color`. The legacy source (`PostPurchaseSettings.styles.starStrokeColor`) is a free
2922
3453
  * string: its converter must validate and fall back to this default rather than let one odd value drop
2923
3454
  * the whole reviews section.
2924
3455
  */
2925
- strokeColor: z36.string().regex(HEX_COLOR_REGEX).default("#fadb14"),
3456
+ strokeColor: z47.string().regex(HEX_COLOR_REGEX).default("#fadb14"),
2926
3457
  /** Star outline width in px; `0` draws no outline. The legacy `styles.strokeWidth` is a STRING ('1') — its converter coerces. */
2927
- strokeWidth: z36.number().nonnegative().default(0)
3458
+ strokeWidth: z47.number().nonnegative().default(0)
2928
3459
  });
2929
3460
 
2930
3461
  // src/schema/widgets/checkout-and-beyond/separator.ts
2931
3462
  import { v7 as uuidv711 } from "uuid";
2932
- import { z as z37 } from "zod";
2933
- var CABSeparatorSection = z37.object({
3463
+ import { z as z48 } from "zod";
3464
+ var CABSeparatorSection = z48.object({
2934
3465
  ...CABVariableFields,
2935
- sectionId: z37.uuid().default(() => uuidv711()),
2936
- sectionType: z37.literal(SectionType.separator).default(SectionType.separator)
3466
+ sectionId: z48.uuid().default(() => uuidv711()),
3467
+ sectionType: z48.literal(SectionType.separator).default(SectionType.separator)
2937
3468
  });
2938
3469
 
2939
3470
  // src/schema/widgets/checkout-and-beyond/variants.ts
2940
3471
  import { slice } from "es-toolkit/compat";
2941
3472
  import { v7 as uuidv712 } from "uuid";
2942
- import { z as z38 } from "zod";
2943
- var CABVariantsSection = z38.object({
3473
+ import { z as z49 } from "zod";
3474
+ var CABVariantsSection = z49.object({
2944
3475
  ...CABVariableFields,
2945
- hideOutOfStockVariants: z38.boolean().default(false),
2946
- name: z38.string().optional(),
2947
- sectionId: z38.uuid().default(() => uuidv712()),
2948
- sectionType: z38.literal(SectionType.variants).default(SectionType.variants),
2949
- selector: z38.enum(slice(variantSelectors, 0, 3)).default(VariantSelector.menu),
2950
- variantMode: z38.enum(variantModes).default(VariantMode.multiple)
3476
+ hideOutOfStockVariants: z49.boolean().default(false),
3477
+ name: z49.string().optional(),
3478
+ sectionId: z49.uuid().default(() => uuidv712()),
3479
+ sectionType: z49.literal(SectionType.variants).default(SectionType.variants),
3480
+ selector: z49.enum(slice(variantSelectors, 0, 3)).default(VariantSelector.menu),
3481
+ variantMode: z49.enum(variantModes).default(VariantMode.multiple)
2951
3482
  });
2952
3483
 
2953
3484
  // src/schema/widgets/checkout-and-beyond/shared.ts
2954
- var CABBorder = z39.object({
2955
- radius: z39.enum(borderRadii).default(BorderRadius.base),
2956
- style: z39.enum(borderStyles).default(BorderStyle.none),
2957
- width: z39.enum(borderWidths).default(BorderWidth.base)
3485
+ var CABBorder = z50.object({
3486
+ radius: z50.enum(borderRadii).default(BorderRadius.base),
3487
+ style: z50.enum(borderStyles).default(BorderStyle.none),
3488
+ width: z50.enum(borderWidths).default(BorderWidth.base)
2958
3489
  }).default({
2959
3490
  radius: BorderRadius.base,
2960
3491
  style: BorderStyle.none,
2961
3492
  width: BorderWidth.base
2962
3493
  });
2963
- var CABSection = z39.lazy(
2964
- () => z39.discriminatedUnion("sectionType", [
3494
+ var CABSection = z50.lazy(
3495
+ () => z50.discriminatedUnion("sectionType", [
2965
3496
  CABBannerSection,
2966
3497
  CABButtonSection,
2967
3498
  CABCarouselSection,
@@ -2984,41 +3515,41 @@ var CABSection = z39.lazy(
2984
3515
  );
2985
3516
 
2986
3517
  // src/schema/widgets/checkout-and-beyond/layout.ts
2987
- var GridItem = z40.union([z40.literal("auto"), z40.literal("fill"), z40.string().regex(/^\d+%$/), z40.number()]);
2988
- var CABLayoutWrapping = z40.object({
2989
- breakAt: z40.number().positive(),
2990
- maxPerLine: z40.number().int().positive()
3518
+ var GridItem = z51.union([z51.literal("auto"), z51.literal("fill"), z51.string().regex(/^\d+%$/), z51.number()]);
3519
+ var CABLayoutWrapping = z51.object({
3520
+ breakAt: z51.number().positive(),
3521
+ maxPerLine: z51.number().int().positive()
2991
3522
  });
2992
- var CABLayoutSection = z40.object({
3523
+ var CABLayoutSection = z51.object({
2993
3524
  ...CABVariableFields,
2994
- alignment: z40.object({
2995
- horizontal: z40.enum(horizontalAlignments).default(HorizontalAlignment.start),
2996
- vertical: z40.enum(verticalAlignments).default(VerticalAlignment.top)
3525
+ alignment: z51.object({
3526
+ horizontal: z51.enum(horizontalAlignments).default(HorizontalAlignment.start),
3527
+ vertical: z51.enum(verticalAlignments).default(VerticalAlignment.top)
2997
3528
  }).default({
2998
3529
  horizontal: HorizontalAlignment.start,
2999
3530
  vertical: VerticalAlignment.top
3000
3531
  }),
3001
- border: z40.lazy(() => CABBorder),
3002
- buttonField: z40.enum(buttonFields).optional(),
3003
- direction: z40.enum(directions).default(Direction.rows),
3532
+ border: z51.lazy(() => CABBorder),
3533
+ buttonField: z51.enum(buttonFields).optional(),
3534
+ direction: z51.enum(directions).default(Direction.rows),
3004
3535
  /**
3005
3536
  * Platform chrome around the section, not a layout behavior: `callout` is a subdued box with block borders
3006
3537
  * (the legacy post-purchase callout banner), `offer-content` the post-purchase offer's own content card.
3007
3538
  */
3008
- frame: z40.enum(layoutFrames).optional(),
3009
- grid: z40.object({
3010
- columns: z40.union([z40.array(GridItem), z40.undefined()]).default(() => ["auto"]),
3011
- rows: z40.union([z40.array(GridItem), z40.undefined()]).default(() => ["auto"])
3539
+ frame: z51.enum(layoutFrames).optional(),
3540
+ grid: z51.object({
3541
+ columns: z51.union([z51.array(GridItem), z51.undefined()]).default(() => ["auto"]),
3542
+ rows: z51.union([z51.array(GridItem), z51.undefined()]).default(() => ["auto"])
3012
3543
  }).default({ columns: ["auto"], rows: ["auto"] }).optional(),
3013
- name: z40.string().optional(),
3014
- padding: z40.enum(spacings).default(Spacing.none),
3015
- sectionId: z40.uuid().default(() => uuidv713()),
3016
- sections: z40.union([z40.array(z40.lazy(() => CABSection)), z40.strictObject({}).transform(() => [])]).default(() => []),
3017
- sectionType: z40.literal(SectionType.layout).default(SectionType.layout),
3018
- spacing: z40.enum(spacings).default(Spacing.base),
3544
+ name: z51.string().optional(),
3545
+ padding: z51.enum(spacings).default(Spacing.none),
3546
+ sectionId: z51.uuid().default(() => uuidv713()),
3547
+ sections: z51.union([z51.array(z51.lazy(() => CABSection)), z51.strictObject({}).transform(() => [])]).default(() => []),
3548
+ sectionType: z51.literal(SectionType.layout).default(SectionType.layout),
3549
+ spacing: z51.enum(spacings).default(Spacing.base),
3019
3550
  /** Fire-and-forget impression pixel POSTed once when the section is shown (e.g. a Monetize offer view). */
3020
- viewUrl: z40.string().optional(),
3021
- width: z40.number().default(100),
3551
+ viewUrl: z51.string().optional(),
3552
+ width: z51.number().default(100),
3022
3553
  wrapping: CABLayoutWrapping.optional()
3023
3554
  });
3024
3555
 
@@ -3040,8 +3571,8 @@ var UI_LABELS = {
3040
3571
  };
3041
3572
 
3042
3573
  // src/schema/widgets/checkout-and-beyond/root.ts
3043
- var localized = (fallback) => z41.record(z41.string(), z41.string()).default(() => ({ ...fallback })).transform((labels) => Object.keys(labels).length > 0 ? labels : { ...fallback });
3044
- var CABUILabels = z41.object({
3574
+ var localized = (fallback) => z52.record(z52.string(), z52.string()).default(() => ({ ...fallback })).transform((labels) => Object.keys(labels).length > 0 ? labels : { ...fallback });
3575
+ var CABUILabels = z52.object({
3045
3576
  currentPage: localized(UI_LABELS.currentPage),
3046
3577
  guest: localized(UI_LABELS.guest),
3047
3578
  loadingOptions: localized(UI_LABELS.loadingOptions),
@@ -3066,154 +3597,154 @@ var CABUILabels = z41.object({
3066
3597
  subscriptionOptions: { ...UI_LABELS.subscriptionOptions },
3067
3598
  updating: { ...UI_LABELS.updating }
3068
3599
  }));
3069
- var TargetArea = z41.object({
3070
- fill: z41.boolean().optional(),
3071
- flip: z41.enum(["both", "horizontal", "vertical"]).optional(),
3072
- icon: z41.string(),
3073
- label: z41.string(),
3074
- width: z41.string()
3600
+ var TargetArea = z52.object({
3601
+ fill: z52.boolean().optional(),
3602
+ flip: z52.enum(["both", "horizontal", "vertical"]).optional(),
3603
+ icon: z52.string(),
3604
+ label: z52.string(),
3605
+ width: z52.string()
3075
3606
  }).default(targetAreas[EditorMode.checkoutExtension][1]);
3076
- var CABTracking = z41.object({
3077
- enableAttribution: z41.boolean().nullish().transform((value) => value ?? true),
3078
- enableSource: z41.boolean().nullish().transform((value) => value ?? true),
3079
- enableWidget: z41.boolean().nullish().transform((value) => value ?? true)
3607
+ var CABTracking = z52.object({
3608
+ enableAttribution: z52.boolean().nullish().transform((value) => value ?? true),
3609
+ enableSource: z52.boolean().nullish().transform((value) => value ?? true),
3610
+ enableWidget: z52.boolean().nullish().transform((value) => value ?? true)
3080
3611
  }).nullish().transform((value) => value ?? { enableAttribution: true, enableSource: true, enableWidget: true });
3081
- var CABExperiment = z41.object({
3082
- elementId: z41.number(),
3083
- experimentId: z41.number(),
3084
- experimentType: z41.string(),
3085
- selectedId: z41.number()
3612
+ var CABExperiment = z52.object({
3613
+ elementId: z52.number(),
3614
+ experimentId: z52.number(),
3615
+ experimentType: z52.string(),
3616
+ selectedId: z52.number()
3086
3617
  });
3087
3618
  var CABRootSection = CABLayoutSection.extend({
3088
- editorMode: z41.enum(editorModes).default(EditorMode.checkoutExtension),
3619
+ editorMode: z52.enum(editorModes).default(EditorMode.checkoutExtension),
3089
3620
  experiment: CABExperiment.optional(),
3090
3621
  // Same rule as CABTracking above: the v1 converters pass raw legacy `previewMode` through, so a
3091
3622
  // `null` must fall back rather than throw the widget; malformed values still throw.
3092
- previewMode: z41.boolean().nullish().transform((value) => value ?? false),
3093
- storeId: z41.number().nullable().default(null),
3623
+ previewMode: z52.boolean().nullish().transform((value) => value ?? false),
3624
+ storeId: z52.number().nullable().default(null),
3094
3625
  targetArea: TargetArea.nullable(),
3095
3626
  tracking: CABTracking,
3096
- type: z41.enum(widgetTypes).default(WidgetType.ui_extension_content_block),
3627
+ type: z52.enum(widgetTypes).default(WidgetType.ui_extension_content_block),
3097
3628
  uiLabels: CABUILabels,
3098
- version: z41.literal(2).default(2),
3099
- widgetId: z41.number().nullable().default(null)
3629
+ version: z52.literal(2).default(2),
3630
+ widgetId: z52.number().nullable().default(null)
3100
3631
  });
3101
3632
 
3102
3633
  // src/schema/widgets/contentBlock.ts
3103
- var ContentBlockV1 = z42.object({
3104
- blockSpacing: z42.enum(spacings).optional(),
3105
- imageBlocks: z42.union([
3106
- z42.array(
3107
- z42.object({
3108
- altText: z42.string().nullable(),
3109
- description: z42.string().nullable(),
3110
- id: z42.uuid(),
3111
- imagePlacement: z42.enum(["top", "right", "bottom", "left"]),
3112
- imageSize: z42.number(),
3113
- imageUrl: z42.url(),
3114
- textAlignment: z42.enum(["left", "center", "right"]),
3634
+ var ContentBlockV1 = z53.object({
3635
+ blockSpacing: z53.enum(spacings).optional(),
3636
+ imageBlocks: z53.union([
3637
+ z53.array(
3638
+ z53.object({
3639
+ altText: z53.string().nullable(),
3640
+ description: z53.string().nullable(),
3641
+ id: z53.uuid(),
3642
+ imagePlacement: z53.enum(["top", "right", "bottom", "left"]),
3643
+ imageSize: z53.number(),
3644
+ imageUrl: z53.url(),
3645
+ textAlignment: z53.enum(["left", "center", "right"]),
3115
3646
  /** Inline scale only: an image caption can never be a block-level heading. */
3116
- textSize: z42.enum(inlineTextSizeNames)
3647
+ textSize: z53.enum(inlineTextSizeNames)
3117
3648
  })
3118
3649
  ),
3119
- z42.strictObject({}).transform(() => [])
3650
+ z53.strictObject({}).transform(() => [])
3120
3651
  ]).optional(),
3121
- imageLayout: z42.enum(["row", "column"]).optional(),
3122
- language: z42.object({
3123
- description: z42.string(),
3124
- superTitle: z42.string(),
3125
- title: z42.string()
3652
+ imageLayout: z53.enum(["row", "column"]).optional(),
3653
+ language: z53.object({
3654
+ description: z53.string(),
3655
+ superTitle: z53.string(),
3656
+ title: z53.string()
3126
3657
  }),
3127
- previewMode: z42.boolean(),
3128
- type: z42.literal(WidgetType.ui_extension_content_block).default(WidgetType.ui_extension_content_block),
3129
- version: z42.literal(1)
3658
+ previewMode: z53.boolean(),
3659
+ type: z53.literal(WidgetType.ui_extension_content_block).default(WidgetType.ui_extension_content_block),
3660
+ version: z53.literal(1)
3130
3661
  });
3131
- var ContentBlock = z42.discriminatedUnion("version", [
3662
+ var ContentBlock = z53.discriminatedUnion("version", [
3132
3663
  ContentBlockV1,
3133
3664
  CABRootSection.extend({
3134
- type: z42.literal(WidgetType.ui_extension_content_block).default(WidgetType.ui_extension_content_block)
3665
+ type: z53.literal(WidgetType.ui_extension_content_block).default(WidgetType.ui_extension_content_block)
3135
3666
  })
3136
3667
  ]);
3137
3668
 
3138
3669
  // src/schema/widgets/giftWithPurchase.ts
3139
- import { z as z43 } from "zod";
3140
- var GiftWithPurchase = z43.looseObject({
3141
- type: z43.literal(WidgetType.gift_with_purchase).default(WidgetType.gift_with_purchase)
3670
+ import { z as z54 } from "zod";
3671
+ var GiftWithPurchase = z54.looseObject({
3672
+ type: z54.literal(WidgetType.gift_with_purchase).default(WidgetType.gift_with_purchase)
3142
3673
  });
3143
3674
 
3144
3675
  // src/schema/widgets/lineItemEditor.ts
3145
- import { z as z44 } from "zod";
3146
- var LineItemEditorSwitchLanguageV1 = z44.object({
3147
- downgradeToOneTimeLabel: z44.string().optional(),
3676
+ import { z as z55 } from "zod";
3677
+ var LineItemEditorSwitchLanguageV1 = z55.object({
3678
+ downgradeToOneTimeLabel: z55.string().optional(),
3148
3679
  /** Frequency-option template (`{{frequency}}`/`{{interval}}`) for the plan select. */
3149
- subscriptionOptionLabel: z44.string().optional(),
3150
- upgradeToSubscriptionLabel: z44.string().optional(),
3151
- upgradeToSubscriptionWithoutDiscountLabel: z44.string().optional()
3680
+ subscriptionOptionLabel: z55.string().optional(),
3681
+ upgradeToSubscriptionLabel: z55.string().optional(),
3682
+ upgradeToSubscriptionWithoutDiscountLabel: z55.string().optional()
3152
3683
  });
3153
- var LineItemEditorV1 = z44.object({
3684
+ var LineItemEditorV1 = z55.object({
3154
3685
  /** Legacy `getStyles` button style; the converter carries a valid kind, defaulting to `plain`. */
3155
- button: z44.object({ kind: z44.enum(["plain", "primary", "secondary"]).optional() }).optional(),
3156
- previewMode: z44.boolean().optional(),
3157
- switchToSubscription: z44.object({
3158
- disableDowngrade: z44.boolean().optional(),
3686
+ button: z55.object({ kind: z55.enum(["plain", "primary", "secondary"]).optional() }).optional(),
3687
+ previewMode: z55.boolean().optional(),
3688
+ switchToSubscription: z55.object({
3689
+ disableDowngrade: z55.boolean().optional(),
3159
3690
  language: LineItemEditorSwitchLanguageV1.optional()
3160
3691
  }).optional(),
3161
- switchToSubscriptionEnabled: z44.boolean().optional(),
3162
- tracking: z44.object({
3163
- enableAttribution: z44.boolean().optional(),
3164
- enableSource: z44.boolean().optional(),
3165
- enableWidget: z44.boolean().optional()
3692
+ switchToSubscriptionEnabled: z55.boolean().optional(),
3693
+ tracking: z55.object({
3694
+ enableAttribution: z55.boolean().optional(),
3695
+ enableSource: z55.boolean().optional(),
3696
+ enableWidget: z55.boolean().optional()
3166
3697
  }).optional(),
3167
- type: z44.literal(WidgetType.ui_extension_line_item_editor).default(WidgetType.ui_extension_line_item_editor),
3168
- version: z44.literal(1)
3698
+ type: z55.literal(WidgetType.ui_extension_line_item_editor).default(WidgetType.ui_extension_line_item_editor),
3699
+ version: z55.literal(1)
3169
3700
  });
3170
- var LineItemEditor = z44.discriminatedUnion("version", [
3701
+ var LineItemEditor = z55.discriminatedUnion("version", [
3171
3702
  LineItemEditorV1,
3172
3703
  CABRootSection.extend({
3173
- type: z44.literal(WidgetType.ui_extension_line_item_editor).default(WidgetType.ui_extension_line_item_editor)
3704
+ type: z55.literal(WidgetType.ui_extension_line_item_editor).default(WidgetType.ui_extension_line_item_editor)
3174
3705
  })
3175
3706
  ]);
3176
3707
 
3177
3708
  // src/schema/widgets/progressBar.ts
3178
- import { z as z45 } from "zod";
3179
- var ProgressBar = z45.looseObject({
3180
- type: z45.literal(WidgetType.ui_extension_progress_bar).default(WidgetType.ui_extension_progress_bar)
3709
+ import { z as z56 } from "zod";
3710
+ var ProgressBar = z56.looseObject({
3711
+ type: z56.literal(WidgetType.ui_extension_progress_bar).default(WidgetType.ui_extension_progress_bar)
3181
3712
  });
3182
3713
 
3183
3714
  // src/schema/widgets/rebuyButton.ts
3184
- import { z as z46 } from "zod";
3185
- var RebuyButtonV1 = z46.looseObject({
3186
- type: z46.literal(WidgetType.ui_extension_button).default(WidgetType.ui_extension_button),
3187
- version: z46.literal(1)
3715
+ import { z as z57 } from "zod";
3716
+ var RebuyButtonV1 = z57.looseObject({
3717
+ type: z57.literal(WidgetType.ui_extension_button).default(WidgetType.ui_extension_button),
3718
+ version: z57.literal(1)
3188
3719
  });
3189
- var RebuyButton = z46.discriminatedUnion("version", [
3720
+ var RebuyButton = z57.discriminatedUnion("version", [
3190
3721
  RebuyButtonV1,
3191
3722
  CABRootSection.extend({
3192
- type: z46.literal(WidgetType.ui_extension_button).default(WidgetType.ui_extension_button)
3723
+ type: z57.literal(WidgetType.ui_extension_button).default(WidgetType.ui_extension_button)
3193
3724
  })
3194
3725
  ]);
3195
3726
 
3196
3727
  // src/schema/widgets/rebuyMonetize.ts
3197
- import { z as z47 } from "zod";
3198
- var RebuyMonetize = z47.looseObject({
3199
- type: z47.literal(WidgetType.ui_extension_ad).default(WidgetType.ui_extension_ad)
3728
+ import { z as z58 } from "zod";
3729
+ var RebuyMonetize = z58.looseObject({
3730
+ type: z58.literal(WidgetType.ui_extension_ad).default(WidgetType.ui_extension_ad)
3200
3731
  });
3201
- var RebuyMonetizeV1 = z47.object({
3202
- name: z47.string().nullable().optional(),
3203
- previewMode: z47.boolean().optional(),
3732
+ var RebuyMonetizeV1 = z58.object({
3733
+ name: z58.string().nullable().optional(),
3734
+ previewMode: z58.boolean().optional(),
3204
3735
  /** Privacy Policy footer href → the marker section's `privacyPolicyUrl`. */
3205
- privacyPolicyUrl: z47.string().nullable().optional(),
3736
+ privacyPolicyUrl: z58.string().nullable().optional(),
3206
3737
  /** Ads-taxonomy sub-vertical id — one of the admin Monetize editor's two configurables. */
3207
- subVertical: z47.string().nullable().optional(),
3208
- tracking: z47.object({
3209
- enableAttribution: z47.boolean().optional(),
3210
- enableSource: z47.boolean().optional(),
3211
- enableWidget: z47.boolean().optional()
3738
+ subVertical: z58.string().nullable().optional(),
3739
+ tracking: z58.object({
3740
+ enableAttribution: z58.boolean().optional(),
3741
+ enableSource: z58.boolean().optional(),
3742
+ enableWidget: z58.boolean().optional()
3212
3743
  }).optional(),
3213
- type: z47.literal(WidgetType.ui_extension_ad).default(WidgetType.ui_extension_ad),
3214
- version: z47.literal(1),
3744
+ type: z58.literal(WidgetType.ui_extension_ad).default(WidgetType.ui_extension_ad),
3745
+ version: z58.literal(1),
3215
3746
  /** Ads-taxonomy vertical id — one of the admin Monetize editor's two configurables. */
3216
- vertical: z47.string().nullable().optional()
3747
+ vertical: z58.string().nullable().optional()
3217
3748
  });
3218
3749
 
3219
3750
  // src/schema/widgetData.ts
@@ -3227,7 +3758,7 @@ var extensionWidgetTypes = [
3227
3758
  WidgetType.ui_extension_line_item_editor,
3228
3759
  WidgetType.ui_extension_progress_bar
3229
3760
  ];
3230
- var WidgetData = z48.discriminatedUnion("type", [
3761
+ var WidgetData = z59.discriminatedUnion("type", [
3231
3762
  ABTestingPlaceholder,
3232
3763
  CheckoutExtension,
3233
3764
  ContentBlock,
@@ -3586,391 +4117,37 @@ var SWITCH_LABELS = {
3586
4117
  }
3587
4118
  };
3588
4119
 
3589
- // src/schema/widgets/post-purchase-offer/common.ts
3590
- import { replace, toNumber, toString } from "es-toolkit/compat";
3591
- import { z as z49 } from "zod";
3592
- var strictNumber = z49.union([
3593
- z49.number(),
3594
- z49.string().transform((value) => toNumber(replace(toString(value), /[^0-9.]/g, "")) || 0),
3595
- z49.unknown().transform(() => 0)
3596
- ]);
3597
-
3598
- // src/schema/widgets/post-purchase-offer/constants.ts
3599
- import { z as z50 } from "zod";
3600
- var blockTypes = [
3601
- "callout_banner",
3602
- "image",
3603
- "image_content",
3604
- "pay_button",
3605
- "product_information",
3606
- "separator",
3607
- "text",
3608
- "timer"
3609
- ];
3610
- var blockType = z50.enum(blockTypes);
3611
- var BlockType = blockType.enum;
3612
-
3613
- // src/schema/widgets/post-purchase-offer/postPurchaseBlocks.ts
3614
- import { get as get3, isEqual } from "es-toolkit/compat";
3615
- import { v4 as uuidv42 } from "uuid";
3616
- import { z as z51 } from "zod";
3617
- var TextAlignment2 = z51.union([z51.enum(["leading", "center", "trailing"]), z51.unknown().transform(() => "leading")]);
3618
- var TextSize = z51.union([
3619
- z51.enum(["xsmall", "small", "base", "default", "medium", "large", "xlarge"]),
3620
- z51.unknown().transform(() => "medium")
3621
- ]);
3622
- var CalloutBannerBlock = z51.object({
3623
- id: z51.string().optional().default(() => uuidv42()),
3624
- name: z51.string().optional(),
3625
- settings: z51.object({
3626
- superTitle: z51.union([z51.string(), TiptapDocument]).default(() => "Limited-time Offer"),
3627
- title: z51.union([z51.string(), TiptapDocument]).default(() => "Add this customer favorite to your order")
3628
- }),
3629
- styles: z51.object({
3630
- superTitleEmphasized: z51.boolean().default(false),
3631
- superTitleSize: TextSize.default("large"),
3632
- textAlignment: TextAlignment2.default("center"),
3633
- titleEmphasized: z51.boolean().default(true),
3634
- titleSize: TextSize.default("large")
3635
- }),
3636
- type: z51.literal(BlockType.callout_banner).default(BlockType.callout_banner)
3637
- });
3638
- var ImageBlock = z51.object({
3639
- id: z51.string().optional().default(() => uuidv42()),
3640
- name: z51.string().optional(),
3641
- settings: z51.union([
3642
- z51.object({
3643
- /** This isn't used in the post-purchase offer widget */
3644
- alt: z51.string().optional().default(""),
3645
- image: z51.union([z51.literal(""), z51.url()]).default(""),
3646
- imageSize: z51.number().default(20),
3647
- imageType: z51.enum(["URL", "UPLOAD"]).default("URL")
3648
- }),
3649
- z51.array(z51.never()).transform(() => ({}))
3650
- ]),
3651
- type: z51.literal(BlockType.image).default(BlockType.image)
3652
- });
3653
- var ImageContentBlock = z51.object({
3654
- id: z51.string().optional().default(() => uuidv42()),
3655
- name: z51.string().optional(),
3656
- settings: z51.object({
3657
- alt: z51.string().optional().default(""),
3658
- description: z51.union([z51.string(), TiptapDocument, z51.null()]).default(
3659
- "Lorem ipsum dolor sit amet, consectetur adipiscing elit, sed do eiusmod tempor incididunt ut labore et dolore magna aliqua. Ut enim ad minim veniam, quis nostrud exercitation ullamco laboris nisi ut aliquip ex ea commodo consequat. Duis aute irure dolor in reprehenderit in voluptate velit esse cillum dolore eu fugiat nulla pariatur. Excepteur sint occaecat cupidatat non proident, sunt in culpa qui officia deserunt mollit anim id est laborum."
3660
- ),
3661
- descriptionSize: TextSize.default("medium"),
3662
- horizontalAlignment: TextAlignment2.default("leading"),
3663
- image: z51.union([z51.literal(""), z51.url()]).default(""),
3664
- imagePlacement: z51.enum(["bottom", "left", "right", "top"]).optional().default("left"),
3665
- imageSize: z51.number().default(20),
3666
- superTitle: z51.union([z51.string(), TiptapDocument]).default("Lorem Ipsum!"),
3667
- superTitleSize: TextSize.default("medium"),
3668
- /** This isn't configurable in the admin-nextjs editor */
3669
- swapContent: z51.boolean().optional().default(false),
3670
- title: z51.union([z51.string(), TiptapDocument]).nullable().default("Lorem ipsum dolor sit amet"),
3671
- titleSize: TextSize.default("medium")
3672
- }),
3673
- type: z51.literal(BlockType.image_content).default(BlockType.image_content)
3674
- });
3675
- var PayButtonBlock = z51.object({
3676
- id: z51.string().optional().default(() => uuidv42()),
3677
- name: z51.string().optional(),
3678
- settings: z51.union([
3679
- z51.object({
3680
- label: z51.string().default("Pay Now")
3681
- }),
3682
- z51.array(z51.never()).transform(() => ({
3683
- label: "Pay Now"
3684
- }))
3685
- ]),
3686
- styles: z51.union([
3687
- z51.object({
3688
- buttonWidth: z51.number().min(10).max(100).default(50)
3689
- }),
3690
- z51.array(z51.never()).transform(() => ({
3691
- buttonWidth: 50
3692
- }))
3693
- ]),
3694
- type: z51.literal(BlockType.pay_button).default(BlockType.pay_button)
3695
- });
3696
- var ProductInformationBlock = z51.object({
3697
- /** This isn't configurable in the admin-nextjs editor */
3698
- hideProductImage: z51.boolean().optional().default(false),
3699
- id: z51.string().optional().default(() => uuidv42()),
3700
- name: z51.string().optional(),
3701
- type: z51.literal(BlockType.product_information).default(BlockType.product_information)
3702
- });
3703
- var SeparatorBlock = z51.object({
3704
- id: z51.string().optional().default(() => uuidv42()),
3705
- name: z51.string().optional(),
3706
- type: z51.literal(BlockType.separator).default(BlockType.separator)
3707
- });
3708
- var TextBlock = z51.object({
3709
- id: z51.string().optional().default(() => uuidv42()),
3710
- name: z51.string().optional(),
3711
- settings: z51.object({
3712
- description: z51.union([z51.string(), TiptapDocument]).optional().default(
3713
- "Lorem ipsum dolor sit amet, consectetur adipiscing elit, sed do eiusmod tempor incididunt ut labore et dolore magna aliqua. Ut enim ad minim veniam, quis nostrud exercitation ullamco laboris nisi ut aliquip ex ea commodo consequat. Duis aute irure dolor in reprehenderit in voluptate velit esse cillum dolore eu fugiat nulla pariatur. Excepteur sint occaecat cupidatat non proident, sunt in culpa qui officia deserunt mollit anim id est laborum."
3714
- ),
3715
- /** This isn't used in the post-purchase offer widget */
3716
- descriptionSize: TextSize.default("medium"),
3717
- horizontalAlignment: TextAlignment2.default("leading"),
3718
- superTitle: z51.union([z51.string(), TiptapDocument]).default("Super Title"),
3719
- /** This isn't used in the post-purchase offer widget */
3720
- superTitleSize: TextSize.default("medium"),
3721
- title: z51.union([z51.string(), TiptapDocument]).nullable().default("Lorem ipsum dolor sit amet."),
3722
- /** This isn't used in the post-purchase offer widget */
3723
- titleSize: TextSize.default("medium")
3724
- }),
3725
- type: z51.literal(BlockType.text).default(BlockType.text)
3726
- });
3727
- var TimerBlock = z51.object({
3728
- id: z51.string().optional().default(() => uuidv42()),
3729
- name: z51.string().optional(),
3730
- settings: z51.object({
3731
- durationMinutes: z51.number().min(0).default(10),
3732
- durationSeconds: z51.union([z51.number().min(0), z51.unknown().transform(() => 0)]).default(0),
3733
- endOffer: z51.boolean().default(true),
3734
- title: z51.union([z51.string(), TiptapDocument]).default("Hurry \u2014 your special offer ends in:")
3735
- }),
3736
- styles: z51.object({
3737
- textAlignment: TextAlignment2.default("center"),
3738
- timerBackgroundColor: z51.enum(["info", "warning", "success", "critical"]).default("warning"),
3739
- timerEmphasized: z51.union([z51.boolean(), z51.unknown().transform(() => true)]).default(true),
3740
- timerSize: TextSize.default("medium"),
3741
- timerWidth: z51.number().min(10).max(100).optional().default(100),
3742
- titleEmphasized: z51.union([z51.boolean(), z51.unknown().transform(() => true)]).default(false),
3743
- titleSize: TextSize.default("medium")
3744
- }),
3745
- type: z51.literal(BlockType.timer).default(BlockType.timer)
3746
- });
3747
- var PostPurchaseBlock = z51.discriminatedUnion("type", [
3748
- CalloutBannerBlock,
3749
- ImageBlock,
3750
- ImageContentBlock,
3751
- PayButtonBlock,
3752
- ProductInformationBlock,
3753
- SeparatorBlock,
3754
- TextBlock,
3755
- TimerBlock
3756
- ]);
3757
- var isCalloutBannerBlock = (block) => isEqual(get3(block, "type"), BlockType.callout_banner);
3758
- var isImageBlock = (block) => isEqual(get3(block, "type"), BlockType.image);
3759
- var isImageContentBlock = (block) => isEqual(get3(block, "type"), BlockType.image_content);
3760
- var isPayButtonBlock = (block) => isEqual(get3(block, "type"), BlockType.pay_button);
3761
- var isProductInformationBlock = (block) => isEqual(get3(block, "type"), BlockType.product_information);
3762
- var isSeparatorBlock = (block) => isEqual(get3(block, "type"), BlockType.separator);
3763
- var isTextBlock = (block) => isEqual(get3(block, "type"), BlockType.text);
3764
- var isTimerBlock = (block) => isEqual(get3(block, "type"), BlockType.timer);
3765
-
3766
4120
  // src/schema/widgets/post-purchase-offer/postPurchaseOffer.ts
3767
- import { z as z54 } from "zod";
4121
+ import { z as z61 } from "zod";
3768
4122
 
3769
4123
  // src/schema/widgets/post-purchase-offer/postPurchaseWidget.ts
3770
- import { z as z53 } from "zod";
3771
-
3772
- // src/schema/widgets/post-purchase-offer/postPurchaseSettings.ts
3773
- import { z as z52 } from "zod";
3774
- var PostPurchaseSettings = z52.object({
3775
- advance: z52.object({ removePartialOrder: z52.boolean().default(true) }).optional().default(() => ({ removePartialOrder: true })),
3776
- blocks: z52.union([z52.array(PostPurchaseBlock), z52.unknown().transform(() => [])]).default(() => [
3777
- PostPurchaseBlock.parse({ settings: {}, styles: {}, type: BlockType.timer }),
3778
- PostPurchaseBlock.parse({ settings: {}, styles: {}, type: BlockType.callout_banner }),
3779
- PostPurchaseBlock.parse({ type: BlockType.product_information })
3780
- ]),
3781
- columnLayout: z52.boolean().optional(),
3782
- discount: z52.object({
3783
- amount: strictNumber.default(30),
3784
- shouldShowSavingText: z52.boolean().optional().default(true),
3785
- type: z52.enum(["none", "fixed_amount", "percentage"]).default("none")
3786
- }),
3787
- discountedFrom: z52.enum(["price", "compare_at_price"]).optional().default("price"),
3788
- endpoint: z52.string().optional(),
3789
- integrations: z52.object({
3790
- judgeme: z52.boolean().default(false),
3791
- junip: z52.boolean().optional().default(false),
3792
- klaviyo: z52.boolean().default(false),
3793
- loox: z52.boolean().default(false),
3794
- okendo: z52.boolean().default(false),
3795
- opinew: z52.boolean().optional().default(false),
3796
- reviewsio: z52.boolean().optional().default(false),
3797
- stamped: z52.boolean().default(false),
3798
- yotpo: z52.boolean().default(false)
3799
- }),
3800
- key: z52.string().optional(),
3801
- language: z52.object({
3802
- description: z52.union([z52.string(), z52.unknown().transform(() => "")]).default(""),
3803
- descriptionEnabled: z52.boolean().optional().default(false),
3804
- descriptionRte: z52.object({
3805
- content: z52.array(z52.unknown()),
3806
- type: z52.string()
3807
- }).optional(),
3808
- descriptionSpacing: z52.enum(["none", "xtight", "tight", "default", "loose", "xloose"]).optional(),
3809
- displayCtaPrice: z52.boolean().default(true),
3810
- global: z52.object({
3811
- declineAll: z52.string().optional().default("Decline All"),
3812
- declineThisOffer: z52.string().default("Decline this offer"),
3813
- free: z52.string().optional().default("Free"),
3814
- notAvailable: z52.string().optional().default("Not available"),
3815
- payNow: z52.string().default("Pay Now"),
3816
- payNowUpgradeToSubscription: z52.string().optional().default("Upgrade to Subscription"),
3817
- quantity: z52.string().default("Quantity"),
3818
- /** This isn't configurable in the admin-nextjs editor */
3819
- recurringShipping: z52.string().optional().default("Recurring shipping"),
3820
- recurringSubtotal: z52.string().default("Recurring subtotal"),
3821
- reviewsPlural: z52.string().optional().default("Reviews"),
3822
- reviewsSingular: z52.string().optional().default("Review"),
3823
- save: z52.union([z52.string(), z52.unknown().transform(() => "Save")]).optional().default("Save"),
3824
- shipping: z52.string().default("Shipping"),
3825
- subscriptionOption: z52.string().optional().default("Subscribe and Save"),
3826
- subtotal: z52.string().default("Subtotal"),
3827
- taxes: z52.string().default("Taxes"),
3828
- total: z52.string().default("Total")
3829
- }).optional().default(() => ({
3830
- declineAll: "Decline All",
3831
- declineThisOffer: "Decline this offer",
3832
- free: "Free",
3833
- notAvailable: "Not available",
3834
- payNow: "Pay Now",
3835
- payNowUpgradeToSubscription: "Upgrade to Subscription",
3836
- quantity: "Quantity",
3837
- /** This isn't configurable in the admin-nextjs editor */
3838
- recurringShipping: "Recurring shipping",
3839
- recurringSubtotal: "Recurring subtotal",
3840
- reviewsPlural: "Reviews",
3841
- reviewsSingular: "Review",
3842
- save: "Save",
3843
- shipping: "Shipping",
3844
- subscriptionOption: "Subscribe and Save",
3845
- subtotal: "Subtotal",
3846
- taxes: "Taxes",
3847
- total: "Total"
3848
- })),
3849
- globalTranslation: z52.string().optional().default("english")
3850
- }),
3851
- metafields: z52.boolean().default(false),
3852
- /** This isn't configurable in the admin-nextjs editor */
3853
- offer: z52.object({
3854
- count: z52.number().default(1)
3855
- }),
3856
- offersLayout: z52.object({
3857
- itemsPerPage: z52.number().optional(),
3858
- type: z52.enum(["list", "grid", "carousel"]).default("list")
3859
- }).optional().default({
3860
- type: "list"
3861
- }),
3862
- /** This isn't configurable in the admin-nextjs editor */
3863
- previewMode: z52.boolean().default(false),
3864
- productLimit: z52.number().optional().default(1),
3865
- productOptions: z52.object({
3866
- /** This isn't configurable in the admin-nextjs editor */
3867
- hideOutOfStockVariants: z52.boolean().optional().default(false),
3868
- matchVariant: z52.boolean().optional().default(true),
3869
- showDeclineAll: z52.enum(["above", "below", "both", "none"]).optional(),
3870
- showShipping: z52.boolean().optional().default(true),
3871
- showSubtotal: z52.boolean().optional().default(true),
3872
- showTaxes: z52.boolean().optional().default(true),
3873
- showTotal: z52.boolean().optional().default(true),
3874
- showVariantSelectors: z52.boolean().optional().default(true),
3875
- variantSelectorDisplayMode: z52.enum(["separate", "single"]).optional().default("separate")
3876
- }),
3877
- productType: z52.union([z52.enum(["one-time", "subscription", "both"]), z52.literal("").transform(() => "one-time")]).default("one-time"),
3878
- productTypeSelector: z52.enum(["dropdown", "radio"]).optional().default("radio"),
3879
- quantityInputs: z52.object({
3880
- defaultQuantity: z52.union([z52.number(), z52.null().transform(() => 1)]).default(1),
3881
- enabled: z52.boolean().default(true),
3882
- maxValue: z52.union([z52.number(), z52.null().transform(() => 15)]).default(15),
3883
- minValue: z52.union([z52.number().min(0), z52.unknown().transform(() => 0)]).default(1)
3884
- }),
3885
- shipping: z52.object({
3886
- amount: strictNumber.default(10),
3887
- /** This isn't configurable in the admin-nextjs editor */
3888
- enabled: z52.boolean().default(true),
3889
- title: z52.string().optional().default("Shipping Fees"),
3890
- type: z52.enum(["free", "fixed_amount"]).default("free")
3891
- }),
3892
- styles: z52.object({
3893
- starColor: z52.string().optional().default("#fadb14"),
3894
- starSize: z52.union([z52.enum(["small", "medium", "large"]), z52.unknown().transform(() => "large")]).optional().default("large"),
3895
- starStrokeColor: z52.string().optional().default("#fadb14"),
3896
- strokeWidth: z52.string().optional().default("1")
3897
- }).optional(),
3898
- subImages: z52.number().nullish().default(8),
3899
- subscription: z52.object({
3900
- discount: z52.object({
3901
- amount: strictNumber.default(30),
3902
- shouldShowSavingText: z52.boolean().optional().default(true),
3903
- type: z52.enum(["none", "fixed_amount", "percentage"]).default("none")
3904
- }),
3905
- shipping: z52.object({
3906
- amount: strictNumber.default(1),
3907
- /** This isn't configurable in the admin-nextjs editor */
3908
- enabled: z52.boolean().default(true),
3909
- /** This isn't configurable in the admin-nextjs editor */
3910
- recurringAmount: strictNumber.default(2),
3911
- shippingTitle: z52.string().default("Shipping Fees"),
3912
- type: z52.enum(["free", "fixed_amount"]).default("free")
3913
- })
3914
- }).optional().default({
3915
- discount: {
3916
- amount: 30,
3917
- shouldShowSavingText: true,
3918
- type: "none"
3919
- },
3920
- shipping: {
3921
- amount: 1,
3922
- /** This isn't configurable in the admin-nextjs editor */
3923
- enabled: true,
3924
- /** This isn't configurable in the admin-nextjs editor */
3925
- recurringAmount: 2,
3926
- shippingTitle: "Shipping Fees",
3927
- type: "free"
3928
- }
3929
- }),
3930
- subscriptionIsDefault: z52.boolean().optional(),
3931
- /** This isn't configurable in the admin-nextjs editor */
3932
- template: z52.string().optional().default(""),
3933
- type: z52.literal("shopify_post_purchase_extension").default("shopify_post_purchase_extension"),
3934
- upgradeToSubscription: z52.object({
3935
- acceptButtonText: z52.string().optional().default("Upgrade"),
3936
- allow: z52.boolean().optional().default(false),
3937
- emailRefundNotice: z52.boolean().optional().default(false),
3938
- errorBannerText: z52.string().optional().default("This subscription cannot be added - limit one per order")
3939
- }).optional().default(() => ({
3940
- acceptButtonText: "Upgrade",
3941
- allow: false,
3942
- emailRefundNotice: false,
3943
- errorBannerText: "This subscription cannot be added - limit one per order"
3944
- }))
4124
+ import { z as z60 } from "zod";
4125
+ var PostPurchaseWidgetLinkedFlow = z60.object({
4126
+ id: z60.number(),
4127
+ name: z60.string()
3945
4128
  });
3946
-
3947
- // src/schema/widgets/post-purchase-offer/postPurchaseWidget.ts
3948
- var PostPurchaseWidgetLinkedFlow = z53.object({
3949
- id: z53.number(),
3950
- name: z53.string()
3951
- });
3952
- var PostPurchaseWidget = z53.object({
3953
- classification: z53.literal("post_purchase_offer_page").default("post_purchase_offer_page"),
3954
- createdAtTime: z53.iso.datetime({ offset: true }).optional(),
3955
- customEndpointName: z53.string().nullish(),
3956
- id: z53.number().default(0),
3957
- lastViewed: z53.iso.datetime({ offset: true }).nullish(),
3958
- linkedCustomEndpointId: z53.number().nullish(),
3959
- linkedFlows: z53.array(PostPurchaseWidgetLinkedFlow).optional(),
3960
- name: z53.string().default(""),
3961
- owner: z53.number().nullish(),
4129
+ var PostPurchaseWidget = z60.object({
4130
+ classification: z60.literal("post_purchase_offer_page").default("post_purchase_offer_page"),
4131
+ createdAtTime: z60.iso.datetime({ offset: true }).optional(),
4132
+ customEndpointName: z60.string().nullish(),
4133
+ id: z60.number().default(0),
4134
+ lastViewed: z60.iso.datetime({ offset: true }).nullish(),
4135
+ linkedCustomEndpointId: z60.number().nullish(),
4136
+ linkedFlows: z60.array(PostPurchaseWidgetLinkedFlow).optional(),
4137
+ name: z60.string().default(""),
4138
+ owner: z60.number().nullish(),
3962
4139
  settings: PostPurchaseSettings
3963
4140
  });
3964
4141
 
3965
4142
  // src/schema/widgets/post-purchase-offer/postPurchaseOffer.ts
3966
- var PostPurchaseOffer = z54.discriminatedUnion("successful", [
3967
- z54.strictObject({
3968
- errors: z54.array(z54.object({ message: z54.string() })),
3969
- message: z54.string(),
3970
- successful: z54.literal(false)
4143
+ var PostPurchaseOffer = z61.discriminatedUnion("successful", [
4144
+ z61.strictObject({
4145
+ errors: z61.array(z61.object({ message: z61.string() })),
4146
+ message: z61.string(),
4147
+ successful: z61.literal(false)
3971
4148
  }),
3972
- z54.strictObject({
3973
- successful: z54.literal(true),
4149
+ z61.strictObject({
4150
+ successful: z61.literal(true),
3974
4151
  widget: PostPurchaseWidget
3975
4152
  })
3976
4153
  ]);
@@ -4277,7 +4454,7 @@ var OFFER_TEMPLATE_SEED = {
4277
4454
  marks: [
4278
4455
  {
4279
4456
  attrs: {
4280
- color: "accent",
4457
+ color: "base",
4281
4458
  fontSize: "medium"
4282
4459
  },
4283
4460
  type: "textStyle"
@@ -4491,9 +4668,13 @@ var buildPriceContent = () => ({
4491
4668
  content: [
4492
4669
  {
4493
4670
  content: [
4494
- /** Legacy renders the price in the checkout's brand color (`<Text appearance="accent">`). */
4671
+ /**
4672
+ * Regular text color, not legacy's `<Text appearance="accent">`: the checkout's web components
4673
+ * can't render app text in the accent color, and `accent`'s nearest tint shows default blue on
4674
+ * most stores (REB-24049).
4675
+ */
4495
4676
  {
4496
- marks: [{ attrs: { color: "accent", fontSize: "base" }, type: "textStyle" }],
4677
+ marks: [{ attrs: { color: "base", fontSize: "base" }, type: "textStyle" }],
4497
4678
  text: "{{variantPrice}}",
4498
4679
  type: "text"
4499
4680
  },
@@ -4685,7 +4866,7 @@ var buildQuantity = (settings) => {
4685
4866
  };
4686
4867
  var buildSubscriptionButton = (settings) => {
4687
4868
  if (settings.productType !== "both" && settings.productType !== "subscription") return [];
4688
- const language = settings.language;
4869
+ const language2 = settings.language;
4689
4870
  const slot = (buttonField, override) => ({
4690
4871
  buttonField,
4691
4872
  content: localizedContent(SWITCH_LABELS[buttonField], override, SWITCH_LABEL_TOKENS),
@@ -4699,9 +4880,9 @@ var buildSubscriptionButton = (settings) => {
4699
4880
  ...settings.productType === "subscription" && { disableDowngrade: true },
4700
4881
  sections: [
4701
4882
  slot("subscriptionOption", void 0),
4702
- slot("switchToOneTimePurchase", language?.cartSwitchToOnetime),
4703
- slot("switchToSubscriptionNoDiscount", language?.upgradeToSubscription),
4704
- slot("switchToSubscriptionWithDiscount", language?.upgradeToSubscription)
4883
+ slot("switchToOneTimePurchase", language2?.cartSwitchToOnetime),
4884
+ slot("switchToSubscriptionNoDiscount", language2?.upgradeToSubscription),
4885
+ slot("switchToSubscriptionWithDiscount", language2?.upgradeToSubscription)
4705
4886
  ],
4706
4887
  sectionType: "button"
4707
4888
  }
@@ -4814,9 +4995,9 @@ var buildCarouselNav = () => ({
4814
4995
  sectionType: "layout"
4815
4996
  });
4816
4997
  var HEADER_FIELDS = ["superTitle", "title", "description"];
4817
- var sanitizedHeader = (language) => Object.fromEntries(
4998
+ var sanitizedHeader = (language2) => Object.fromEntries(
4818
4999
  HEADER_FIELDS.flatMap((field) => {
4819
- const value = language?.[field];
5000
+ const value = language2?.[field];
4820
5001
  const sanitized = value ? stripContentBlockHtml(normalizeTokens(value)) : "";
4821
5002
  return sanitized ? [[field, sanitized]] : [];
4822
5003
  })
@@ -4913,7 +5094,7 @@ var coerceIntegrations = (integrations) => Object.fromEntries(
4913
5094
  return [key, value];
4914
5095
  })
4915
5096
  );
4916
- var buildBanner = (language) => language?.successBannerEnabled ? [
5097
+ var buildBanner = (language2) => language2?.successBannerEnabled ? [
4917
5098
  {
4918
5099
  /**
4919
5100
  * The banner-level tag is the extraction/routing key on BOTH renderers (React CAB's
@@ -4926,7 +5107,7 @@ var buildBanner = (language) => language?.successBannerEnabled ? [
4926
5107
  dismissible: true,
4927
5108
  sections: [
4928
5109
  {
4929
- content: bannerMessageContent(language.successBannerMessageRte),
5110
+ content: bannerMessageContent(language2.successBannerMessageRte),
4930
5111
  sectionType: "text"
4931
5112
  },
4932
5113
  {
@@ -5154,10 +5335,19 @@ export {
5154
5335
  POST_PURCHASE_SKIP_LIMIT,
5155
5336
  PayButtonBlock,
5156
5337
  PopoverPosition,
5338
+ PostPurchaseAmount,
5157
5339
  PostPurchaseAppIdSchema,
5158
5340
  PostPurchaseBlock,
5341
+ PostPurchaseExcludedProductIds,
5159
5342
  PostPurchaseOffer,
5343
+ PostPurchaseOrderAttributes,
5160
5344
  PostPurchaseOrderIdSchema,
5345
+ PostPurchasePrimaryImageSource,
5346
+ PostPurchaseProductDisplay,
5347
+ PostPurchaseProductGallery,
5348
+ PostPurchaseProductId,
5349
+ PostPurchaseProductSettings,
5350
+ PostPurchaseProductSource,
5161
5351
  PostPurchaseSettings,
5162
5352
  PostPurchaseShadowReportFields,
5163
5353
  PostPurchaseShadowReportSchema,
@@ -5165,6 +5355,13 @@ export {
5165
5355
  PostPurchaseSkipReasonSchema,
5166
5356
  PostPurchaseSkipTraceSchema,
5167
5357
  PostPurchaseTimestampSchema,
5358
+ PostPurchaseVariantCatalog,
5359
+ PostPurchaseVariantDefaultProduct,
5360
+ PostPurchaseVariantDefaultSettings,
5361
+ PostPurchaseVariantId,
5362
+ PostPurchaseVariantOption,
5363
+ PostPurchaseVariantSelector,
5364
+ PostPurchaseVariantValues,
5168
5365
  PostPurchaseWidget,
5169
5366
  PostPurchaseWidgetLinkedFlow,
5170
5367
  Product,