@pisell/pisellos 2.2.202 → 2.2.204

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.
@@ -612,6 +612,8 @@ export interface OrderModuleAPI {
612
612
  updateOrderProductQuantity: (params: UpdateOrderProductQuantityParams) => Promise<OrderProduct[]>;
613
613
  updateOrderBooking: (params: UpdateOrderBookingParams) => any[];
614
614
  removeProductFromOrder: (identity: OrderProductIdentity) => Promise<OrderProduct[]>;
615
+ /** 批量删除购物车行,末尾仅触发一次促销重算与 summary 刷新 */
616
+ removeProductsFromOrder: (identities: OrderProductIdentity[]) => Promise<OrderProduct[]>;
615
617
  /** @deprecated no-op;OrderModule 不再负责 tempOrder localStorage 持久化。 */
616
618
  persistTempOrder: () => void;
617
619
  /**
@@ -245,6 +245,13 @@ export declare class BaseSalesImpl extends BaseModule implements Module {
245
245
  * 多行同 SKU 时必须传入与删除/更新一致的 unique_identification_number。
246
246
  */
247
247
  setOrderProductLineNote(identity: BaseSalesOrderProductIdentity, note: string): Promise<import("../../modules/Order/types").OrderProduct[]>;
248
+ /**
249
+ * 批量删除购物车行,末尾仅一次促销重算。
250
+ *
251
+ * @example
252
+ * await baseSales.removeProductsFromOrder([identityA, identityB]);
253
+ */
254
+ removeProductsFromOrder(identities: BaseSalesOrderProductIdentity[]): Promise<import("../../modules/Order/types").OrderProduct[]>;
248
255
  removeProductFromOrder(identity: BaseSalesOrderProductIdentity): Promise<import("../../modules/Order/types").OrderProduct[]>;
249
256
  /**
250
257
  * 注入促销评估器到底层 OrderModule。
@@ -1836,9 +1836,8 @@ export var BaseSalesImpl = /*#__PURE__*/function (_BaseModule) {
1836
1836
  } : {}), (params === null || params === void 0 ? void 0 : params.enhancePayload) !== undefined ? {
1837
1837
  enhancePayload: params.enhancePayload
1838
1838
  } : {});
1839
- console.log(submitParams, 'submitParams123');
1840
1839
  return _context18.abrupt("return", this.store.order.submitTempOrder(submitParams));
1841
- case 7:
1840
+ case 6:
1842
1841
  case "end":
1843
1842
  return _context18.stop();
1844
1843
  }
@@ -2497,12 +2496,18 @@ export var BaseSalesImpl = /*#__PURE__*/function (_BaseModule) {
2497
2496
  return _setOrderProductLineNote.apply(this, arguments);
2498
2497
  }
2499
2498
  return setOrderProductLineNote;
