@pisell/pisellos 0.10.36 → 0.10.37

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.
@@ -28,6 +28,8 @@ export interface SmallTicketItem {
28
28
  value: string;
29
29
  size?: number;
30
30
  align?: string;
31
+ product_uid?: string | number;
32
+ booking_uid?: string | number;
31
33
  }
32
34
  export interface SmallTicketProduct {
33
35
  product_title: string;
@@ -53,11 +55,7 @@ export interface SmallTicketProduct {
53
55
  variant?: string;
54
56
  combinations?: any[];
55
57
  }
56
- export interface SmallTicketBookingSnapshot extends Record<string, any> {
57
- product_uid?: string | number;
58
- booking_uid?: string | number;
59
- }
60
- export type SmallTicketAppointment = SmallTicketItem[] | SmallTicketBookingSnapshot[];
58
+ export type SmallTicketAppointment = SmallTicketItem[];
61
59
  export interface SmallTicketLocaleData {
62
60
  base_data: Record<string, any>;
63
61
  products: SmallTicketProduct[];
@@ -1,12 +1,16 @@
1
+ var _excluded = ["isMarkup"];
1
2
  function _slicedToArray(arr, i) { return _arrayWithHoles(arr) || _iterableToArrayLimit(arr, i) || _unsupportedIterableToArray(arr, i) || _nonIterableRest(); }
2
3
  function _nonIterableRest() { throw new TypeError("Invalid attempt to destructure non-iterable instance.\nIn order to be iterable, non-array objects must have a [Symbol.iterator]() method."); }
3
4
  function _iterableToArrayLimit(r, l) { var t = null == r ? null : "undefined" != typeof Symbol && r[Symbol.iterator] || r["@@iterator"]; if (null != t) { var e, n, i, u, a = [], f = !0, o = !1; try { if (i = (t = t.call(r)).next, 0 === l) { if (Object(t) !== t) return; f = !1; } else for (; !(f = (e = i.call(t)).done) && (a.push(e.value), a.length !== l); f = !0); } catch (r) { o = !0, n = r; } finally { try { if (!f && null != t.return && (u = t.return(), Object(u) !== u)) return; } finally { if (o) throw n; } } return a; } }
4
5
  function _arrayWithHoles(arr) { if (Array.isArray(arr)) return arr; }
6
+ function _objectWithoutProperties(source, excluded) { if (source == null) return {}; var target = _objectWithoutPropertiesLoose(source, excluded); var key, i; if (Object.getOwnPropertySymbols) { var sourceSymbolKeys = Object.getOwnPropertySymbols(source); for (i = 0; i < sourceSymbolKeys.length; i++) { key = sourceSymbolKeys[i]; if (excluded.indexOf(key) >= 0) continue; if (!Object.prototype.propertyIsEnumerable.call(source, key)) continue; target[key] = source[key]; } } return target; }
7
+ function _objectWithoutPropertiesLoose(source, excluded) { if (source == null) return {}; var target = {}; var sourceKeys = Object.keys(source); var key, i; for (i = 0; i < sourceKeys.length; i++) { key = sourceKeys[i]; if (excluded.indexOf(key) >= 0) continue; target[key] = source[key]; } return target; }
5
8
  function _toConsumableArray(arr) { return _arrayWithoutHoles(arr) || _iterableToArray(arr) || _unsupportedIterableToArray(arr) || _nonIterableSpread(); }
6
9
  function _nonIterableSpread() { throw new TypeError("Invalid attempt to spread non-iterable instance.\nIn order to be iterable, non-array objects must have a [Symbol.iterator]() method."); }
7
- function _unsupportedIterableToArray(o, minLen) { if (!o) return; if (typeof o === "string") return _arrayLikeToArray(o, minLen); var n = Object.prototype.toString.call(o).slice(8, -1); if (n === "Object" && o.constructor) n = o.constructor.name; if (n === "Map" || n === "Set") return Array.from(o); if (n === "Arguments" || /^(?:Ui|I)nt(?:8|16|32)(?:Clamped)?Array$/.test(n)) return _arrayLikeToArray(o, minLen); }
8
10
  function _iterableToArray(iter) { if (typeof Symbol !== "undefined" && iter[Symbol.iterator] != null || iter["@@iterator"] != null) return Array.from(iter); }
9
11
  function _arrayWithoutHoles(arr) { if (Array.isArray(arr)) return _arrayLikeToArray(arr); }
12
+ function _createForOfIteratorHelper(o, allowArrayLike) { var it = typeof Symbol !== "undefined" && o[Symbol.iterator] || o["@@iterator"]; if (!it) { if (Array.isArray(o) || (it = _unsupportedIterableToArray(o)) || allowArrayLike && o && typeof o.length === "number") { if (it) o = it; var i = 0; var F = function F() {}; return { s: F, n: function n() { if (i >= o.length) return { done: true }; return { done: false, value: o[i++] }; }, e: function e(_e) { throw _e; }, f: F }; } throw new TypeError("Invalid attempt to iterate non-iterable instance.\nIn order to be iterable, non-array objects must have a [Symbol.iterator]() method."); } var normalCompletion = true, didErr = false, err; return { s: function s() { it = it.call(o); }, n: function n() { var step = it.next(); normalCompletion = step.done; return step; }, e: function e(_e2) { didErr = true; err = _e2; }, f: function f() { try { if (!normalCompletion && it.return != null) it.return(); } finally { if (didErr) throw err; } } }; }
13
+ function _unsupportedIterableToArray(o, minLen) { if (!o) return; if (typeof o === "string") return _arrayLikeToArray(o, minLen); var n = Object.prototype.toString.call(o).slice(8, -1); if (n === "Object" && o.constructor) n = o.constructor.name; if (n === "Map" || n === "Set") return Array.from(o); if (n === "Arguments" || /^(?:Ui|I)nt(?:8|16|32)(?:Clamped)?Array$/.test(n)) return _arrayLikeToArray(o, minLen); }
10
14
  function _arrayLikeToArray(arr, len) { if (len == null || len > arr.length) len = arr.length; for (var i = 0, arr2 = new Array(len); i < len; i++) arr2[i] = arr[i]; return arr2; }
11
15
  function ownKeys(e, r) { var t = Object.keys(e); if (Object.getOwnPropertySymbols) { var o = Object.getOwnPropertySymbols(e); r && (o = o.filter(function (r) { return Object.getOwnPropertyDescriptor(e, r).enumerable; })), t.push.apply(t, o); } return t; }
12
16
  function _objectSpread(e) { for (var r = 1; r < arguments.length; r++) { var t = null != arguments[r] ? arguments[r] : {}; r % 2 ? ownKeys(Object(t), !0).forEach(function (r) { _defineProperty(e, r, t[r]); }) : Object.getOwnPropertyDescriptors ? Object.defineProperties(e, Object.getOwnPropertyDescriptors(t)) : ownKeys(Object(t)).forEach(function (r) { Object.defineProperty(e, r, Object.getOwnPropertyDescriptor(t, r)); }); } return e; }
@@ -41,8 +45,13 @@ var LABELS = {
41
45
  redeemPoints: 'Redeem points',
42
46
  remainingPoints: 'Points balance',
43
47
  table: 'Table',
48
+ bookingId: 'Booking ID',
49
+ bookingDateTime: 'Date & time',
50
+ bookingResource: 'Resource',
51
+ bookingHolder: 'Holder',
44
52
  orderDiscount: 'Order discount',
45
53
  manualDiscount: 'Manual discount',
54
+ manualMarkup: 'Manual markup',
46
55
  payProcessingFee: 'Pay processing fee',
47
56
  surchargeIncluded: 'Surcharge(Included)',
48
57
  rounding: 'Rounding',
@@ -74,8 +83,13 @@ var LABELS = {
74
83
  redeemPoints: '本次使用积分',
75
84
  remainingPoints: '积分余额',
76
85
  table: '桌台',
86
+ bookingId: '预约编号',
87
+ bookingDateTime: '日期和时间',
88
+ bookingResource: '资源',
89
+ bookingHolder: '预约人',
77
90
  orderDiscount: '整单折扣',
78
91
  manualDiscount: '手动折扣',
92
+ manualMarkup: '手动加价',
79
93
  payProcessingFee: '支付手续费',
80
94
  surchargeIncluded: '手续费(已含)',
81
95
  rounding: '抹零',
@@ -107,8 +121,13 @@ var LABELS = {
107
121
  redeemPoints: '本次使用積分',
108
122
  remainingPoints: '積分餘額',
109
123
  table: '桌台',
124
+ bookingId: '預約編號',
125
+ bookingDateTime: '日期和時間',
126
+ bookingResource: '資源',
127
+ bookingHolder: '預約人',
110
128
  orderDiscount: '整單折扣',
111
129
  manualDiscount: '手動折扣',
130
+ manualMarkup: '手動加價',
112
131
  payProcessingFee: '支付手續費',
113
132
  surchargeIncluded: '手續費(已含)',
114
133
  rounding: '抹零',
@@ -138,8 +157,13 @@ var LABELS = {
138
157
  redeemPoints: '利用ポイント',
139
158
  remainingPoints: 'ポイント残高',
140
159
  table: 'テーブル',
160
+ bookingId: '予約ID',
161
+ bookingDateTime: '日時',
162
+ bookingResource: 'リソース',
163
+ bookingHolder: '予約者',
141
164
  orderDiscount: '注文割引',
142
165
  manualDiscount: '手動割引',
166
+ manualMarkup: '手動値上げ',
143
167
  payProcessingFee: '決済手数料',
144
168
  rounding: '端数調整',
145
169
  gross: '総重量',
@@ -170,8 +194,13 @@ var LABELS = {
170
194
  redeemPoints: 'Pontos utilizados',
171
195
  remainingPoints: 'Saldo de pontos',
172
196
  table: 'Mesa',
197
+ bookingId: 'ID da reserva',
198
+ bookingDateTime: 'Data e hora',
199
+ bookingResource: 'Recurso',
200
+ bookingHolder: 'Titular',
173
201
  orderDiscount: 'Desconto do pedido',
174
202
  manualDiscount: 'Desconto manual',
203
+ manualMarkup: 'Acréscimo manual',
175
204
  payProcessingFee: 'Taxa de processamento',
176
205
  rounding: 'Arredondamento',
177
206
  gross: 'Peso bruto',
@@ -285,8 +314,9 @@ function buildBaseData(params) {
285
314
  }
286
315
  function buildProducts(order, locale, productMap) {
287
316
  var products = Array.isArray(order.products) ? order.products : [];
288
- return products.map(function (product) {
317
+ return products.map(function (rawProduct) {
289
318
  var _ref, _ref2, _product$product_quan, _ref3, _ref4, _ref5, _product$original_pri, _ref6, _ref7, _product$selling_pric, _product$product_id, _product$metadata, _product$metadata2;
319
+ var product = restoreReceiptDiscountHierarchy(rawProduct);
290
320
  var quantity = toNumber((_ref = (_ref2 = (_product$product_quan = product.product_quantity) !== null && _product$product_quan !== void 0 ? _product$product_quan : product.quantity) !== null && _ref2 !== void 0 ? _ref2 : product.num) !== null && _ref !== void 0 ? _ref : 1, 1);
291
321
  var originalPrice = (_ref3 = (_ref4 = (_ref5 = (_product$original_pri = product.original_price) !== null && _product$original_pri !== void 0 ? _product$original_pri : product.selling_price) !== null && _ref5 !== void 0 ? _ref5 : product.payment_price) !== null && _ref4 !== void 0 ? _ref4 : product.price) !== null && _ref3 !== void 0 ? _ref3 : 0;
292
322
  var sellingPrice = (_ref6 = (_ref7 = (_product$selling_pric = product.selling_price) !== null && _product$selling_pric !== void 0 ? _product$selling_pric : product.payment_price) !== null && _ref7 !== void 0 ? _ref7 : product.price) !== null && _ref6 !== void 0 ? _ref6 : originalPrice;
@@ -359,6 +389,96 @@ function buildProducts(order, locale, productMap) {
359
389
  } : {});
360
390
  });
361
391
  }
392
+ var RECEIPT_BUNDLE_MAP_ID_KEY = 'custom_product_bundle_map_id';
393
+ function restoreReceiptDiscountHierarchy(source) {
394
+ if (!source || _typeof(source) !== 'object' || Array.isArray(source)) {
395
+ return source;
396
+ }
397
+ var childKey = Array.isArray(source.combinations) && source.combinations.length ? 'combinations' : Array.isArray(source.product_bundle) && source.product_bundle.length ? 'product_bundle' : null;
398
+ if (!childKey) return _objectSpread({}, source);
399
+ var children = source[childKey].map(function (child) {
400
+ return child && _typeof(child) === 'object' && !Array.isArray(child) ? restoreReceiptDiscountHierarchy(child) : child;
401
+ });
402
+ var restored = _objectSpread(_objectSpread({}, source), {}, _defineProperty({}, childKey, children));
403
+ if (!Array.isArray(source.discount_list) || !source.discount_list.length) {
404
+ return restored;
405
+ }
406
+ var descendantsByMapId = new Map();
407
+ indexReceiptDiscountTargets(children, descendantsByMapId);
408
+ if (!descendantsByMapId.size) return restored;
409
+ var ownDiscounts = [];
410
+ var _iterator = _createForOfIteratorHelper(source.discount_list),
411
+ _step;
412
+ try {
413
+ var _loop = function _loop() {
414
+ var discount = _step.value;
415
+ var mapId = getReceiptDiscountBundleMapId(discount);
416
+ var target = mapId ? descendantsByMapId.get(mapId) : undefined;
417
+ if (!target) {
418
+ ownDiscounts.push(discount);
419
+ return 1; // continue
420
+ }
421
+ var targetDiscounts = Array.isArray(target.discount_list) ? target.discount_list : [];
422
+ if (!targetDiscounts.some(function (item) {
423
+ return isSameReceiptDiscount(item, discount);
424
+ })) {
425
+ target.discount_list = [].concat(_toConsumableArray(targetDiscounts), [discount]);
426
+ }
427
+ };
428
+ for (_iterator.s(); !(_step = _iterator.n()).done;) {
429
+ if (_loop()) continue;
430
+ }
431
+ } catch (err) {
432
+ _iterator.e(err);
433
+ } finally {
434
+ _iterator.f();
435
+ }
436
+ restored.discount_list = ownDiscounts;
437
+ return restored;
438
+ }
439
+ function indexReceiptDiscountTargets(nodes, targets) {
440
+ var _iterator2 = _createForOfIteratorHelper(nodes),
441
+ _step2;
442
+ try {
443
+ for (_iterator2.s(); !(_step2 = _iterator2.n()).done;) {
444
+ var node = _step2.value;
445
+ if (!node || _typeof(node) !== 'object' || Array.isArray(node)) continue;
446
+ var mapId = getReceiptBundleMapId(node);
447
+ if (mapId && !targets.has(mapId)) targets.set(mapId, node);
448
+ var children = Array.isArray(node.combinations) && node.combinations.length ? node.combinations : Array.isArray(node.product_bundle) ? node.product_bundle : [];
449
+ indexReceiptDiscountTargets(children, targets);
450
+ }
451
+ } catch (err) {
452
+ _iterator2.e(err);
453
+ } finally {
454
+ _iterator2.f();
455
+ }
456
+ }
457
+ function normalizeReceiptId(value) {
458
+ if (value === undefined || value === null) return null;
459
+ var normalized = String(value).trim();
460
+ return normalized ? normalized : null;
461
+ }
462
+ function getReceiptBundleMapId(node) {
463
+ var _node$metadata$RECEIP, _node$metadata;
464
+ return normalizeReceiptId((_node$metadata$RECEIP = (_node$metadata = node.metadata) === null || _node$metadata === void 0 ? void 0 : _node$metadata[RECEIPT_BUNDLE_MAP_ID_KEY]) !== null && _node$metadata$RECEIP !== void 0 ? _node$metadata$RECEIP : node._id);
465
+ }
466
+ function getReceiptDiscountBundleMapId(discount) {
467
+ var _discount$metadata;
468
+ return normalizeReceiptId(discount === null || discount === void 0 || (_discount$metadata = discount.metadata) === null || _discount$metadata === void 0 ? void 0 : _discount$metadata[RECEIPT_BUNDLE_MAP_ID_KEY]);
469
+ }
470
+ function isSameReceiptDiscount(left, right) {
471
+ var _ref8, _left$discount$resour, _left$discount, _ref9, _right$discount$resou, _right$discount, _ref10, _ref11, _left$amount, _ref12, _ref13, _right$amount;
472
+ var leftOrderDiscountId = normalizeReceiptId(left === null || left === void 0 ? void 0 : left.order_discount_id);
473
+ var rightOrderDiscountId = normalizeReceiptId(right === null || right === void 0 ? void 0 : right.order_discount_id);
474
+ if (leftOrderDiscountId && rightOrderDiscountId) {
475
+ return leftOrderDiscountId === rightOrderDiscountId;
476
+ }
477
+ var leftResourceId = normalizeReceiptId((_ref8 = (_left$discount$resour = left === null || left === void 0 || (_left$discount = left.discount) === null || _left$discount === void 0 ? void 0 : _left$discount.resource_id) !== null && _left$discount$resour !== void 0 ? _left$discount$resour : left === null || left === void 0 ? void 0 : left.resource_id) !== null && _ref8 !== void 0 ? _ref8 : left === null || left === void 0 ? void 0 : left.discount_id);
478
+ var rightResourceId = normalizeReceiptId((_ref9 = (_right$discount$resou = right === null || right === void 0 || (_right$discount = right.discount) === null || _right$discount === void 0 ? void 0 : _right$discount.resource_id) !== null && _right$discount$resou !== void 0 ? _right$discount$resou : right === null || right === void 0 ? void 0 : right.resource_id) !== null && _ref9 !== void 0 ? _ref9 : right === null || right === void 0 ? void 0 : right.discount_id);
479
+ if (!leftResourceId || !rightResourceId) return false;
480
+ return leftResourceId === rightResourceId && getReceiptDiscountBundleMapId(left) === getReceiptDiscountBundleMapId(right) && String((_ref10 = (_ref11 = (_left$amount = left === null || left === void 0 ? void 0 : left.amount) !== null && _left$amount !== void 0 ? _left$amount : left === null || left === void 0 ? void 0 : left.value) !== null && _ref11 !== void 0 ? _ref11 : left === null || left === void 0 ? void 0 : left.discount_amount) !== null && _ref10 !== void 0 ? _ref10 : '') === String((_ref12 = (_ref13 = (_right$amount = right === null || right === void 0 ? void 0 : right.amount) !== null && _right$amount !== void 0 ? _right$amount : right === null || right === void 0 ? void 0 : right.value) !== null && _ref13 !== void 0 ? _ref13 : right === null || right === void 0 ? void 0 : right.discount_amount) !== null && _ref12 !== void 0 ? _ref12 : '');
481
+ }
362
482
  function resolveProductBasePrice(product) {
363
483
  var _product$product_vari, _product$_origin, _product$_origin2;
364
484
  var metadata = product.metadata || {};
@@ -375,26 +495,43 @@ function normalizeProductDiscounts(params) {
375
495
  locale = params.locale,
376
496
  currencySymbol = params.currencySymbol,
377
497
  quantity = params.quantity;
378
- return normalizeArray(product.discount_list).filter(function (discount) {
379
- var _ref8, _discount$amount;
380
- var amount = (_ref8 = (_discount$amount = discount.amount) !== null && _discount$amount !== void 0 ? _discount$amount : discount.value) !== null && _ref8 !== void 0 ? _ref8 : discount.discount_amount;
498
+ var rows = normalizeArray(product.discount_list).filter(function (discount) {
499
+ var _ref14, _discount$amount;
500
+ var amount = (_ref14 = (_discount$amount = discount.amount) !== null && _discount$amount !== void 0 ? _discount$amount : discount.value) !== null && _ref14 !== void 0 ? _ref14 : discount.discount_amount;
381
501
  return isNonZero(amount);
382
502
  }).map(function (discount) {
383
- var _ref9, _discount$amount2;
503
+ var _ref15, _discount$amount2;
384
504
  var title = resolveDiscountTitleWithPercent(discount, locale);
385
- var amount = (_ref9 = (_discount$amount2 = discount.amount) !== null && _discount$amount2 !== void 0 ? _discount$amount2 : discount.value) !== null && _ref9 !== void 0 ? _ref9 : discount.discount_amount;
386
- var formattedAmount = formatNegativeMoney(new Decimal(toMoneyNumber(amount)).mul(quantity), currencySymbol);
505
+ var amount = (_ref15 = (_discount$amount2 = discount.amount) !== null && _discount$amount2 !== void 0 ? _discount$amount2 : discount.value) !== null && _ref15 !== void 0 ? _ref15 : discount.discount_amount;
506
+ var isMarkup = isManualMarkup(discount);
507
+ var totalAmount = new Decimal(toMoneyNumber(amount)).mul(quantity);
508
+ var formattedAmount = isMarkup ? formatMoney(totalAmount.abs(), currencySymbol) : formatNegativeMoney(totalAmount, currencySymbol);
387
509
  return {
388
510
  item: title,
389
- value: formattedAmount
511
+ value: formattedAmount,
512
+ isMarkup: isMarkup
390
513
  };
391
514
  });
515
+ return rows.sort(function (left, right) {
516
+ return Number(right.isMarkup) - Number(left.isMarkup);
517
+ }).map(function (_ref16) {
518
+ var _isMarkup = _ref16.isMarkup,
519
+ row = _objectWithoutProperties(_ref16, _excluded);
520
+ return row;
521
+ });
522
+ }
523
+ function isManualMarkup(discount) {
524
+ var _discount$discount, _ref17, _discount$amount3;
525
+ if (discount.type !== 'product') return false;
526
+ if (((_discount$discount = discount.discount) === null || _discount$discount === void 0 ? void 0 : _discount$discount.discount_type) === 'change_price') return true;
527
+ var amount = (_ref17 = (_discount$amount3 = discount.amount) !== null && _discount$amount3 !== void 0 ? _discount$amount3 : discount.value) !== null && _ref17 !== void 0 ? _ref17 : discount.discount_amount;
528
+ return new Decimal(toMoneyNumber(amount)).isNegative();
392
529
  }
393
530
  function hasProductDiscount(product) {
394
531
  var extensionList = arguments.length > 1 && arguments[1] !== undefined ? arguments[1] : [];
395
532
  var hasDiscountListAmount = normalizeArray(product.discount_list).some(function (discount) {
396
- var _ref10, _discount$amount3;
397
- return isNonZero((_ref10 = (_discount$amount3 = discount.amount) !== null && _discount$amount3 !== void 0 ? _discount$amount3 : discount.value) !== null && _ref10 !== void 0 ? _ref10 : discount.discount_amount);
533
+ var _ref18, _discount$amount4;
534
+ return isNonZero((_ref18 = (_discount$amount4 = discount.amount) !== null && _discount$amount4 !== void 0 ? _discount$amount4 : discount.value) !== null && _ref18 !== void 0 ? _ref18 : discount.discount_amount);
398
535
  });
399
536
  return hasDiscountListAmount || extensionList.some(function (row) {
400
537
  return /^\s*-/.test(stringify(row === null || row === void 0 ? void 0 : row.value));
@@ -465,10 +602,10 @@ function buildProductQuantityPriceText(params) {
465
602
  return "".concat(quantity, " @ ").concat(currencySymbol).concat(stringify(price), " EACH");
466
603
  }
467
604
  function resolveDiscountTitleWithPercent(discount, locale) {
468
- var _discount$discount, _discount$discount$di, _discount$discount2;
605
+ var _discount$discount2, _discount$discount$di, _discount$discount3;
469
606
  var title = resolveDiscountTitle(discount, locale);
470
- var percentRaw = (_discount$discount = discount.discount) === null || _discount$discount === void 0 ? void 0 : _discount$discount.percent;
471
- var cardType = (_discount$discount$di = (_discount$discount2 = discount.discount) === null || _discount$discount2 === void 0 ? void 0 : _discount$discount2.discount_card_type) !== null && _discount$discount$di !== void 0 ? _discount$discount$di : 'percent';
607
+ var percentRaw = (_discount$discount2 = discount.discount) === null || _discount$discount2 === void 0 ? void 0 : _discount$discount2.percent;
608
+ var cardType = (_discount$discount$di = (_discount$discount3 = discount.discount) === null || _discount$discount3 === void 0 ? void 0 : _discount$discount3.discount_card_type) !== null && _discount$discount$di !== void 0 ? _discount$discount$di : 'percent';
472
609
  var percent = percentRaw !== undefined && percentRaw !== null ? Math.trunc(Number(percentRaw)) : NaN;
473
610
  if (percentRaw === undefined || percentRaw === null) return title;
474
611
  if (cardType !== 'percent') return title;
@@ -476,10 +613,12 @@ function resolveDiscountTitleWithPercent(discount, locale) {
476
613
  return "".concat(title, " (").concat(percent, "%)");
477
614
  }
478
615
  function resolveDiscountTitle(discount, locale) {
479
- var _ref11, _ref12, _ref13, _ref14, _discount$discount$na, _discount$discount3, _discount$discount4, _discount$discount5;
480
- var title = getLocalizedValue((_ref11 = (_ref12 = (_ref13 = (_ref14 = (_discount$discount$na = (_discount$discount3 = discount.discount) === null || _discount$discount3 === void 0 ? void 0 : _discount$discount3.name) !== null && _discount$discount$na !== void 0 ? _discount$discount$na : (_discount$discount4 = discount.discount) === null || _discount$discount4 === void 0 ? void 0 : _discount$discount4.title) !== null && _ref14 !== void 0 ? _ref14 : (_discount$discount5 = discount.discount) === null || _discount$discount5 === void 0 ? void 0 : _discount$discount5.message) !== null && _ref13 !== void 0 ? _ref13 : discount.name) !== null && _ref12 !== void 0 ? _ref12 : discount.title) !== null && _ref11 !== void 0 ? _ref11 : discount.message, locale);
616
+ var _ref19, _ref20, _ref21, _ref22, _discount$discount$na, _discount$discount4, _discount$discount5, _discount$discount6;
617
+ var title = getLocalizedValue((_ref19 = (_ref20 = (_ref21 = (_ref22 = (_discount$discount$na = (_discount$discount4 = discount.discount) === null || _discount$discount4 === void 0 ? void 0 : _discount$discount4.name) !== null && _discount$discount$na !== void 0 ? _discount$discount$na : (_discount$discount5 = discount.discount) === null || _discount$discount5 === void 0 ? void 0 : _discount$discount5.title) !== null && _ref22 !== void 0 ? _ref22 : (_discount$discount6 = discount.discount) === null || _discount$discount6 === void 0 ? void 0 : _discount$discount6.message) !== null && _ref21 !== void 0 ? _ref21 : discount.name) !== null && _ref20 !== void 0 ? _ref20 : discount.title) !== null && _ref19 !== void 0 ? _ref19 : discount.message, locale);
481
618
  if (title) return title;
482
- if (discount.type === 'product') return label(locale, 'manualDiscount');
619
+ if (discount.type === 'product') {
620
+ return label(locale, isManualMarkup(discount) ? 'manualMarkup' : 'manualDiscount');
621
+ }
483
622
  return '';
484
623
  }
485
624
  function resolveProductTitle(params) {
@@ -502,10 +641,10 @@ function normalizeProductOptions(params) {
502
641
  parentProduct = params.parentProduct;
503
642
  var rawOptions = Array.isArray(params.options) ? params.options : Array.isArray(product.options) ? product.options : Array.isArray((_product$product_sku = product.product_sku) === null || _product$product_sku === void 0 ? void 0 : _product$product_sku.option) ? product.product_sku.option : [];
504
643
  return rawOptions.map(function (option) {
505
- var _ref15, _option$original_pric, _ref16, _option$num, _ref17, _option$value;
506
- var price = (_ref15 = (_option$original_pric = option.original_price) !== null && _option$original_pric !== void 0 ? _option$original_pric : option.add_price) !== null && _ref15 !== void 0 ? _ref15 : option.price;
507
- var quantity = toNumber((_ref16 = (_option$num = option.num) !== null && _option$num !== void 0 ? _option$num : option.quantity) !== null && _ref16 !== void 0 ? _ref16 : 1, 1);
508
- var value = (_ref17 = (_option$value = option.value) !== null && _option$value !== void 0 ? _option$value : option.option) !== null && _ref17 !== void 0 ? _ref17 : option.item;
644
+ var _ref23, _option$original_pric, _ref24, _option$num, _ref25, _option$value;
645
+ var price = (_ref23 = (_option$original_pric = option.original_price) !== null && _option$original_pric !== void 0 ? _option$original_pric : option.add_price) !== null && _ref23 !== void 0 ? _ref23 : option.price;
646
+ var quantity = toNumber((_ref24 = (_option$num = option.num) !== null && _option$num !== void 0 ? _option$num : option.quantity) !== null && _ref24 !== void 0 ? _ref24 : 1, 1);
647
+ var value = (_ref25 = (_option$value = option.value) !== null && _option$value !== void 0 ? _option$value : option.option) !== null && _ref25 !== void 0 ? _ref25 : option.item;
509
648
  var name = getProductTitleSource(option, locale) || resolveOptionTitleFromParentProduct({
510
649
  option: option,
511
650
  parentProduct: parentProduct,
@@ -532,7 +671,7 @@ function normalizeProductCombinations(params) {
532
671
  parentProduct = params.parentProduct;
533
672
  var bundles = Array.isArray(product.product_bundle) ? product.product_bundle : [];
534
673
  return bundles.map(function (bundle) {
535
- var _ref18, _bundle$num, _bundle$metadata;
674
+ var _ref26, _bundle$num, _bundle$metadata;
536
675
  var combinationsOptions = normalizeProductOptions({
537
676
  product: {},
538
677
  locale: locale,
@@ -548,13 +687,20 @@ function normalizeProductCombinations(params) {
548
687
  });
549
688
  var productNote = resolveProductNote(bundle, locale);
550
689
  var nestedCombinations = Array.isArray(bundle.combinations) ? normalizeExistingCombinations(bundle.combinations, locale, currencySymbol) : [];
551
- var quantity = toNumber((_ref18 = (_bundle$num = bundle.num) !== null && _bundle$num !== void 0 ? _bundle$num : bundle.quantity) !== null && _ref18 !== void 0 ? _ref18 : 1, 1);
690
+ var quantity = toNumber((_ref26 = (_bundle$num = bundle.num) !== null && _bundle$num !== void 0 ? _bundle$num : bundle.quantity) !== null && _ref26 !== void 0 ? _ref26 : 1, 1);
552
691
  var formattedPrice = formatBundlePrice(bundle, currencySymbol);
553
692
  var optionsTotal = sumNormalizedOptionTotals(combinationsOptions, currencySymbol);
554
693
  var explicitBasePrice = firstPresentValue(bundle.base_price, (_bundle$metadata = bundle.metadata) === null || _bundle$metadata === void 0 ? void 0 : _bundle$metadata.source_product_price);
555
694
  var basePrice = isPresentId(explicitBasePrice) ? explicitBasePrice : 0;
556
- var shouldIncludeBasePrice = combinationsOptions.length > 0 || nestedCombinations.length > 0 || hasProductDiscount(bundle);
557
- return _objectSpread(_objectSpread(_objectSpread(_objectSpread(_objectSpread({
695
+ var extensionList = buildProductExtensionList({
696
+ product: bundle,
697
+ locale: locale,
698
+ currencySymbol: currencySymbol,
699
+ quantity: quantity,
700
+ originalPrice: formattedPrice
701
+ });
702
+ var shouldIncludeBasePrice = combinationsOptions.length > 0 || nestedCombinations.length > 0 || hasProductDiscount(bundle, extensionList);
703
+ return _objectSpread(_objectSpread(_objectSpread(_objectSpread(_objectSpread(_objectSpread({
558
704
  product_title: baseTitle,
559
705
  product_quantity: quantity,
560
706
  price: formattedPrice,
@@ -569,6 +715,8 @@ function normalizeProductCombinations(params) {
569
715
  package_items_total_price: sumCombinationTotals(nestedCombinations, currencySymbol)
570
716
  } : {}), productNote ? {
571
717
  product_note: productNote
718
+ } : {}), extensionList.length ? {
719
+ extension_list: extensionList
572
720
  } : {}), nestedCombinations.length ? {
573
721
  combinations: nestedCombinations
574
722
  } : {});
@@ -576,7 +724,7 @@ function normalizeProductCombinations(params) {
576
724
  }
577
725
  function normalizeExistingCombinations(combinations, locale, currencySymbol) {
578
726
  return combinations.map(function (combination) {
579
- var _ref19, _ref20, _combination$product_, _firstPresentValue;
727
+ var _ref27, _ref28, _combination$product_, _firstPresentValue;
580
728
  if (!combination || _typeof(combination) !== 'object' || Array.isArray(combination)) {
581
729
  return combination;
582
730
  }
@@ -593,15 +741,23 @@ function normalizeExistingCombinations(combinations, locale, currencySymbol) {
593
741
  delete snapshot.product_note;
594
742
  delete snapshot.note;
595
743
  delete snapshot.combinations;
596
- var quantity = toNumber((_ref19 = (_ref20 = (_combination$product_ = combination.product_quantity) !== null && _combination$product_ !== void 0 ? _combination$product_ : combination.num) !== null && _ref20 !== void 0 ? _ref20 : combination.quantity) !== null && _ref19 !== void 0 ? _ref19 : 1, 1);
744
+ delete snapshot.discount_list;
745
+ var quantity = toNumber((_ref27 = (_ref28 = (_combination$product_ = combination.product_quantity) !== null && _combination$product_ !== void 0 ? _combination$product_ : combination.num) !== null && _ref28 !== void 0 ? _ref28 : combination.quantity) !== null && _ref27 !== void 0 ? _ref27 : 1, 1);
597
746
  var unitPrice = (_firstPresentValue = firstPresentValue(combination.selling_price, combination.price, combination.original_price)) !== null && _firstPresentValue !== void 0 ? _firstPresentValue : 0;
598
747
  var optionsAmount = sumMoneyValues(normalizedOptions.map(function (option) {
599
748
  return option.total_price;
600
749
  }));
601
750
  var explicitBasePrice = firstPresentValue(combination.base_price);
602
751
  var basePrice = isPresentId(explicitBasePrice) ? explicitBasePrice : 0;
603
- var shouldIncludeBasePrice = normalizedOptions.length > 0 || nestedCombinations.length > 0 || hasProductDiscount(combination, normalizeArray(combination.extension_list));
604
- return _objectSpread(_objectSpread(_objectSpread(_objectSpread(_objectSpread(_objectSpread(_objectSpread({}, snapshot), {}, {
752
+ var extensionList = buildProductExtensionList({
753
+ product: combination,
754
+ locale: locale,
755
+ currencySymbol: currencySymbol,
756
+ quantity: quantity,
757
+ originalPrice: unitPrice
758
+ });
759
+ var shouldIncludeBasePrice = normalizedOptions.length > 0 || nestedCombinations.length > 0 || hasProductDiscount(combination, extensionList);
760
+ return _objectSpread(_objectSpread(_objectSpread(_objectSpread(_objectSpread(_objectSpread(_objectSpread(_objectSpread({}, snapshot), {}, {
605
761
  product_quantity: quantity,
606
762
  total_selling_price: formatCalculatedMoney(new Decimal(toMoneyNumber(unitPrice)).mul(quantity), currencySymbol)
607
763
  }, shouldIncludeBasePrice ? {
@@ -616,6 +772,8 @@ function normalizeExistingCombinations(combinations, locale, currencySymbol) {
616
772
  package_items_total_price: sumCombinationTotals(nestedCombinations, currencySymbol)
617
773
  } : {}), productNote ? {
618
774
  product_note: productNote
775
+ } : {}), extensionList.length ? {
776
+ extension_list: extensionList
619
777
  } : {}), nestedCombinations.length ? {
620
778
  combinations: nestedCombinations
621
779
  } : {});
@@ -642,7 +800,7 @@ function resolveProductNote(product, locale) {
642
800
  return getLocalizedValue(product.note, locale).trim();
643
801
  }
644
802
  function resolveBundleProductTitle(params) {
645
- var _ref21, _ref22, _bundle$bundle_produc;
803
+ var _ref29, _ref30, _bundle$bundle_produc;
646
804
  var bundle = params.bundle,
647
805
  productMap = params.productMap,
648
806
  locale = params.locale,
@@ -655,7 +813,7 @@ function resolveBundleProductTitle(params) {
655
813
  });
656
814
  var parentBundleTitle = parentBundleItem ? getProductTitleSource(parentBundleItem, locale) : '';
657
815
  if (parentBundleTitle) return parentBundleTitle;
658
- var productId = (_ref21 = (_ref22 = (_bundle$bundle_produc = bundle.bundle_product_id) !== null && _bundle$bundle_produc !== void 0 ? _bundle$bundle_produc : bundle._bundle_product_id) !== null && _ref22 !== void 0 ? _ref22 : bundle.product_id) !== null && _ref21 !== void 0 ? _ref21 : bundle.id;
816
+ var productId = (_ref29 = (_ref30 = (_bundle$bundle_produc = bundle.bundle_product_id) !== null && _bundle$bundle_produc !== void 0 ? _bundle$bundle_produc : bundle._bundle_product_id) !== null && _ref30 !== void 0 ? _ref30 : bundle.product_id) !== null && _ref29 !== void 0 ? _ref29 : bundle.id;
659
817
  var fallbackProduct = resolveProductFromMap(productId, productMap);
660
818
  if (!fallbackProduct) return '';
661
819
  return getProductTitleSource(fallbackProduct, locale);
@@ -707,10 +865,10 @@ function resolveVariantTextFromSkuKey(params) {
707
865
  }
708
866
  function resolveVariantTextFromNameMap(params) {
709
867
  if (!params.nameMap || _typeof(params.nameMap) !== 'object') return '';
710
- return Object.entries(params.nameMap).map(function (_ref23) {
711
- var _ref24 = _slicedToArray(_ref23, 2),
712
- groupPositionId = _ref24[0],
713
- value = _ref24[1];
868
+ return Object.entries(params.nameMap).map(function (_ref31) {
869
+ var _ref32 = _slicedToArray(_ref31, 2),
870
+ groupPositionId = _ref32[0],
871
+ value = _ref32[1];
714
872
  var group = resolveVariantGroup(params.parentProduct, groupPositionId);
715
873
  if (!group) return '';
716
874
  var groupName = getLocalizedValue(group.name, params.locale);
@@ -744,12 +902,12 @@ function getProductTitleSource(source, locale) {
744
902
  return resolveTitleValue(source.product_title, locale) || resolveTitleValue(source.title, locale) || resolveTitleValue(source.name, locale);
745
903
  }
746
904
  function resolveTitleValue(value, locale) {
747
- var _ref25, _ref26, _ref27, _ref28, _value$locale;
905
+ var _ref33, _ref34, _ref35, _ref36, _value$locale;
748
906
  if (value === undefined || value === null) return '';
749
907
  if (_typeof(value) !== 'object') return stringify(value);
750
908
  var dashedLocale = locale.replace('_', '-');
751
909
  var underscoredLocale = locale.replace('-', '_');
752
- return stringify((_ref25 = (_ref26 = (_ref27 = (_ref28 = (_value$locale = value[locale]) !== null && _value$locale !== void 0 ? _value$locale : value[dashedLocale]) !== null && _ref28 !== void 0 ? _ref28 : value[underscoredLocale]) !== null && _ref27 !== void 0 ? _ref27 : value.original) !== null && _ref26 !== void 0 ? _ref26 : value.auto) !== null && _ref25 !== void 0 ? _ref25 : '');
910
+ return stringify((_ref33 = (_ref34 = (_ref35 = (_ref36 = (_value$locale = value[locale]) !== null && _value$locale !== void 0 ? _value$locale : value[dashedLocale]) !== null && _ref36 !== void 0 ? _ref36 : value[underscoredLocale]) !== null && _ref35 !== void 0 ? _ref35 : value.original) !== null && _ref34 !== void 0 ? _ref34 : value.auto) !== null && _ref33 !== void 0 ? _ref33 : '');
753
911
  }
754
912
  function resolveOptionTitleFromParentProduct(params) {
755
913
  var option = params.option,
@@ -767,17 +925,17 @@ function flattenOptionItems(parentProduct) {
767
925
  return optionGroups.flatMap(function (group) {
768
926
  var items = normalizeArray(group.option_item || group.option_items || group.option || group.options || group.items || group.children || group.product_option_item);
769
927
  return items.map(function (item) {
770
- var _ref29, _item$option_group_id;
928
+ var _ref37, _item$option_group_id;
771
929
  return _objectSpread(_objectSpread({}, item), {}, {
772
- option_group_id: (_ref29 = (_item$option_group_id = item.option_group_id) !== null && _item$option_group_id !== void 0 ? _item$option_group_id : group.id) !== null && _ref29 !== void 0 ? _ref29 : group.option_group_id
930
+ option_group_id: (_ref37 = (_item$option_group_id = item.option_group_id) !== null && _item$option_group_id !== void 0 ? _item$option_group_id : group.id) !== null && _ref37 !== void 0 ? _ref37 : group.option_group_id
773
931
  });
774
932
  });
775
933
  });
776
934
  }
777
935
  function isOptionItemMatch(option, item) {
778
- var _ref30, _option$option_group_, _ref31, _item$option_group_it, _option$option_group_2, _item$option_group_id2;
779
- var optionItemId = (_ref30 = (_option$option_group_ = option.option_group_item_id) !== null && _option$option_group_ !== void 0 ? _option$option_group_ : option.product_option_item_id) !== null && _ref30 !== void 0 ? _ref30 : option.id;
780
- var itemId = (_ref31 = (_item$option_group_it = item.option_group_item_id) !== null && _item$option_group_it !== void 0 ? _item$option_group_it : item.product_option_item_id) !== null && _ref31 !== void 0 ? _ref31 : item.id;
936
+ var _ref38, _option$option_group_, _ref39, _item$option_group_it, _option$option_group_2, _item$option_group_id2;
937
+ var optionItemId = (_ref38 = (_option$option_group_ = option.option_group_item_id) !== null && _option$option_group_ !== void 0 ? _option$option_group_ : option.product_option_item_id) !== null && _ref38 !== void 0 ? _ref38 : option.id;
938
+ var itemId = (_ref39 = (_item$option_group_it = item.option_group_item_id) !== null && _item$option_group_it !== void 0 ? _item$option_group_it : item.product_option_item_id) !== null && _ref39 !== void 0 ? _ref39 : item.id;
781
939
  if (!isSameId(optionItemId, itemId)) return false;
782
940
  var optionGroupId = (_option$option_group_2 = option.option_group_id) !== null && _option$option_group_2 !== void 0 ? _option$option_group_2 : option.group_id;
783
941
  var itemGroupId = (_item$option_group_id2 = item.option_group_id) !== null && _item$option_group_id2 !== void 0 ? _item$option_group_id2 : item.group_id;
@@ -787,16 +945,16 @@ function isOptionItemMatch(option, item) {
787
945
  return true;
788
946
  }
789
947
  function resolveBundleItemFromParentProduct(params) {
790
- var _ref32, _bundle$bundle_varian, _bundle$bundle_id, _bundle$bundle_group_, _ref34, _bundle$bundle_produc2;
948
+ var _ref40, _bundle$bundle_varian, _bundle$bundle_id, _bundle$bundle_group_, _ref42, _bundle$bundle_produc2;
791
949
  var bundle = params.bundle,
792
950
  parentProduct = params.parentProduct;
793
951
  if (!parentProduct) return null;
794
952
  var bundleItems = flattenBundleItems(parentProduct);
795
- var bundleVariantId = (_ref32 = (_bundle$bundle_varian = bundle.bundle_variant_id) !== null && _bundle$bundle_varian !== void 0 ? _bundle$bundle_varian : bundle.variant_id) !== null && _ref32 !== void 0 ? _ref32 : bundle.product_variant_id;
953
+ var bundleVariantId = (_ref40 = (_bundle$bundle_varian = bundle.bundle_variant_id) !== null && _bundle$bundle_varian !== void 0 ? _bundle$bundle_varian : bundle.variant_id) !== null && _ref40 !== void 0 ? _ref40 : bundle.product_variant_id;
796
954
  if (isNonZeroId(bundleVariantId)) {
797
955
  var matchedByVariant = bundleItems.find(function (item) {
798
- var _ref33, _item$bundle_variant_;
799
- return isSameId((_ref33 = (_item$bundle_variant_ = item.bundle_variant_id) !== null && _item$bundle_variant_ !== void 0 ? _item$bundle_variant_ : item.variant_id) !== null && _ref33 !== void 0 ? _ref33 : item.product_variant_id, bundleVariantId);
956
+ var _ref41, _item$bundle_variant_;
957
+ return isSameId((_ref41 = (_item$bundle_variant_ = item.bundle_variant_id) !== null && _item$bundle_variant_ !== void 0 ? _item$bundle_variant_ : item.variant_id) !== null && _ref41 !== void 0 ? _ref41 : item.product_variant_id, bundleVariantId);
800
958
  });
801
959
  if (matchedByVariant) return matchedByVariant;
802
960
  }
@@ -809,18 +967,18 @@ function resolveBundleItemFromParentProduct(params) {
809
967
  if (matchedByBundleId) return matchedByBundleId;
810
968
  }
811
969
  var bundleGroupId = (_bundle$bundle_group_ = bundle.bundle_group_id) !== null && _bundle$bundle_group_ !== void 0 ? _bundle$bundle_group_ : bundle.group_id;
812
- var bundleProductId = (_ref34 = (_bundle$bundle_produc2 = bundle.bundle_product_id) !== null && _bundle$bundle_produc2 !== void 0 ? _bundle$bundle_produc2 : bundle._bundle_product_id) !== null && _ref34 !== void 0 ? _ref34 : bundle.product_id;
970
+ var bundleProductId = (_ref42 = (_bundle$bundle_produc2 = bundle.bundle_product_id) !== null && _bundle$bundle_produc2 !== void 0 ? _bundle$bundle_produc2 : bundle._bundle_product_id) !== null && _ref42 !== void 0 ? _ref42 : bundle.product_id;
813
971
  if (isPresentId(bundleGroupId) && isPresentId(bundleProductId)) {
814
972
  var matchedByGroupAndProduct = bundleItems.find(function (item) {
815
- var _item$group_id, _ref35, _item$bundle_product_;
816
- return isSameId((_item$group_id = item.group_id) !== null && _item$group_id !== void 0 ? _item$group_id : item.bundle_group_id, bundleGroupId) && isSameId((_ref35 = (_item$bundle_product_ = item.bundle_product_id) !== null && _item$bundle_product_ !== void 0 ? _item$bundle_product_ : item._bundle_product_id) !== null && _ref35 !== void 0 ? _ref35 : item.product_id, bundleProductId);
973
+ var _item$group_id, _ref43, _item$bundle_product_;
974
+ return isSameId((_item$group_id = item.group_id) !== null && _item$group_id !== void 0 ? _item$group_id : item.bundle_group_id, bundleGroupId) && isSameId((_ref43 = (_item$bundle_product_ = item.bundle_product_id) !== null && _item$bundle_product_ !== void 0 ? _item$bundle_product_ : item._bundle_product_id) !== null && _ref43 !== void 0 ? _ref43 : item.product_id, bundleProductId);
817
975
  });
818
976
  if (matchedByGroupAndProduct) return matchedByGroupAndProduct;
819
977
  }
820
978
  if (isPresentId(bundleProductId)) {
821
979
  return bundleItems.find(function (item) {
822
- var _ref36, _item$bundle_product_2;
823
- return isSameId((_ref36 = (_item$bundle_product_2 = item.bundle_product_id) !== null && _item$bundle_product_2 !== void 0 ? _item$bundle_product_2 : item._bundle_product_id) !== null && _ref36 !== void 0 ? _ref36 : item.product_id, bundleProductId);
980
+ var _ref44, _item$bundle_product_2;
981
+ return isSameId((_ref44 = (_item$bundle_product_2 = item.bundle_product_id) !== null && _item$bundle_product_2 !== void 0 ? _item$bundle_product_2 : item._bundle_product_id) !== null && _ref44 !== void 0 ? _ref44 : item.product_id, bundleProductId);
824
982
  }) || null;
825
983
  }
826
984
  return null;
@@ -830,9 +988,9 @@ function flattenBundleItems(parentProduct) {
830
988
  return bundleGroups.flatMap(function (group) {
831
989
  var items = Array.isArray(group.bundle_item) ? group.bundle_item : [];
832
990
  return items.map(function (item) {
833
- var _ref37, _item$group_id2;
991
+ var _ref45, _item$group_id2;
834
992
  return _objectSpread(_objectSpread({}, item), {}, {
835
- group_id: (_ref37 = (_item$group_id2 = item.group_id) !== null && _item$group_id2 !== void 0 ? _item$group_id2 : group.id) !== null && _ref37 !== void 0 ? _ref37 : group.group_id
993
+ group_id: (_ref45 = (_item$group_id2 = item.group_id) !== null && _item$group_id2 !== void 0 ? _item$group_id2 : group.id) !== null && _ref45 !== void 0 ? _ref45 : group.group_id
836
994
  });
837
995
  });
838
996
  });
@@ -856,8 +1014,8 @@ function isSameId(left, right) {
856
1014
  return String(left) === String(right);
857
1015
  }
858
1016
  function formatBundlePrice(bundle, currencySymbol) {
859
- var _ref38, _ref39, _bundle$bundle_sellin;
860
- var value = (_ref38 = (_ref39 = (_bundle$bundle_sellin = bundle.bundle_selling_price) !== null && _bundle$bundle_sellin !== void 0 ? _bundle$bundle_sellin : bundle.bundle_sum_price) !== null && _ref39 !== void 0 ? _ref39 : bundle.price) !== null && _ref38 !== void 0 ? _ref38 : 0;
1017
+ var _ref46, _ref47, _bundle$bundle_sellin;
1018
+ var value = (_ref46 = (_ref47 = (_bundle$bundle_sellin = bundle.bundle_selling_price) !== null && _bundle$bundle_sellin !== void 0 ? _bundle$bundle_sellin : bundle.bundle_sum_price) !== null && _ref47 !== void 0 ? _ref47 : bundle.price) !== null && _ref46 !== void 0 ? _ref46 : 0;
861
1019
  var amount = new Decimal(toMoneyNumber(value));
862
1020
  // 套餐价格协议:只有 markdown 是减价;加价与商品原价都保持正数。
863
1021
  var isNegative = bundle.price_type === 'markdown';
@@ -875,9 +1033,9 @@ function buildFees(params) {
875
1033
  financials = params.financials;
876
1034
  var fees = [];
877
1035
  for (var _i = 0, _normalizeArray = normalizeArray(order.surcharges || summary.surcharges); _i < _normalizeArray.length; _i++) {
878
- var _ref40, _surcharge$amount;
1036
+ var _ref48, _surcharge$amount;
879
1037
  var surcharge = _normalizeArray[_i];
880
- var value = (_ref40 = (_surcharge$amount = surcharge.amount) !== null && _surcharge$amount !== void 0 ? _surcharge$amount : surcharge.value) !== null && _ref40 !== void 0 ? _ref40 : surcharge.total_amount;
1038
+ var value = (_ref48 = (_surcharge$amount = surcharge.amount) !== null && _surcharge$amount !== void 0 ? _surcharge$amount : surcharge.value) !== null && _ref48 !== void 0 ? _ref48 : surcharge.total_amount;
881
1039
  if (!isNonZero(value)) continue;
882
1040
  fees.push({
883
1041
  item: getLocalizedValue(surcharge.name || surcharge.title || surcharge.item, locale),
@@ -985,9 +1143,9 @@ function resolveTaxTitle(params) {
985
1143
  }
986
1144
  function calculateProductOriginalAmount(order) {
987
1145
  return normalizeArray(order.products).reduce(function (total, product) {
988
- var _ref41, _ref42, _product$product_quan2, _ref43, _ref44, _ref45, _product$original_pri2;
989
- var quantity = toNumber((_ref41 = (_ref42 = (_product$product_quan2 = product.product_quantity) !== null && _product$product_quan2 !== void 0 ? _product$product_quan2 : product.quantity) !== null && _ref42 !== void 0 ? _ref42 : product.num) !== null && _ref41 !== void 0 ? _ref41 : 1, 1);
990
- var originalPrice = (_ref43 = (_ref44 = (_ref45 = (_product$original_pri2 = product.original_price) !== null && _product$original_pri2 !== void 0 ? _product$original_pri2 : product.selling_price) !== null && _ref45 !== void 0 ? _ref45 : product.payment_price) !== null && _ref44 !== void 0 ? _ref44 : product.price) !== null && _ref43 !== void 0 ? _ref43 : 0;
1146
+ var _ref49, _ref50, _product$product_quan2, _ref51, _ref52, _ref53, _product$original_pri2;
1147
+ var quantity = toNumber((_ref49 = (_ref50 = (_product$product_quan2 = product.product_quantity) !== null && _product$product_quan2 !== void 0 ? _product$product_quan2 : product.quantity) !== null && _ref50 !== void 0 ? _ref50 : product.num) !== null && _ref49 !== void 0 ? _ref49 : 1, 1);
1148
+ var originalPrice = (_ref51 = (_ref52 = (_ref53 = (_product$original_pri2 = product.original_price) !== null && _product$original_pri2 !== void 0 ? _product$original_pri2 : product.selling_price) !== null && _ref53 !== void 0 ? _ref53 : product.payment_price) !== null && _ref52 !== void 0 ? _ref52 : product.price) !== null && _ref51 !== void 0 ? _ref51 : 0;
991
1149
  return total.plus(new Decimal(toMoneyNumber(originalPrice)).mul(quantity));
992
1150
  }, new Decimal(0));
993
1151
  }
@@ -1035,18 +1193,14 @@ function buildAppointment(order, locale) {
1035
1193
  var _order$metadata13, _order$metadata14, _order$form_data;
1036
1194
  var bookings = sortBookings(normalizeArray(order.bookings));
1037
1195
  if (bookings.length) {
1038
- return bookings.map(function (booking) {
1039
- var _booking$metadata, _booking$metadata2;
1040
- var snapshot = _objectSpread({}, booking);
1041
- delete snapshot.product_uid;
1042
- delete snapshot.booking_uid;
1043
- var productUid = firstPresentValue(booking.product_uid, (_booking$metadata = booking.metadata) === null || _booking$metadata === void 0 ? void 0 : _booking$metadata.product_uid);
1044
- var bookingUid = firstPresentValue((_booking$metadata2 = booking.metadata) === null || _booking$metadata2 === void 0 ? void 0 : _booking$metadata2.unique_identification_number, booking.booking_uid);
1045
- return _objectSpread(_objectSpread(_objectSpread({}, snapshot), isPresentId(productUid) ? {
1046
- product_uid: productUid
1047
- } : {}), isPresentId(bookingUid) ? {
1048
- booking_uid: bookingUid
1049
- } : {});
1196
+ var allResources = normalizeArray(order.resources || order.resource_list);
1197
+ return bookings.flatMap(function (booking) {
1198
+ return buildAppointmentRows({
1199
+ booking: booking,
1200
+ allResources: allResources,
1201
+ bookingCount: bookings.length,
1202
+ locale: locale
1203
+ });
1050
1204
  });
1051
1205
  }
1052
1206
  var tableName = order.table_name || ((_order$metadata13 = order.metadata) === null || _order$metadata13 === void 0 ? void 0 : _order$metadata13.table_name) || ((_order$metadata14 = order.metadata) === null || _order$metadata14 === void 0 || (_order$metadata14 = _order$metadata14.table) === null || _order$metadata14 === void 0 ? void 0 : _order$metadata14.name) || ((_order$form_data = order.form_data) === null || _order$form_data === void 0 ? void 0 : _order$form_data.table_name);
@@ -1056,6 +1210,104 @@ function buildAppointment(order, locale) {
1056
1210
  value: getLocalizedValue(tableName, locale)
1057
1211
  }];
1058
1212
  }
1213
+ function buildAppointmentRows(params) {
1214
+ var _booking$metadata, _booking$metadata2, _booking$holder$name, _booking$holder, _booking$metadata3;
1215
+ var booking = params.booking,
1216
+ allResources = params.allResources,
1217
+ bookingCount = params.bookingCount,
1218
+ locale = params.locale;
1219
+ var productUid = stringify(firstPresentValue(booking.product_uid, (_booking$metadata = booking.metadata) === null || _booking$metadata === void 0 ? void 0 : _booking$metadata.product_uid)).trim();
1220
+ var bookingUid = stringify(firstPresentValue((_booking$metadata2 = booking.metadata) === null || _booking$metadata2 === void 0 ? void 0 : _booking$metadata2.unique_identification_number, booking.booking_uid)).trim();
1221
+ var association = {
1222
+ product_uid: productUid,
1223
+ booking_uid: bookingUid
1224
+ };
1225
+ var bookingId = stringify(firstPresentValue(booking.booking_id, booking.schedule_event_id, bookingUid)).trim();
1226
+ var bookingTime = formatBookingRange(booking, locale);
1227
+ var resourceText = formatBookingResources(resolveBookingResourcesForReceipt(booking, allResources, bookingCount), locale);
1228
+ var holder = getLocalizedValue((_booking$holder$name = (_booking$holder = booking.holder) === null || _booking$holder === void 0 ? void 0 : _booking$holder.name) !== null && _booking$holder$name !== void 0 ? _booking$holder$name : (_booking$metadata3 = booking.metadata) === null || _booking$metadata3 === void 0 || (_booking$metadata3 = _booking$metadata3.holder) === null || _booking$metadata3 === void 0 ? void 0 : _booking$metadata3.name, locale).trim();
1229
+ return [_objectSpread({
1230
+ item: label(locale, 'bookingId'),
1231
+ value: bookingId
1232
+ }, association), _objectSpread({
1233
+ item: label(locale, 'bookingDateTime'),
1234
+ value: bookingTime
1235
+ }, association), _objectSpread({
1236
+ item: label(locale, 'bookingResource'),
1237
+ value: resourceText
1238
+ }, association), _objectSpread({
1239
+ item: label(locale, 'bookingHolder'),
1240
+ value: holder
1241
+ }, association)].filter(function (row) {
1242
+ return Boolean(row.value);
1243
+ });
1244
+ }
1245
+ function formatBookingRange(booking, locale) {
1246
+ var startDate = stringify(booking.start_date);
1247
+ var startTime = stringify(booking.start_time);
1248
+ var endDate = stringify(booking.end_date || startDate);
1249
+ var endTime = stringify(booking.end_time);
1250
+ var start = firstValidBookingDate(booking.start_at, booking.start_datetime, booking.start_date_time, "".concat(startDate, " ").concat(startTime).trim());
1251
+ var end = firstValidBookingDate(booking.end_at, booking.end_datetime, booking.end_date_time, endTime ? "".concat(endDate, " ").concat(endTime).trim() : '');
1252
+ if (!start) {
1253
+ return [startDate, startTime, endTime ? "- ".concat(endDate, " ").concat(endTime) : ''].filter(Boolean).join(' ');
1254
+ }
1255
+ var dateFormat = locale === 'en' ? 'DD/MM/YYYY' : 'YYYY/MM/DD';
1256
+ var startText = start.format("".concat(dateFormat, " HH:mm"));
1257
+ if (!end) return startText;
1258
+ return "".concat(startText, " - ").concat(end.isSame(start, 'day') ? end.format('HH:mm') : end.format("".concat(dateFormat, " HH:mm")));
1259
+ }
1260
+ function firstValidBookingDate() {
1261
+ for (var _len2 = arguments.length, values = new Array(_len2), _key2 = 0; _key2 < _len2; _key2++) {
1262
+ values[_key2] = arguments[_key2];
1263
+ }
1264
+ for (var _i2 = 0, _values = values; _i2 < _values.length; _i2++) {
1265
+ var value = _values[_i2];
1266
+ if (!isPresentId(value)) continue;
1267
+ var parsed = dayjs(value);
1268
+ if (parsed.isValid()) return parsed;
1269
+ }
1270
+ return null;
1271
+ }
1272
+ function resolveBookingResourcesForReceipt(booking, allResources, bookingCount) {
1273
+ var _booking$metadata4;
1274
+ var embedded = normalizeArray(booking.resources).filter(function (resource) {
1275
+ return Boolean(resource) && _typeof(resource) === 'object' && !Array.isArray(resource);
1276
+ });
1277
+ var resourceIds = new Set([booking.resource_id, booking.relation_id].concat(_toConsumableArray(normalizeArray(booking.resource_ids)), _toConsumableArray(normalizeArray((_booking$metadata4 = booking.metadata) === null || _booking$metadata4 === void 0 ? void 0 : _booking$metadata4.resource_ids))).map(function (value) {
1278
+ return stringify(value).trim();
1279
+ }).filter(Boolean));
1280
+ var _iterator3 = _createForOfIteratorHelper(embedded),
1281
+ _step3;
1282
+ try {
1283
+ for (_iterator3.s(); !(_step3 = _iterator3.n()).done;) {
1284
+ var _ref55, _resource$id2;
1285
+ var resource = _step3.value;
1286
+ var id = stringify((_ref55 = (_resource$id2 = resource.id) !== null && _resource$id2 !== void 0 ? _resource$id2 : resource.resource_id) !== null && _ref55 !== void 0 ? _ref55 : resource.relation_id).trim();
1287
+ if (id) resourceIds.add(id);
1288
+ }
1289
+ } catch (err) {
1290
+ _iterator3.e(err);
1291
+ } finally {
1292
+ _iterator3.f();
1293
+ }
1294
+ if (resourceIds.size) {
1295
+ var matched = allResources.filter(function (resource) {
1296
+ var _ref54, _resource$id;
1297
+ return resourceIds.has(stringify((_ref54 = (_resource$id = resource.id) !== null && _resource$id !== void 0 ? _resource$id : resource.resource_id) !== null && _ref54 !== void 0 ? _ref54 : resource.relation_id).trim());
1298
+ });
1299
+ if (matched.length) return matched;
1300
+ }
1301
+ if (embedded.length) return embedded;
1302
+ if (bookingCount === 1 && allResources.length) return allResources;
1303
+ return [];
1304
+ }
1305
+ function formatBookingResources(resources, locale) {
1306
+ return resources.map(function (resource) {
1307
+ var _resource$metadata, _resource$metadata2, _resource$metadata3, _resource$metadata4;
1308
+ return [getLocalizedValue(resource.form_title || ((_resource$metadata = resource.metadata) === null || _resource$metadata === void 0 ? void 0 : _resource$metadata.form_name) || resource.relation_form_name || ((_resource$metadata2 = resource.metadata) === null || _resource$metadata2 === void 0 ? void 0 : _resource$metadata2.relation_form_name), locale), getLocalizedValue(resource.title || resource.name || resource.main_field || ((_resource$metadata3 = resource.metadata) === null || _resource$metadata3 === void 0 ? void 0 : _resource$metadata3.main_field) || ((_resource$metadata4 = resource.metadata) === null || _resource$metadata4 === void 0 ? void 0 : _resource$metadata4.resource_name), locale)].filter(Boolean).join(' ');
1309
+ }).filter(Boolean).join(', ');
1310
+ }
1059
1311
  function sortBookings(bookings) {
1060
1312
  return bookings.map(function (booking, index) {
1061
1313
  return {
@@ -1067,23 +1319,23 @@ function sortBookings(bookings) {
1067
1319
  var leftStart = bookingStartTimestamp(left.booking);
1068
1320
  var rightStart = bookingStartTimestamp(right.booking);
1069
1321
  if (leftStart !== rightStart) return leftStart < rightStart ? -1 : 1;
1070
- for (var _i2 = 0, _arr = ['booking_id', 'schedule_event_id']; _i2 < _arr.length; _i2++) {
1322
+ for (var _i3 = 0, _arr = ['booking_id', 'schedule_event_id']; _i3 < _arr.length; _i3++) {
1071
1323
  var _left$booking, _right$booking;
1072
- var field = _arr[_i2];
1324
+ var field = _arr[_i3];
1073
1325
  var fieldOrder = compareOptionalValues((_left$booking = left.booking) === null || _left$booking === void 0 ? void 0 : _left$booking[field], (_right$booking = right.booking) === null || _right$booking === void 0 ? void 0 : _right$booking[field]);
1074
1326
  if (fieldOrder !== 0) return fieldOrder;
1075
1327
  }
1076
1328
  var bookingUidOrder = compareOptionalValues(firstPresentValue((_left$booking2 = left.booking) === null || _left$booking2 === void 0 || (_left$booking2 = _left$booking2.metadata) === null || _left$booking2 === void 0 ? void 0 : _left$booking2.unique_identification_number, (_left$booking3 = left.booking) === null || _left$booking3 === void 0 ? void 0 : _left$booking3.booking_uid), firstPresentValue((_right$booking2 = right.booking) === null || _right$booking2 === void 0 || (_right$booking2 = _right$booking2.metadata) === null || _right$booking2 === void 0 ? void 0 : _right$booking2.unique_identification_number, (_right$booking3 = right.booking) === null || _right$booking3 === void 0 ? void 0 : _right$booking3.booking_uid));
1077
1329
  return bookingUidOrder || left.index - right.index;
1078
- }).map(function (_ref46) {
1079
- var booking = _ref46.booking;
1330
+ }).map(function (_ref56) {
1331
+ var booking = _ref56.booking;
1080
1332
  return booking;
1081
1333
  });
1082
1334
  }
1083
1335
  function bookingStartTimestamp(booking) {
1084
1336
  var startValues = [booking === null || booking === void 0 ? void 0 : booking.start_at, booking === null || booking === void 0 ? void 0 : booking.start_datetime, booking === null || booking === void 0 ? void 0 : booking.booking_time, isPresentId(booking === null || booking === void 0 ? void 0 : booking.start_date) ? "".concat(booking.start_date, " ").concat(stringify(booking.start_time)).trim() : undefined];
1085
- for (var _i3 = 0, _startValues = startValues; _i3 < _startValues.length; _i3++) {
1086
- var startValue = _startValues[_i3];
1337
+ for (var _i4 = 0, _startValues = startValues; _i4 < _startValues.length; _i4++) {
1338
+ var startValue = _startValues[_i4];
1087
1339
  if (!isPresentId(startValue)) continue;
1088
1340
  var timestamp = dayjs(startValue).valueOf();
1089
1341
  if (Number.isFinite(timestamp)) return timestamp;
@@ -1138,8 +1390,8 @@ function buildRefundData(params) {
1138
1390
  result.set(identity, candidate);
1139
1391
  }
1140
1392
  return result;
1141
- }, new Map()).values()).filter(function (_ref47) {
1142
- var refund = _ref47.refund;
1393
+ }, new Map()).values()).filter(function (_ref57) {
1394
+ var refund = _ref57.refund;
1143
1395
  return isPrintableRefund(refund);
1144
1396
  }).sort(function (left, right) {
1145
1397
  var leftTime = refundTimestamp(left.refund);
@@ -1147,9 +1399,9 @@ function buildRefundData(params) {
1147
1399
  if (leftTime !== rightTime) return leftTime < rightTime ? -1 : 1;
1148
1400
  return left.index - right.index;
1149
1401
  });
1150
- return refunds.map(function (_ref48) {
1402
+ return refunds.map(function (_ref58) {
1151
1403
  var _firstPresentValue8;
1152
- var refund = _ref48.refund;
1404
+ var refund = _ref58.refund;
1153
1405
  var payment = resolveRefundPayment(refund, payments);
1154
1406
  var methodName = paymentMethodName(payment, params.locale) || label(params.locale, 'refund');
1155
1407
  var amount = (_firstPresentValue8 = firstPresentValue(refund.amount, refund.refund_amount, refund.total_amount)) !== null && _firstPresentValue8 !== void 0 ? _firstPresentValue8 : 0;
@@ -1377,8 +1629,8 @@ function buildPaymentItems(params) {
1377
1629
  includeUsage: includeFundRecordUsage
1378
1630
  })));
1379
1631
  } else {
1380
- var _ref49, _payment$remaining_am, _payment$metadata;
1381
- var remainingAmount = (_ref49 = (_payment$remaining_am = payment.remaining_amount) !== null && _payment$remaining_am !== void 0 ? _payment$remaining_am : payment.balance) !== null && _ref49 !== void 0 ? _ref49 : (_payment$metadata = payment.metadata) === null || _payment$metadata === void 0 ? void 0 : _payment$metadata.remaining_amount;
1632
+ var _ref59, _payment$remaining_am, _payment$metadata;
1633
+ var remainingAmount = (_ref59 = (_payment$remaining_am = payment.remaining_amount) !== null && _payment$remaining_am !== void 0 ? _payment$remaining_am : payment.balance) !== null && _ref59 !== void 0 ? _ref59 : (_payment$metadata = payment.metadata) === null || _payment$metadata === void 0 ? void 0 : _payment$metadata.remaining_amount;
1382
1634
  if (remainingAmount !== undefined && remainingAmount !== null) {
1383
1635
  items.push({
1384
1636
  item: label(locale, 'remainingAmount'),
@@ -1532,12 +1784,12 @@ function label(locale, key) {
1532
1784
  return ((_LABELS$locale = LABELS[locale]) === null || _LABELS$locale === void 0 ? void 0 : _LABELS$locale[key]) || LABELS.en[key] || key;
1533
1785
  }
1534
1786
  function getLocalizedValue(value, locale) {
1535
- var _ref50, _ref51, _ref52, _ref53, _ref54, _ref55, _value$locale2;
1787
+ var _ref60, _ref61, _ref62, _ref63, _ref64, _ref65, _value$locale2;
1536
1788
  if (value === undefined || value === null) return '';
1537
1789
  if (_typeof(value) !== 'object') return stringify(value);
1538
1790
  var dashedLocale = locale.replace('_', '-');
1539
1791
  var underscoredLocale = locale.replace('-', '_');
1540
- return stringify((_ref50 = (_ref51 = (_ref52 = (_ref53 = (_ref54 = (_ref55 = (_value$locale2 = value[locale]) !== null && _value$locale2 !== void 0 ? _value$locale2 : value[dashedLocale]) !== null && _ref55 !== void 0 ? _ref55 : value[underscoredLocale]) !== null && _ref54 !== void 0 ? _ref54 : value.original) !== null && _ref53 !== void 0 ? _ref53 : value.auto) !== null && _ref52 !== void 0 ? _ref52 : value.default) !== null && _ref51 !== void 0 ? _ref51 : value.en) !== null && _ref50 !== void 0 ? _ref50 : '');
1792
+ return stringify((_ref60 = (_ref61 = (_ref62 = (_ref63 = (_ref64 = (_ref65 = (_value$locale2 = value[locale]) !== null && _value$locale2 !== void 0 ? _value$locale2 : value[dashedLocale]) !== null && _ref65 !== void 0 ? _ref65 : value[underscoredLocale]) !== null && _ref64 !== void 0 ? _ref64 : value.original) !== null && _ref63 !== void 0 ? _ref63 : value.auto) !== null && _ref62 !== void 0 ? _ref62 : value.default) !== null && _ref61 !== void 0 ? _ref61 : value.en) !== null && _ref60 !== void 0 ? _ref60 : '');
1541
1793
  }
1542
1794
  function resolveServiceTypeLabelKey(serviceType, order) {
1543
1795
  var normalized = serviceType.trim().toLowerCase().replace(/[\s-]+/g, '_');
@@ -326,7 +326,7 @@ export declare class BookingByStepImpl extends BaseModule implements Module {
326
326
  date: string;
327
327
  status: string;
328
328
  week: string;
329
- weekNum: 0 | 1 | 2 | 5 | 4 | 3 | 6;
329
+ weekNum: 0 | 1 | 2 | 3 | 4 | 5 | 6;
330
330
  }[]>;
331
331
  submitTimeSlot(timeSlots: TimeSliceItem): void;
332
332
  private getScheduleDataByIds;
@@ -28,6 +28,8 @@ export interface SmallTicketItem {
28
28
  value: string;
29
29
  size?: number;
30
30
  align?: string;
31
+ product_uid?: string | number;
32
+ booking_uid?: string | number;
31
33
  }
32
34
  export interface SmallTicketProduct {
33
35
  product_title: string;
@@ -53,11 +55,7 @@ export interface SmallTicketProduct {
53
55
  variant?: string;
54
56
  combinations?: any[];
55
57
  }
56
- export interface SmallTicketBookingSnapshot extends Record<string, any> {
57
- product_uid?: string | number;
58
- booking_uid?: string | number;
59
- }
60
- export type SmallTicketAppointment = SmallTicketItem[] | SmallTicketBookingSnapshot[];
58
+ export type SmallTicketAppointment = SmallTicketItem[];
61
59
  export interface SmallTicketLocaleData {
62
60
  base_data: Record<string, any>;
63
61
  products: SmallTicketProduct[];
@@ -33,8 +33,13 @@ const LABELS = {
33
33
  redeemPoints: 'Redeem points',
34
34
  remainingPoints: 'Points balance',
35
35
  table: 'Table',
36
+ bookingId: 'Booking ID',
37
+ bookingDateTime: 'Date & time',
38
+ bookingResource: 'Resource',
39
+ bookingHolder: 'Holder',
36
40
  orderDiscount: 'Order discount',
37
41
  manualDiscount: 'Manual discount',
42
+ manualMarkup: 'Manual markup',
38
43
  payProcessingFee: 'Pay processing fee',
39
44
  surchargeIncluded: 'Surcharge(Included)',
40
45
  rounding: 'Rounding',
@@ -66,8 +71,13 @@ const LABELS = {
66
71
  redeemPoints: '本次使用积分',
67
72
  remainingPoints: '积分余额',
68
73
  table: '桌台',
74
+ bookingId: '预约编号',
75
+ bookingDateTime: '日期和时间',
76
+ bookingResource: '资源',
77
+ bookingHolder: '预约人',
69
78
  orderDiscount: '整单折扣',
70
79
  manualDiscount: '手动折扣',
80
+ manualMarkup: '手动加价',
71
81
  payProcessingFee: '支付手续费',
72
82
  surchargeIncluded: '手续费(已含)',
73
83
  rounding: '抹零',
@@ -99,8 +109,13 @@ const LABELS = {
99
109
  redeemPoints: '本次使用積分',
100
110
  remainingPoints: '積分餘額',
101
111
  table: '桌台',
112
+ bookingId: '預約編號',
113
+ bookingDateTime: '日期和時間',
114
+ bookingResource: '資源',
115
+ bookingHolder: '預約人',
102
116
  orderDiscount: '整單折扣',
103
117
  manualDiscount: '手動折扣',
118
+ manualMarkup: '手動加價',
104
119
  payProcessingFee: '支付手續費',
105
120
  surchargeIncluded: '手續費(已含)',
106
121
  rounding: '抹零',
@@ -130,8 +145,13 @@ const LABELS = {
130
145
  redeemPoints: '利用ポイント',
131
146
  remainingPoints: 'ポイント残高',
132
147
  table: 'テーブル',
148
+ bookingId: '予約ID',
149
+ bookingDateTime: '日時',
150
+ bookingResource: 'リソース',
151
+ bookingHolder: '予約者',
133
152
  orderDiscount: '注文割引',
134
153
  manualDiscount: '手動割引',
154
+ manualMarkup: '手動値上げ',
135
155
  payProcessingFee: '決済手数料',
136
156
  rounding: '端数調整',
137
157
  gross: '総重量',
@@ -162,8 +182,13 @@ const LABELS = {
162
182
  redeemPoints: 'Pontos utilizados',
163
183
  remainingPoints: 'Saldo de pontos',
164
184
  table: 'Mesa',
185
+ bookingId: 'ID da reserva',
186
+ bookingDateTime: 'Data e hora',
187
+ bookingResource: 'Recurso',
188
+ bookingHolder: 'Titular',
165
189
  orderDiscount: 'Desconto do pedido',
166
190
  manualDiscount: 'Desconto manual',
191
+ manualMarkup: 'Acréscimo manual',
167
192
  payProcessingFee: 'Taxa de processamento',
168
193
  rounding: 'Arredondamento',
169
194
  gross: 'Peso bruto',
@@ -281,7 +306,8 @@ function buildBaseData(params) {
281
306
  }
282
307
  function buildProducts(order, locale, productMap) {
283
308
  const products = Array.isArray(order.products) ? order.products : [];
284
- return products.map(product => {
309
+ return products.map(rawProduct => {
310
+ const product = restoreReceiptDiscountHierarchy(rawProduct);
285
311
  const quantity = toNumber(product.product_quantity ?? product.quantity ?? product.num ?? 1, 1);
286
312
  const originalPrice = product.original_price ?? product.selling_price ?? product.payment_price ?? product.price ?? 0;
287
313
  const sellingPrice = product.selling_price ?? product.payment_price ?? product.price ?? originalPrice;
@@ -361,6 +387,73 @@ function buildProducts(order, locale, productMap) {
361
387
  };
362
388
  });
363
389
  }
390
+ const RECEIPT_BUNDLE_MAP_ID_KEY = 'custom_product_bundle_map_id';
391
+ function restoreReceiptDiscountHierarchy(source) {
392
+ if (!source || typeof source !== 'object' || Array.isArray(source)) {
393
+ return source;
394
+ }
395
+ const childKey = Array.isArray(source.combinations) && source.combinations.length ? 'combinations' : Array.isArray(source.product_bundle) && source.product_bundle.length ? 'product_bundle' : null;
396
+ if (!childKey) return {
397
+ ...source
398
+ };
399
+ const children = source[childKey].map(child => child && typeof child === 'object' && !Array.isArray(child) ? restoreReceiptDiscountHierarchy(child) : child);
400
+ const restored = {
401
+ ...source,
402
+ [childKey]: children
403
+ };
404
+ if (!Array.isArray(source.discount_list) || !source.discount_list.length) {
405
+ return restored;
406
+ }
407
+ const descendantsByMapId = new Map();
408
+ indexReceiptDiscountTargets(children, descendantsByMapId);
409
+ if (!descendantsByMapId.size) return restored;
410
+ const ownDiscounts = [];
411
+ for (const discount of source.discount_list) {
412
+ const mapId = getReceiptDiscountBundleMapId(discount);
413
+ const target = mapId ? descendantsByMapId.get(mapId) : undefined;
414
+ if (!target) {
415
+ ownDiscounts.push(discount);
416
+ continue;
417
+ }
418
+ const targetDiscounts = Array.isArray(target.discount_list) ? target.discount_list : [];
419
+ if (!targetDiscounts.some(item => isSameReceiptDiscount(item, discount))) {
420
+ target.discount_list = [...targetDiscounts, discount];
421
+ }
422
+ }
423
+ restored.discount_list = ownDiscounts;
424
+ return restored;
425
+ }
426
+ function indexReceiptDiscountTargets(nodes, targets) {
427
+ for (const node of nodes) {
428
+ if (!node || typeof node !== 'object' || Array.isArray(node)) continue;
429
+ const mapId = getReceiptBundleMapId(node);
430
+ if (mapId && !targets.has(mapId)) targets.set(mapId, node);
431
+ const children = Array.isArray(node.combinations) && node.combinations.length ? node.combinations : Array.isArray(node.product_bundle) ? node.product_bundle : [];
432
+ indexReceiptDiscountTargets(children, targets);
433
+ }
434
+ }
435
+ function normalizeReceiptId(value) {
436
+ if (value === undefined || value === null) return null;
437
+ const normalized = String(value).trim();
438
+ return normalized ? normalized : null;
439
+ }
440
+ function getReceiptBundleMapId(node) {
441
+ return normalizeReceiptId(node.metadata?.[RECEIPT_BUNDLE_MAP_ID_KEY] ?? node._id);
442
+ }
443
+ function getReceiptDiscountBundleMapId(discount) {
444
+ return normalizeReceiptId(discount?.metadata?.[RECEIPT_BUNDLE_MAP_ID_KEY]);
445
+ }
446
+ function isSameReceiptDiscount(left, right) {
447
+ const leftOrderDiscountId = normalizeReceiptId(left?.order_discount_id);
448
+ const rightOrderDiscountId = normalizeReceiptId(right?.order_discount_id);
449
+ if (leftOrderDiscountId && rightOrderDiscountId) {
450
+ return leftOrderDiscountId === rightOrderDiscountId;
451
+ }
452
+ const leftResourceId = normalizeReceiptId(left?.discount?.resource_id ?? left?.resource_id ?? left?.discount_id);
453
+ const rightResourceId = normalizeReceiptId(right?.discount?.resource_id ?? right?.resource_id ?? right?.discount_id);
454
+ if (!leftResourceId || !rightResourceId) return false;
455
+ return leftResourceId === rightResourceId && getReceiptDiscountBundleMapId(left) === getReceiptDiscountBundleMapId(right) && String(left?.amount ?? left?.value ?? left?.discount_amount ?? '') === String(right?.amount ?? right?.value ?? right?.discount_amount ?? '');
456
+ }
364
457
  function resolveProductBasePrice(product) {
365
458
  const metadata = product.metadata || {};
366
459
  const origin = product._origin || metadata.origin || {};
@@ -376,18 +469,31 @@ function normalizeProductDiscounts(params) {
376
469
  currencySymbol,
377
470
  quantity
378
471
  } = params;
379
- return normalizeArray(product.discount_list).filter(discount => {
472
+ const rows = normalizeArray(product.discount_list).filter(discount => {
380
473
  const amount = discount.amount ?? discount.value ?? discount.discount_amount;
381
474
  return isNonZero(amount);
382
475
  }).map(discount => {
383
476
  const title = resolveDiscountTitleWithPercent(discount, locale);
384
477
  const amount = discount.amount ?? discount.value ?? discount.discount_amount;
385
- const formattedAmount = formatNegativeMoney(new _decimal.default(toMoneyNumber(amount)).mul(quantity), currencySymbol);
478
+ const isMarkup = isManualMarkup(discount);
479
+ const totalAmount = new _decimal.default(toMoneyNumber(amount)).mul(quantity);
480
+ const formattedAmount = isMarkup ? formatMoney(totalAmount.abs(), currencySymbol) : formatNegativeMoney(totalAmount, currencySymbol);
386
481
  return {
387
482
  item: title,
388
- value: formattedAmount
483
+ value: formattedAmount,
484
+ isMarkup
389
485
  };
390
486
  });
487
+ return rows.sort((left, right) => Number(right.isMarkup) - Number(left.isMarkup)).map(({
488
+ isMarkup: _isMarkup,
489
+ ...row
490
+ }) => row);
491
+ }
492
+ function isManualMarkup(discount) {
493
+ if (discount.type !== 'product') return false;
494
+ if (discount.discount?.discount_type === 'change_price') return true;
495
+ const amount = discount.amount ?? discount.value ?? discount.discount_amount;
496
+ return new _decimal.default(toMoneyNumber(amount)).isNegative();
391
497
  }
392
498
  function hasProductDiscount(product, extensionList = []) {
393
499
  const hasDiscountListAmount = normalizeArray(product.discount_list).some(discount => isNonZero(discount.amount ?? discount.value ?? discount.discount_amount));
@@ -474,7 +580,9 @@ function resolveDiscountTitleWithPercent(discount, locale) {
474
580
  function resolveDiscountTitle(discount, locale) {
475
581
  const title = getLocalizedValue(discount.discount?.name ?? discount.discount?.title ?? discount.discount?.message ?? discount.name ?? discount.title ?? discount.message, locale);
476
582
  if (title) return title;
477
- if (discount.type === 'product') return label(locale, 'manualDiscount');
583
+ if (discount.type === 'product') {
584
+ return label(locale, isManualMarkup(discount) ? 'manualMarkup' : 'manualDiscount');
585
+ }
478
586
  return '';
479
587
  }
480
588
  function resolveProductTitle(params) {
@@ -552,7 +660,14 @@ function normalizeProductCombinations(params) {
552
660
  const optionsTotal = sumNormalizedOptionTotals(combinationsOptions, currencySymbol);
553
661
  const explicitBasePrice = firstPresentValue(bundle.base_price, bundle.metadata?.source_product_price);
554
662
  const basePrice = isPresentId(explicitBasePrice) ? explicitBasePrice : 0;
555
- const shouldIncludeBasePrice = combinationsOptions.length > 0 || nestedCombinations.length > 0 || hasProductDiscount(bundle);
663
+ const extensionList = buildProductExtensionList({
664
+ product: bundle,
665
+ locale,
666
+ currencySymbol,
667
+ quantity,
668
+ originalPrice: formattedPrice
669
+ });
670
+ const shouldIncludeBasePrice = combinationsOptions.length > 0 || nestedCombinations.length > 0 || hasProductDiscount(bundle, extensionList);
556
671
  return {
557
672
  product_title: baseTitle,
558
673
  product_quantity: quantity,
@@ -571,6 +686,9 @@ function normalizeProductCombinations(params) {
571
686
  ...(productNote ? {
572
687
  product_note: productNote
573
688
  } : {}),
689
+ ...(extensionList.length ? {
690
+ extension_list: extensionList
691
+ } : {}),
574
692
  ...(nestedCombinations.length ? {
575
693
  combinations: nestedCombinations
576
694
  } : {})
@@ -597,12 +715,20 @@ function normalizeExistingCombinations(combinations, locale, currencySymbol) {
597
715
  delete snapshot.product_note;
598
716
  delete snapshot.note;
599
717
  delete snapshot.combinations;
718
+ delete snapshot.discount_list;
600
719
  const quantity = toNumber(combination.product_quantity ?? combination.num ?? combination.quantity ?? 1, 1);
601
720
  const unitPrice = firstPresentValue(combination.selling_price, combination.price, combination.original_price) ?? 0;
602
721
  const optionsAmount = sumMoneyValues(normalizedOptions.map(option => option.total_price));
603
722
  const explicitBasePrice = firstPresentValue(combination.base_price);
604
723
  const basePrice = isPresentId(explicitBasePrice) ? explicitBasePrice : 0;
605
- const shouldIncludeBasePrice = normalizedOptions.length > 0 || nestedCombinations.length > 0 || hasProductDiscount(combination, normalizeArray(combination.extension_list));
724
+ const extensionList = buildProductExtensionList({
725
+ product: combination,
726
+ locale,
727
+ currencySymbol,
728
+ quantity,
729
+ originalPrice: unitPrice
730
+ });
731
+ const shouldIncludeBasePrice = normalizedOptions.length > 0 || nestedCombinations.length > 0 || hasProductDiscount(combination, extensionList);
606
732
  return {
607
733
  ...snapshot,
608
734
  product_quantity: quantity,
@@ -624,6 +750,9 @@ function normalizeExistingCombinations(combinations, locale, currencySymbol) {
624
750
  ...(productNote ? {
625
751
  product_note: productNote
626
752
  } : {}),
753
+ ...(extensionList.length ? {
754
+ extension_list: extensionList
755
+ } : {}),
627
756
  ...(nestedCombinations.length ? {
628
757
  combinations: nestedCombinations
629
758
  } : {})
@@ -998,24 +1127,13 @@ function buildDelivery(order, locale) {
998
1127
  function buildAppointment(order, locale) {
999
1128
  const bookings = sortBookings(normalizeArray(order.bookings));
1000
1129
  if (bookings.length) {
1001
- return bookings.map(booking => {
1002
- const snapshot = {
1003
- ...booking
1004
- };
1005
- delete snapshot.product_uid;
1006
- delete snapshot.booking_uid;
1007
- const productUid = firstPresentValue(booking.product_uid, booking.metadata?.product_uid);
1008
- const bookingUid = firstPresentValue(booking.metadata?.unique_identification_number, booking.booking_uid);
1009
- return {
1010
- ...snapshot,
1011
- ...(isPresentId(productUid) ? {
1012
- product_uid: productUid
1013
- } : {}),
1014
- ...(isPresentId(bookingUid) ? {
1015
- booking_uid: bookingUid
1016
- } : {})
1017
- };
1018
- });
1130
+ const allResources = normalizeArray(order.resources || order.resource_list);
1131
+ return bookings.flatMap(booking => buildAppointmentRows({
1132
+ booking,
1133
+ allResources,
1134
+ bookingCount: bookings.length,
1135
+ locale
1136
+ }));
1019
1137
  }
1020
1138
  const tableName = order.table_name || order.metadata?.table_name || order.metadata?.table?.name || order.form_data?.table_name;
1021
1139
  if (!tableName) return [];
@@ -1024,6 +1142,82 @@ function buildAppointment(order, locale) {
1024
1142
  value: getLocalizedValue(tableName, locale)
1025
1143
  }];
1026
1144
  }
1145
+ function buildAppointmentRows(params) {
1146
+ const {
1147
+ booking,
1148
+ allResources,
1149
+ bookingCount,
1150
+ locale
1151
+ } = params;
1152
+ const productUid = stringify(firstPresentValue(booking.product_uid, booking.metadata?.product_uid)).trim();
1153
+ const bookingUid = stringify(firstPresentValue(booking.metadata?.unique_identification_number, booking.booking_uid)).trim();
1154
+ const association = {
1155
+ product_uid: productUid,
1156
+ booking_uid: bookingUid
1157
+ };
1158
+ const bookingId = stringify(firstPresentValue(booking.booking_id, booking.schedule_event_id, bookingUid)).trim();
1159
+ const bookingTime = formatBookingRange(booking, locale);
1160
+ const resourceText = formatBookingResources(resolveBookingResourcesForReceipt(booking, allResources, bookingCount), locale);
1161
+ const holder = getLocalizedValue(booking.holder?.name ?? booking.metadata?.holder?.name, locale).trim();
1162
+ return [{
1163
+ item: label(locale, 'bookingId'),
1164
+ value: bookingId,
1165
+ ...association
1166
+ }, {
1167
+ item: label(locale, 'bookingDateTime'),
1168
+ value: bookingTime,
1169
+ ...association
1170
+ }, {
1171
+ item: label(locale, 'bookingResource'),
1172
+ value: resourceText,
1173
+ ...association
1174
+ }, {
1175
+ item: label(locale, 'bookingHolder'),
1176
+ value: holder,
1177
+ ...association
1178
+ }].filter(row => Boolean(row.value));
1179
+ }
1180
+ function formatBookingRange(booking, locale) {
1181
+ const startDate = stringify(booking.start_date);
1182
+ const startTime = stringify(booking.start_time);
1183
+ const endDate = stringify(booking.end_date || startDate);
1184
+ const endTime = stringify(booking.end_time);
1185
+ const start = firstValidBookingDate(booking.start_at, booking.start_datetime, booking.start_date_time, `${startDate} ${startTime}`.trim());
1186
+ const end = firstValidBookingDate(booking.end_at, booking.end_datetime, booking.end_date_time, endTime ? `${endDate} ${endTime}`.trim() : '');
1187
+ if (!start) {
1188
+ return [startDate, startTime, endTime ? `- ${endDate} ${endTime}` : ''].filter(Boolean).join(' ');
1189
+ }
1190
+ const dateFormat = locale === 'en' ? 'DD/MM/YYYY' : 'YYYY/MM/DD';
1191
+ const startText = start.format(`${dateFormat} HH:mm`);
1192
+ if (!end) return startText;
1193
+ return `${startText} - ${end.isSame(start, 'day') ? end.format('HH:mm') : end.format(`${dateFormat} HH:mm`)}`;
1194
+ }
1195
+ function firstValidBookingDate(...values) {
1196
+ for (const value of values) {
1197
+ if (!isPresentId(value)) continue;
1198
+ const parsed = (0, _dayjs.default)(value);
1199
+ if (parsed.isValid()) return parsed;
1200
+ }
1201
+ return null;
1202
+ }
1203
+ function resolveBookingResourcesForReceipt(booking, allResources, bookingCount) {
1204
+ const embedded = normalizeArray(booking.resources).filter(resource => Boolean(resource) && typeof resource === 'object' && !Array.isArray(resource));
1205
+ const resourceIds = new Set([booking.resource_id, booking.relation_id, ...normalizeArray(booking.resource_ids), ...normalizeArray(booking.metadata?.resource_ids)].map(value => stringify(value).trim()).filter(Boolean));
1206
+ for (const resource of embedded) {
1207
+ const id = stringify(resource.id ?? resource.resource_id ?? resource.relation_id).trim();
1208
+ if (id) resourceIds.add(id);
1209
+ }
1210
+ if (resourceIds.size) {
1211
+ const matched = allResources.filter(resource => resourceIds.has(stringify(resource.id ?? resource.resource_id ?? resource.relation_id).trim()));
1212
+ if (matched.length) return matched;
1213
+ }
1214
+ if (embedded.length) return embedded;
1215
+ if (bookingCount === 1 && allResources.length) return allResources;
1216
+ return [];
1217
+ }
1218
+ function formatBookingResources(resources, locale) {
1219
+ return resources.map(resource => [getLocalizedValue(resource.form_title || resource.metadata?.form_name || resource.relation_form_name || resource.metadata?.relation_form_name, locale), getLocalizedValue(resource.title || resource.name || resource.main_field || resource.metadata?.main_field || resource.metadata?.resource_name, locale)].filter(Boolean).join(' ')).filter(Boolean).join(', ');
1220
+ }
1027
1221
  function sortBookings(bookings) {
1028
1222
  return bookings.map((booking, index) => ({
1029
1223
  booking,
@@ -326,7 +326,7 @@ export declare class BookingByStepImpl extends BaseModule implements Module {
326
326
  date: string;
327
327
  status: string;
328
328
  week: string;
329
- weekNum: 0 | 1 | 2 | 5 | 4 | 3 | 6;
329
+ weekNum: 0 | 1 | 2 | 3 | 4 | 5 | 6;
330
330
  }[]>;
331
331
  submitTimeSlot(timeSlots: TimeSliceItem): void;
332
332
  private getScheduleDataByIds;
package/package.json CHANGED
@@ -1,7 +1,7 @@
1
1
  {
2
2
  "private": false,
3
3
  "name": "@pisell/pisellos",
4
- "version": "0.10.36",
4
+ "version": "0.10.37",
5
5
  "description": "一个可扩展的前端模块化SDK框架,支持插件系统",
6
6
  "main": "dist/index.js",
7
7
  "types": "dist/index.d.ts",