@wix/himalaya-cli 0.1496.0 → 0.1498.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 (138) hide show
  1. package/dist/authoring-runtime/node_modules/@wix/himalaya/dist/_types/core/sdk/iap/src/attendance-classifier.d.ts +37 -0
  2. package/dist/authoring-runtime/node_modules/@wix/himalaya/dist/_types/core/sdk/iap/src/catalog-pricing-contract.d.ts +1 -1
  3. package/dist/authoring-runtime/node_modules/@wix/himalaya/dist/_types/core/sdk/iap/src/index.d.ts +2 -1
  4. package/dist/authoring-runtime/node_modules/@wix/himalaya/dist/_types/core/sdk/iap/src/wix-payments-contract.d.ts +11 -3
  5. package/dist/authoring-runtime/node_modules/@wix/himalaya/dist/_types/stdlib/flows/iap-checkout/src/apple-iap-contract.d.ts +27 -3
  6. package/dist/authoring-runtime/node_modules/@wix/himalaya/dist/_types/stdlib/flows/iap-checkout/src/commerce-contract.d.ts +1 -0
  7. package/dist/authoring-runtime/node_modules/@wix/himalaya/dist/_types/stdlib/flows/iap-checkout/src/iap-verticals/attendance.d.ts +10 -0
  8. package/dist/authoring-runtime/node_modules/@wix/himalaya/dist/_types/stdlib/flows/iap-checkout/src/iap-verticals/index.d.ts +1 -0
  9. package/dist/authoring-runtime/node_modules/@wix/himalaya/dist/_types/stdlib/flows/iap-checkout/src/index.d.ts +1 -1
  10. package/dist/authoring-runtime/node_modules/@wix/himalaya/dist/_types/stdlib/wix-sdk/events/src/index.d.ts +33 -2
  11. package/dist/authoring-runtime/node_modules/@wix/himalaya/dist/iap-checkout.mjs +346 -26
  12. package/dist/authoring-runtime/node_modules/@wix/himalaya/dist/iap.mjs +132 -3
  13. package/dist/authoring-runtime/node_modules/@wix/himalaya/dist/screens.mjs +366 -48
  14. package/dist/authoring-runtime/node_modules/@wix/himalaya/dist/wix-events.mjs +5 -0
  15. package/dist/cli.mjs +817 -666
  16. package/guides/iap-products.md +7 -1
  17. package/package.json +2 -2
  18. package/templates/beauty-salon/dev/index.ts +394 -0
  19. package/templates/beauty-salon/tier5-src/_shared/iap-attendance-form.ts +106 -0
  20. package/templates/beauty-salon/tier5-src/_shared/iap-attendance-purchase.ts +211 -0
  21. package/templates/beauty-salon/tier5-src/_shared/iap-attendance.ts +38 -0
  22. package/templates/beauty-salon/tier5-src/himi-booking-time/index.ts +52 -7
  23. package/templates/beauty-salon-owner/dev/index.ts +571 -0
  24. package/templates/beauty-salon-owner/himalaya.content.json +6 -0
  25. package/templates/beauty-salon-owner/tier5-src/_shared/owner-today-rollup.ts +307 -0
  26. package/templates/beauty-salon-owner/tier5-src/_shared/owner-widget-reads.ts +23 -0
  27. package/templates/beauty-salon-owner/tier5-src/himi-owner-lite-today/index.ts +8 -20
  28. package/templates/beauty-salon-owner/tier5-src/himi-owner-lite-today-rollup/index.ts +121 -0
  29. package/templates/branded-lite/dev/index.ts +1429 -278
  30. package/templates/branded-lite/tier5-src/_shared/business-chat-presenter.ts +46 -8
  31. package/templates/branded-lite/tier5-src/_shared/iap-attendance-form.ts +106 -0
  32. package/templates/branded-lite/tier5-src/_shared/iap-attendance-purchase.ts +211 -0
  33. package/templates/branded-lite/tier5-src/_shared/iap-attendance.ts +38 -0
  34. package/templates/branded-lite/tier5-src/business-chat/index.ts +3 -2
  35. package/templates/branded-lite/tier5-src/himi-booking-time/index.ts +52 -7
  36. package/templates/branded-lite/tier5-src/himi-events-detail/index.ts +112 -21
  37. package/templates/community-club/dev/index.ts +397 -2
  38. package/templates/community-club/tier5-src/_shared/iap-attendance-form.ts +106 -0
  39. package/templates/community-club/tier5-src/_shared/iap-attendance-purchase.ts +211 -0
  40. package/templates/community-club/tier5-src/_shared/iap-attendance.ts +38 -0
  41. package/templates/community-club/tier5-src/himi-events-detail/index.ts +112 -21
  42. package/templates/community-club-owner/dev/index.ts +571 -0
  43. package/templates/community-club-owner/himalaya.content.json +6 -0
  44. package/templates/community-club-owner/tier5-src/_shared/owner-today-rollup.ts +307 -0
  45. package/templates/community-club-owner/tier5-src/_shared/owner-widget-reads.ts +23 -0
  46. package/templates/community-club-owner/tier5-src/himi-owner-lite-today/index.ts +8 -20
  47. package/templates/community-club-owner/tier5-src/himi-owner-lite-today-rollup/index.ts +121 -0
  48. package/templates/events-meetups/dev/index.ts +397 -2
  49. package/templates/events-meetups/tier5-src/_shared/iap-attendance-form.ts +106 -0
  50. package/templates/events-meetups/tier5-src/_shared/iap-attendance-purchase.ts +211 -0
  51. package/templates/events-meetups/tier5-src/_shared/iap-attendance.ts +38 -0
  52. package/templates/events-meetups/tier5-src/himi-events-detail/index.ts +112 -21
  53. package/templates/events-meetups-owner/dev/index.ts +571 -0
  54. package/templates/events-meetups-owner/himalaya.content.json +6 -0
  55. package/templates/events-meetups-owner/tier5-src/_shared/owner-today-rollup.ts +307 -0
  56. package/templates/events-meetups-owner/tier5-src/_shared/owner-widget-reads.ts +23 -0
  57. package/templates/events-meetups-owner/tier5-src/himi-owner-lite-today/index.ts +8 -20
  58. package/templates/events-meetups-owner/tier5-src/himi-owner-lite-today-rollup/index.ts +121 -0
  59. package/templates/gym-fitness/dev/index.ts +828 -39
  60. package/templates/gym-fitness/tier5-src/_shared/iap-attendance-form.ts +106 -0
  61. package/templates/gym-fitness/tier5-src/_shared/iap-attendance-purchase.ts +211 -0
  62. package/templates/gym-fitness/tier5-src/_shared/iap-attendance.ts +38 -0
  63. package/templates/gym-fitness/tier5-src/himi-booking-time/index.ts +52 -7
  64. package/templates/gym-fitness/tier5-src/himi-events-detail/index.ts +112 -21
  65. package/templates/gym-fitness-owner/dev/index.ts +571 -0
  66. package/templates/gym-fitness-owner/himalaya.content.json +6 -0
  67. package/templates/gym-fitness-owner/tier5-src/_shared/owner-today-rollup.ts +307 -0
  68. package/templates/gym-fitness-owner/tier5-src/_shared/owner-widget-reads.ts +23 -0
  69. package/templates/gym-fitness-owner/tier5-src/himi-owner-lite-today/index.ts +8 -20
  70. package/templates/gym-fitness-owner/tier5-src/himi-owner-lite-today-rollup/index.ts +121 -0
  71. package/templates/nonprofit-cause/dev/index.ts +397 -2
  72. package/templates/nonprofit-cause/tier5-src/_shared/iap-attendance-form.ts +106 -0
  73. package/templates/nonprofit-cause/tier5-src/_shared/iap-attendance-purchase.ts +211 -0
  74. package/templates/nonprofit-cause/tier5-src/_shared/iap-attendance.ts +38 -0
  75. package/templates/nonprofit-cause/tier5-src/himi-events-detail/index.ts +112 -21
  76. package/templates/nonprofit-cause-owner/dev/index.ts +571 -0
  77. package/templates/nonprofit-cause-owner/himalaya.content.json +6 -0
  78. package/templates/nonprofit-cause-owner/tier5-src/_shared/owner-today-rollup.ts +307 -0
  79. package/templates/nonprofit-cause-owner/tier5-src/_shared/owner-widget-reads.ts +23 -0
  80. package/templates/nonprofit-cause-owner/tier5-src/himi-owner-lite-today/index.ts +8 -20
  81. package/templates/nonprofit-cause-owner/tier5-src/himi-owner-lite-today-rollup/index.ts +121 -0
  82. package/templates/owner-lite/dev/index.ts +571 -0
  83. package/templates/owner-lite/himalaya.content.json +6 -0
  84. package/templates/owner-lite/tier5-src/_shared/owner-today-rollup.ts +307 -0
  85. package/templates/owner-lite/tier5-src/_shared/owner-widget-reads.ts +23 -0
  86. package/templates/owner-lite/tier5-src/himi-owner-lite-today/index.ts +8 -20
  87. package/templates/owner-lite/tier5-src/himi-owner-lite-today-rollup/index.ts +121 -0
  88. package/templates/podcast-creator/dev/index.ts +397 -2
  89. package/templates/podcast-creator/tier5-src/_shared/iap-attendance-form.ts +106 -0
  90. package/templates/podcast-creator/tier5-src/_shared/iap-attendance-purchase.ts +211 -0
  91. package/templates/podcast-creator/tier5-src/_shared/iap-attendance.ts +38 -0
  92. package/templates/podcast-creator/tier5-src/himi-events-detail/index.ts +112 -21
  93. package/templates/podcast-creator-owner/dev/index.ts +571 -0
  94. package/templates/podcast-creator-owner/himalaya.content.json +6 -0
  95. package/templates/podcast-creator-owner/tier5-src/_shared/owner-today-rollup.ts +307 -0
  96. package/templates/podcast-creator-owner/tier5-src/_shared/owner-widget-reads.ts +23 -0
  97. package/templates/podcast-creator-owner/tier5-src/himi-owner-lite-today/index.ts +8 -20
  98. package/templates/podcast-creator-owner/tier5-src/himi-owner-lite-today-rollup/index.ts +121 -0
  99. package/templates/portfolio-creative/dev/index.ts +397 -2
  100. package/templates/portfolio-creative/tier5-src/_shared/iap-attendance-form.ts +106 -0
  101. package/templates/portfolio-creative/tier5-src/_shared/iap-attendance-purchase.ts +211 -0
  102. package/templates/portfolio-creative/tier5-src/_shared/iap-attendance.ts +38 -0
  103. package/templates/portfolio-creative/tier5-src/himi-events-detail/index.ts +112 -21
  104. package/templates/portfolio-creative-owner/dev/index.ts +571 -0
  105. package/templates/portfolio-creative-owner/himalaya.content.json +6 -0
  106. package/templates/portfolio-creative-owner/tier5-src/_shared/owner-today-rollup.ts +307 -0
  107. package/templates/portfolio-creative-owner/tier5-src/_shared/owner-widget-reads.ts +23 -0
  108. package/templates/portfolio-creative-owner/tier5-src/himi-owner-lite-today/index.ts +8 -20
  109. package/templates/portfolio-creative-owner/tier5-src/himi-owner-lite-today-rollup/index.ts +121 -0
  110. package/templates/restaurant/dev/index.ts +397 -2
  111. package/templates/restaurant/tier5-src/_shared/iap-attendance-form.ts +106 -0
  112. package/templates/restaurant/tier5-src/_shared/iap-attendance-purchase.ts +211 -0
  113. package/templates/restaurant/tier5-src/_shared/iap-attendance.ts +38 -0
  114. package/templates/restaurant/tier5-src/himi-events-detail/index.ts +112 -21
  115. package/templates/restaurant-owner/dev/index.ts +571 -0
  116. package/templates/restaurant-owner/himalaya.content.json +6 -0
  117. package/templates/restaurant-owner/tier5-src/_shared/owner-today-rollup.ts +307 -0
  118. package/templates/restaurant-owner/tier5-src/_shared/owner-widget-reads.ts +23 -0
  119. package/templates/restaurant-owner/tier5-src/himi-owner-lite-today/index.ts +8 -20
  120. package/templates/restaurant-owner/tier5-src/himi-owner-lite-today-rollup/index.ts +121 -0
  121. package/templates/retail-store-owner/dev/index.ts +571 -0
  122. package/templates/retail-store-owner/himalaya.content.json +6 -0
  123. package/templates/retail-store-owner/tier5-src/_shared/owner-today-rollup.ts +307 -0
  124. package/templates/retail-store-owner/tier5-src/_shared/owner-widget-reads.ts +23 -0
  125. package/templates/retail-store-owner/tier5-src/himi-owner-lite-today/index.ts +8 -20
  126. package/templates/retail-store-owner/tier5-src/himi-owner-lite-today-rollup/index.ts +121 -0
  127. package/templates/yoga-studio/dev/index.ts +828 -39
  128. package/templates/yoga-studio/tier5-src/_shared/iap-attendance-form.ts +106 -0
  129. package/templates/yoga-studio/tier5-src/_shared/iap-attendance-purchase.ts +211 -0
  130. package/templates/yoga-studio/tier5-src/_shared/iap-attendance.ts +38 -0
  131. package/templates/yoga-studio/tier5-src/himi-booking-time/index.ts +52 -7
  132. package/templates/yoga-studio/tier5-src/himi-events-detail/index.ts +112 -21
  133. package/templates/yoga-studio-owner/dev/index.ts +571 -0
  134. package/templates/yoga-studio-owner/himalaya.content.json +6 -0
  135. package/templates/yoga-studio-owner/tier5-src/_shared/owner-today-rollup.ts +307 -0
  136. package/templates/yoga-studio-owner/tier5-src/_shared/owner-widget-reads.ts +23 -0
  137. package/templates/yoga-studio-owner/tier5-src/himi-owner-lite-today/index.ts +8 -20
  138. package/templates/yoga-studio-owner/tier5-src/himi-owner-lite-today-rollup/index.ts +121 -0
