diff --git a/adapters/promotion/AbstractPromotionAdapter.d.ts b/adapters/promotion/AbstractPromotionAdapter.d.ts index 85cc0638..815b8074 100644 --- a/adapters/promotion/AbstractPromotionAdapter.d.ts +++ b/adapters/promotion/AbstractPromotionAdapter.d.ts @@ -19,7 +19,7 @@ export default abstract class AbstractPromotionAdapter { static getAllConcept: (concept: string[]) => Promise; abstract getActivePromotionsIds(): string[]; static clearOfPromotion(orderId: any): Promise; - static applyPromotion: (orderId: any, spendPromotion: IconfigDiscount, promotionId: any) => Promise; + static applyPromotion: (orderId: any, spendPromotion: IconfigDiscount, promotionId: any) => Promise; static initialize: (initParams?: { [key: string]: string | number | boolean; }) => PromotionAdapter; diff --git a/adapters/promotion/AbstractPromotionAdapter.js b/adapters/promotion/AbstractPromotionAdapter.js index 76c260cb..fb48555c 100644 --- a/adapters/promotion/AbstractPromotionAdapter.js +++ b/adapters/promotion/AbstractPromotionAdapter.js @@ -14,7 +14,7 @@ class AbstractPromotionAdapter { for (const orderDish of orderDishes) { await OrderDish.update({ id: orderDish.id }, { discountTotal: 0, discountType: "" }).fetch(); } - await Order.updateOne({ id: order.id }, { discountTotal: 0 }); // isPromoted: false + await Order.updateOne({ id: order.id }, { discountTotal: 0 }); // isPromoting: false } } exports.default = AbstractPromotionAdapter; diff --git a/adapters/promotion/AbstractPromotionAdapter.ts b/adapters/promotion/AbstractPromotionAdapter.ts index da5b217e..ab02375d 100644 --- a/adapters/promotion/AbstractPromotionAdapter.ts +++ b/adapters/promotion/AbstractPromotionAdapter.ts @@ -40,7 +40,7 @@ export default abstract class AbstractPromotionAdapter { await Order.updateOne({ id: order.id }, { discountTotal: 0}) // isPromoting: false } - public static applyPromotion: (orderId: any, spendPromotion: IconfigDiscount, promotionId: any) => Promise; + public static applyPromotion: (orderId: any, spendPromotion: IconfigDiscount, promotionId: any) => Promise; public static initialize:(initParams?: { [key: string]: string | number | boolean; }) => PromotionAdapter; diff --git a/adapters/promotion/default/configuredPromotion.d.ts b/adapters/promotion/default/configuredPromotion.d.ts index b044440f..5eb1c476 100644 --- a/adapters/promotion/default/configuredPromotion.d.ts +++ b/adapters/promotion/default/configuredPromotion.d.ts @@ -19,4 +19,5 @@ export default class configuredPromotion extends AbstractPromotionHandler { action(order: Order): Promise; displayGroup(group: Group, user?: string | User): Promise; displayDish(dish: Dish, user?: string | User): Promise; + static applyPromotion(orderId: any, spendDiscount: IconfigDiscount, promotionId: any): Promise; } diff --git a/adapters/promotion/default/configuredPromotion.js b/adapters/promotion/default/configuredPromotion.js index 5d0170fa..fb28528c 100644 --- a/adapters/promotion/default/configuredPromotion.js +++ b/adapters/promotion/default/configuredPromotion.js @@ -20,17 +20,18 @@ class configuredPromotion extends AbstractPromotion_1.default { this.externalId = promotion.externalId; } condition(arg) { - if ((0, findModelInstance_1.default)(arg) === "Order" && this.concept.includes(arg.concept)) { + if ((0, findModelInstance_1.default)(arg) === "Order" && (0, stringsInArray_1.stringsInArray)(arg.concept, this.concept)) { // order not used for configuredPromotion // Order.populate() + console.log("condition"); return true; } - if ((0, findModelInstance_1.default)(arg) === "Dish" && this.concept.includes(arg.concept)) { + if ((0, findModelInstance_1.default)(arg) === "Dish" && (0, stringsInArray_1.stringsInArray)(arg.concept, this.concept)) { if (this.config.dishes.includes(arg.id)) { return true; } } - if ((0, findModelInstance_1.default)(arg) === "Group" && this.concept.includes(arg.concept)) { + if ((0, findModelInstance_1.default)(arg) === "Group" && (0, stringsInArray_1.stringsInArray)(arg.concept, this.concept)) { if (this.config.groups.includes(arg.id)) { return true; } @@ -39,9 +40,25 @@ class configuredPromotion extends AbstractPromotion_1.default { } async action(order) { console.log(this.config + " action"); - // return await PromotionAdapter.applyPromotion(order.id, this.config, this.id) - // return Promise.resolve() + let mass = await configuredPromotion.applyPromotion(order.id, this.config, this.id); + return mass; + } + async displayGroup(group, user) { + if (user) { + // return await Group.display(this.concept, group.id) + return await Group.display(group); + } + } + async displayDish(dish, user) { + if (user) { + // return await Dish.display(this.concept, group.id) + return await Dish.display(dish); + } + } + static async applyPromotion(orderId, spendDiscount, promotionId) { + const order = await Order.findOne({ id: orderId }); if (order.user && typeof order.user === "string") { + const promotion = await Promotion.findOne({ id: promotionId }); // order.dishes const orderDishes = await OrderDish.find({ order: order.id }).populate("dish"); let discountCost = new decimal_js_1.default(0); @@ -51,29 +68,31 @@ class configuredPromotion extends AbstractPromotion_1.default { sails.log.error("orderDish", orderDish.id, "has no such dish"); continue; } - if (!(0, stringsInArray_1.stringsInArray)(orderDish.dish.concept, this.concept)) { + if (!(0, stringsInArray_1.stringsInArray)(orderDish.dish.concept, promotion.concept)) { continue; } - // TODO: if concept:arrays // ------------------------------------------ Decimal ------------------------------------------ - if (this.configDiscount.discountType === "flat") { - orderDishDiscountCost = new decimal_js_1.default(this.configDiscount.discountAmount).mul(orderDish.amount).toNumber(); + if (spendDiscount.discountType === "flat") { + orderDishDiscountCost = new decimal_js_1.default(spendDiscount.discountAmount).mul(orderDish.amount).toNumber(); discountCost = new decimal_js_1.default(orderDishDiscountCost).add(discountCost); // discountCost += new Decimal(orderDish.dish.price * orderDish.dish.amount).sub(spendDiscount.discountAmount * orderDish.dish.amount ).toNumber(); } - if (this.configDiscount.discountType === "percentage") { + if (spendDiscount.discountType === "percentage") { // let discountPrice:number = new Decimal(orderDish.dish.price).mul(orderDish.amount).mul(+spendDiscount.discountAmount / 100).toNumber(); - orderDishDiscountCost = new decimal_js_1.default(orderDish.dish.price).mul(orderDish.amount).mul(+this.configDiscount.discountAmount / 100).toNumber(); + orderDishDiscountCost = new decimal_js_1.default(orderDish.dish.price) + .mul(orderDish.amount) + .mul(+spendDiscount.discountAmount / 100) + .toNumber(); discountCost = new decimal_js_1.default(orderDishDiscountCost).add(discountCost); } let orderDishDiscount = new decimal_js_1.default(orderDish.discountTotal).add(orderDishDiscountCost).toNumber(); - await OrderDish.update({ id: orderDish.id }, { discountTotal: orderDishDiscount, discountType: this.configDiscount.discountType }).fetch(); + await OrderDish.update({ id: orderDish.id }, { discountTotal: orderDishDiscount, discountType: spendDiscount.discountType }).fetch(); // await OrderDish.update({ id: orderDish.id }, { discountTotal: orderDishDiscountCost, discountType: spendDiscount.discountType}).fetch(); // await OrderDish.update({ id: orderDish.id }, { amount: orderDish.dish.price, discount: discountCost}).fetch(); } // Update the order with new total let orderDiscount = new decimal_js_1.default(order.discountTotal).add(discountCost.toNumber()).toNumber(); - await Order.updateOne({ id: order.id }, { discountTotal: orderDiscount }); + await Order.updateOne({ id: orderId }, { discountTotal: orderDiscount }); // let discountCoverage: Decimal; // await Order.updateOne({id: orderId}, {total: order.total, discountTotal: discountCoverage.toNumber()}); } @@ -86,17 +105,5 @@ class configuredPromotion extends AbstractPromotion_1.default { state: {} }; } - async displayGroup(group, user) { - if (user) { - // return await Group.display(this.concept, group.id) - return await Group.display(group); - } - } - async displayDish(dish, user) { - if (user) { - // return await Dish.display(this.concept, group.id) - return await Dish.display(dish); - } - } } exports.default = configuredPromotion; diff --git a/adapters/promotion/default/configuredPromotion.ts b/adapters/promotion/default/configuredPromotion.ts index 7c987202..8cceef1f 100644 --- a/adapters/promotion/default/configuredPromotion.ts +++ b/adapters/promotion/default/configuredPromotion.ts @@ -35,82 +35,32 @@ export default class configuredPromotion extends AbstractPromotionHandler { public externalId: string; public condition(arg: Group | Dish | Order): boolean { - if (findModelInstanceByAttributes(arg) === "Order" && this.concept.includes(arg.concept)) { + if (findModelInstanceByAttributes(arg) === "Order" && stringsInArray(arg.concept, this.concept) ) { // order not used for configuredPromotion // Order.populate() + console.log("condition") return true; } - if (findModelInstanceByAttributes(arg) === "Dish" && this.concept.includes(arg.concept)) { + if (findModelInstanceByAttributes(arg) === "Dish" && stringsInArray(arg.concept, this.concept)) { if(this.config.dishes.includes(arg.id)){ return true; } } - if (findModelInstanceByAttributes(arg) === "Group" && this.concept.includes(arg.concept)) { + if (findModelInstanceByAttributes(arg) === "Group" && stringsInArray(arg.concept, this.concept)) { if(this.config.groups.includes(arg.id)){ return true; } } - + return false } public async action(order: Order): Promise { console.log(this.config + " action") - // return await PromotionAdapter.applyPromotion(order.id, this.config, this.id) - // return Promise.resolve() - - if (order.user && typeof order.user === "string") { - // order.dishes - const orderDishes = await OrderDish.find({ order: order.id }).populate("dish"); - let discountCost: Decimal = new Decimal(0); - - for (const orderDish of orderDishes) { - let orderDishDiscountCost: number = 0; - if (!orderDish.dish) { - sails.log.error("orderDish", orderDish.id, "has no such dish"); - continue; - } - - if(!stringsInArray(orderDish.dish.concept,this.concept)){ - continue - } - - // TODO: if concept:arrays - // ------------------------------------------ Decimal ------------------------------------------ - if(this.configDiscount.discountType === "flat"){ - orderDishDiscountCost = new Decimal(this.configDiscount.discountAmount).mul(orderDish.amount).toNumber() - discountCost = new Decimal(orderDishDiscountCost).add(discountCost) - // discountCost += new Decimal(orderDish.dish.price * orderDish.dish.amount).sub(spendDiscount.discountAmount * orderDish.dish.amount ).toNumber(); - } - - if(this.configDiscount.discountType === "percentage") { - // let discountPrice:number = new Decimal(orderDish.dish.price).mul(orderDish.amount).mul(+spendDiscount.discountAmount / 100).toNumber(); - orderDishDiscountCost = new Decimal(orderDish.dish.price).mul(orderDish.amount).mul(+this.configDiscount.discountAmount / 100).toNumber() - discountCost = new Decimal(orderDishDiscountCost).add(discountCost) - } - - let orderDishDiscount:number = new Decimal(orderDish.discountTotal).add(orderDishDiscountCost).toNumber() - await OrderDish.update({ id: orderDish.id }, { discountTotal: orderDishDiscount, discountType: this.configDiscount.discountType}).fetch(); - - // await OrderDish.update({ id: orderDish.id }, { discountTotal: orderDishDiscountCost, discountType: spendDiscount.discountType}).fetch(); - // await OrderDish.update({ id: orderDish.id }, { amount: orderDish.dish.price, discount: discountCost}).fetch(); - } - // Update the order with new total - let orderDiscount:number = new Decimal(order.discountTotal).add(discountCost.toNumber()).toNumber() - await Order.updateOne({id: order.id}, {discountTotal: orderDiscount}) - - // let discountCoverage: Decimal; - // await Order.updateOne({id: orderId}, {total: order.total, discountTotal: discountCoverage.toNumber()}); - } else { - throw `User not found in Order, applyDiscount failed` - } - return { - message: `Configured promotion`, - type: "configured-promotion", - state: {} - } + let mass:PromotionState = await configuredPromotion.applyPromotion(order.id, this.config, this.id) + return mass } public async displayGroup(group: Group, user?: string | User): Promise { @@ -127,7 +77,7 @@ export default class configuredPromotion extends AbstractPromotionHandler { } } - public static async applyPromotion(orderId, spendDiscount: IconfigDiscount, promotionId): Promise { + public static async applyPromotion(orderId, spendDiscount: IconfigDiscount, promotionId): Promise { const order = await Order.findOne({ id: orderId }); if (order.user && typeof order.user === "string") { @@ -178,6 +128,11 @@ export default class configuredPromotion extends AbstractPromotionHandler { } else { throw `User not found in Order, applyDiscount failed`; } + return { + message: `Configured promotion`, + type: "configured-promotion", + state: {} + } } } diff --git a/adapters/promotion/default/promotionAdapter.d.ts b/adapters/promotion/default/promotionAdapter.d.ts index 40fff22c..88d1cf24 100644 --- a/adapters/promotion/default/promotionAdapter.d.ts +++ b/adapters/promotion/default/promotionAdapter.d.ts @@ -1,7 +1,6 @@ import Order, { PromotionState } from "../../../models/Order"; import AbstractPromotionHandler from "../AbstractPromotion"; import AbstractPromotionAdapter from "../AbstractPromotionAdapter"; -import { IconfigDiscount } from "../../../interfaces/ConfigDiscount"; import Promotion from "../../../models/Promotion"; import Group from "../../../models/Group"; import Dish from "../../../models/Dish"; @@ -20,11 +19,6 @@ export declare class PromotionAdapter extends AbstractPromotionAdapter { static getPromotionHandlerById(id: string): Promise; getAllConcept(concept: string[]): Promise; getActivePromotionsIds(): string[]; - static clearOfPromotion(orderId: any): Promise; - /** - * @deprecated //TODO: move to configured discount - */ - static applyPromotion(orderId: any, spendDiscount: IconfigDiscount, promotionId: any): Promise; static initialize(initParams?: { [key: string]: string | number | boolean; }): PromotionAdapter; diff --git a/adapters/promotion/default/promotionAdapter.js b/adapters/promotion/default/promotionAdapter.js index cad56e2a..761ee6a8 100644 --- a/adapters/promotion/default/promotionAdapter.js +++ b/adapters/promotion/default/promotionAdapter.js @@ -1,11 +1,9 @@ "use strict"; Object.defineProperty(exports, "__esModule", { value: true }); exports.PromotionAdapter = void 0; -const decimal_js_1 = require("decimal.js"); const AbstractPromotionAdapter_1 = require("../AbstractPromotionAdapter"); const configuredPromotion_1 = require("./configuredPromotion"); const worktime_1 = require("@webresto/worktime"); -const stringsInArray_1 = require("../../../libs/stringsInArray"); class PromotionAdapter extends AbstractPromotionAdapter_1.default { async processOrder(order) { const promotionStates = []; @@ -105,7 +103,6 @@ class PromotionAdapter extends AbstractPromotionAdapter_1.default { ...(promotionToAdd.concept && { concept: promotionToAdd.concept }), configDiscount: promotionToAdd.configDiscount, sortOrder: 0, - // productCategoryDiscounts: {},// discountToAdd.productCategoryDiscounts, externalId: promotionToAdd.externalId, worktime: null, // promotionToAdd.worktime }; @@ -129,73 +126,6 @@ class PromotionAdapter extends AbstractPromotionAdapter_1.default { getActivePromotionsIds() { return Object.keys(PromotionAdapter.promotions); } -<<<<<<< HEAD -======= - static async clearOfPromotion(orderId) { - const order = await Order.findOne({ id: orderId }); - // if Order.status ="PAYMENT" or "ORDER" can't clear promotions - if (order.state === "ORDER") - throw "order with orderId " + order.id + "in state ORDER"; - if (order.state === "PAYMENT") - throw "order with orderId " + order.id + "in state PAYMENT"; - // ------------------------------------------ OrderDish update ------------------------------------------ - const orderDishes = await OrderDish.find({ order: order.id }).populate("dish"); - for (const orderDish of orderDishes) { - await OrderDish.update({ id: orderDish.id }, { discountTotal: 0, discountType: "" }).fetch(); - } - await Order.updateOne({ id: order.id }, { discountTotal: 0 }); - } - /** - * @deprecated //TODO: move to configured discount - */ ->>>>>>> origin/next - static async applyPromotion(orderId, spendDiscount, promotionId) { - const order = await Order.findOne({ id: orderId }); - if (order.user && typeof order.user === "string") { - const promotion = await Promotion.findOne({ id: promotionId }); - // order.dishes - const orderDishes = await OrderDish.find({ order: order.id }).populate("dish"); - let discountCost = new decimal_js_1.default(0); - for (const orderDish of orderDishes) { - let orderDishDiscountCost = 0; - if (!orderDish.dish) { - sails.log.error("orderDish", orderDish.id, "has no such dish"); - continue; - } - // TODO: if concept:arrays - if (!(0, stringsInArray_1.stringsInArray)(orderDish.dish.concept, promotion.concept)) { - // console.log("stringsInArray: ==== ", orderDish.dish.concept, promotion.concept); - continue; - } - // ------------------------------------------ Decimal ------------------------------------------ - if (spendDiscount.discountType === "flat") { - orderDishDiscountCost = new decimal_js_1.default(spendDiscount.discountAmount).mul(orderDish.amount).toNumber(); - discountCost = new decimal_js_1.default(orderDishDiscountCost).add(discountCost); - // discountCost += new Decimal(orderDish.dish.price * orderDish.dish.amount).sub(spendDiscount.discountAmount * orderDish.dish.amount ).toNumber(); - } - if (spendDiscount.discountType === "percentage") { - // let discountPrice:number = new Decimal(orderDish.dish.price).mul(orderDish.amount).mul(+spendDiscount.discountAmount / 100).toNumber(); - orderDishDiscountCost = new decimal_js_1.default(orderDish.dish.price) - .mul(orderDish.amount) - .mul(+spendDiscount.discountAmount / 100) - .toNumber(); - discountCost = new decimal_js_1.default(orderDishDiscountCost).add(discountCost); - } - let orderDishDiscount = new decimal_js_1.default(orderDish.discountTotal).add(orderDishDiscountCost).toNumber(); - await OrderDish.update({ id: orderDish.id }, { discountTotal: orderDishDiscount, discountType: spendDiscount.discountType }).fetch(); - // await OrderDish.update({ id: orderDish.id }, { discountTotal: orderDishDiscountCost, discountType: spendDiscount.discountType}).fetch(); - // await OrderDish.update({ id: orderDish.id }, { amount: orderDish.dish.price, discount: discountCost}).fetch(); - } - // Update the order with new total - let orderDiscount = new decimal_js_1.default(order.discountTotal).add(discountCost.toNumber()).toNumber(); - await Order.updateOne({ id: orderId }, { discountTotal: orderDiscount }); - // let discountCoverage: Decimal; - // await Order.updateOne({id: orderId}, {total: order.total, discountTotal: discountCoverage.toNumber()}); - } - else { - throw `User not found in Order, applyDiscount failed`; - } - } static initialize(initParams) { return PromotionAdapter.prototype; } diff --git a/adapters/promotion/default/promotionAdapter.ts b/adapters/promotion/default/promotionAdapter.ts index ea264b9c..ae3df280 100644 --- a/adapters/promotion/default/promotionAdapter.ts +++ b/adapters/promotion/default/promotionAdapter.ts @@ -8,10 +8,11 @@ import { IconfigDiscount } from "../../../interfaces/ConfigDiscount"; import Promotion from "../../../models/Promotion"; import Group from "../../../models/Group"; import Dish from "../../../models/Dish"; -import { stringsInArray } from "../../../libs/stringsInArray"; + export class PromotionAdapter extends AbstractPromotionAdapter { static promotions: { [key: string]: AbstractPromotionHandler } = {}; + public async processOrder(order: Order): Promise { const promotionStates = [] as PromotionState[] // Order.populate() @@ -156,62 +157,6 @@ export class PromotionAdapter extends AbstractPromotionAdapter { return Object.keys(PromotionAdapter.promotions); } - /** - * @deprecated //TODO: move to configured discount - */ - public static async applyPromotion(orderId, spendDiscount: IconfigDiscount, promotionId): Promise { - const order = await Order.findOne({ id: orderId }); - - if (order.user && typeof order.user === "string") { - const promotion = await Promotion.findOne({ id: promotionId }); - // order.dishes - const orderDishes = await OrderDish.find({ order: order.id }).populate("dish"); - let discountCost: Decimal = new Decimal(0); - - for (const orderDish of orderDishes) { - let orderDishDiscountCost: number = 0; - if (!orderDish.dish) { - sails.log.error("orderDish", orderDish.id, "has no such dish"); - continue; - } - - if (!stringsInArray(orderDish.dish.concept, promotion.concept)) { - continue; - } - - // ------------------------------------------ Decimal ------------------------------------------ - if (spendDiscount.discountType === "flat") { - orderDishDiscountCost = new Decimal(spendDiscount.discountAmount).mul(orderDish.amount).toNumber(); - discountCost = new Decimal(orderDishDiscountCost).add(discountCost); - // discountCost += new Decimal(orderDish.dish.price * orderDish.dish.amount).sub(spendDiscount.discountAmount * orderDish.dish.amount ).toNumber(); - } - - if (spendDiscount.discountType === "percentage") { - // let discountPrice:number = new Decimal(orderDish.dish.price).mul(orderDish.amount).mul(+spendDiscount.discountAmount / 100).toNumber(); - orderDishDiscountCost = new Decimal(orderDish.dish.price) - .mul(orderDish.amount) - .mul(+spendDiscount.discountAmount / 100) - .toNumber(); - discountCost = new Decimal(orderDishDiscountCost).add(discountCost); - } - - let orderDishDiscount: number = new Decimal(orderDish.discountTotal).add(orderDishDiscountCost).toNumber(); - await OrderDish.update({ id: orderDish.id }, { discountTotal: orderDishDiscount, discountType: spendDiscount.discountType }).fetch(); - - // await OrderDish.update({ id: orderDish.id }, { discountTotal: orderDishDiscountCost, discountType: spendDiscount.discountType}).fetch(); - // await OrderDish.update({ id: orderDish.id }, { amount: orderDish.dish.price, discount: discountCost}).fetch(); - } - // Update the order with new total - let orderDiscount: number = new Decimal(order.discountTotal).add(discountCost.toNumber()).toNumber(); - await Order.updateOne({ id: orderId }, { discountTotal: orderDiscount }) - - // let discountCoverage: Decimal; - // await Order.updateOne({id: orderId}, {total: order.total, discountTotal: discountCoverage.toNumber()}); - } else { - throw `User not found in Order, applyDiscount failed`; - } - } - static initialize(initParams?: { [key: string]: string | number | boolean }): PromotionAdapter { return PromotionAdapter.prototype; } diff --git a/models/Order.d.ts b/models/Order.d.ts index dd2ef813..d272ceea 100644 --- a/models/Order.d.ts +++ b/models/Order.d.ts @@ -29,7 +29,7 @@ declare let attributes: { /** * @deprecated will be rename to `Items` in **v2** */ - dishes: OrderDish[] | number[]; + dishes: number[] | OrderDish[]; paymentMethod: any; /** */ paymentMethodTitle: string; @@ -47,7 +47,7 @@ declare let attributes: { ** Means that the basket was modified by the adapter, * It also prevents the repeat call of the action of the handler of the handler * */ - isPromoted: boolean; + isPromoting: boolean; /** */ dishesCount: number; uniqueDishes: number; @@ -119,7 +119,7 @@ export default Order; declare let Model: { beforeCreate(orderInit: any, cb: (err?: string) => void): void; /** Add dish into order */ - addDish(criteria: CriteriaQuery, dish: Dish | string, amount: number, modifiers: OrderModifier[], comment: string, addedBy: string, replace?: boolean, orderDishId?: number): Promise; + addDish(criteria: CriteriaQuery, dish: string | Dish, amount: number, modifiers: OrderModifier[], comment: string, addedBy: string, replace?: boolean, orderDishId?: number): Promise; removeDish(criteria: CriteriaQuery, dish: OrderDish, amount: number, stack?: boolean): Promise; setCount(criteria: CriteriaQuery, dish: OrderDish, amount: number): Promise; setComment(criteria: CriteriaQuery, dish: OrderDish, comment: string): Promise; @@ -163,13 +163,13 @@ declare let Model: { shortId?: string; concept?: string; isMixedConcept?: boolean; - dishes?: OrderDish[] | number[]; + dishes?: number[] | OrderDish[]; paymentMethod?: any; paymentMethodTitle?: string; paid?: boolean; isPaymentPromise?: boolean; promotionState?: PromotionState[]; - isPromoted?: boolean; + isPromoting?: boolean; dishesCount?: number; uniqueDishes?: number; modifiers?: any; diff --git a/models/Order.js b/models/Order.js index df947147..876599eb 100644 --- a/models/Order.js +++ b/models/Order.js @@ -53,7 +53,7 @@ let attributes = { ** Means that the basket was modified by the adapter, * It also prevents the repeat call of the action of the handler of the handler * */ - isPromoted: { + isPromoting: { type: "boolean" }, /** */ @@ -926,12 +926,12 @@ let Model = { order.orderTotal = basketTotal.toNumber(); order.basketTotal = basketTotal.toNumber(); // Calcualte promotion cost - if (!order.isPromoted) { + if (!order.isPromoting) { emitter.emit("core:count-before-promotion", order); let promotionAdapter = await Adapter.getPromotionAdapter(); try { order.promotionState = await promotionAdapter.processOrder(order); - order.isPromoted = true; + order.isPromoting = true; } catch (error) { sails.log.error(`Core > order > promotion calculate fail: `, error); diff --git a/models/User.d.ts b/models/User.d.ts index 1f5e3cc1..018d1978 100644 --- a/models/User.d.ts +++ b/models/User.d.ts @@ -87,7 +87,7 @@ declare let Model: { * @param {WaterlineCriteria} criteria * @returns String */ - getPhoneString(phone: Phone, target?: "login" | "print" | "string"): Promise; + getPhoneString(phone: Phone, target?: "string" | "login" | "print"): Promise; /** * Update user password * diff --git a/models/UserBonusProgram.d.ts b/models/UserBonusProgram.d.ts index aed9c2ac..9a615615 100644 --- a/models/UserBonusProgram.d.ts +++ b/models/UserBonusProgram.d.ts @@ -22,13 +22,13 @@ interface UserBonusProgram extends attributes, ORM { export default UserBonusProgram; declare let Model: { beforeCreate(init: UserBonusProgram, cb: (err?: string) => void): void; - registration(user: User | string, adapterOrId: string): Promise; - delete(user: User | string, adapterOrId: string): Promise; - syncAll(user: User | string): Promise; + registration(user: string | User, adapterOrId: string): Promise; + delete(user: string | User, adapterOrId: string): Promise; + syncAll(user: string | User): Promise; /** Full sync all transaction with external system */ - sync(user: User | string, bonusProgram: BonusProgram | string, force?: boolean): Promise; - checkEnoughToSpend(user: User | string, bonusProgram: BonusProgram | string, amount: number): Promise; - sumCurrentBalance(user: User | string, bonusProgram: BonusProgram | string): Promise; + sync(user: string | User, bonusProgram: string | BonusProgram, force?: boolean): Promise; + checkEnoughToSpend(user: string | User, bonusProgram: string | BonusProgram, amount: number): Promise; + sumCurrentBalance(user: string | User, bonusProgram: string | BonusProgram): Promise; }; declare global { const UserBonusProgram: typeof Model & ORMModel; diff --git a/test/generators/discount.generator.ts b/test/generators/discount.generator.ts index 905db1a6..629629aa 100644 --- a/test/generators/discount.generator.ts +++ b/test/generators/discount.generator.ts @@ -5,6 +5,7 @@ import Order, { PromotionState } from './../../models/Order'; import { PromotionAdapter } from "../../adapters/promotion/default/promotionAdapter"; import findModelInstanceByAttributes from "../../libs/findModelInstance"; import AbstractPromotionHandler from "../../adapters/promotion/AbstractPromotion"; +import configuredPromotion from "../../adapters/promotion/default/configuredPromotion"; var autoincrement: number = 0; @@ -62,12 +63,7 @@ export default function discountGenerator(config: AbstractPromotionHandler = { return false }, action: async function (order: Order):Promise { - await PromotionAdapter.applyPromotion(order.id, this.configDiscount, this.id) - return { - message: this.id, - type: this.id, - state: {} - } + return await configuredPromotion.applyPromotion(order.id, this.configDiscount, this.id) }, // sortOrder: 0, displayGroup: async function (group:Group, user?: string): Promise { diff --git a/test/integration/adapters/promotion.test.ts b/test/integration/adapters/promotion.test.ts index 738d8905..49518a06 100644 --- a/test/integration/adapters/promotion.test.ts +++ b/test/integration/adapters/promotion.test.ts @@ -4,6 +4,18 @@ import { TestRMS } from "../../mocks/adapter/RMS"; import { Adapter } from "../../../adapters"; import { expect } from "chai"; import { address, customer } from "../../mocks/customer"; +import AbstractPromotionAdapter from "../../../adapters/promotion/AbstractPromotionAdapter"; +import { PromotionAdapter } from "../../../adapters/promotion/default/promotionAdapter"; +import dishGenerator from "../../generators/dish.generator"; +import configuredPromotion from "../../../adapters/promotion/default/configuredPromotion"; +import { IconfigDiscount } from "../../../interfaces/ConfigDiscount"; +import AbstractPromotionHandler from "../../../adapters/promotion/AbstractPromotion"; +import { stringsInArray } from "../../../libs/stringsInArray"; +import findModelInstanceByAttributes from "../../../libs/findModelInstance"; +import { PromotionState } from "../../../models/Order"; +import Group from './../../../models/Group'; +import Dish from './../../../models/Dish'; +import Order from './../../../models/Order'; describe("Promotion adapter integration test", function () { @@ -13,7 +25,6 @@ describe("Promotion adapter integration test", function () { }); - it("Configured discount total: 10% for all group", async () => { // // If item is added, then see that it stood in line. // // Pass the test response of Messaja @@ -25,8 +36,48 @@ describe("Promotion adapter integration test", function () { // let order = await Order.create({id: "configured-promotion-integration-test"}).fetch(); // await Order.addDish({id: order.id}, dishes[0], 1, [], "", "user"); + let config:IconfigDiscount = { + discountType: "percentage", + discountAmount: 10, + dishes: [], + groups: [], + excludeModifiers: true + } + + let promotion10Percent = new configuredPromotion({ + concept: ["road"], + id: 'aa2-id', + isJoint: true, + name: 'awdawd', + isPublic: true, + configDiscount: null, + description: "aaa", + externalId: "externalID" + }, + config) + + let discountAdapter:AbstractPromotionAdapter = PromotionAdapter.initialize() + let order = await Order.create({id: "configured-promotion-integration-testa"}).fetch(); + await Order.updateOne({id: order.id}, {concept: "road",user: "user"}); + + let dish1 = await Dish.createOrUpdate(dishGenerator({name: "test dish", price: 10.1, concept: "road"})); + let dish2 = await Dish.createOrUpdate(dishGenerator({name: "test fish", price: 15.2, concept: "road"})); + + await Order.addDish({id: order.id}, dish1, 5, [], "", "test"); + await Order.addDish({id: order.id}, dish2, 4, [], "", "test"); + + await discountAdapter.addPromotionHandler(promotion10Percent) + + order = await Order.findOne(order.id) + await discountAdapter.processOrder(order) - + let result = await Order.findOne(order.id) + // console.log(result) + + expect(result.discountTotal).to.equal(11.13); + + + // order = await Order.findOne({id: order.id}); @@ -91,9 +142,87 @@ describe("Promotion adapter integration test", function () { it("Promotion states should passed in order", ()=>{}) - it("Check prepend recursion", ()=>{ + it("Check prepend recursion", async ()=>{ // for call recursion we should add dish from action in promotionHandler + let discountEx:AbstractPromotionHandler = { + id: "1-id", + configDiscount: { + discountType: "percentage", + discountAmount: 10, + dishes: [], + groups: [], + excludeModifiers: true + }, + name: "1-name", + description: "string", + concept: ["origin","clear","Happy Birthday","Recursion"], + condition: (arg: Group | Dish | Order): boolean =>{ + if (findModelInstanceByAttributes(arg) === "Order" && stringsInArray(arg.concept, discountEx.concept) ) { + // Order.populate() + //discountEx.concept.includes(arg.concept) + return true; + } + + if (findModelInstanceByAttributes(arg) === "Dish" && stringsInArray(arg.concept, discountEx.concept)) { + // TODO: check if includes in IconfigDish + return true; + } + + if (findModelInstanceByAttributes(arg) === "Group" && stringsInArray(arg.concept, discountEx.concept) ) { + // TODO: check if includes in IconfigG + return true; + } + + return false + }, + action: async (order: Order): Promise => { + // console.log("ACTION ================awdawdawd") + let dish2 = await Dish.createOrUpdate(dishGenerator({name: "test fish", price: 15.2, concept: "Recursion"})); + + await Order.addDish({id: order.id}, dish1, 5, [], "", "test"); + + return await configuredPromotion.applyPromotion(order.id, discountEx.configDiscount, discountEx.id) + }, + isPublic: true, + isJoint: true, + // sortOrder: 0, + displayGroup: async function (group:Group, user?: string): Promise { + if(user){ + // return await Dish.display(this.concept, group.id) + return await Group.display(group) + } + }, + displayDish: async function (dish:Dish, user?: string): Promise { + if(user){ + // return await Dish.display(this.concept, group.id) + return await Dish.display(dish) + } + }, + externalId: "1-externalId", + } + + let discountAdapter:AbstractPromotionAdapter = PromotionAdapter.initialize() + let order = await Order.create({id: "configured-promotion-integration-recursion"}).fetch(); + await Order.updateOne({id: order.id}, {concept: "Recursion",user: "user"}); + + let dish1 = await Dish.createOrUpdate(dishGenerator({name: "test dish", price: 10.1, concept: "Recursion"})); + let dish2 = await Dish.createOrUpdate(dishGenerator({name: "test fish", price: 15.2, concept: "Recursion"})); + + await Order.addDish({id: order.id}, dish1, 5, [], "", "test"); + await Order.addDish({id: order.id}, dish2, 4, [], "", "test"); + + await discountAdapter.addPromotionHandler(discountEx) + + order = await Order.findOne(order.id) + await discountAdapter.processOrder(order) + + let result = await Order.findOne(order.id) + // console.log(result) + + expect(result.discountTotal).to.equal(11.13); + + }) }); diff --git a/test/mocks/adapter/discount.js b/test/mocks/adapter/discount.js index ea788ded..a92b8a4e 100644 --- a/test/mocks/adapter/discount.js +++ b/test/mocks/adapter/discount.js @@ -3,8 +3,8 @@ Object.defineProperty(exports, "__esModule", { value: true }); exports.InMemoryDiscountAdapter = void 0; const AbstractPromotion_1 = require("../../../adapters/promotion/AbstractPromotion"); const findModelInstance_1 = require("../../../libs/findModelInstance"); -const promotionAdapter_1 = require("./../../../adapters/promotion/default/promotionAdapter"); const stringsInArray_1 = require("../../../libs/stringsInArray"); +const configuredPromotion_1 = require("../../../adapters/promotion/default/configuredPromotion"); class InMemoryDiscountAdapter extends AbstractPromotion_1.default { constructor() { super(...arguments); @@ -12,9 +12,6 @@ class InMemoryDiscountAdapter extends AbstractPromotion_1.default { this.isJoint = true; this.name = "New Year"; this.isPublic = false; - // public enable: boolean = true; - // public isDeleted: boolean = false; - // public createdByUser: boolean = false; this.description = "some text"; this.concept = ["NewYear", "Happy Birthday", "origin"]; this.configDiscount = { @@ -47,7 +44,7 @@ class InMemoryDiscountAdapter extends AbstractPromotion_1.default { return false; } async action(order) { - await promotionAdapter_1.PromotionAdapter.applyPromotion(order.id, this.configDiscount, this.id); + await configuredPromotion_1.default.applyPromotion(order.id, this.configDiscount, this.id); return { message: "test", type: "test", diff --git a/test/mocks/adapter/discount.ts b/test/mocks/adapter/discount.ts index 30874107..2f40c3db 100644 --- a/test/mocks/adapter/discount.ts +++ b/test/mocks/adapter/discount.ts @@ -7,6 +7,7 @@ import Dish from './../../../models/Dish'; import findModelInstanceByAttributes from "../../../libs/findModelInstance"; import { PromotionAdapter } from './../../../adapters/promotion/default/promotionAdapter'; import { stringsInArray } from "../../../libs/stringsInArray"; +import configuredPromotion from "../../../adapters/promotion/default/configuredPromotion"; export class InMemoryDiscountAdapter extends AbstractPromotionHandler { public id: string = "aaaa"; @@ -49,7 +50,7 @@ export class InMemoryDiscountAdapter extends AbstractPromotionHandler { } public async action(order: Order): Promise { - await PromotionAdapter.applyPromotion(order.id, this.configDiscount, this.id) + await configuredPromotion.applyPromotion(order.id, this.configDiscount, this.id) return { message: "test", type: "test", diff --git a/test/unit/discount/discount.test.ts b/test/unit/discount/discount.test.ts index 7da572fb..b32045ed 100644 --- a/test/unit/discount/discount.test.ts +++ b/test/unit/discount/discount.test.ts @@ -14,6 +14,7 @@ import Group from './../../../models/Group'; import Dish from './../../../models/Dish'; import Order, { PromotionState } from './../../../models/Order'; import { stringsInArray } from '../../../libs/stringsInArray'; +import configuredPromotion from '../../../adapters/promotion/default/configuredPromotion'; describe('Discount', function () { // TODO: tests throw get adapter @@ -34,7 +35,7 @@ describe('Discount', function () { }, name: "1-name", description: "string", - concept: ["origin","clear"], + concept: ["origin","clear","Happy Birthday"], condition: (arg: Group | Dish | Order): boolean =>{ if (findModelInstanceByAttributes(arg) === "Order" && stringsInArray(arg.concept, discountEx.concept) ) { // Order.populate() @@ -56,12 +57,7 @@ describe('Discount', function () { }, action: async (order: Order): Promise => { // console.log("ACTION ================awdawdawd") - await PromotionAdapter.applyPromotion(order.id, discountEx.configDiscount, discountEx.id) - return { - message: "test", - type: "test", - state: {} - } + return await configuredPromotion.applyPromotion(order.id, discountEx.configDiscount, discountEx.id) }, isPublic: true, isJoint: true, @@ -108,7 +104,7 @@ describe('Discount', function () { // await DiscountAdapter.addPromotionHandler(discInMemory) let discount = await Promotion.find({}); let discountById = await PromotionAdapter.getPromotionHandlerById(discountEx.id) - // console.log(discount); + // console.log(discountById); expect(discount[0]).to.be.an("object"); expect(discountById).to.be.an("object"); @@ -126,7 +122,7 @@ describe('Discount', function () { await discountAdapter.addPromotionHandler(discountEx) - await PromotionAdapter.applyPromotion(order.id, discountEx.configDiscount, discountEx.id) + await configuredPromotion.applyPromotion(order.id, discountEx.configDiscount, discountEx.id) // const orderDishes = await OrderDish.find({ order: order.id }).populate("dish"); // console.log(orderDishes) @@ -152,7 +148,8 @@ describe('Discount', function () { // let result1 = await Dish.findOne(dish1.id) // DiscountAdapter.applyToOrder(order) - await PromotionAdapter.applyPromotion(order.id, discountEx.configDiscount, discountEx.id) + await configuredPromotion.applyPromotion(order.id, discountEx.configDiscount, discountEx.id) + // await PromotionAdapter.applyPromotion(order.id, discountEx.configDiscount, discountEx.id) let result = await Order.findOne(order.id) //.populate("dishes"); // console.log(result, "get discount order") @@ -165,8 +162,8 @@ describe('Discount', function () { await Order.updateOne({id: order.id}, {concept: "origin",user: "user"}); //Decimal check 15.2, 10.1 - let dish1 = await Dish.createOrUpdate(dishGenerator({name: "test disha", price: 10.1, concept: "origin"})); - let dish2 = await Dish.createOrUpdate(dishGenerator({name: "test fisha", price: 15.2, concept: "origin"})); + let dish1 = await Dish.createOrUpdate(dishGenerator({name: "test disha", price: 10.1, concept: "clear"})); + let dish2 = await Dish.createOrUpdate(dishGenerator({name: "test fisha", price: 15.2, concept: "clear"})); await Order.addDish({id: order.id}, dish1, 5, [], "", "testa"); @@ -184,10 +181,10 @@ describe('Discount', function () { // console.log(result, "get discount order") expect(result.discountTotal).to.equal(11.97); - // let dish3 = await Dish.createOrUpdate(dishGenerator({name: "test disha", price: 10, concept: "a"})); - // let dish4 = await Dish.createOrUpdate(dishGenerator({name: "test fisha", price: 15, concept: "a"})); - // await Order.addDish({id: order.id}, dish3, 5, [], "", "test"); - // await Order.addDish({id: order.id}, dish4, 4, [], "", "test"); + let dish3 = await Dish.createOrUpdate(dishGenerator({name: "test disha", price: 10, concept: "a"})); + let dish4 = await Dish.createOrUpdate(dishGenerator({name: "test fisha", price: 15, concept: "a"})); + await Order.addDish({id: order.id}, dish3, 5, [], "", "test"); + await Order.addDish({id: order.id}, dish4, 4, [], "", "test"); order = await Order.findOne(order.id) @@ -217,7 +214,7 @@ describe('Discount', function () { // let result1 = await Dish.findOne(dish1.id) // DiscountAdapter.applyToOrder(order) - await PromotionAdapter.applyPromotion(order.id, discInMemory.configDiscount, discInMemory.id) + await configuredPromotion.applyPromotion(order.id, discInMemory.configDiscount, discInMemory.id) let result = await Order.findOne(order.id) //.populate("dishes"); // console.log(result, "get discount order") @@ -229,11 +226,11 @@ describe('Discount', function () { let order = await Order.create({id: "test-discounts-on-different-types"}).fetch(); await Order.updateOne({id: order.id}, {concept: "origin",user: "user"}); - let dish1 = await Dish.createOrUpdate(dishGenerator({name: "test dish", price: 10.1, concept: "origin"})); - let dish2 = await Dish.createOrUpdate(dishGenerator({name: "test fish", price: 15.2, concept: "origin"})); - let dish3 = await Dish.createOrUpdate(dishGenerator({name: "test disha", price: 10.1, concept: "origin"})); - let dish4 = await Dish.createOrUpdate(dishGenerator({name: "test fisha", price: 15.2, concept: "origin"})); - let dish5 = await Dish.createOrUpdate(dishGenerator({name: "test fishw", price: 15.2, concept: "origin"})); + let dish1 = await Dish.createOrUpdate(dishGenerator({name: "test dish", price: 10.1, concept: "Happy Birthday"})); + let dish2 = await Dish.createOrUpdate(dishGenerator({name: "test fish", price: 15.2, concept: "Happy Birthday"})); + let dish3 = await Dish.createOrUpdate(dishGenerator({name: "test disha", price: 10.1, concept: "Happy Birthday"})); + let dish4 = await Dish.createOrUpdate(dishGenerator({name: "test fisha", price: 15.2, concept: "Happy Birthday"})); + let dish5 = await Dish.createOrUpdate(dishGenerator({name: "test fishw", price: 15.2, concept: "Happy Birthday"})); await Order.addDish({id: order.id}, dish1, 5, [], "", "testa2"); await Order.addDish({id: order.id}, dish2, 4, [], "", "tes"); @@ -258,11 +255,11 @@ describe('Discount', function () { let order = await Order.create({id: "test-different-types-and-concept"}).fetch(); await Order.updateOne({id: order.id}, {concept: "origin",user: "user"}); - let dish1 = await Dish.createOrUpdate(dishGenerator({name: "test dish", price: 10.1, concept: "origin"})); + let dish1 = await Dish.createOrUpdate(dishGenerator({name: "test dish", price: 10.1, concept: "Happy Birthday"})); let dish2 = await Dish.createOrUpdate(dishGenerator({name: "test fish", price: 15.2, concept: "NewYear"})); - let dish3 = await Dish.createOrUpdate(dishGenerator({name: "test disha", price: 10.1, concept: "origin"})); + let dish3 = await Dish.createOrUpdate(dishGenerator({name: "test disha", price: 10.1, concept: "Happy Birthday"})); let dish4 = await Dish.createOrUpdate(dishGenerator({name: "test fisha", price: 15.2, concept: "NewYear"})); - let dish5 = await Dish.createOrUpdate(dishGenerator({name: "test fishw", price: 15.2, concept: "origin"})); + let dish5 = await Dish.createOrUpdate(dishGenerator({name: "test fishw", price: 15.2, concept: "Happy Birthday"})); await Order.addDish({id: order.id}, dish1, 5, [], "", "testa2"); await Order.addDish({id: order.id}, dish2, 4, [], "", "tes");