UNPKG

@pisell/pisellos

Version:

一个可扩展的前端模块化SDK框架,支持插件系统

218 lines (216 loc) 6.93 kB
var __defProp = Object.defineProperty; var __getOwnPropDesc = Object.getOwnPropertyDescriptor; var __getOwnPropNames = Object.getOwnPropertyNames; var __hasOwnProp = Object.prototype.hasOwnProperty; var __export = (target, all) => { for (var name in all) __defProp(target, name, { get: all[name], enumerable: true }); }; var __copyProps = (to, from, except, desc) => { if (from && typeof from === "object" || typeof from === "function") { for (let key of __getOwnPropNames(from)) if (!__hasOwnProp.call(to, key) && key !== except) __defProp(to, key, { get: () => from[key], enumerable: !(desc = __getOwnPropDesc(from, key)) || desc.enumerable }); } return to; }; var __toCommonJS = (mod) => __copyProps(__defProp({}, "__esModule", { value: true }), mod); // src/model/strategy/adapter/promotion/adapter.ts var adapter_exports = {}; __export(adapter_exports, { PromotionAdapter: () => PromotionAdapter, default: () => adapter_default }); module.exports = __toCommonJS(adapter_exports); var import_type = require("./type"); var PromotionAdapter = class { constructor() { this.name = "PromotionAdapter"; this.version = "1.0.0"; } /** * 准备运行时上下文 * * 将业务数据转换为策略引擎可识别的 RuntimeContext */ prepareContext(businessData) { const { products, currentProduct, channel, custom } = businessData; const now = /* @__PURE__ */ new Date(); const currentDateTime = this.formatDateTime(now); const evaluatingProduct = currentProduct || (products.length > 0 ? products[0] : null); return { entities: { products, currentProduct: evaluatingProduct }, attributes: { // 当前时间(格式化字符串,用于时间条件判断) currentDateTime, // 当前评估的商品信息(用于 product_match 运算符) productIdAndVariantId: evaluatingProduct ? { product_id: evaluatingProduct.product_id, product_variant_id: evaluatingProduct.product_variant_id } : null, // 渠道 channel: channel || "", // 商品总数量 totalQuantity: products.reduce((sum, p) => sum + p.quantity, 0), // 商品总金额 totalAmount: products.reduce((sum, p) => sum + p.price * p.quantity, 0), // 自定义属性 ...custom }, metadata: { timestamp: Date.now() } }; } /** * 转换执行结果 * * 将策略引擎的通用结果转换为业务层需要的格式 * 主要是整理 matchedActions,让业务层更容易使用 */ transformResult(result, businessData) { const applicableProducts = businessData ? this.getApplicableProducts(result, businessData) : []; if (!result.applicable) { return { isApplicable: false, applicableProducts: [], reason: result.message, reasonCode: result.code, strategyResult: result }; } const matchedAction = result.matchedActions[0]; if (!matchedAction) { return { isApplicable: false, applicableProducts: [], reason: "No matched action", reasonCode: "NO_ACTION", strategyResult: result }; } const actionDetail = this.parseActionDetail(matchedAction); return { isApplicable: true, actionType: matchedAction.type, actionDetail, applicableProducts, strategyResult: result }; } /** * 格式化配置 */ formatConfig(result, businessData) { return { result, businessData }; } // ============================================ // 私有辅助方法 // ============================================ /** * 格式化日期时间 */ formatDateTime(date) { const year = date.getFullYear(); const month = String(date.getMonth() + 1).padStart(2, "0"); const day = String(date.getDate()).padStart(2, "0"); const hours = String(date.getHours()).padStart(2, "0"); const minutes = String(date.getMinutes()).padStart(2, "0"); const seconds = String(date.getSeconds()).padStart(2, "0"); return `${year}-${month}-${day} ${hours}:${minutes}:${seconds}`; } /** * 解析 Action 详情 * * 将 matchedAction 转换为更易用的结构 */ parseActionDetail(action) { switch (action.type) { case import_type.PROMOTION_ACTION_TYPES.X_ITEMS_FOR_Y_PRICE: return this.parseXItemsForYPriceAction(action); case import_type.PROMOTION_ACTION_TYPES.BUY_X_GET_Y_FREE: return this.parseBuyXGetYFreeAction(action); default: return void 0; } } /** * 解析 X件Y元 Action */ parseXItemsForYPriceAction(action) { const value = action.value || {}; const config = action.config || {}; return { type: import_type.PROMOTION_ACTION_TYPES.X_ITEMS_FOR_Y_PRICE, x: value.x || 2, price: value.price || 0, allowCrossProduct: config.allowCrossProduct ?? true, cumulative: config.cumulative ?? true }; } /** * 解析 买X送Y Action */ parseBuyXGetYFreeAction(action) { const value = action.value || {}; const config = action.config || {}; return { type: import_type.PROMOTION_ACTION_TYPES.BUY_X_GET_Y_FREE, buyQuantity: value.buyQuantity || 1, freeQuantity: value.freeQuantity || 1, giftSelectionMode: config.giftSelectionMode || "user_select", cumulative: config.cumulative ?? true, giftProducts: config.giftProducts || [] }; } /** * 获取适用的商品列表 * * 从购物车商品中筛选出符合策略条件的商品 */ getApplicableProducts(result, businessData) { const { products } = businessData; const productMatchRule = this.findProductMatchRule(result.config); if (!productMatchRule) { return products; } const configProducts = productMatchRule.value; return products.filter( (product) => this.isProductMatch(product, configProducts) ); } /** * 查找商品匹配规则 */ findProductMatchRule(config) { var _a; if (!((_a = config == null ? void 0 : config.conditions) == null ? void 0 : _a.rules)) { return null; } return config.conditions.rules.find( (rule) => rule.field === "productIdAndVariantId" && (rule.operator === "product_match" || rule.operator === "object_in") ); } /** * 检查商品是否匹配 */ isProductMatch(product, configProducts) { return configProducts.some((config) => { if (config.product_id !== product.product_id) { return false; } if (config.product_variant_id === 0) { return true; } return config.product_variant_id === product.product_variant_id; }); } }; var adapter_default = PromotionAdapter; // Annotate the CommonJS export names for ESM import in node: 0 && (module.exports = { PromotionAdapter });