@pisell/pisellos 2.3.51 → 2.3.54
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.
- package/dist/modules/BookingContext/utils/buildCacheItemFromOrderLine.js +12 -10
- package/dist/modules/Order/index.d.ts +6 -6
- package/dist/modules/Order/index.js +140 -86
- package/dist/modules/Order/types.d.ts +21 -3
- package/dist/modules/Order/types.js +11 -0
- package/dist/modules/ProductList/index.js +1 -1
- package/dist/modules/Rules/index.js +19 -9
- package/dist/modules/SalesSummary/utils.js +7 -1
- package/dist/solution/BaseSales/index.d.ts +15 -5
- package/dist/solution/BaseSales/index.js +173 -135
- package/dist/solution/BaseSales/utils/cartPromotion.js +5 -3
- package/dist/solution/BookingByStep/index.d.ts +1 -1
- package/dist/solution/BookingTicket/types.d.ts +3 -0
- package/dist/solution/BookingTicket/utils/cartView.js +44 -32
- package/dist/solution/Sales/index.d.ts +1 -0
- package/dist/solution/Sales/index.js +16 -2
- package/dist/solution/UnifiedBookingSales/index.d.ts +0 -4
- package/dist/solution/UnifiedBookingSales/index.js +27 -26
- package/lib/model/strategy/adapter/promotion/index.js +0 -51
- package/lib/modules/BookingContext/utils/buildCacheItemFromOrderLine.js +3 -1
- package/lib/modules/Order/index.d.ts +6 -6
- package/lib/modules/Order/index.js +79 -12
- package/lib/modules/Order/types.d.ts +21 -3
- package/lib/modules/ProductList/index.js +9 -1
- package/lib/modules/Rules/index.js +16 -11
- package/lib/modules/SalesSummary/utils.js +5 -1
- package/lib/solution/BaseSales/index.d.ts +15 -5
- package/lib/solution/BaseSales/index.js +44 -11
- package/lib/solution/BaseSales/utils/cartPromotion.js +5 -2
- package/lib/solution/BookingByStep/index.d.ts +1 -1
- package/lib/solution/BookingTicket/types.d.ts +3 -0
- package/lib/solution/BookingTicket/utils/cartView.js +43 -30
- package/lib/solution/Sales/index.d.ts +1 -0
- package/lib/solution/Sales/index.js +15 -3
- package/lib/solution/UnifiedBookingSales/index.d.ts +0 -4
- package/lib/solution/UnifiedBookingSales/index.js +27 -26
- package/package.json +1 -1
|
@@ -468,11 +468,13 @@ function getProductLineNoteSignature(product) {
|
|
|
468
468
|
}
|
|
469
469
|
|
|
470
470
|
/**
|
|
471
|
-
*
|
|
472
|
-
* 以历史行 uid 作为促销前后的行边界;新增行返回空边界,仍保留原有合并语义。
|
|
471
|
+
* 称重行以及编辑订单历史行都有各自的促销合并边界。
|
|
473
472
|
*/
|
|
474
473
|
function getPromotionLineMergeBoundary(product) {
|
|
475
|
-
var _product$metadata3;
|
|
474
|
+
var _product$product_sku, _product$metadata3;
|
|
475
|
+
if (Number((product === null || product === void 0 || (_product$product_sku = product.product_sku) === null || _product$product_sku === void 0 ? void 0 : _product$product_sku.open_sold_weight) || 0) === 1) {
|
|
476
|
+
return "weighing:".concat(getOrderProductUid(product));
|
|
477
|
+
}
|
|
476
478
|
if ((product === null || product === void 0 || (_product$metadata3 = product.metadata) === null || _product$metadata3 === void 0 ? void 0 : _product$metadata3.is_edit_for_runtime) !== true) return '';
|
|
477
479
|
return "edit:".concat(getOrderProductUid(product));
|
|
478
480
|
}
|
|
@@ -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 |
|
|
329
|
+
weekNum: 0 | 5 | 2 | 1 | 6 | 4 | 3;
|
|
330
330
|
}[]>;
|
|
331
331
|
submitTimeSlot(timeSlots: TimeSliceItem): void;
|
|
332
332
|
private getScheduleDataByIds;
|
|
@@ -118,12 +118,15 @@ export interface BookingTicketCartBookingView extends ISalesBooking {
|
|
|
118
118
|
canAddTime: boolean;
|
|
119
119
|
};
|
|
120
120
|
}
|
|
121
|
+
export type BookingTicketCartLineView = BookingTicketCartBookingView | BookingTicketCartItemView;
|
|
121
122
|
/**
|
|
122
123
|
* BookingTicket 面向 UI 的购物车视图。
|
|
123
124
|
*/
|
|
124
125
|
export interface BookingTicketCartView {
|
|
125
126
|
bookings: BookingTicketCartBookingView[];
|
|
126
127
|
items: BookingTicketCartItemView[];
|
|
128
|
+
/** 以 tempOrder.products 为唯一顺序真源的统一购物车行(旧到新)。 */
|
|
129
|
+
lines: BookingTicketCartLineView[];
|
|
127
130
|
}
|
|
128
131
|
/**
|
|
129
132
|
* BookingTicket 面向 UI 的客户展示视图。
|
|
@@ -108,33 +108,28 @@ export function buildCartView(lines, bookings) {
|
|
|
108
108
|
var options = arguments.length > 2 && arguments[2] !== undefined ? arguments[2] : {};
|
|
109
109
|
var productLines = Array.isArray(lines) ? lines : [];
|
|
110
110
|
var bookingList = Array.isArray(bookings) ? bookings : [];
|
|
111
|
+
var childBookings = bookingList.filter(function (booking) {
|
|
112
|
+
return booking.parent_id !== 0;
|
|
113
|
+
});
|
|
114
|
+
var bookingsByProductUid = indexBookingsByProductUid(childBookings);
|
|
111
115
|
var linesByUid = indexProductsByUid(productLines);
|
|
112
116
|
var addTimeLinesByBookingUid = indexAddTimeProductsByBookingUid(productLines);
|
|
113
|
-
var claimedUids = new Set();
|
|
114
117
|
var claimedAddTimeLines = new Set();
|
|
115
|
-
|
|
116
|
-
return booking.parent_id !== 0;
|
|
117
|
-
}).reduce(function (acc, booking) {
|
|
118
|
-
var uid = booking === null || booking === void 0 ? void 0 : booking.product_uid;
|
|
118
|
+
childBookings.forEach(function (booking) {
|
|
119
119
|
var bookingUid = getBookingUid(booking);
|
|
120
|
-
|
|
121
|
-
|
|
122
|
-
|
|
123
|
-
if (!claimedUids.has(key)) {
|
|
124
|
-
var line = linesByUid[key];
|
|
125
|
-
// 赠品预约只作为提交数据保留,不在购物车顶部预约卡片区展示。
|
|
126
|
-
if (isGiftProductLine(line)) return acc;
|
|
127
|
-
if (line) {
|
|
128
|
-
claimedUids.add(key);
|
|
129
|
-
product = line;
|
|
130
|
-
}
|
|
131
|
-
}
|
|
132
|
-
}
|
|
133
|
-
var addTimeProduct = bookingUid ? addTimeLinesByBookingUid[bookingUid] || [] : [];
|
|
134
|
-
addTimeProduct.forEach(function (line) {
|
|
135
|
-
return claimedAddTimeLines.add(line);
|
|
120
|
+
if (!bookingUid) return;
|
|
121
|
+
(addTimeLinesByBookingUid[bookingUid] || []).forEach(function (line) {
|
|
122
|
+
claimedAddTimeLines.add(line);
|
|
136
123
|
});
|
|
137
|
-
|
|
124
|
+
});
|
|
125
|
+
var claimedBookings = new Set();
|
|
126
|
+
var cartBookings = [];
|
|
127
|
+
var items = [];
|
|
128
|
+
var orderedLines = [];
|
|
129
|
+
var buildBookingView = function buildBookingView(booking, product) {
|
|
130
|
+
var bookingUid = getBookingUid(booking);
|
|
131
|
+
var addTimeProduct = bookingUid ? addTimeLinesByBookingUid[bookingUid] || [] : [];
|
|
132
|
+
return _objectSpread(_objectSpread({}, booking), {}, {
|
|
138
133
|
_extend: {
|
|
139
134
|
product: product,
|
|
140
135
|
addTimeProduct: addTimeProduct,
|
|
@@ -147,21 +142,38 @@ export function buildCartView(lines, bookings) {
|
|
|
147
142
|
shopOpeningHours: options.shopOpeningHours
|
|
148
143
|
})
|
|
149
144
|
}
|
|
150
|
-
})
|
|
151
|
-
|
|
152
|
-
|
|
153
|
-
var items = productLines.filter(function (line) {
|
|
145
|
+
});
|
|
146
|
+
};
|
|
147
|
+
productLines.forEach(function (line) {
|
|
154
148
|
var _line$metadata6;
|
|
155
|
-
//
|
|
156
|
-
if (isGiftProductLine(line)) return
|
|
157
|
-
if (claimedAddTimeLines.has(line)) return false;
|
|
149
|
+
// 赠品由主商品 Gift 行展示;加时商品挂在 booking._extend.addTimeProduct。
|
|
150
|
+
if (isGiftProductLine(line) || claimedAddTimeLines.has(line)) return;
|
|
158
151
|
var uid = (_line$metadata6 = line.metadata) === null || _line$metadata6 === void 0 ? void 0 : _line$metadata6.unique_identification_number;
|
|
159
|
-
|
|
160
|
-
|
|
152
|
+
var matchedBooking = uid === undefined || uid === null || uid === '' ? undefined : (bookingsByProductUid[String(uid)] || []).find(function (booking) {
|
|
153
|
+
return !claimedBookings.has(booking);
|
|
154
|
+
});
|
|
155
|
+
if (matchedBooking) {
|
|
156
|
+
claimedBookings.add(matchedBooking);
|
|
157
|
+
var bookingView = buildBookingView(matchedBooking, line);
|
|
158
|
+
cartBookings.push(bookingView);
|
|
159
|
+
orderedLines.push(bookingView);
|
|
160
|
+
return;
|
|
161
|
+
}
|
|
162
|
+
items.push(line);
|
|
163
|
+
orderedLines.push(line);
|
|
164
|
+
});
|
|
165
|
+
childBookings.forEach(function (booking) {
|
|
166
|
+
if (claimedBookings.has(booking)) return;
|
|
167
|
+
var uid = booking === null || booking === void 0 ? void 0 : booking.product_uid;
|
|
168
|
+
var linkedProduct = uid === undefined || uid === null || uid === '' ? null : linesByUid[String(uid)] || null;
|
|
169
|
+
// 赠品预约只作为提交数据保留,不在购物车预约卡片区展示。
|
|
170
|
+
if (isGiftProductLine(linkedProduct)) return;
|
|
171
|
+
cartBookings.push(buildBookingView(booking, null));
|
|
161
172
|
});
|
|
162
173
|
return {
|
|
163
174
|
bookings: cartBookings,
|
|
164
|
-
items: items
|
|
175
|
+
items: items,
|
|
176
|
+
lines: orderedLines
|
|
165
177
|
};
|
|
166
178
|
}
|
|
167
179
|
export function isWalkInCustomer(customer) {
|
|
@@ -95,6 +95,7 @@ export declare class SalesImpl extends BaseModule implements Module, SalesModule
|
|
|
95
95
|
* 2) 若无 active,返回已超时且仍占用中的预约(允许并发多条)
|
|
96
96
|
* 3) 若仍无,返回最近一组未来预约(同 start_time 的并发预约全部返回)
|
|
97
97
|
* 4) 最后兜底返回一条(避免资源有历史预约时完全无反馈)
|
|
98
|
+
* - includeAllFuture 时,保留选中预约并返回当天全部后续预约;仅详情接口启用。
|
|
98
99
|
*/
|
|
99
100
|
private pickBookingsForCurrentPoint;
|
|
100
101
|
/**
|
|
@@ -485,11 +485,13 @@ export var SalesImpl = /*#__PURE__*/function (_BaseModule) {
|
|
|
485
485
|
* 2) 若无 active,返回已超时且仍占用中的预约(允许并发多条)
|
|
486
486
|
* 3) 若仍无,返回最近一组未来预约(同 start_time 的并发预约全部返回)
|
|
487
487
|
* 4) 最后兜底返回一条(避免资源有历史预约时完全无反馈)
|
|
488
|
+
* - includeAllFuture 时,保留选中预约并返回当天全部后续预约;仅详情接口启用。
|
|
488
489
|
*/
|
|
489
490
|
}, {
|
|
490
491
|
key: "pickBookingsForCurrentPoint",
|
|
491
492
|
value: function pickBookingsForCurrentPoint(current, bookings) {
|
|
492
493
|
var _this4 = this;
|
|
494
|
+
var options = arguments.length > 2 && arguments[2] !== undefined ? arguments[2] : {};
|
|
493
495
|
if (bookings.length === 0) return [];
|
|
494
496
|
var currentDayStart = current.startOf('day');
|
|
495
497
|
var currentDayEnd = current.endOf('day');
|
|
@@ -504,6 +506,13 @@ export var SalesImpl = /*#__PURE__*/function (_BaseModule) {
|
|
|
504
506
|
if (dayScopedBookings.length === 0) return [];
|
|
505
507
|
var appendNextStartGroupIfNeeded = function appendNextStartGroupIfNeeded(selectedBookings) {
|
|
506
508
|
if (selectedBookings.length === 0) return selectedBookings;
|
|
509
|
+
if (options.includeAllFuture) {
|
|
510
|
+
var allFutureBookings = dayScopedBookings.filter(function (booking) {
|
|
511
|
+
var startAt = _this4.toBookingDateTime(booking.start_date, booking.start_time);
|
|
512
|
+
return startAt.isValid() && startAt.isAfter(current);
|
|
513
|
+
});
|
|
514
|
+
return [].concat(_toConsumableArray(selectedBookings), _toConsumableArray(allFutureBookings));
|
|
515
|
+
}
|
|
507
516
|
var shouldAppendNextGroup = selectedBookings.some(function (booking) {
|
|
508
517
|
return booking.status === 'reserved' || booking.status === 'occupied';
|
|
509
518
|
});
|
|
@@ -554,6 +563,7 @@ export var SalesImpl = /*#__PURE__*/function (_BaseModule) {
|
|
|
554
563
|
return startAt.isValid() && startAt.isAfter(current) && startAt.isSame(current, 'day');
|
|
555
564
|
});
|
|
556
565
|
if (upcoming.length > 0) {
|
|
566
|
+
if (options.includeAllFuture) return upcoming;
|
|
557
567
|
var firstStartAt = this.toBookingDateTime(upcoming[0].start_date, upcoming[0].start_time).valueOf();
|
|
558
568
|
var upcomingStartGroup = upcoming.filter(function (booking) {
|
|
559
569
|
var startAt = _this4.toBookingDateTime(booking.start_date, booking.start_time);
|
|
@@ -907,7 +917,9 @@ export var SalesImpl = /*#__PURE__*/function (_BaseModule) {
|
|
|
907
917
|
unpaidBookingList = matchedBookingList.filter(function (booking) {
|
|
908
918
|
return _this7.isUnpaidBooking(booking);
|
|
909
919
|
});
|
|
910
|
-
bookings = this.pickBookingsForCurrentPoint(current, this.normalizeResourceBookings(current, deviceCurrent, matchedBookingList)
|
|
920
|
+
bookings = this.pickBookingsForCurrentPoint(current, this.normalizeResourceBookings(current, deviceCurrent, matchedBookingList), {
|
|
921
|
+
includeAllFuture: true
|
|
922
|
+
});
|
|
911
923
|
completedBookings = completedBookingList.map(function (booking) {
|
|
912
924
|
return _objectSpread(_objectSpread({}, booking), {}, {
|
|
913
925
|
status: 'compelete',
|
|
@@ -919,7 +931,9 @@ export var SalesImpl = /*#__PURE__*/function (_BaseModule) {
|
|
|
919
931
|
remainingReserveTime: undefined
|
|
920
932
|
});
|
|
921
933
|
});
|
|
922
|
-
unpaidBookings = this.pickBookingsForCurrentPoint(current, this.normalizeResourceBookings(current, deviceCurrent, unpaidBookingList)
|
|
934
|
+
unpaidBookings = this.pickBookingsForCurrentPoint(current, this.normalizeResourceBookings(current, deviceCurrent, unpaidBookingList), {
|
|
935
|
+
includeAllFuture: true
|
|
936
|
+
});
|
|
923
937
|
orderCount = this.countBookingOrders(statsBookingList);
|
|
924
938
|
bookingCount = statsBookingList.length;
|
|
925
939
|
compeleteBookingCount = this.countCompletedBookings(statsBookingList);
|
|
@@ -102,10 +102,6 @@ export declare class UnifiedBookingSalesImpl extends BookingTicket {
|
|
|
102
102
|
* Read-only compatibility view for salesSdk skins. It reconnects a booking to its product but
|
|
103
103
|
* must not be used to mutate tempOrder; all writes go through BaseSales / planner APIs.
|
|
104
104
|
*/
|
|
105
|
-
getCart(): {
|
|
106
|
-
items: any[];
|
|
107
|
-
bookings: any[];
|
|
108
|
-
};
|
|
109
105
|
/**
|
|
110
106
|
* Loads the current customer's product coupons and discount cards after planner lines exist,
|
|
111
107
|
* then optionally lets the existing Rules engine select the best valid combination. This is a
|
|
@@ -880,32 +880,33 @@ export var UnifiedBookingSalesImpl = /*#__PURE__*/function (_BookingTicket) {
|
|
|
880
880
|
* Read-only compatibility view for salesSdk skins. It reconnects a booking to its product but
|
|
881
881
|
* must not be used to mutate tempOrder; all writes go through BaseSales / planner APIs.
|
|
882
882
|
*/
|
|
883
|
-
|
|
884
|
-
|
|
885
|
-
|
|
886
|
-
|
|
887
|
-
|
|
888
|
-
|
|
889
|
-
|
|
890
|
-
|
|
891
|
-
|
|
892
|
-
|
|
893
|
-
|
|
894
|
-
|
|
895
|
-
|
|
896
|
-
|
|
897
|
-
|
|
898
|
-
|
|
899
|
-
|
|
900
|
-
|
|
901
|
-
|
|
902
|
-
|
|
903
|
-
|
|
904
|
-
|
|
905
|
-
|
|
906
|
-
|
|
907
|
-
|
|
908
|
-
}
|
|
883
|
+
// getCart(): BookingTicketCartView {
|
|
884
|
+
// const tempOrder = this.getTempOrder();
|
|
885
|
+
// const salesDetail = this.getSalesOrder();
|
|
886
|
+
// const items = tempOrder?.products || [];
|
|
887
|
+
// const bookings = salesDetail?.bookings || tempOrder?.bookings || [];
|
|
888
|
+
// return {
|
|
889
|
+
// items,
|
|
890
|
+
// bookings: bookings.map((booking: any) => {
|
|
891
|
+
// const productUid = booking?.product_uid;
|
|
892
|
+
// const product = productUid
|
|
893
|
+
// ? items.find((item: any) => {
|
|
894
|
+
// const uid = item?.metadata?.unique_identification_number || item?.unique_identification_number;
|
|
895
|
+
// return String(uid || '') === String(productUid);
|
|
896
|
+
// }) || null
|
|
897
|
+
// : null;
|
|
898
|
+
// return {
|
|
899
|
+
// ...booking,
|
|
900
|
+
// _extend: {
|
|
901
|
+
// ...(booking?._extend || {}),
|
|
902
|
+
// product,
|
|
903
|
+
// addTimeProduct: [],
|
|
904
|
+
// canAddTime: false,
|
|
905
|
+
// },
|
|
906
|
+
// };
|
|
907
|
+
// }),
|
|
908
|
+
// };
|
|
909
|
+
// }
|
|
909
910
|
|
|
910
911
|
/**
|
|
911
912
|
* Loads the current customer's product coupons and discount cards after planner lines exist,
|
|
@@ -1,51 +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
|
-
ITEM_REWARD_STRATEGY: () => import_examples.ITEM_REWARD_STRATEGY,
|
|
34
|
-
PromotionAdapter: () => import_adapter.PromotionAdapter,
|
|
35
|
-
PromotionEvaluator: () => import_evaluator.PromotionEvaluator,
|
|
36
|
-
X_ITEMS_FOR_Y_PRICE_STRATEGY: () => import_examples.X_ITEMS_FOR_Y_PRICE_STRATEGY,
|
|
37
|
-
default: () => import_adapter2.default
|
|
38
|
-
});
|
|
39
|
-
module.exports = __toCommonJS(promotion_exports);
|
|
40
|
-
var import_evaluator = require("./evaluator");
|
|
41
|
-
var import_adapter = require("./adapter");
|
|
42
|
-
var import_adapter2 = __toESM(require("./adapter"));
|
|
43
|
-
var import_examples = require("./examples");
|
|
44
|
-
// Annotate the CommonJS export names for ESM import in node:
|
|
45
|
-
0 && (module.exports = {
|
|
46
|
-
BUY_X_GET_Y_FREE_STRATEGY,
|
|
47
|
-
ITEM_REWARD_STRATEGY,
|
|
48
|
-
PromotionAdapter,
|
|
49
|
-
PromotionEvaluator,
|
|
50
|
-
X_ITEMS_FOR_Y_PRICE_STRATEGY
|
|
51
|
-
});
|
|
@@ -149,7 +149,9 @@ function mapOrderBundleToOtherBundle(bundle) {
|
|
|
149
149
|
return bundle.map((item) => {
|
|
150
150
|
return {
|
|
151
151
|
...item,
|
|
152
|
-
|
|
152
|
+
// 后端历史订单可能没有 original_price;此时 price 是折前毛价,
|
|
153
|
+
// bundle_selling_price 已包含折扣,不能把它当成编辑时的新原价。
|
|
154
|
+
original_price: item.original_price ?? item.product_price ?? item.price ?? item.bundle_selling_price
|
|
153
155
|
};
|
|
154
156
|
});
|
|
155
157
|
}
|
|
@@ -3,7 +3,7 @@ import { BaseModule } from '../BaseModule';
|
|
|
3
3
|
import { OrderModuleAPI, CommitOrderParams, UpdateOrderBookingParams, UpdateOrderProductParams, UpdateOrderProductQuantityParams, CancelOrderParams, ChangeBookingStatusParams, CheckoutOrderParams } from './types';
|
|
4
4
|
import { CartItem } from '../Cart/types';
|
|
5
5
|
import { type SubmitPayloadEnhancer } from './utils';
|
|
6
|
-
import type { OrderAmountSnapshot, AddProductBookingInput, OrderIdentitySnapshot, OrderPaymentSource, OrderSnapshot, OrderSyncState, SyncPaymentsToOrderParams, SyncPaymentsToOrderResult, SubmitSalesOrderParams, OrderProduct, OrderProductIdentity, OrderSummary, OrderTempOrder, OrderPaymentData, OrderPaymentUpdateOptions, OrderPaymentUpdateResult, SendCustomerPayLinkParams, UpdateTempOrderCustomerInput, OrderCustomerPatch, OrderCustomerView, ReplaceTempOrderOptions, OrderPromotionEvaluator, OrderGiftSelectResolver, OrderUnfulfilledPromotion, OrderLastGiftActions } from './types';
|
|
6
|
+
import type { OrderAmountSnapshot, AddProductBookingInput, AddProductToOrderOptions, OrderIdentitySnapshot, OrderPaymentSource, OrderSnapshot, OrderSyncState, SyncPaymentsToOrderParams, SyncPaymentsToOrderResult, SubmitSalesOrderParams, OrderProduct, OrderProductIdentity, OrderSummary, OrderTempOrder, OrderPaymentData, OrderPaymentUpdateOptions, OrderPaymentUpdateResult, SendCustomerPayLinkParams, UpdateTempOrderCustomerInput, OrderCustomerPatch, OrderCustomerView, ReplaceTempOrderOptions, OrderPromotionEvaluator, OrderGiftSelectResolver, OrderUnfulfilledPromotion, OrderLastGiftActions, RemoveProductsFromOrderOptions } from './types';
|
|
7
7
|
import type { ICustomer } from '../AccountList/types';
|
|
8
8
|
import type { Discount } from '../Discount/types';
|
|
9
9
|
import { UnavailableReason } from '../Rules/types';
|
|
@@ -385,7 +385,7 @@ export declare class OrderModule extends BaseModule implements Module, OrderModu
|
|
|
385
385
|
* await order.addProductToOrder({ product_id: 1, num: 3 }, { start_time: '10:00' });
|
|
386
386
|
* // → tempOrder.products 新增 3 行,每行 num=1,bookings 3 条
|
|
387
387
|
*/
|
|
388
|
-
addProductToOrder(product: Partial<OrderProduct> & OrderProductIdentity, booking?: AddProductBookingInput): Promise<OrderProduct[]>;
|
|
388
|
+
addProductToOrder(product: Partial<OrderProduct> & OrderProductIdentity, booking?: AddProductBookingInput, options?: AddProductToOrderOptions): Promise<OrderProduct[]>;
|
|
389
389
|
/**
|
|
390
390
|
* 批量添加商品行,所有行追加完成后只触发一次促销、折扣、summary 重算与持久化。
|
|
391
391
|
*
|
|
@@ -423,8 +423,8 @@ export declare class OrderModule extends BaseModule implements Module, OrderModu
|
|
|
423
423
|
* @example
|
|
424
424
|
* await order.removeProductsFromOrder([identityA, identityB]);
|
|
425
425
|
*/
|
|
426
|
-
removeProductsFromOrder(identities: OrderProductIdentity[]): Promise<OrderProduct[]>;
|
|
427
|
-
removeProductFromOrder(identity: OrderProductIdentity): Promise<OrderProduct[]>;
|
|
426
|
+
removeProductsFromOrder(identities: OrderProductIdentity[], options?: RemoveProductsFromOrderOptions): Promise<OrderProduct[]>;
|
|
427
|
+
removeProductFromOrder(identity: OrderProductIdentity, options?: RemoveProductsFromOrderOptions): Promise<OrderProduct[]>;
|
|
428
428
|
/**
|
|
429
429
|
* 仅清空购物车行(products / bookings),不重置整单。
|
|
430
430
|
* 用于「仅清空商品」;客户、备注、支付等协议字段保持不变。
|
|
@@ -487,7 +487,7 @@ export declare class OrderModule extends BaseModule implements Module, OrderModu
|
|
|
487
487
|
generateIdempotencyToken(): string;
|
|
488
488
|
syncPaymentsToOrder<T = any>(params: SyncPaymentsToOrderParams): Promise<SyncPaymentsToOrderResult<T>>;
|
|
489
489
|
createOrder(params: CommitOrderParams['query']): {
|
|
490
|
-
type: "
|
|
490
|
+
type: "appointment_booking" | "virtual";
|
|
491
491
|
platform: string;
|
|
492
492
|
sales_channel: string;
|
|
493
493
|
order_sales_channel: string;
|
|
@@ -563,4 +563,4 @@ export declare class OrderModule extends BaseModule implements Module, OrderModu
|
|
|
563
563
|
getOrderInfo(order_id: number): Promise<any>;
|
|
564
564
|
getVouchers(): any[];
|
|
565
565
|
}
|
|
566
|
-
export type { UpdateOrderBookingParams, UpdateOrderProductParams, UpdateOrderProductQuantityParams, } from './types';
|
|
566
|
+
export type { AddProductToOrderOptions, RemoveProductsFromOrderOptions, UpdateOrderBookingParams, UpdateOrderProductParams, UpdateOrderProductQuantityParams, } from './types';
|
|
@@ -2897,8 +2897,8 @@ var OrderModule = class extends import_BaseModule.BaseModule {
|
|
|
2897
2897
|
* @example
|
|
2898
2898
|
* await this.appendProductLineToTempOrder(tempOrder, { product_id: 1, num: 1 }, booking);
|
|
2899
2899
|
*/
|
|
2900
|
-
async appendProductLineToTempOrder(tempOrder, product, booking) {
|
|
2901
|
-
var _a, _b;
|
|
2900
|
+
async appendProductLineToTempOrder(tempOrder, product, booking, options) {
|
|
2901
|
+
var _a, _b, _c, _d;
|
|
2902
2902
|
const linked = booking ? this.createLinkedProductAndBooking({ product, booking }) : null;
|
|
2903
2903
|
const productToAdd = (linked == null ? void 0 : linked.product) || product;
|
|
2904
2904
|
const incomingFingerprint = (0, import_utils3.buildProductLineFingerprint)(
|
|
@@ -2909,7 +2909,12 @@ var OrderModule = class extends import_BaseModule.BaseModule {
|
|
|
2909
2909
|
productToAdd,
|
|
2910
2910
|
(0, import_utils3.normalizeOrderProduct)(productToAdd)
|
|
2911
2911
|
);
|
|
2912
|
-
const
|
|
2912
|
+
const isWeighingProduct = Number(((_a = normalizedIncoming.product_sku) == null ? void 0 : _a.open_sold_weight) || 0) === 1;
|
|
2913
|
+
const netWeight = Number((_b = normalizedIncoming.product_sku) == null ? void 0 : _b.net_weight);
|
|
2914
|
+
if (isWeighingProduct && (!Number.isFinite(netWeight) || netWeight <= 0)) {
|
|
2915
|
+
throw new Error("[Order] 称重商品净重必须大于 0");
|
|
2916
|
+
}
|
|
2917
|
+
const incomingBookingUid = productToAdd.booking_uid ?? ((_c = productToAdd.metadata) == null ? void 0 : _c.booking_uid);
|
|
2913
2918
|
if (incomingBookingUid !== void 0 && incomingBookingUid !== null && String(incomingBookingUid) !== "") {
|
|
2914
2919
|
normalizedIncoming.booking_uid = String(incomingBookingUid);
|
|
2915
2920
|
normalizedIncoming.metadata = {
|
|
@@ -2925,7 +2930,7 @@ var OrderModule = class extends import_BaseModule.BaseModule {
|
|
|
2925
2930
|
);
|
|
2926
2931
|
const hasIncomingProductNote = this.hasOrderProductLineNote(normalizedIncoming);
|
|
2927
2932
|
const hasIncomingBookingUid = this.hasLinkedBookingUid(productToAdd) || this.hasLinkedBookingUid(normalizedIncoming);
|
|
2928
|
-
const shouldForceNewLine = !!booking || hasIncomingProductNote || hasIncomingBookingUid;
|
|
2933
|
+
const shouldForceNewLine = !!booking || hasIncomingProductNote || hasIncomingBookingUid || isWeighingProduct;
|
|
2929
2934
|
const matchedIndex = hasIncomingGoodPass || shouldForceNewLine ? -1 : tempOrder.products.findIndex((item) => {
|
|
2930
2935
|
var _a2;
|
|
2931
2936
|
if (this.hasGoodPassDiscount(item))
|
|
@@ -2974,10 +2979,19 @@ var OrderModule = class extends import_BaseModule.BaseModule {
|
|
|
2974
2979
|
booking_uid: linked.bookingUid
|
|
2975
2980
|
};
|
|
2976
2981
|
}
|
|
2977
|
-
|
|
2982
|
+
const insertAtIndex = options == null ? void 0 : options.insertAtIndex;
|
|
2983
|
+
if (Number.isInteger(insertAtIndex) && Number(insertAtIndex) >= 0 && Number(insertAtIndex) < tempOrder.products.length) {
|
|
2984
|
+
tempOrder.products = [
|
|
2985
|
+
...tempOrder.products.slice(0, insertAtIndex),
|
|
2986
|
+
normalizedIncoming,
|
|
2987
|
+
...tempOrder.products.slice(insertAtIndex)
|
|
2988
|
+
];
|
|
2989
|
+
} else {
|
|
2990
|
+
tempOrder.products = [...tempOrder.products, normalizedIncoming];
|
|
2991
|
+
}
|
|
2978
2992
|
} else {
|
|
2979
2993
|
const targetProduct = matchedProduct;
|
|
2980
|
-
const targetUid = (
|
|
2994
|
+
const targetUid = (_d = targetProduct.metadata) == null ? void 0 : _d.unique_identification_number;
|
|
2981
2995
|
const normalizedProduct = (0, import_utils.mergeOrderProductDisplayFields)(
|
|
2982
2996
|
targetProduct,
|
|
2983
2997
|
(0, import_utils3.normalizeOrderProduct)({
|
|
@@ -3033,6 +3047,14 @@ var OrderModule = class extends import_BaseModule.BaseModule {
|
|
|
3033
3047
|
tempOrder.products[matchedIndex],
|
|
3034
3048
|
targetUid
|
|
3035
3049
|
);
|
|
3050
|
+
if (matchedIndex !== tempOrder.products.length - 1) {
|
|
3051
|
+
const mergedProduct = tempOrder.products[matchedIndex];
|
|
3052
|
+
tempOrder.products = [
|
|
3053
|
+
...tempOrder.products.slice(0, matchedIndex),
|
|
3054
|
+
...tempOrder.products.slice(matchedIndex + 1),
|
|
3055
|
+
mergedProduct
|
|
3056
|
+
];
|
|
3057
|
+
}
|
|
3036
3058
|
}
|
|
3037
3059
|
if (linked) {
|
|
3038
3060
|
tempOrder.bookings = [...tempOrder.bookings || [], linked.booking];
|
|
@@ -3045,8 +3067,15 @@ var OrderModule = class extends import_BaseModule.BaseModule {
|
|
|
3045
3067
|
* await order.addProductToOrder({ product_id: 1, num: 3 }, { start_time: '10:00' });
|
|
3046
3068
|
* // → tempOrder.products 新增 3 行,每行 num=1,bookings 3 条
|
|
3047
3069
|
*/
|
|
3048
|
-
async addProductToOrder(product, booking) {
|
|
3070
|
+
async addProductToOrder(product, booking, options) {
|
|
3049
3071
|
const tempOrder = this.ensureTempOrder();
|
|
3072
|
+
const insertAfterProductUid = options == null ? void 0 : options.insertAfterProductUid;
|
|
3073
|
+
const anchorIndex = booking && insertAfterProductUid ? tempOrder.products.findIndex((line) => {
|
|
3074
|
+
var _a;
|
|
3075
|
+
const uid = ((_a = line.metadata) == null ? void 0 : _a.unique_identification_number) || line.unique_identification_number;
|
|
3076
|
+
return uid !== void 0 && uid !== null && String(uid) === String(insertAfterProductUid);
|
|
3077
|
+
}) : -1;
|
|
3078
|
+
let insertAtIndex = anchorIndex >= 0 ? anchorIndex + 1 : void 0;
|
|
3050
3079
|
if (booking) {
|
|
3051
3080
|
const productRecord = product;
|
|
3052
3081
|
const splitCount = (0, import_utils3.getSafeProductNum)(
|
|
@@ -3060,14 +3089,22 @@ var OrderModule = class extends import_BaseModule.BaseModule {
|
|
|
3060
3089
|
await this.appendProductLineToTempOrder(
|
|
3061
3090
|
tempOrder,
|
|
3062
3091
|
singleLine,
|
|
3063
|
-
(0, import_lodash_es.cloneDeep)(booking)
|
|
3092
|
+
(0, import_lodash_es.cloneDeep)(booking),
|
|
3093
|
+
{ insertAtIndex }
|
|
3064
3094
|
);
|
|
3095
|
+
if (insertAtIndex !== void 0)
|
|
3096
|
+
insertAtIndex += 1;
|
|
3065
3097
|
}
|
|
3066
3098
|
await this.finalizeProductOrderMutation(tempOrder);
|
|
3067
3099
|
return tempOrder.products;
|
|
3068
3100
|
}
|
|
3069
3101
|
}
|
|
3070
|
-
await this.appendProductLineToTempOrder(
|
|
3102
|
+
await this.appendProductLineToTempOrder(
|
|
3103
|
+
tempOrder,
|
|
3104
|
+
product,
|
|
3105
|
+
booking,
|
|
3106
|
+
{ insertAtIndex }
|
|
3107
|
+
);
|
|
3071
3108
|
await this.finalizeProductOrderMutation(tempOrder);
|
|
3072
3109
|
this.logInfo("addProductToOrder success", {
|
|
3073
3110
|
product_id: product.product_id,
|
|
@@ -3548,7 +3585,7 @@ var OrderModule = class extends import_BaseModule.BaseModule {
|
|
|
3548
3585
|
* @example
|
|
3549
3586
|
* await order.removeProductsFromOrder([identityA, identityB]);
|
|
3550
3587
|
*/
|
|
3551
|
-
async removeProductsFromOrder(identities) {
|
|
3588
|
+
async removeProductsFromOrder(identities, options) {
|
|
3552
3589
|
var _a, _b, _c, _d;
|
|
3553
3590
|
const tempOrder = this.ensureTempOrder();
|
|
3554
3591
|
if (!identities.length) {
|
|
@@ -3556,6 +3593,13 @@ var OrderModule = class extends import_BaseModule.BaseModule {
|
|
|
3556
3593
|
}
|
|
3557
3594
|
const productsBeforeRemove = tempOrder.products || [];
|
|
3558
3595
|
const bookingsBeforeRemove = tempOrder.bookings || [];
|
|
3596
|
+
const preserveDisplayPosition = options == null ? void 0 : options.preserveDisplayPosition;
|
|
3597
|
+
const anchorIndex = preserveDisplayPosition ? productsBeforeRemove.findIndex((item) => {
|
|
3598
|
+
var _a2;
|
|
3599
|
+
const uid = ((_a2 = item.metadata) == null ? void 0 : _a2.unique_identification_number) || item.unique_identification_number;
|
|
3600
|
+
return uid !== void 0 && uid !== null && String(uid) === String(preserveDisplayPosition.anchorProductUid);
|
|
3601
|
+
}) : -1;
|
|
3602
|
+
const productsAfterAnchor = anchorIndex >= 0 ? productsBeforeRemove.slice(anchorIndex + 1) : [];
|
|
3559
3603
|
const matchedProducts = productsBeforeRemove.filter((item) => {
|
|
3560
3604
|
return identities.some((identity) => (0, import_utils3.isIdentityMatch)(item, identity));
|
|
3561
3605
|
});
|
|
@@ -3596,14 +3640,37 @@ var OrderModule = class extends import_BaseModule.BaseModule {
|
|
|
3596
3640
|
return !(isAddTimeProduct && lineBookingUid !== void 0 && lineBookingUid !== null && linkedBookingUidsToRemove.has(String(lineBookingUid)));
|
|
3597
3641
|
});
|
|
3598
3642
|
}
|
|
3643
|
+
if (preserveDisplayPosition && anchorIndex >= 0) {
|
|
3644
|
+
const remainingProductIndex = tempOrder.products.findIndex((item) => {
|
|
3645
|
+
var _a2;
|
|
3646
|
+
const uid = ((_a2 = item.metadata) == null ? void 0 : _a2.unique_identification_number) || item.unique_identification_number;
|
|
3647
|
+
return uid !== void 0 && uid !== null && String(uid) === String(preserveDisplayPosition.remainingProductUid);
|
|
3648
|
+
});
|
|
3649
|
+
if (remainingProductIndex >= 0) {
|
|
3650
|
+
const remainingProduct = tempOrder.products[remainingProductIndex];
|
|
3651
|
+
const nextProduct = productsAfterAnchor.find(
|
|
3652
|
+
(item) => tempOrder.products.includes(item)
|
|
3653
|
+
);
|
|
3654
|
+
const productsWithoutRemaining = [
|
|
3655
|
+
...tempOrder.products.slice(0, remainingProductIndex),
|
|
3656
|
+
...tempOrder.products.slice(remainingProductIndex + 1)
|
|
3657
|
+
];
|
|
3658
|
+
const nextProductIndex = nextProduct ? productsWithoutRemaining.indexOf(nextProduct) : -1;
|
|
3659
|
+
tempOrder.products = nextProductIndex >= 0 ? [
|
|
3660
|
+
...productsWithoutRemaining.slice(0, nextProductIndex),
|
|
3661
|
+
remainingProduct,
|
|
3662
|
+
...productsWithoutRemaining.slice(nextProductIndex)
|
|
3663
|
+
] : [...productsWithoutRemaining, remainingProduct];
|
|
3664
|
+
}
|
|
3665
|
+
}
|
|
3599
3666
|
await this.finalizeAfterProductsMutation(tempOrder);
|
|
3600
3667
|
this.logInfo("removeProductsFromOrder success", {
|
|
3601
3668
|
identities
|
|
3602
3669
|
});
|
|
3603
3670
|
return tempOrder.products;
|
|
3604
3671
|
}
|
|
3605
|
-
async removeProductFromOrder(identity) {
|
|
3606
|
-
return this.removeProductsFromOrder([identity]);
|
|
3672
|
+
async removeProductFromOrder(identity, options) {
|
|
3673
|
+
return this.removeProductsFromOrder([identity], options);
|
|
3607
3674
|
}
|
|
3608
3675
|
/**
|
|
3609
3676
|
* 仅清空购物车行(products / bookings),不重置整单。
|
|
@@ -321,6 +321,24 @@ export interface ReplaceTempOrderOptions {
|
|
|
321
321
|
saveDraft?: boolean;
|
|
322
322
|
}
|
|
323
323
|
export type AddProductBookingInput = Record<string, any>;
|
|
324
|
+
/**
|
|
325
|
+
* 添加商品行时的顺序控制。
|
|
326
|
+
* 默认追加到 products 尾部;预约数量同步可插入到既有预约组的最新行之后,
|
|
327
|
+
* 避免步进器修改数量改变该组展示位置。
|
|
328
|
+
*/
|
|
329
|
+
export interface AddProductToOrderOptions {
|
|
330
|
+
insertAfterProductUid?: string;
|
|
331
|
+
}
|
|
332
|
+
/**
|
|
333
|
+
* 删除商品后的可选位置保持策略。
|
|
334
|
+
* 预约合并行减量时仍删除最新真实行,再把剩余代表行移动到被删除代表行原位置。
|
|
335
|
+
*/
|
|
336
|
+
export interface RemoveProductsFromOrderOptions {
|
|
337
|
+
preserveDisplayPosition?: {
|
|
338
|
+
remainingProductUid: string;
|
|
339
|
+
anchorProductUid: string;
|
|
340
|
+
};
|
|
341
|
+
}
|
|
324
342
|
/** 更新购物车行:仅传 SKU 时命中同 SKU 第一行;多行同 SKU 须传 unique_identification_number / 选项指纹等 */
|
|
325
343
|
export interface UpdateOrderProductParams {
|
|
326
344
|
product_id: number | null;
|
|
@@ -722,15 +740,15 @@ export interface OrderModuleAPI {
|
|
|
722
740
|
updateTempOrderCustomer: (customer: UpdateTempOrderCustomerInput) => OrderSnapshot['customer'];
|
|
723
741
|
updateTempOrderBuzzer: (buzzer: string) => string;
|
|
724
742
|
updateTempOrderContactsInfo: (contactsInfo: Record<string, any> | null) => Record<string, any> | null;
|
|
725
|
-
addProductToOrder: (product: Partial<OrderProduct> & OrderProductIdentity, booking?: AddProductBookingInput) => Promise<OrderProduct[]>;
|
|
743
|
+
addProductToOrder: (product: Partial<OrderProduct> & OrderProductIdentity, booking?: AddProductBookingInput, options?: AddProductToOrderOptions) => Promise<OrderProduct[]>;
|
|
726
744
|
updateOrderProduct: (params: UpdateOrderProductParams) => Promise<OrderProduct[]>;
|
|
727
745
|
/** 批量更新购物车行,末尾仅触发一次促销重算与 summary 刷新 */
|
|
728
746
|
updateOrderProducts: (paramsList: UpdateOrderProductParams[]) => Promise<OrderProduct[]>;
|
|
729
747
|
updateOrderProductQuantity: (params: UpdateOrderProductQuantityParams) => Promise<OrderProduct[]>;
|
|
730
748
|
updateOrderBooking: (params: UpdateOrderBookingParams) => any[];
|
|
731
|
-
removeProductFromOrder: (identity: OrderProductIdentity) => Promise<OrderProduct[]>;
|
|
749
|
+
removeProductFromOrder: (identity: OrderProductIdentity, options?: RemoveProductsFromOrderOptions) => Promise<OrderProduct[]>;
|
|
732
750
|
/** 批量删除购物车行,末尾仅触发一次促销重算与 summary 刷新 */
|
|
733
|
-
removeProductsFromOrder: (identities: OrderProductIdentity[]) => Promise<OrderProduct[]>;
|
|
751
|
+
removeProductsFromOrder: (identities: OrderProductIdentity[], options?: RemoveProductsFromOrderOptions) => Promise<OrderProduct[]>;
|
|
734
752
|
/** @deprecated no-op;OrderModule 不再负责 tempOrder localStorage 持久化。 */
|
|
735
753
|
persistTempOrder: () => void;
|
|
736
754
|
/**
|
|
@@ -126,7 +126,15 @@ var ProductList = class extends import_BaseModule.BaseModule {
|
|
|
126
126
|
"ticket",
|
|
127
127
|
"event_item"
|
|
128
128
|
],
|
|
129
|
-
with: [
|
|
129
|
+
with: [
|
|
130
|
+
"category",
|
|
131
|
+
"collection",
|
|
132
|
+
"resourceRelation",
|
|
133
|
+
"bundleGroup.bundleItem",
|
|
134
|
+
"optionGroup.optionItem",
|
|
135
|
+
"variantGroup.variantItem",
|
|
136
|
+
"dataVariants"
|
|
137
|
+
],
|
|
130
138
|
status,
|
|
131
139
|
num: 500,
|
|
132
140
|
skip: 1,
|