UNPKG

@chevre/domain

Version:

Chevre Domain Library for Node.js

187 lines (186 loc) 9.32 kB
"use strict"; var __awaiter = (this && this.__awaiter) || function (thisArg, _arguments, P, generator) { function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); } return new (P || (P = Promise))(function (resolve, reject) { function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } } function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } } function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); } step((generator = generator.apply(thisArg, _arguments || [])).next()); }); }; Object.defineProperty(exports, "__esModule", { value: true }); exports.preStart = void 0; exports.start = start; exports.confirm = confirm; exports.exportTasksById = exportTasksById; /** * 返品取引サービス */ const moment = require("moment-timezone"); const factory = require("../../factory"); const factory_1 = require("./returnOrder/exportTasks/factory"); const potentialActions_1 = require("./returnOrder/potentialActions"); const preStart_1 = require("./returnOrder/preStart"); Object.defineProperty(exports, "preStart", { enumerable: true, get: function () { return preStart_1.preStart; } }); const errorHandler_1 = require("../../errorHandler"); /** * 返品取引開始 */ function start(params) { return (repos) => __awaiter(this, void 0, void 0, function* () { const { transactionObject, expiresInSeconds, seller } = yield (0, preStart_1.preStart)(params)(repos); const returnOrderAttributes = { project: params.project, typeOf: factory.transactionType.ReturnOrder, agent: params.agent, seller: { id: String(seller.id), typeOf: seller.typeOf, name: seller.name }, object: transactionObject, expiresInSeconds }; let returnOrderTransaction; try { returnOrderTransaction = yield repos.transaction.start(returnOrderAttributes); } catch (error) { if (yield (0, errorHandler_1.isMongoError)(error)) { // 同一取引に対して返品取引を作成しようとすると、MongoDBでE11000 duplicate key errorが発生する // tslint:disable-next-line:no-single-line-block-comment /* istanbul ignore else */ if (error.code === errorHandler_1.MongoErrorCode.DuplicateKey) { throw new factory.errors.Argument('orderNumber', 'Already returned'); } } throw error; } return returnOrderTransaction; }); } function saveMessagesIfNeeded(params) { return (repos) => __awaiter(this, void 0, void 0, function* () { const { project, order, emailMessages, seller } = params; if (emailMessages.length > 0) { const { orderNumber } = order; // const saveMessageResult = await repos.message.upsertByIdentifier( // emailMessages.map(({ identifier, name, about, text, toRecipient, sender }) => { // return { // identifier, name, about, text, toRecipient, sender, // project: { id: project.id, typeOf: factory.organizationType.Project }, // provider: { id: seller.id, typeOf: factory.organizationType.Corporation }, // mainEntity: { orderNumber, typeOf: factory.order.OrderType.Order } // }; // }) // ); for (const { identifier, name, about, text, toRecipient, sender } of emailMessages) { yield repos.message.upsertOneByIdentifier({ identifier, name, about, text, toRecipient, sender, project: { id: project.id, typeOf: factory.organizationType.Project }, provider: { id: seller.id, typeOf: factory.organizationType.Corporation }, mainEntity: { orderNumber, typeOf: factory.order.OrderType.Order } }); } } }); } /** * 取引確定 */ function confirm(params) { return (repos // settings: Settings ) => __awaiter(this, void 0, void 0, function* () { var _a; const transaction = yield repos.transaction.projectFieldsById({ typeOf: factory.transactionType.ReturnOrder, id: params.id }, ['typeOf', 'status', 'project', 'agent', 'object', 'result']); if (transaction.status === factory.transactionStatusType.Confirmed) { // すでに確定済の場合 return transaction.result; } else if (transaction.status === factory.transactionStatusType.Expired) { throw new factory.errors.Argument('transaction', 'Transaction already expired'); } else if (transaction.status === factory.transactionStatusType.Canceled) { throw new factory.errors.Argument('transaction', 'Transaction already canceled'); } if (typeof ((_a = params.agent) === null || _a === void 0 ? void 0 : _a.id) === 'string' && transaction.agent.id !== params.agent.id) { throw new factory.errors.Forbidden('Transaction not yours'); } // ひとまず同時返品可能な注文数を1に限定(2022-04-28~) if (transaction.object.order.length !== 1) { throw new factory.errors.Argument('object.order', 'number of orders must be 1'); } const returningOrders = yield repos.order.projectFields({ limit: 1, page: 1, project: { id: { $eq: transaction.project.id } }, confirmationNumbers: [transaction.object.order[0].confirmationNumber], orderNumbers: [transaction.object.order[0].orderNumber] }, { inclusion: [ 'confirmationNumber', 'customer', 'identifier', 'orderDate', 'orderNumber', 'orderStatus', 'orderedItem', 'paymentMethods', 'price', 'priceCurrency', 'project', 'seller', 'typeOf' ] }); // デフォルトEメールメッセージを検索 let emailMessageOnOrderReturned; if (repos.emailMessage !== undefined) { const searchEmailMessagesResult = yield repos.emailMessage.search({ limit: 1, page: 1, project: { id: { $eq: transaction.project.id } }, about: { identifier: { $eq: factory.creativeWork.message.email.AboutIdentifier.OnOrderReturned } } }); emailMessageOnOrderReturned = searchEmailMessagesResult.shift(); } const setting = yield repos.setting.findOne({ project: { id: { $eq: '*' } } }, ['defaultSenderEmail']); if (typeof (setting === null || setting === void 0 ? void 0 : setting.defaultSenderEmail) !== 'string') { throw new factory.errors.NotFound('setting.defaultSenderEmail'); } const result = {}; const { emailMessages, potentialActions } = yield (0, potentialActions_1.createPotentialActions)(Object.assign(Object.assign({ dateReturned: params.object.order.dateReturned, orders: returningOrders, transaction: transaction }, (params.potentialActions !== undefined) ? { potentialActions: params.potentialActions } : undefined), (emailMessageOnOrderReturned !== undefined) ? { emailMessageOnOrderReturned } : undefined), // settings setting); // save messages(2024-06-27~) yield saveMessagesIfNeeded({ project: { id: transaction.project.id }, order: { orderNumber: returningOrders[0].orderNumber }, seller: { id: returningOrders[0].seller.id }, emailMessages })(repos); // ステータス変更 yield repos.transaction.confirm({ typeOf: transaction.typeOf, id: transaction.id, result, potentialActions }); return result; }); } /** * 取引のタスクを出力します * 複数タスクが生成されます * この関数では、取引のタスクエクスポートステータスは見ません */ function exportTasksById(params) { return (repos // settings: Settings ) => __awaiter(this, void 0, void 0, function* () { const transaction = yield repos.transaction.projectFieldsById({ typeOf: factory.transactionType.ReturnOrder, id: params.id }, ['typeOf', 'status', 'project', 'endDate', 'startDate', 'object', 'potentialActions']); // タスク実行日時バッファの指定があれば調整 let taskRunsAt = new Date(); if (typeof params.runsTasksAfterInSeconds === 'number') { taskRunsAt = moment(taskRunsAt) .add(params.runsTasksAfterInSeconds, 'seconds') .toDate(); } // search settings const setting = yield repos.setting.findOne({ project: { id: { $eq: '*' } } }, ['storage']); const taskAttributes = (0, factory_1.createTasks)({ transaction, runsAt: taskRunsAt }, setting // settings ); yield repos.task.saveMany(taskAttributes, { emitImmediately: true }); }); }