2500
- }())
2499
+ }()
2500
+ /**
2501
+ * 批量删除购物车行,末尾仅一次促销重算。
2502
+ *
2503
+ * @example
2504
+ * await baseSales.removeProductsFromOrder([identityA, identityB]);
2505
+ */
2506
+ )
2501
2507
  }, {
2502
- key: "removeProductFromOrder",
2503
- value: function () {
2504
- var _removeProductFromOrder = _asyncToGenerator( /*#__PURE__*/_regeneratorRuntime().mark(function _callee28(identity) {
2505
- var products;
2508
+ key: "removeProductsFromOrder",
2509
+ value: (function () {
2510
+ var _removeProductsFromOrder = _asyncToGenerator( /*#__PURE__*/_regeneratorRuntime().mark(function _callee28(identities) {
2506
2511
  return _regeneratorRuntime().wrap(function _callee28$(_context28) {
2507
2512
  while (1) switch (_context28.prev = _context28.next) {
2508
2513
  case 0:
@@ -2514,21 +2519,39 @@ export var BaseSalesImpl = /*#__PURE__*/function (_BaseModule) {
2514
2519
  throw new Error('order 模块未初始化');
2515
2520
  case 3:
2516
2521
  _context28.next = 5;
2517
- return this.store.order.removeProductFromOrder(identity);
2522
+ return this.store.order.removeProductsFromOrder(identities);
2518
2523
  case 5:
2519
- products = _context28.sent;
2520
- return _context28.abrupt("return", products);
2521
- case 9:
2522
- _context28.prev = 9;
2524
+ return _context28.abrupt("return", _context28.sent);
2525
+ case 8:
2526
+ _context28.prev = 8;
2523
2527
  _context28.t0 = _context28["catch"](0);
2524
2528
  throw _context28.t0;
2525
- case 12:
2529
+ case 11:
2526
2530
  case "end":
2527
2531
  return _context28.stop();
2528
2532
  }
2529
- }, _callee28, this, [[0, 9]]);
2533
+ }, _callee28, this, [[0, 8]]);
2534
+ }));
2535
+ function removeProductsFromOrder(_x25) {
2536
+ return _removeProductsFromOrder.apply(this, arguments);
2537
+ }
2538
+ return removeProductsFromOrder;
2539
+ }())
2540
+ }, {
2541
+ key: "removeProductFromOrder",
2542
+ value: function () {
2543
+ var _removeProductFromOrder = _asyncToGenerator( /*#__PURE__*/_regeneratorRuntime().mark(function _callee29(identity) {
2544
+ return _regeneratorRuntime().wrap(function _callee29$(_context29) {
2545
+ while (1) switch (_context29.prev = _context29.next) {
2546
+ case 0:
2547
+ return _context29.abrupt("return", this.removeProductsFromOrder([identity]));
2548
+ case 1:
2549
+ case "end":
2550
+ return _context29.stop();
2551
+ }
2552
+ }, _callee29, this);
2530
2553
  }));
2531
- function removeProductFromOrder(_x25) {
2554
+ function removeProductFromOrder(_x26) {
2532
2555
  return _removeProductFromOrder.apply(this, arguments);
2533
2556
  }
2534
2557
  return removeProductFromOrder;
@@ -2578,23 +2601,23 @@ export var BaseSalesImpl = /*#__PURE__*/function (_BaseModule) {
2578
2601
  }, {
2579
2602
  key: "applyPromotion",
2580
2603
  value: (function () {
2581
- var _applyPromotion = _asyncToGenerator( /*#__PURE__*/_regeneratorRuntime().mark(function _callee29() {
2582
- return _regeneratorRuntime().wrap(function _callee29$(_context29) {
2583
- while (1) switch (_context29.prev = _context29.next) {
2604
+ var _applyPromotion = _asyncToGenerator( /*#__PURE__*/_regeneratorRuntime().mark(function _callee30() {
2605
+ return _regeneratorRuntime().wrap(function _callee30$(_context30) {
2606
+ while (1) switch (_context30.prev = _context30.next) {
2584
2607
  case 0:
2585
2608
  if (this.store.order) {
2586
- _context29.next = 2;
2609
+ _context30.next = 2;
2587
2610
  break;
2588
2611
  }
2589
2612
  throw new Error('order 模块未初始化');
2590
2613
  case 2:
2591
- _context29.next = 4;
2614
+ _context30.next = 4;
2592
2615
  return this.store.order.applyPromotion();
2593
2616
  case 4:
2594
2617
  case "end":
2595
- return _context29.stop();
2618
+ return _context30.stop();
2596
2619
  }
2597
- }, _callee29, this);
2620
+ }, _callee30, this);
2598
2621
  }));
2599
2622
  function applyPromotion() {
2600
2623
  return _applyPromotion.apply(this, arguments);
@@ -2621,18 +2644,18 @@ export var BaseSalesImpl = /*#__PURE__*/function (_BaseModule) {
2621
2644
  }, {
2622
2645
  key: "getProductList",
2623
2646
  value: function () {
2624
- var _getProductList = _asyncToGenerator( /*#__PURE__*/_regeneratorRuntime().mark(function _callee30() {
2647
+ var _getProductList = _asyncToGenerator( /*#__PURE__*/_regeneratorRuntime().mark(function _callee31() {
2625
2648
  var _this$otherParams13;
2626
2649
  var menu_list_ids, _this$store$products, res;
2627
- return _regeneratorRuntime().wrap(function _callee30$(_context30) {
2628
- while (1) switch (_context30.prev = _context30.next) {
2650
+ return _regeneratorRuntime().wrap(function _callee31$(_context31) {
2651
+ while (1) switch (_context31.prev = _context31.next) {
2629
2652
  case 0:
2630
2653
  // 可以直接通过配置里的 menu 读取
2631
2654
  menu_list_ids = ((_this$otherParams13 = this.otherParams) === null || _this$otherParams13 === void 0 || (_this$otherParams13 = _this$otherParams13.dineInConfig) === null || _this$otherParams13 === void 0 ? void 0 : _this$otherParams13['menu.associated_menus'].map(function (n) {
2632
2655
  return Number(n.value);
2633
2656
  })) || [];
2634
- _context30.prev = 1;
2635
- _context30.next = 4;
2657
+ _context31.prev = 1;
2658
+ _context31.next = 4;
2636
2659
  return (_this$store$products = this.store.products) === null || _this$store$products === void 0 ? void 0 : _this$store$products.loadProducts({
2637
2660
  menu_list_ids: menu_list_ids,
2638
2661
  cacheId: this.cacheId,
@@ -2640,17 +2663,17 @@ export var BaseSalesImpl = /*#__PURE__*/function (_BaseModule) {
2640
2663
  schedule_datetime: dayjs().format('YYYY-MM-DD HH:mm:ss')
2641
2664
  });
2642
2665
  case 4:
2643
- res = _context30.sent;
2644
- return _context30.abrupt("return", res);
2666
+ res = _context31.sent;
2667
+ return _context31.abrupt("return", res);
2645
2668
  case 8:
2646
- _context30.prev = 8;
2647
- _context30.t0 = _context30["catch"](1);
2648
- throw _context30.t0;
2669
+ _context31.prev = 8;
2670
+ _context31.t0 = _context31["catch"](1);
2671
+ throw _context31.t0;
2649
2672
  case 11:
2650
2673
  case "end":
2651
- return _context30.stop();
2674
+ return _context31.stop();
2652
2675
  }
2653
- }, _callee30, this, [[1, 8]]);
2676
+ }, _callee31, this, [[1, 8]]);
2654
2677
  }));
2655
2678
  function getProductList() {
2656
2679
  return _getProductList.apply(this, arguments);
@@ -2665,15 +2688,15 @@ export var BaseSalesImpl = /*#__PURE__*/function (_BaseModule) {
2665
2688
  }, {
2666
2689
  key: "setOtherParams",
2667
2690
  value: function () {
2668
- var _setOtherParams = _asyncToGenerator( /*#__PURE__*/_regeneratorRuntime().mark(function _callee31(params) {
2691
+ var _setOtherParams = _asyncToGenerator( /*#__PURE__*/_regeneratorRuntime().mark(function _callee32(params) {
2669
2692
  var _ref14,
2670
2693
  _ref14$cover,
2671
2694
  cover,
2672
- _args31 = arguments;
2673
- return _regeneratorRuntime().wrap(function _callee31$(_context31) {
2674
- while (1) switch (_context31.prev = _context31.next) {
2695
+ _args32 = arguments;
2696
+ return _regeneratorRuntime().wrap(function _callee32$(_context32) {
2697
+ while (1) switch (_context32.prev = _context32.next) {
2675
2698
  case 0:
2676
- _ref14 = _args31.length > 1 && _args31[1] !== undefined ? _args31[1] : {}, _ref14$cover = _ref14.cover, cover = _ref14$cover === void 0 ? false : _ref14$cover;
2699
+ _ref14 = _args32.length > 1 && _args32[1] !== undefined ? _args32[1] : {}, _ref14$cover = _ref14.cover, cover = _ref14$cover === void 0 ? false : _ref14$cover;
2677
2700
  if (cover) {
2678
2701
  this.otherParams = params;
2679
2702
  } else {
@@ -2681,11 +2704,11 @@ export var BaseSalesImpl = /*#__PURE__*/function (_BaseModule) {
2681
2704
  }
2682
2705
  case 2:
2683
2706
  case "end":
2684
- return _context31.stop();
2707
+ return _context32.stop();
2685
2708
  }
2686
- }, _callee31, this);
2709
+ }, _callee32, this);
2687
2710
  }));
2688
- function setOtherParams(_x26) {
2711
+ function setOtherParams(_x27) {
2689
2712
  return _setOtherParams.apply(this, arguments);
2690
2713
  }
2691
2714
  return setOtherParams;
@@ -311,7 +311,7 @@ export declare class BookingByStepImpl extends BaseModule implements Module {
311
311
  date: string;
312
312
  status: string;
313
313
  week: string;
314
- weekNum: 0 | 2 | 1 | 6 | 3 | 4 | 5;
314
+ weekNum: 0 | 2 | 1 | 5 | 3 | 4 | 6;
315
315
  }[]>;
316
316
  submitTimeSlot(timeSlots: TimeSliceItem): void;
317
317
  private getScheduleDataByIds;
@@ -1,49 +0,0 @@
1
- var __create = Object.create;
2
- var __defProp = Object.defineProperty;
3
- var __getOwnPropDesc = Object.getOwnPropertyDescriptor;
4
- var __getOwnPropNames = Object.getOwnPropertyNames;
5
- var __getProtoOf = Object.getPrototypeOf;
6
- var __hasOwnProp = Object.prototype.hasOwnProperty;
7
- var __export = (target, all) => {
8
- for (var name in all)
9
- __defProp(target, name, { get: all[name], enumerable: true });
10
- };
11
- var __copyProps = (to, from, except, desc) => {
12
- if (from && typeof from === "object" || typeof from === "function") {
13
- for (let key of __getOwnPropNames(from))
14
- if (!__hasOwnProp.call(to, key) && key !== except)
15
- __defProp(to, key, { get: () => from[key], enumerable: !(desc = __getOwnPropDesc(from, key)) || desc.enumerable });
16
- }
17
- return to;
18
- };
19
- var __toESM = (mod, isNodeMode, target) => (target = mod != null ? __create(__getProtoOf(mod)) : {}, __copyProps(
20
- // If the importer is in node compatibility mode or this is not an ESM
21
- // file that has been converted to a CommonJS file using a Babel-
22
- // compatible transform (i.e. "__esModule" has not been set), then set
23
- // "default" to the CommonJS "module.exports" for node compatibility.
24
- isNodeMode || !mod || !mod.__esModule ? __defProp(target, "default", { value: mod, enumerable: true }) : target,
25
- mod
26
- ));
27
- var __toCommonJS = (mod) => __copyProps(__defProp({}, "__esModule", { value: true }), mod);
28
-
29
- // src/model/strategy/adapter/promotion/index.ts
30
- var promotion_exports = {};
31
- __export(promotion_exports, {
32
- BUY_X_GET_Y_FREE_STRATEGY: () => import_examples.BUY_X_GET_Y_FREE_STRATEGY,
33
- PromotionAdapter: () => import_adapter.PromotionAdapter,
34
- PromotionEvaluator: () => import_evaluator.PromotionEvaluator,
35
- X_ITEMS_FOR_Y_PRICE_STRATEGY: () => import_examples.X_ITEMS_FOR_Y_PRICE_STRATEGY,
36
- default: () => import_adapter2.default
37
- });
38
- module.exports = __toCommonJS(promotion_exports);
39
- var import_evaluator = require("./evaluator");
40
- var import_adapter = require("./adapter");
41
- var import_adapter2 = __toESM(require("./adapter"));
42
- var import_examples = require("./examples");
43
- // Annotate the CommonJS export names for ESM import in node:
44
- 0 && (module.exports = {
45
- BUY_X_GET_Y_FREE_STRATEGY,
46
- PromotionAdapter,
47
- PromotionEvaluator,
48
- X_ITEMS_FOR_Y_PRICE_STRATEGY
49
- });
@@ -250,6 +250,28 @@ export declare class OrderModule extends BaseModule implements Module, OrderModu
250
250
  */
251
251
  updateVoucherOrderPayments(payments: OrderPaymentSource[]): OrderPaymentData[];
252
252
  private shouldMergeProductToOrder;
253
+ /**
254
+ * 预约商品加车后的统一收尾:促销、折扣、summary 重算与持久化(批量拆行时只调用一次)。
255
+ *
256
+ * @example
257
+ * await this.finalizeProductOrderMutation(tempOrder);
258
+ */
259
+ private finalizeProductOrderMutation;
260
+ /**
261
+ * 向 tempOrder 追加一条商品行(及可选 booking),不触发 summary 重算。
262
+ * 带 booking 且 num>1 时由 `addProductToOrder` 拆成多次本方法调用(每次 num=1)。
263
+ *
264
+ * @example
265
+ * await this.appendProductLineToTempOrder(tempOrder, { product_id: 1, num: 1 }, booking);
266
+ */
267
+ private appendProductLineToTempOrder;
268
+ /**
269
+ * 添加商品行。带 booking 时强制独立行;num>1 时拆成多条 num=1 的 product+booking(对齐 BookingByStep / ticketBooking addService)。
270
+ *
271
+ * @example
272
+ * await order.addProductToOrder({ product_id: 1, num: 3 }, { start_time: '10:00' });
273
+ * // → tempOrder.products 新增 3 行,每行 num=1,bookings 3 条
274
+ */
253
275
  addProductToOrder(product: Partial<OrderProduct> & OrderProductIdentity, booking?: AddProductBookingInput): Promise<OrderProduct[]>;
254
276
  private hasGoodPassDiscount;
255
277
  private getBundleRuntimeIdentity;
@@ -257,6 +279,21 @@ export declare class OrderModule extends BaseModule implements Module, OrderModu
257
279
  updateOrderProduct(params: UpdateOrderProductParams): Promise<OrderProduct[]>;
258
280
  updateOrderProductQuantity(params: UpdateOrderProductQuantityParams): Promise<OrderProduct[]>;
259
281
  updateOrderBooking(params: UpdateOrderBookingParams): any[];
282
+ /**
283
+ * 商品行写路径收尾:促销 → 折扣 → 清洗 → summary → 持久化。
284
+ * 批量删除等多行变更场景只应调用一次,避免 N 次 applyPromotion。
285
+ *
286
+ * @example
287
+ * await this.finalizeAfterProductsMutation(tempOrder);
288
+ */
289
+ private finalizeAfterProductsMutation;
290
+ /**
291
+ * 批量按 identity 删除购物车行,末尾仅一次促销重算。
292
+ *
293
+ * @example
294
+ * await order.removeProductsFromOrder([identityA, identityB]);
295
+ */
296
+ removeProductsFromOrder(identities: OrderProductIdentity[]): Promise<OrderProduct[]>;
260
297
  removeProductFromOrder(identity: OrderProductIdentity): Promise<OrderProduct[]>;
261
298
  /**
262
299
  * 仅清空购物车行(products / bookings),不重置整单。
@@ -287,7 +324,7 @@ export declare class OrderModule extends BaseModule implements Module, OrderModu
287
324
  private logSubmitBackendRejected;
288
325
  syncPaymentsToOrder<T = any>(params: SyncPaymentsToOrderParams): Promise<SyncPaymentsToOrderResult<T>>;
289
326
  createOrder(params: CommitOrderParams['query']): {
290
- type: "virtual" | "appointment_booking";
327
+ type: "appointment_booking" | "virtual";
291
328
  platform: string;
292
329
  sales_channel: string;
293
330
  order_sales_channel: string;
@@ -518,13 +518,16 @@ var OrderModule = class extends import_BaseModule.BaseModule {
518
518
  * - 不主动调用 applyDiscount / recalculateSummary,调用方负责跟进。
519
519
  */
520
520
  async applyPromotion() {
521
- if (this.isApplyingPromotion)
521
+ if (this.isApplyingPromotion) {
522
522
  return;
523
- if (!this.promotionEvaluator)
523
+ }
524
+ if (!this.promotionEvaluator) {
524
525
  return;
526
+ }
525
527
  const tempOrder = this.store.tempOrder;
526
- if (!tempOrder)
528
+ if (!tempOrder) {
527
529
  return;
530
+ }
528
531
  this.isApplyingPromotion = true;
529
532
  try {
530
533
  const result = (0, import_cartPromotion.processCartPromotion)(
@@ -1915,7 +1918,7 @@ var OrderModule = class extends import_BaseModule.BaseModule {
1915
1918
  };
1916
1919
  const mappedVouchers = (0, import_utils.mapPaymentItemsToOrderPayments)(
1917
1920
  payments.map(
1918
- (payment) => this.normalizePaymentSource(payment, { defaultPaid: false })
1921
+ (payment) => this.normalizePaymentSource(payment, { defaultPaid: true })
1919
1922
  )
1920
1923
  ).filter((payment) => {
1921
1924
  return isVoucherPayment(payment);
@@ -1968,9 +1971,29 @@ var OrderModule = class extends import_BaseModule.BaseModule {
1968
1971
  return true;
1969
1972
  }
1970
1973
  // ─── TempOrder: 商品 CRUD ───
1971
- async addProductToOrder(product, booking) {
1974
+ /**
1975
+ * 预约商品加车后的统一收尾:促销、折扣、summary 重算与持久化(批量拆行时只调用一次)。
1976
+ *
1977
+ * @example
1978
+ * await this.finalizeProductOrderMutation(tempOrder);
1979
+ */
1980
+ async finalizeProductOrderMutation(tempOrder) {
1981
+ await this.ensureEditDiscountConfigForProductChange(tempOrder);
1982
+ await this.applyPromotion();
1983
+ this.applyDiscount();
1984
+ this.sanitizeTempOrderProducts(tempOrder);
1985
+ await this.recalculateSummary({ createIfMissing: true });
1986
+ this.persistTempOrder();
1987
+ }
1988
+ /**
1989
+ * 向 tempOrder 追加一条商品行(及可选 booking),不触发 summary 重算。
1990
+ * 带 booking 且 num>1 时由 `addProductToOrder` 拆成多次本方法调用(每次 num=1)。
1991
+ *
1992
+ * @example
1993
+ * await this.appendProductLineToTempOrder(tempOrder, { product_id: 1, num: 1 }, booking);
1994
+ */
1995
+ async appendProductLineToTempOrder(tempOrder, product, booking) {
1972
1996
  var _a;
1973
- const tempOrder = this.ensureTempOrder();
1974
1997
  const linked = booking ? this.createLinkedProductAndBooking({ product, booking }) : null;
1975
1998
  const productToAdd = (linked == null ? void 0 : linked.product) || product;
1976
1999
  const incomingFingerprint = (0, import_utils3.buildProductLineFingerprint)(
@@ -2092,12 +2115,38 @@ var OrderModule = class extends import_BaseModule.BaseModule {
2092
2115
  if (linked) {
2093
2116
  tempOrder.bookings = [...tempOrder.bookings || [], linked.booking];
2094
2117
  }
2095
- await this.ensureEditDiscountConfigForProductChange(tempOrder);
2096
- await this.applyPromotion();
2097
- this.applyDiscount();
2098
- this.sanitizeTempOrderProducts(tempOrder);
2099
- await this.recalculateSummary({ createIfMissing: true });
2100
- this.persistTempOrder();
2118
+ }
2119
+ /**
2120
+ * 添加商品行。带 booking 时强制独立行;num>1 时拆成多条 num=1 的 product+booking(对齐 BookingByStep / ticketBooking addService)。
2121
+ *
2122
+ * @example
2123
+ * await order.addProductToOrder({ product_id: 1, num: 3 }, { start_time: '10:00' });
2124
+ * // → tempOrder.products 新增 3 行,每行 num=1,bookings 3 条
2125
+ */
2126
+ async addProductToOrder(product, booking) {
2127
+ const tempOrder = this.ensureTempOrder();
2128
+ if (booking) {
2129
+ const productRecord = product;
2130
+ const splitCount = (0, import_utils3.getSafeProductNum)(
2131
+ productRecord.num ?? productRecord.product_quantity ?? 1
2132
+ );
2133
+ if (splitCount > 1) {
2134
+ for (let i = 0; i < splitCount; i += 1) {
2135
+ const singleLine = (0, import_lodash_es.cloneDeep)(productRecord);
2136
+ singleLine.num = 1;
2137
+ delete singleLine.product_quantity;
2138
+ await this.appendProductLineToTempOrder(
2139
+ tempOrder,
2140
+ singleLine,
2141
+ (0, import_lodash_es.cloneDeep)(booking)
2142
+ );
2143
+ }
2144
+ await this.finalizeProductOrderMutation(tempOrder);
2145
+ return tempOrder.products;
2146
+ }
2147
+ }
2148
+ await this.appendProductLineToTempOrder(tempOrder, product, booking);
2149
+ await this.finalizeProductOrderMutation(tempOrder);
2101
2150
  return tempOrder.products;
2102
2151
  }
2103
2152
  hasGoodPassDiscount(product) {
@@ -2395,11 +2444,34 @@ var OrderModule = class extends import_BaseModule.BaseModule {
2395
2444
  this.persistTempOrder();
2396
2445
  return tempOrder.bookings;
2397
2446
  }
2398
- async removeProductFromOrder(identity) {
2447
+ /**
2448
+ * 商品行写路径收尾:促销 → 折扣 → 清洗 → summary → 持久化。
2449
+ * 批量删除等多行变更场景只应调用一次,避免 N 次 applyPromotion。
2450
+ *
2451
+ * @example
2452
+ * await this.finalizeAfterProductsMutation(tempOrder);
2453
+ */
2454
+ async finalizeAfterProductsMutation(tempOrder) {
2455
+ await this.applyPromotion();
2456
+ this.applyDiscount();
2457
+ this.sanitizeTempOrderProducts(tempOrder);
2458
+ await this.recalculateSummary({ createIfMissing: true });
2459
+ this.persistTempOrder();
2460
+ }
2461
+ /**
2462
+ * 批量按 identity 删除购物车行,末尾仅一次促销重算。
2463
+ *
2464
+ * @example
2465
+ * await order.removeProductsFromOrder([identityA, identityB]);
2466
+ */
2467
+ async removeProductsFromOrder(identities) {
2399
2468
  const tempOrder = this.ensureTempOrder();
2469
+ if (!identities.length) {
2470
+ return tempOrder.products;
2471
+ }
2400
2472
  const removedProducts = [];
2401
2473
  tempOrder.products = tempOrder.products.filter((item) => {
2402
- const shouldRemove = (0, import_utils3.isIdentityMatch)(item, identity);
2474
+ const shouldRemove = identities.some((identity) => (0, import_utils3.isIdentityMatch)(item, identity));
2403
2475
  if (shouldRemove)
2404
2476
  removedProducts.push(item);
2405
2477
  return !shouldRemove;
@@ -2407,13 +2479,12 @@ var OrderModule = class extends import_BaseModule.BaseModule {
2407
2479
  for (const product of removedProducts) {
2408
2480
  this.removeLinkedBookingsForProduct(tempOrder, product);
2409
2481
  }
2410
- await this.applyPromotion();
2411
- this.applyDiscount();
2412
- this.sanitizeTempOrderProducts(tempOrder);
2413
- await this.recalculateSummary({ createIfMissing: true });
2414
- this.persistTempOrder();
2482
+ await this.finalizeAfterProductsMutation(tempOrder);
2415
2483
  return tempOrder.products;
2416
2484
  }
2485
+ async removeProductFromOrder(identity) {
2486
+ return this.removeProductsFromOrder([identity]);
2487
+ }
2417
2488
  /**
2418
2489
  * 仅清空购物车行(products / bookings),不重置整单。
2419
2490
  * 用于「仅清空商品」;客户、备注、支付等协议字段保持不变。
@@ -612,6 +612,8 @@ export interface OrderModuleAPI {
612
612
  updateOrderProductQuantity: (params: UpdateOrderProductQuantityParams) => Promise<OrderProduct[]>;
613
613
  updateOrderBooking: (params: UpdateOrderBookingParams) => any[];
614
614
  removeProductFromOrder: (identity: OrderProductIdentity) => Promise<OrderProduct[]>;
615
+ /** 批量删除购物车行,末尾仅触发一次促销重算与 summary 刷新 */
616
+ removeProductsFromOrder: (identities: OrderProductIdentity[]) => Promise<OrderProduct[]>;
615
617
  /** @deprecated no-op;OrderModule 不再负责 tempOrder localStorage 持久化。 */
616
618
  persistTempOrder: () => void;
617
619
  /**
@@ -245,6 +245,13 @@ export declare class BaseSalesImpl extends BaseModule implements Module {
245
245
  * 多行同 SKU 时必须传入与删除/更新一致的 unique_identification_number。
246
246
  */
247
247
  setOrderProductLineNote(identity: BaseSalesOrderProductIdentity, note: string): Promise<import("../../modules/Order/types").OrderProduct[]>;
248
+ /**
249
+ * 批量删除购物车行,末尾仅一次促销重算。
250
+ *
251
+ * @example
252
+ * await baseSales.removeProductsFromOrder([identityA, identityB]);
253
+ */
254
+ removeProductsFromOrder(identities: BaseSalesOrderProductIdentity[]): Promise<import("../../modules/Order/types").OrderProduct[]>;
248
255
  removeProductFromOrder(identity: BaseSalesOrderProductIdentity): Promise<import("../../modules/Order/types").OrderProduct[]>;
249
256
  /**
250
257
  * 注入促销评估器到底层 OrderModule。
@@ -1162,7 +1162,6 @@ var BaseSalesImpl = class extends import_BaseModule.BaseModule {
1162
1162
  ...(params == null ? void 0 : params.smallTicketDataFlag) !== void 0 ? { smallTicketDataFlag: params.smallTicketDataFlag } : {},
1163
1163
  ...(params == null ? void 0 : params.enhancePayload) !== void 0 ? { enhancePayload: params.enhancePayload } : {}
1164
1164
  };
1165
- console.log(submitParams, "submitParams123");
1166
1165
  return this.store.order.submitTempOrder(submitParams);
1167
1166
  }
1168
1167
  getSubmitPaymentStatus(paymentStatus) {
@@ -1550,16 +1549,24 @@ var BaseSalesImpl = class extends import_BaseModule.BaseModule {
1550
1549
  throw error;
1551
1550
  }
1552
1551
  }
1553
- async removeProductFromOrder(identity) {
1552
+ /**
1553
+ * 批量删除购物车行,末尾仅一次促销重算。
1554
+ *
1555
+ * @example
1556
+ * await baseSales.removeProductsFromOrder([identityA, identityB]);
1557
+ */
1558
+ async removeProductsFromOrder(identities) {
1554
1559
  try {
1555
1560
  if (!this.store.order)
1556
1561
  throw new Error("order 模块未初始化");
1557
- const products = await this.store.order.removeProductFromOrder(identity);
1558
- return products;
1562
+ return await this.store.order.removeProductsFromOrder(identities);
1559
1563
  } catch (error) {
1560
1564
  throw error;
1561
1565
  }
1562
1566
  }
1567
+ async removeProductFromOrder(identity) {
1568
+ return this.removeProductsFromOrder([identity]);
1569
+ }
1563
1570
  // ─── 促销/赠品 透传(迁移自 booking usePromotion) ────────────────
1564
1571
  /**
1565
1572
  * 注入促销评估器到底层 OrderModule。
@@ -311,7 +311,7 @@ export declare class BookingByStepImpl extends BaseModule implements Module {
311
311
  date: string;
312
312
  status: string;
313
313
  week: string;
314
- weekNum: 0 | 2 | 1 | 6 | 3 | 4 | 5;
314
+ weekNum: 0 | 2 | 1 | 5 | 3 | 4 | 6;
315
315
  }[]>;
316
316
  submitTimeSlot(timeSlots: TimeSliceItem): void;
317
317
  private getScheduleDataByIds;
package/package.json CHANGED
@@ -1,7 +1,7 @@
1
1
  {
2
2
  "private": false,
3
3
  "name": "@pisell/pisellos",
4
- "version": "2.2.202",
4
+ "version": "2.2.204",
5
5
  "description": "一个可扩展的前端模块化SDK框架,支持插件系统",
6
6
  "main": "dist/index.js",
7
7
  "types": "dist/index.d.ts",