@@ -135,9 +135,9 @@ function createPurchaseCoordinator(deps) {
135
135
  if (session.kind !== "member") return requireSignIn();
136
136
  if (listing === "listed") clearReconcileProblem();
137
137
  const now = deps.clock.now();
138
- const eligible = itemsWhere((item) => isAwaitingDelivery(item) && (item.state.nextAttemptAt === null || item.state.nextAttemptAt <= now));
139
- eligible.forEach(restartAttemptBudget);
140
- await settleDelivery(session, await deliver(session, eligible));
138
+ const eligible2 = itemsWhere((item) => isAwaitingDelivery(item) && (item.state.nextAttemptAt === null || item.state.nextAttemptAt <= now));
139
+ eligible2.forEach(restartAttemptBudget);
140
+ await settleDelivery(session, await deliver(session, eligible2));
141
141
  }
142
142
  async function settleDelivery(session, delivered) {
143
143
  applyDelivered(delivered);
@@ -667,7 +667,8 @@ function applePrice(mapping, products) {
667
667
  const matches = products.filter((value) => isObject2(value) && value.id === mapping.productId);
668
668
  const product = matches[0];
669
669
  if (matches.length !== 1 || !nonempty(product?.displayPrice)) return unavailable(mapping.reference, "priceUnavailable");
670
- if (product?.type !== "nonConsumable") return unavailable(mapping.reference, "unsupportedProductType");
670
+ const attendance = mapping.reference.kind === "bookingsService" || mapping.reference.kind === "eventsTicket";
671
+ if (product?.type !== (attendance ? "consumable" : "nonConsumable")) return unavailable(mapping.reference, "unsupportedProductType");
671
672
  return {
672
673
  reference: mapping.reference,
673
674
  status: "ready",
@@ -686,6 +687,9 @@ var sameReference = (value, reference) => isObject2(value) && value.kind === ref
686
687
 
687
688
  // ../../core/sdk/iap/src/wix-payments-contract.ts
688
689
  var HIMALAYA_SERVE_IAP_ROUTE = { prefix: "/himalaya-serve/v1/iap" };
690
+ var BOOKINGS_APPLE_SALES_ENABLED = false;
691
+ var EVENTS_APPLE_SALES_ENABLED = false;
692
+ var ATTENDANCE_SALE_RULE = { appProductId: (id) => id, productType: "CONSUMABLE" };
689
693
  var STORES_ITEM_PAYMENT_ENABLED = false;
690
694
  var STORES_APPLE_SALES_ENABLED = true;
691
695
  var STORES_PRODUCT_SALE_RULE = { appProductId: (id) => id, productType: "NON_CONSUMABLE" };
@@ -696,10 +700,17 @@ function appleSaleRules(options = {}) {
696
700
  return {
697
701
  onlineProgram: ONLINE_PROGRAM_SALE_RULE,
698
702
  ...(options.storesAppleSalesEnabled ?? STORES_APPLE_SALES_ENABLED) || (options.storesItemPaymentEnabled ?? STORES_ITEM_PAYMENT_ENABLED) ? { storesProduct: STORES_PRODUCT_SALE_RULE } : {},
699
- ...options.pricingPlanAppleSalesEnabled ?? PRICING_PLAN_APPLE_SALES_ENABLED ? { pricingPlan: PRICING_PLAN_SALE_RULE } : {}
703
+ ...options.pricingPlanAppleSalesEnabled ?? PRICING_PLAN_APPLE_SALES_ENABLED ? { pricingPlan: PRICING_PLAN_SALE_RULE } : {},
704
+ ...options.bookingsAppleSalesEnabled ?? BOOKINGS_APPLE_SALES_ENABLED ? { bookingsService: ATTENDANCE_SALE_RULE } : {},
705
+ ...options.eventsAppleSalesEnabled ?? EVENTS_APPLE_SALES_ENABLED ? { eventsTicket: ATTENDANCE_SALE_RULE } : {}
700
706
  };
701
707
  }
702
708
  var APPLE_SALE_RULES = appleSaleRules();
709
+ var APPLE_PROVISIONING_RULES = {
710
+ ...APPLE_SALE_RULES,
711
+ bookingsService: ATTENDANCE_SALE_RULE,
712
+ eventsTicket: ATTENDANCE_SALE_RULE
713
+ };
703
714
 
704
715
  // ../../core/sdk/iap/src/mapping-source.ts
705
716
  function iapMappingSource() {
@@ -1338,6 +1349,109 @@ var COMPLETE_PAYMENT_CODES = [
1338
1349
  ];
1339
1350
  var GET_PAYMENT_CODES = ["NOT_FOUND"];
1340
1351
 
1352
+ // ../../core/sdk/iap/src/attendance-classifier.ts
1353
+ function classifyForApple(item, currency) {
1354
+ if (item.hidden !== false || item.attendance === "hybrid") return "decide";
1355
+ if (item.kind === "bookingsService") return bookingRoute(item, currency);
1356
+ return ticketRoute(item, currency);
1357
+ }
1358
+ function bookingRoute(item, currency) {
1359
+ if (item.onlineBooking !== true) return "decide";
1360
+ if (item.conferencing === false && item.locations?.length && item.locations.every((type) => type === "BUSINESS" || type === "CUSTOMER" || type === "CUSTOM")) {
1361
+ return item.attendance === "online" ? "decide" : "wixPayments";
1362
+ }
1363
+ if (item.conferencing !== true || item.attendance === "physical") return "decide";
1364
+ if (item.attendance !== "online" && (!item.locations || item.locations.length > 0)) return "decide";
1365
+ if (item.type === "APPOINTMENT") {
1366
+ return item.capacity === 1 && item.maxParticipantsPerBooking === 1 ? "wixPayments" : "decide";
1367
+ }
1368
+ if (item.type !== "CLASS" && item.type !== "COURSE" || !item.capacity || item.capacity <= 1) return "decide";
1369
+ if (item.priceType === "NO_FEE" || zeroPrice(item.amount)) return "wixPayments";
1370
+ if (item.onlinePayment !== true || item.deposit !== false || item.priceType !== "FIXED") return "decide";
1371
+ return fixedPriceRoute(item, currency);
1372
+ }
1373
+ function ticketRoute(item, currency) {
1374
+ if (item.location === "VENUE") return item.attendance === "online" ? "decide" : "wixPayments";
1375
+ if (item.location !== "ONLINE" || item.attendance === "physical" || item.registration !== "TICKETING") return "decide";
1376
+ if (item.eventStatus !== "UPCOMING" && item.eventStatus !== "STARTED") return "decide";
1377
+ if (item.saleStatus !== "SALE_STARTED") return "decide";
1378
+ if (zeroPrice(item.amount)) return "wixPayments";
1379
+ return item.priceType === "STANDARD" ? fixedPriceRoute(item, currency) : "decide";
1380
+ }
1381
+ function fixedPriceRoute(item, currency) {
1382
+ const amount = item.amount;
1383
+ return typeof amount === "string" && /^\d+(?:\.\d+)?$/.test(amount) && Number.isFinite(Number(amount)) && Number(amount) > 0 && /^[A-Z]{3}$/.test(currency) && item.currency === currency ? "appleIap" : "decide";
1384
+ }
1385
+ function bookingAttendanceOf(raw) {
1386
+ const s = object(raw);
1387
+ const payment = object(s.payment);
1388
+ const fixed = object(payment.fixed);
1389
+ const price = object(fixed.price);
1390
+ const options = object(payment.options);
1391
+ const policy = object(object(s.bookingPolicy).participantsPolicy);
1392
+ return {
1393
+ kind: "bookingsService",
1394
+ type: text(s.type),
1395
+ capacity: numeric(s.defaultCapacity),
1396
+ maxParticipantsPerBooking: policy.enabled === true ? numeric(policy.maxParticipantsPerBooking) : void 0,
1397
+ hidden: boolean(s.hidden),
1398
+ conferencing: boolean(object(s.conferencing).enabled),
1399
+ locations: Array.isArray(s.locations) ? s.locations.map((l) => text(object(l).type) ?? "UNKNOWN") : void 0,
1400
+ onlineBooking: boolean(object(s.onlineBooking).enabled),
1401
+ onlinePayment: boolean(options.online),
1402
+ deposit: options.deposit === true || fixed.deposit !== void 0,
1403
+ priceType: text(payment.rateType),
1404
+ amount: text(price.value),
1405
+ currency: text(price.currency)
1406
+ };
1407
+ }
1408
+ function ticketAttendanceOf(event, definition) {
1409
+ const e = object(event);
1410
+ const t = object(definition);
1411
+ const pricing = object(t.pricingMethod);
1412
+ const price = object(pricing.fixedPrice);
1413
+ const registration = object(e.registration);
1414
+ const type = text(registration.type) ?? text(registration.initialType) ?? text(e.eventType);
1415
+ const status = text(e.status) ?? text(e.eventStatus);
1416
+ return {
1417
+ kind: "eventsTicket",
1418
+ location: text(object(e.location).type),
1419
+ registration: type === "TICKETS" || type === "RSVP_AND_TICKETS" ? "TICKETING" : type,
1420
+ eventStatus: status === "SCHEDULED" ? "UPCOMING" : status,
1421
+ saleStatus: text(t.saleStatus),
1422
+ hidden: boolean(t.hidden),
1423
+ priceType: text(pricing.pricingType),
1424
+ amount: text(price.value),
1425
+ currency: text(price.currency)
1426
+ };
1427
+ }
1428
+ function availableTicketAttendanceOf(event, ticket) {
1429
+ const e = object(event);
1430
+ const t = object(ticket);
1431
+ const pricing = object(t.pricing);
1432
+ const fixed = object(pricing.fixedPrice);
1433
+ const price = object(t.price);
1434
+ const visible = Array.isArray(t.state) && t.state.length === 0 && object(t.dashboard).hidden !== true && typeof t.id === "string" && t.id.length > 0 && typeof e.id === "string" && e.id.length > 0 && t.eventId === e.id;
1435
+ const fixedPrice = t.free === false && pricing.pricingType === "STANDARD" && sameTicketAmount(fixed.amount, price.amount) && fixed.currency === price.currency;
1436
+ return ticketAttendanceOf(e, {
1437
+ hidden: visible ? false : void 0,
1438
+ saleStatus: t.saleStatus,
1439
+ pricingMethod: { pricingType: fixedPrice ? "STANDARD" : void 0, fixedPrice: { value: fixed.amount, currency: fixed.currency } }
1440
+ });
1441
+ }
1442
+ function sameTicketAmount(left, right) {
1443
+ const valid = (value) => typeof value === "string" && /^\d+(?:\.\d+)?$/.test(value);
1444
+ const normalized = (value) => value.replace(/^0+(?=\d)/, "").replace(/(\.\d*?)0+$/, "$1").replace(/\.$/, "");
1445
+ return valid(left) && valid(right) && normalized(left) === normalized(right);
1446
+ }
1447
+ function object(value) {
1448
+ return value !== null && typeof value === "object" && !Array.isArray(value) ? value : {};
1449
+ }
1450
+ var text = (value) => typeof value === "string" ? value : void 0;
1451
+ var numeric = (value) => typeof value === "number" ? value : void 0;
1452
+ var boolean = (value) => typeof value === "boolean" ? value : void 0;
1453
+ var zeroPrice = (value) => typeof value === "string" && /^0+(?:\.0+)?$/.test(value);
1454
+
1341
1455
  // ../../core/sdk/iap/src/index.ts
1342
1456
  async function getProducts(productIds) {
1343
1457
  if (!productIds || productIds.length === 0) return [];
@@ -1641,11 +1755,11 @@ function partitionKey(key) {
1641
1755
  return `${PREFIX}.${key.purchasesAppId}.${key.siteId}.${memberKey(key.memberId)}`;
1642
1756
  }
1643
1757
  function memberKey(memberId) {
1644
- const text = memberId.toLowerCase();
1758
+ const text2 = memberId.toLowerCase();
1645
1759
  let h1 = 3735928559;
1646
1760
  let h2 = 1103547991;
1647
- for (let i = 0; i < text.length; i++) {
1648
- const code = text.charCodeAt(i);
1761
+ for (let i = 0; i < text2.length; i++) {
1762
+ const code = text2.charCodeAt(i);
1649
1763
  h1 = Math.imul(h1 ^ code, 2654435761);
1650
1764
  h2 = Math.imul(h2 ^ code, 1597334677);
1651
1765
  }
@@ -1684,9 +1798,9 @@ function isUUID3(value) {
1684
1798
  }
1685
1799
  var VERSION = 1;
1686
1800
  var PREFIX = "himi.iap.wix-checkout.v1";
1687
- var STAGES = /* @__PURE__ */ new Set(["startingItem", "ordered", "charged", "started", "submitted", "held", "needsSupport"]);
1801
+ var STAGES = /* @__PURE__ */ new Set(["startingItem", "openingOrder", "ordered", "charged", "started", "submitted", "fulfilled", "held", "needsSupport"]);
1688
1802
  var HOLD_MS = { held: NEEDS_SUPPORT_HOLD_MS, needsSupport: NEEDS_SUPPORT_HOLD_MS, startingItem: ITEM_START_HOLD_MS };
1689
- var EVICTABLE = /* @__PURE__ */ new Set(["ordered", "charged", "started"]);
1803
+ var EVICTABLE = /* @__PURE__ */ new Set(["fulfilled", "ordered", "charged", "started"]);
1690
1804
 
1691
1805
  // ../../stdlib/flows/iap-checkout/src/wix-bridge.ts
1692
1806
  function bindBridge(session, provider, bridge) {
@@ -1727,10 +1841,10 @@ function isLiveHost(bridge) {
1727
1841
  }
1728
1842
  function refusalOf(error) {
1729
1843
  const message = error?.message;
1730
- const text = typeof message === "string" ? message : "";
1731
- if (BRIDGE_REFUSAL2.test(text)) return { status: "notEnabled" };
1732
- if (PRINCIPAL_CHANGED2.test(text)) return SESSION_CHANGED;
1733
- const http = /^HTTP (\d{3})(?: \[([^\]]+)\])?:/.exec(text);
1844
+ const text2 = typeof message === "string" ? message : "";
1845
+ if (BRIDGE_REFUSAL2.test(text2)) return { status: "notEnabled" };
1846
+ if (PRINCIPAL_CHANGED2.test(text2)) return SESSION_CHANGED;
1847
+ const http = /^HTTP (\d{3})(?: \[([^\]]+)\])?:/.exec(text2);
1734
1848
  if (!http) return { status: "unavailable" };
1735
1849
  return httpRefusal(Number(http[1]), http[2] ?? "");
1736
1850
  }
@@ -1786,12 +1900,19 @@ function createWixOrderBackend(deps) {
1786
1900
  const stage = refAt(sale.partition, sale.catalogRef)?.stage;
1787
1901
  const failure3 = stage && BLOCKING_STAGES[stage];
1788
1902
  if (failure3) return stopWith("rejected", failure3);
1903
+ if (sale.adapter.repeatable) {
1904
+ const prefix = `${sale.item.reference.kind}:${sale.item.reference.id}#`;
1905
+ const unresolved = sale.partition.refs().find((ref) => ref.key.startsWith(prefix) && ["openingOrder", "held", "needsSupport"].includes(ref.stage));
1906
+ if (unresolved) return stopWith("rejected", unresolved.stage === "openingOrder" ? "outcomeUnknown" : "needsSupport");
1907
+ }
1789
1908
  return deps.productBusy?.(sale.appleProduct.productId) ? stopWith("rejected", "paymentInProgress") : null;
1790
1909
  }
1791
1910
  async function saleFor(session, catalogRef) {
1792
1911
  const sold = deps.itemFor(catalogRef);
1793
1912
  const adapter = sold && adapterFor(sold.item.reference.kind);
1794
1913
  if (!sold || !adapter) return stopWith("rejected", "unsupportedItem");
1914
+ if (adapter.repeatable && !sold.item.attemptId) return stopWith("rejected", "unsupportedItem");
1915
+ if (!adapter.repeatable && sold.item.attemptId) return stopWith("rejected", "unsupportedItem");
1795
1916
  const eligibility2 = adapter.eligibility(sold.item);
1796
1917
  if (!eligibility2.eligible) return stopWith("rejected", eligibility2.reason);
1797
1918
  const member = await memberOf(session);
@@ -1811,15 +1932,37 @@ function createWixOrderBackend(deps) {
1811
1932
  }
1812
1933
  async function orderFor(sale) {
1813
1934
  const existing = refAt(sale.partition, sale.catalogRef);
1814
- const attempt3 = existing?.cashierOrderId && existing.verticalRef ? await reopenOrOpen(sale, { cashierOrderId: existing.cashierOrderId, verticalRef: existing.verticalRef }) : await sale.adapter.openOrder(sale.item, sale.bridge);
1815
- return recordOrder(sale, existing, attempt3);
1935
+ let prevented;
1936
+ const beforeCreate = () => {
1937
+ if (!sale.adapter.repeatable || existing) return true;
1938
+ if (!sale.bridge.isCurrent()) {
1939
+ prevented = STALE2;
1940
+ return false;
1941
+ }
1942
+ const blocked = saleBlocked(sale);
1943
+ if (blocked) {
1944
+ prevented = blocked;
1945
+ return false;
1946
+ }
1947
+ const opening = persist(sale, { key: sale.catalogRef, kind: sale.adapter.kind, stage: "openingOrder", updatedAt: now() });
1948
+ if (isStop(opening)) {
1949
+ prevented = opening;
1950
+ return false;
1951
+ }
1952
+ return true;
1953
+ };
1954
+ const attempt3 = existing?.cashierOrderId && existing.verticalRef ? await reopenOrOpen(sale, { cashierOrderId: existing.cashierOrderId, verticalRef: existing.verticalRef }) : await sale.adapter.openOrder(sale.item, sale.bridge, beforeCreate);
1955
+ return prevented ?? recordOrder(sale, existing, attempt3);
1816
1956
  }
1817
1957
  async function reopenOrOpen(sale, order) {
1818
1958
  const reopened = await sale.adapter.reopenOrder(order, sale.bridge);
1819
1959
  const closed = reopened.status === "refused" && reopened.reason === "orderClosed";
1820
- return closed ? sale.adapter.openOrder(sale.item, sale.bridge) : reopened;
1960
+ return closed && !sale.adapter.repeatable ? sale.adapter.openOrder(sale.item, sale.bridge) : reopened;
1821
1961
  }
1822
1962
  function recordOrder(sale, existing, attempt3) {
1963
+ if (attempt3.noOrderCreated && refAt(sale.partition, sale.catalogRef)?.stage === "openingOrder" && !sale.partition.remove(sale.catalogRef)) {
1964
+ return stopWith("rejected", "storageUnavailable");
1965
+ }
1823
1966
  if (attempt3.status === "granted") return alreadyOwned(sale);
1824
1967
  if (attempt3.status === "refused") return stopWith("rejected", attempt3.reason);
1825
1968
  if (attempt3.status !== "open") return attempt3.status === "sessionChanged" ? STALE2 : retry("unavailable");
@@ -1857,6 +2000,7 @@ function createWixOrderBackend(deps) {
1857
2000
  }
1858
2001
  }
1859
2002
  async function reorder(sale) {
2003
+ if (sale.adapter.repeatable) return stopWith("rejected", "orderClosed");
1860
2004
  if (!forget(sale, sale.catalogRef)) return stopWith("rejected", "storageUnavailable");
1861
2005
  const recorded = recordOrder(sale, void 0, await sale.adapter.openOrder(sale.item, sale.bridge));
1862
2006
  return isStop(recorded) ? recorded : chargeFor(sale, recorded, { reordered: true });
@@ -1933,7 +2077,7 @@ function createWixOrderBackend(deps) {
1933
2077
  return stopWith("rejected", failure3.code === "NOT_PENDING" ? "orderClosed" : "paymentRefused");
1934
2078
  }
1935
2079
  function alreadyOwned(sale) {
1936
- forget(sale, sale.catalogRef);
2080
+ if (!sale.adapter.repeatable) forget(sale, sale.catalogRef);
1937
2081
  return stopWith("rejected", "alreadyOwned");
1938
2082
  }
1939
2083
  function persist(sale, ref) {
@@ -1983,7 +2127,9 @@ function createWixOrderBackend(deps) {
1983
2127
  return access === "granted";
1984
2128
  }
1985
2129
  function processed(proof, ref) {
1986
- proof.member.partition?.remove(ref.key);
2130
+ if (adapterFor(ref.kind)?.repeatable) {
2131
+ if (!proof.member.partition?.put({ ...ref, stage: "fulfilled", updatedAt: now() })) return RETRYABLE;
2132
+ } else proof.member.partition?.remove(ref.key);
1987
2133
  deps.report({ key: ref.key, access: "granted" });
1988
2134
  return { status: "processed", acknowledgement: proof.acknowledgement };
1989
2135
  }
@@ -2050,6 +2196,7 @@ var UNAVAILABLE = { stop: true, result: "retryable", failure: "unavailable" };
2050
2196
  var OUTCOME_UNKNOWN = { stop: true, result: "rejected", failure: "outcomeUnknown" };
2051
2197
  var BLOCKING_STAGES = {
2052
2198
  startingItem: "outcomeUnknown",
2199
+ openingOrder: "outcomeUnknown",
2053
2200
  submitted: "paymentInProgress",
2054
2201
  held: "paymentHeld",
2055
2202
  needsSupport: "needsSupport"
@@ -2308,6 +2455,12 @@ function enabledCheckout(deps) {
2308
2455
  for (const ref of tracked.partition.refs()) {
2309
2456
  if (!isCurrent(session)) return;
2310
2457
  if (ref.stage === "needsSupport") setPayment(ref.key, "needsSupport");
2458
+ if (ref.stage === "fulfilled" && !options.dueOnly) {
2459
+ const access = await accessOf3(session, ref);
2460
+ if (!isCurrent(session)) return;
2461
+ if (access === "granted") setPayment(ref.key, "granted");
2462
+ else if (access === "none") payments.delete(ref.key);
2463
+ }
2311
2464
  if (ref.stage !== "submitted" || !ref.paymentId) continue;
2312
2465
  if (!options.dueOnly) restartBudget(ref.key);
2313
2466
  if (isDue(ref.key, options.dueOnly)) await trackOne(session, tracked.partition, ref);
@@ -2362,7 +2515,10 @@ function enabledCheckout(deps) {
2362
2515
  backOff(partition, ref, access === "none");
2363
2516
  }
2364
2517
  function grant(partition, ref) {
2365
- partition.remove(ref.key);
2518
+ const repeatable = deps.adapters.some((adapter) => adapter.kind === ref.kind && adapter.repeatable);
2519
+ if (repeatable) {
2520
+ if (!partition.put({ ...ref, stage: "fulfilled", updatedAt: deps.clock.now() })) return backOff(partition, ref, false);
2521
+ } else partition.remove(ref.key);
2366
2522
  setPayment(ref.key, "granted");
2367
2523
  }
2368
2524
  function settleUnassociated(partition, ref) {
@@ -2431,7 +2587,8 @@ function isInFlight(item) {
2431
2587
  return item.access === "processing" || item.access === "confirming" || item.access === "pending" || item.access === "waitingToRetry";
2432
2588
  }
2433
2589
  function itemKey(item) {
2434
- return `${item.reference.kind}:${item.reference.id}`;
2590
+ const key = `${item.reference.kind}:${item.reference.id}`;
2591
+ return item.attemptId ? `${key}#${encodeURIComponent(item.attemptId)}` : key;
2435
2592
  }
2436
2593
  function labelOf(key) {
2437
2594
  return key.startsWith("payment:") ? "payment" : key;
@@ -2460,10 +2617,20 @@ var OVERLAY_PHASES = /* @__PURE__ */ new Set(["purchasing", "awaitingApproval",
2460
2617
  // ../../stdlib/flows/iap-checkout/src/purchase-fields.ts
2461
2618
  function iapPurchaseFields(view, state, readiness, copy) {
2462
2619
  const key = `${view.reference.kind}:${view.reference.id}`;
2620
+ const repeatable = view.reference.kind === "bookingsService" || view.reference.kind === "eventsTicket";
2463
2621
  if (view.route !== "appleIap" && !holdsSale(state, key)) return { ...action(copy, "enabled", ""), appleRoute: false };
2464
2622
  if (readiness.status !== "ready") return action(copy, "disabled", readiness.status === "checking" ? "" : copy.unavailable);
2465
- const own = state.item === key;
2466
- const payment = state.payments.find((tracked) => tracked.item === key)?.access;
2623
+ const own = sameItem(state.item, key);
2624
+ const matching = state.payments.filter((tracked) => sameItem(tracked.item, key));
2625
+ const payment = matching.find((p) => p.access === "needsSupport")?.access ?? matching.find((p) => p.access === "processing")?.access ?? matching[matching.length - 1]?.access;
2626
+ if (repeatable && payment === "needsSupport") return action(copy, "disabled", copy.support);
2627
+ if (repeatable && IN_FLIGHT.has(state.phase)) return action(copy, "busy", own ? copy.processing : "");
2628
+ if (repeatable && payment === "processing") return action(copy, "busy", copy.processing);
2629
+ if (repeatable && own && state.phase !== "accessReady" && state.phase !== "idle") {
2630
+ if (state.failure === "orderClosed") return action(copy, "disabled", copy.support);
2631
+ return outcomeAction(state, copy);
2632
+ }
2633
+ if (repeatable && (own && state.phase === "accessReady" || payment === "granted")) return action({ ...copy, buy: copy.buyAnother ?? copy.buy }, "enabled", "");
2467
2634
  if (own && state.phase === "accessReady" || payment === "granted") return { ...action(copy, "disabled", ""), accessReady: true };
2468
2635
  if (IN_FLIGHT.has(state.phase)) return action(copy, "busy", own ? copy.processing : "");
2469
2636
  if (own) return outcomeAction(state, copy);
@@ -2472,8 +2639,11 @@ function iapPurchaseFields(view, state, readiness, copy) {
2472
2639
  return action(copy, "enabled", "");
2473
2640
  }
2474
2641
  function holdsSale(state, key) {
2475
- if (state.payments.some((tracked) => tracked.item === key)) return true;
2476
- return state.item === key && (SALE_PHASES.has(state.phase) || state.purchase.phase === "awaitingApproval");
2642
+ if (state.payments.some((tracked) => sameItem(tracked.item, key))) return true;
2643
+ return sameItem(state.item, key) && (SALE_PHASES.has(state.phase) || state.purchase.phase === "awaitingApproval");
2644
+ }
2645
+ function sameItem(item, key) {
2646
+ return item === key || item?.startsWith(`${key}#`) === true;
2477
2647
  }
2478
2648
  function outcomeAction(state, copy) {
2479
2649
  if (state.purchase.phase === "awaitingApproval") return action(copy, "disabled", copy.awaitingApproval);
@@ -2494,7 +2664,7 @@ function outcomeAction(state, copy) {
2494
2664
  }
2495
2665
  function refusalAction(failure3, copy) {
2496
2666
  const [mode, note] = REFUSALS[failure3 ?? "unavailable"] ?? ["enabled", "retry"];
2497
- return action(copy, mode, note ? copy[note] : "");
2667
+ return action(copy, mode, note ? copy[note] ?? "" : "");
2498
2668
  }
2499
2669
  function action(copy, mode, note) {
2500
2670
  return { appleRoute: true, accessReady: false, buyLabel: copy.buy, buyDisabled: mode !== "enabled", buyBusy: mode === "busy", buyNote: note };
@@ -3104,11 +3274,161 @@ async function placedOrder(body, bridge) {
3104
3274
  }
3105
3275
  var PAYMENT_UNDER_WAY2 = /* @__PURE__ */ new Set(["NOT_PAID", "PENDING", "PENDING_MERCHANT", "PARTIALLY_PAID"]);
3106
3276
  var NO_ACCESS2 = /* @__PURE__ */ new Set(["FULLY_REFUNDED", "PARTIALLY_REFUNDED", "CANCELED", "DECLINED", "VOIDED"]);
3277
+
3278
+ // ../../stdlib/flows/iap-checkout/src/iap-verticals/attendance.ts
3279
+ var BOOKING = "bookingsService";
3280
+ var TICKET = "eventsTicket";
3281
+ var NOT_ENABLED = { status: "refused", reason: "notEnabled" };
3282
+ var CHANGED = { status: "refused", reason: "productChanged" };
3283
+ function attendanceOrdersWith(options) {
3284
+ const now = options.now ?? Date.now;
3285
+ return {
3286
+ bookingOrders: {
3287
+ kind: BOOKING,
3288
+ repeatable: true,
3289
+ eligibility: (item) => eligible(item, BOOKING, options.bookingsEnabled),
3290
+ openOrder: (item, bridge, beforeCreate) => options.bookingsEnabled ? openBooking(item, bridge, beforeCreate) : Promise.resolve(NOT_ENABLED),
3291
+ readAccess: bookingAccess,
3292
+ reopenOrder: (order, bridge) => reopen(order, bridge, bookingAccess)
3293
+ },
3294
+ eventTicketOrders: {
3295
+ kind: TICKET,
3296
+ repeatable: true,
3297
+ eligibility: (item) => eligible(item, TICKET, options.eventsEnabled),
3298
+ openOrder: (item, bridge, beforeCreate) => options.eventsEnabled ? openTicket(item, bridge, now, beforeCreate) : Promise.resolve(NOT_ENABLED),
3299
+ readAccess: ticketAccess,
3300
+ reopenOrder: (order, bridge) => reopen(order, bridge, ticketAccess, now)
3301
+ }
3302
+ };
3303
+ }
3304
+ var { bookingOrders, eventTicketOrders } = /* @__PURE__ */ attendanceOrdersWith({ bookingsEnabled: BOOKINGS_APPLE_SALES_ENABLED, eventsEnabled: EVENTS_APPLE_SALES_ENABLED });
3305
+ function eligible(item, kind, enabled) {
3306
+ if (!enabled) return { eligible: false, reason: "notEnabled" };
3307
+ if (!singleUnitOf(kind, item).eligible || !isNonEmpty3(item.attemptId) || !item.attendance) return UNSUPPORTED;
3308
+ const selection = kind === BOOKING ? item.attendance.booking : item.attendance.ticket;
3309
+ return selection ? { eligible: true } : UNSUPPORTED;
3310
+ }
3311
+ async function openBooking(item, bridge, beforeCreate) {
3312
+ if (!eligible(item, BOOKING, true).eligible) return notCreated(ORDER_REFUSED);
3313
+ const selected = item.attendance.booking;
3314
+ if (selected.slot.serviceId !== item.reference.id || !isNonEmpty3(selected.slot.startDate) || !isNonEmpty3(selected.slot.endDate)) return notCreated(ORDER_REFUSED);
3315
+ const read2 = await bridge.call("GET", `/bookings/v2/services/${encodeURIComponent(item.reference.id)}`);
3316
+ if (isRefusal(read2)) return notCreated(attemptRefused(read2));
3317
+ const service = bodyObject(read2, "service");
3318
+ const metadata = bookingAttendanceOf(service);
3319
+ if (classifyForApple(metadata, item.attendance.currency) !== "appleIap" || !samePrice({ amount: metadata.amount, currency: metadata.currency }, item)) return notCreated(CHANGED);
3320
+ if (isObject7(service?.onlineBooking) && service.onlineBooking.requireManualApproval === true) return notCreated({ status: "refused", reason: "approvalRequired" });
3321
+ const availability = await bridge.call("POST", "/bookings/v1/availability/query", { query: { filter: { serviceId: [item.reference.id], startDate: selected.slot.startDate, endDate: selected.slot.endDate, bookable: true } } });
3322
+ if (isRefusal(availability)) return notCreated(attemptRefused(availability));
3323
+ const entries = isObject7(availability.body) ? availability.body.availabilityEntries : void 0;
3324
+ if (!Array.isArray(entries) || !entries.some((entry) => isObject7(entry) && entry.bookable === true && matchesSlot(entry.slot, selected.slot))) return notCreated(CHANGED);
3325
+ if (beforeCreate && !beforeCreate()) return notCreated({ status: "refused", reason: "storageUnavailable" });
3326
+ const created = await bridge.call("POST", "/bookings/v2/bookings", { booking: { bookedEntity: { slot: selected.slot }, contactDetails: selected.contactDetails, totalParticipants: 1, selectedPaymentOption: "ONLINE", ...selected.formInfo ? { formInfo: selected.formInfo } : {} } });
3327
+ if (isRefusal(created)) return creationRefused(created);
3328
+ const bookingId = bodyObject(created, "booking")?.id;
3329
+ return isNonEmpty3(bookingId) ? bookingCheckout(item, bookingId, bridge) : ORDER_REFUSED;
3330
+ }
3331
+ async function bookingCheckout(item, bookingId, bridge) {
3332
+ const checkout = await bridge.call("POST", "/ecom/v1/checkouts", { lineItems: [{ quantity: 1, catalogReference: { appId: "13d21c63-b5ec-5912-8397-c3a5ddb27a97", catalogItemId: bookingId } }], channelType: "OTHER_PLATFORM" });
3333
+ if (isRefusal(checkout)) return attemptRefused(checkout);
3334
+ const entity = bodyObject(checkout, "checkout");
3335
+ const total = isObject7(entity?.priceSummary) ? entity.priceSummary.total : void 0;
3336
+ if (!isObject7(total) || !samePrice({ amount: total.amount, currency: entity?.currency }, item)) return CHANGED;
3337
+ if (!isNonEmpty3(entity?.id)) return ORDER_REFUSED;
3338
+ const placed = await bridge.call("POST", `/ecom/v1/checkouts/${encodeURIComponent(entity.id)}/create-order`, {});
3339
+ if (isRefusal(placed)) return attemptRefused(placed);
3340
+ const body = placed.body;
3341
+ if (!isObject7(body) || !isNonEmpty3(body.orderId) || !isNonEmpty3(body.paymentGatewayOrderId)) return ORDER_REFUSED;
3342
+ return { status: "open", cashierOrderId: body.paymentGatewayOrderId, verticalRef: { serviceId: item.reference.id, bookingId, orderId: body.orderId } };
3343
+ }
3344
+ async function bookingAccess(ref, bridge) {
3345
+ if (!ref.bookingId || !ref.orderId) return "unavailable";
3346
+ const order = await bridge.call("GET", `/ecom/v1/orders/${encodeURIComponent(ref.orderId)}`);
3347
+ if (isRefusal(order)) return accessRefused(order);
3348
+ const payment = bodyObject(order, "order")?.paymentStatus;
3349
+ if (payment === "FULLY_REFUNDED" || payment === "PARTIALLY_REFUNDED") return "none";
3350
+ const read2 = await bridge.call("POST", "/bookings/v2/bookings/query", { query: { filter: { id: { $eq: ref.bookingId } } } });
3351
+ if (isRefusal(read2)) return accessRefused(read2);
3352
+ const rows = isObject7(read2.body) ? read2.body.bookings : void 0;
3353
+ const booking = Array.isArray(rows) ? rows.find((b) => isObject7(b) && b.id === ref.bookingId) : void 0;
3354
+ if (!isObject7(booking)) return "unavailable";
3355
+ if (booking.status === "CANCELED" || booking.status === "CANCELLED" || booking.status === "DECLINED") return "none";
3356
+ return payment === "PAID" && booking.status === "CONFIRMED" && booking.paymentStatus === "PAID" ? "granted" : "pending";
3357
+ }
3358
+ async function openTicket(item, bridge, now, beforeCreate) {
3359
+ if (!eligible(item, TICKET, true).eligible) return notCreated(ORDER_REFUSED);
3360
+ const selected = item.attendance.ticket;
3361
+ if (!isNonEmpty3(selected.eventId)) return notCreated(ORDER_REFUSED);
3362
+ const read2 = await bridge.call("GET", `/events/v3/events/${encodeURIComponent(selected.eventId)}?fields=REGISTRATION&fields=DETAILS&fields=FORM`);
3363
+ if (isRefusal(read2)) return notCreated(attemptRefused(read2));
3364
+ const available = await bridge.call("POST", "/events/v1/checkout/available-tickets/query", { filter: { eventId: selected.eventId }, limit: 100, offset: 0 });
3365
+ if (isRefusal(available)) return notCreated(attemptRefused(available));
3366
+ const definitions = isObject7(available.body) ? available.body.definitions : void 0;
3367
+ const live = Array.isArray(definitions) ? definitions.find((t) => isObject7(t) && t.id === item.reference.id && t.saleStatus === "SALE_STARTED") : void 0;
3368
+ if (!isObject7(live) || !samePrice(live.price, item)) return notCreated(CHANGED);
3369
+ if (live.eventId !== selected.eventId || classifyForApple(availableTicketAttendanceOf(bodyObject(read2, "event"), live), item.attendance.currency) !== "appleIap") return notCreated(ORDER_REFUSED);
3370
+ if (beforeCreate && !beforeCreate()) return notCreated({ status: "refused", reason: "storageUnavailable" });
3371
+ return reserveTicket(item, bridge, now);
3372
+ }
3373
+ async function reserveTicket(item, bridge, now) {
3374
+ const selected = item.attendance.ticket;
3375
+ const held = await bridge.call("POST", "/events/v1/checkout/reservations", { eventId: selected.eventId, ticketQuantities: [{ ticketDefinitionId: item.reference.id, quantity: 1 }], ignoreLimits: false, allowHiddenTickets: false });
3376
+ if (isRefusal(held)) return creationRefused(held);
3377
+ const reservation = held.body;
3378
+ if (!isObject7(reservation) || !isNonEmpty3(reservation.id) || !future(reservation.expires, now)) return ORDER_CLOSED;
3379
+ const invoice = isObject7(reservation.invoice) ? reservation.invoice : {};
3380
+ if (!samePrice(invoice.grandTotal ?? invoice.total, item)) return CHANGED;
3381
+ const placed = await bridge.call("POST", "/events/v1/checkout", { eventId: selected.eventId, reservationId: reservation.id, buyer: selected.buyer, ...selected.guests ? { guests: selected.guests } : {}, ...selected.buyerSubmission ? { buyerSubmission: selected.buyerSubmission } : {}, ...selected.guestSubmissions ? { guestSubmissions: selected.guestSubmissions } : {}, options: { silent: false, payInPerson: false, ignoreFormValidation: false, markAsPaid: false } });
3382
+ if (isRefusal(placed)) return attemptRefused(placed);
3383
+ const order = bodyObject(placed, "order");
3384
+ if (!samePrice(order?.totalPrice, item)) return CHANGED;
3385
+ const expires = isObject7(placed.body) && placed.body.expires || reservation.expires;
3386
+ if (!future(expires, now) || !isNonEmpty3(order?.snapshotId) || !isNonEmpty3(order?.orderNumber)) return ORDER_CLOSED;
3387
+ return { status: "open", cashierOrderId: order.snapshotId, verticalRef: { eventId: selected.eventId, ticketDefinitionId: item.reference.id, reservationId: reservation.id, orderNumber: order.orderNumber, expires: String(expires) } };
3388
+ }
3389
+ async function ticketAccess(ref, bridge) {
3390
+ if (!ref.eventId || !ref.orderNumber || !ref.ticketDefinitionId) return "unavailable";
3391
+ const read2 = await bridge.call("GET", `/events/v1/events/${encodeURIComponent(ref.eventId)}/orders/${encodeURIComponent(ref.orderNumber)}?fieldset=DETAILS&fieldset=TICKETS`);
3392
+ if (isRefusal(read2)) return accessRefused(read2);
3393
+ const order = bodyObject(read2, "order");
3394
+ if (order?.status === "CANCELED" || order?.status === "CANCELLED" || order?.status === "REFUNDED") return "none";
3395
+ const issued = Array.isArray(order?.tickets) && order.tickets.some((t) => isObject7(t) && isNonEmpty3(t.ticketNumber) && t.orderStatus === "PAID" && t.ticketDefinitionId === ref.ticketDefinitionId);
3396
+ return order?.status === "PAID" && issued ? "granted" : order ? "pending" : "unavailable";
3397
+ }
3398
+ async function reopen(order, bridge, accessOf3, now) {
3399
+ const access = await accessOf3(order.verticalRef, bridge);
3400
+ if (access === "granted") return GRANTED;
3401
+ if (access === "unavailable" || access === "sessionChanged") return { status: access };
3402
+ if (access === "none" || now && !future(order.verticalRef.expires, now)) return ORDER_CLOSED;
3403
+ return { status: "open", ...order };
3404
+ }
3405
+ function samePrice(value, item) {
3406
+ return isObject7(value) && value.currency === item.attendance?.currency && decimal(value.amount) !== null && decimal(value.amount) === decimal(item.attendance?.amount);
3407
+ }
3408
+ function decimal(value) {
3409
+ if (typeof value !== "string" || !/^\d+(?:\.\d+)?$/.test(value)) return null;
3410
+ return value.replace(/^0+(?=\d)/, "").replace(/(\.\d*?)0+$/, "$1").replace(/\.$/, "");
3411
+ }
3412
+ function future(value, now) {
3413
+ return typeof value === "string" && Number.isFinite(Date.parse(value)) && Date.parse(value) > now();
3414
+ }
3415
+ function matchesSlot(value, selected) {
3416
+ return isObject7(value) && ["serviceId", "sessionId"].every((key) => value[key] === selected[key]) && ["startDate", "endDate"].every((key) => typeof value[key] === "string" && Date.parse(value[key]) === Date.parse(String(selected[key])));
3417
+ }
3418
+ function creationRefused(refusal) {
3419
+ const attempt3 = attemptRefused(refusal);
3420
+ return refusal.status === "http" && [400, 401, 403, 404, 405, 409, 410, 415, 422].includes(refusal.httpStatus) ? notCreated(attempt3) : attempt3;
3421
+ }
3422
+ function notCreated(attempt3) {
3423
+ return { ...attempt3, noOrderCreated: true };
3424
+ }
3107
3425
  export {
3426
+ bookingOrders,
3108
3427
  classifyCart,
3109
3428
  createAppleIapCheckout,
3110
3429
  createIapCommerce,
3111
3430
  createWorkerOrderRefStore,
3431
+ eventTicketOrders,
3112
3432
  iapPurchaseFields,
3113
3433
  itemPaymentEnabled,
3114
3434
  onlineProgramOrders,