import formatBatchItemStatus from './formatBatchItemStatus' import _ from 'lodash' import getItemDataId from './getItemDataId' import getDisplayStatusKey from './getDisplayStatusKey' export default function apiOrderToAppOrder (apiOrder: IOrder): IAppOrder { const appOrder: IAppOrder = { ...apiOrder, batches: apiOrder.batches?.map(apiBatch => toAppBatch(apiBatch, apiOrder)), // modifiers 為變價新格式,若後端還沒有,從將原本的 discount 格式轉換進來 modifiers: apiOrder.modifiers ?? [apiOrder.discount as IPriceModifier], // payments 為付款新格式,若後端還沒有,從將原本的相關欄位轉換進來 payments: apiOrder.payments?.map(apiPayment => toAppPayment(apiPayment)) ?? [], subOrderIds: apiOrder.subOrderIds ?? [], displayStatusKey: 'unknow', } appOrder.displayStatusKey = getDisplayStatusKey(appOrder) return appOrder } function toAppPayment (apiPayment: IOrderPayment): IAppPayment { return { ...apiPayment, isSended: true, } } function toAppBatch (apiBatch: IOrderBatch, apiOrder: IOrder): IAppOrderBatch { return { ...apiBatch, id: apiBatch.batchId, items: toAppBatchItems(apiBatch.items, apiOrder), } } function toAppBatchItems (apiBatchItems: IOrderBatchItem[], apiOrder: IOrder): IAppBatchItem[] { // group by set const setIndexGroups = _.groupBy(apiBatchItems, 'setMenuIndex') // setMenuIndex null 就是單點的項目 const batchItems: IAppBatchItem[] = [] if (setIndexGroups.null != null) { setIndexGroups.null.forEach(item => { try { const convertedSingleItems = toAppBatchItem(item, apiOrder) batchItems.push(...convertedSingleItems) } catch (error) { console.log(error) } }) } // 處理完單點項目後移除 null array delete setIndexGroups.null // 處理套餐 group _.forEach(setIndexGroups, (setItems) => { // 餐點中的其中一個是套餐本身 const mainSetItemIndex = setItems.findIndex(setItem => setItem.setId !== '') let mainSetItem: IOrderBatchItem & {setItems?: IOrderBatchItem[], isSet?: boolean} if (mainSetItemIndex >= 0) { // 移除套餐本身 mainSetItem = setItems.splice(mainSetItemIndex, 1)[0] // 將套餐餐點放入 mainSetItem mainSetItem.setItems = setItems mainSetItem.isSet = true // 整理成 app 格式 try { const convertedAppBatchItems = toAppBatchItem(mainSetItem, apiOrder) batchItems.push(...convertedAppBatchItems) } catch (error) { console.log(error) } } }) return batchItems } function toAppBatchItem (item: IOrderBatchItem & {setItems?: IOrderBatchItem[], isSet?: boolean}, apiOrder: IOrder): IAppBatchItem[] { const surchargeModifier = apiOrder.surcharge const isSet = Boolean(item.isSet) /** * 後端給的 item 注意事項 * item 會把相同 menuId 的品項都組在一起 * item.ids 會有每個 batch item 各自的 id * item.options 會有每個 batch item 各自的 options * item.originalTotal 為原價 * quantity * item.price 為原價 - discount (單個的價錢) * item.prices 為原價 - discount (單個的價錢) * item.totalDiscount 為計算數量 modifiers 後的總折扣 * item.total 已計算數量 discount 及 modifiers 但未計算服務費 */ const dataIdItemMap: {[dataId: string]: IAppBatchItem} = {} item.ids.forEach((id, index) => { // 原價 const price = item.price // 單個餐點的價格(未算服務費) const totalWithoutSurcharge = item.totals[index] // menu item 折扣 const discount = item.discounts[index] ?? 0 // 折扣總計 const totalDiscount = item.totalDiscounts[index] // 其他折扣 const modifiers: IPriceModifier[] = item.modifiers[index] ?? [] // 計算服務費 const surcharge = totalWithoutSurcharge * surchargeModifier.percent / 100 + surchargeModifier.amount // 計算包含服務費的 total const total = item.cancelled ? 0 : (Number(totalWithoutSurcharge) + Number(surcharge)) const setItems: IAppBatchItem[] = [] if (isSet && item.setItems != null) { item.setItems.map(setItem => { const convertedSetItems = toAppBatchItem(setItem, apiOrder) setItems.push(...convertedSetItems) }) } const appBatchItem: IAppBatchItem = { ...item, id: id, menuId: item.originMenuId, // 原本的 menuId 不可信,用 originMenuId 取代 quantity: 1, totalDiscount, price, discount, surcharge, total, key: id, modifiers, options: toAppBatchItemOptions(item.options[index] ?? []), tags: toAppBatchItemTags(item.tags[index] ?? []), isSet: isSet, setItems: setItems, status: '', } if (isSet) { // set 的 discountTotal, surcharge, total 需連底下餐點一起加總顯示 appBatchItem.totalDiscount += Number(_.sumBy(appBatchItem.setItems, 'totalDiscount')) appBatchItem.surcharge += Number(_.sumBy(appBatchItem.setItems, 'surcharge')) appBatchItem.total += Number(_.sumBy(appBatchItem.setItems, 'total')) // set 的 status 改顯示套餐底下的餐點名稱 appBatchItem.status = appBatchItem.setItems.map(setItem => { if (setItem.status.length > 0) { return `${setItem.name}(setItem.status)` } return setItem.name }).join('/') } // 讓相同的設定的 item 有相同的 dataId const dataId = getItemDataId(appBatchItem) const sameIdItem = dataIdItemMap[dataId] if (sameIdItem == null) { dataIdItemMap[dataId] = appBatchItem } else { // 將這個 item 加入原有的 item sameIdItem.totalDiscount += appBatchItem.totalDiscount sameIdItem.surcharge += appBatchItem.surcharge sameIdItem.total += appBatchItem.total sameIdItem.quantity += 1 } }) const appBatchItems = _.map(dataIdItemMap, appBatchItem => { return formatBatchItemStatus(appBatchItem) }) return appBatchItems } function toAppBatchItemOptions (options: IOrderBatchItemOption[] = []): IAppBatchItemOption[] { const appOptions = options.map(option => { return { ...option, optionItemId: option.optionId, } }) return appOptions } function toAppBatchItemTags (tags: IMenuTag[] = []): IMenuTag[] { return tags }