|
@@ -3,13 +3,117 @@ const { CrudService } = require('naf-framework-mongoose-free/lib/service');
|
|
|
const { BusinessError, ErrorCode } = require('naf-core').Error;
|
|
|
const _ = require('lodash');
|
|
|
const assert = require('assert');
|
|
|
-
|
|
|
+const moment = require('moment');
|
|
|
//
|
|
|
class PayOrderService extends CrudService {
|
|
|
constructor(ctx) {
|
|
|
super(ctx, 'payorder');
|
|
|
this.model = this.ctx.model.Business.PayOrder;
|
|
|
this.payService = this.ctx.service.wxpay;
|
|
|
+ this.lessonStudentModel = this.ctx.model.Business.LessonStudent;
|
|
|
+ }
|
|
|
+
|
|
|
+ async beforeCreate(data) {
|
|
|
+ if (!_.get(data, 'order_no')) data.order_no = this.getOrderNo();
|
|
|
+ return data;
|
|
|
+ }
|
|
|
+
|
|
|
+ async afterCreate(body, data) {
|
|
|
+ await this.syncData(data);
|
|
|
+ const wxSign = await this.payService.create(data);
|
|
|
+ return { data, wxSign };
|
|
|
+ }
|
|
|
+
|
|
|
+ async afterUpdate(filter, body, data) {
|
|
|
+ await this.syncData(data);
|
|
|
+ return data;
|
|
|
+ }
|
|
|
+ /**
|
|
|
+ * 支付同步
|
|
|
+ * @param {Object} data 支付单数据
|
|
|
+ */
|
|
|
+ async syncData(data) {
|
|
|
+ const pay_for = _.get(data, 'pay_for');
|
|
|
+ if (!pay_for) {
|
|
|
+ // 不知道该去同步哪个表的支付状态,不处理
|
|
|
+ return;
|
|
|
+ }
|
|
|
+ if (pay_for === 'Lesson') {
|
|
|
+ // 因为上课产生的支付,去找lessonStudent,修改指定学生的支付状态
|
|
|
+ const { form_id: _id, status: is_pay } = data;
|
|
|
+ await this.lessonStudentModel.updateOne({ _id }, { is_pay });
|
|
|
+ }
|
|
|
+ }
|
|
|
+
|
|
|
+ /**
|
|
|
+ * 重新支付
|
|
|
+ * @param {String} body 参数体
|
|
|
+ * @property {String} id 数据id
|
|
|
+ */
|
|
|
+ async toRePay({ id }) {
|
|
|
+ const data = await this.model.findById(id);
|
|
|
+ if (!data) throw new BusinessError(ErrorCode.DATA_NOT_EXIST, '未找到支付的信息');
|
|
|
+ // 找到这个订单,然后获取到订单号
|
|
|
+ const { order_no } = data;
|
|
|
+ // 利用订单号去查询微信那边,该订单是否还存在
|
|
|
+ const wxOrder = await this.payService.search(order_no);
|
|
|
+ let wxSign;
|
|
|
+ if (_.get(wxOrder, 'trade_state') === 'NOTPAY') {
|
|
|
+ // 未支付就用原数据,去支付
|
|
|
+ wxSign = await this.payService.create(data);
|
|
|
+ } else if (_.get(wxOrder, 'trade_state') === 'SUCCESS') {
|
|
|
+ throw new BusinessError(ErrorCode.SERVICE_FAULT, '订单已支付,无需重复支付');
|
|
|
+ } else if (_.get(wxOrder, 'trade_state') === 'USERPAYING') {
|
|
|
+ throw new BusinessError(ErrorCode.SERVICE_FAULT, '订单支付中');
|
|
|
+ } else {
|
|
|
+ // 其他情况就当订单被关闭了.直接新订单
|
|
|
+ const order_no = this.getOrderNo();
|
|
|
+ data.order_no = order_no;
|
|
|
+ await data.save();
|
|
|
+ wxSign = await this.payService.create(data);
|
|
|
+ }
|
|
|
+ return { data, wxSign };
|
|
|
+ }
|
|
|
+
|
|
|
+ /**
|
|
|
+ * 申请退款
|
|
|
+ * @param {Object} body 参数体
|
|
|
+ * @property {String} id 支付单的数据id
|
|
|
+ */
|
|
|
+ async toRefund({ id }) {
|
|
|
+ // 查询支付
|
|
|
+ const data = await this.model.findById(id);
|
|
|
+ if (!data) throw new BusinessError(ErrorCode.DATA_NOT_EXIST, '未找到要退款的支付数据');
|
|
|
+ const wxOrderReq = await this.payService.search(data.order_no);
|
|
|
+ if (wxOrderReq) {
|
|
|
+ if (!wxOrderReq) throw new BusinessError(ErrorCode.DATA_NOT_EXIST, '未查询到微信支付订单');
|
|
|
+ const wxRefundReq = await this.payService.refund(data.order_no, '退赛');
|
|
|
+ if (wxRefundReq) {
|
|
|
+ if (wxRefundReq.status !== 'REFUND') throw new BusinessError(ErrorCode.SERVICE_FAULT, '退款失败');
|
|
|
+ // 退款成功
|
|
|
+ data.status = '-3';
|
|
|
+ await data.save();
|
|
|
+ await this.syncData(data);
|
|
|
+ return 'ok';
|
|
|
+ }
|
|
|
+ }
|
|
|
+ throw new BusinessError(ErrorCode.SERVICE_FAULT, '查询微信支付订单失败');
|
|
|
+ }
|
|
|
+
|
|
|
+ /**
|
|
|
+ * 关闭订单
|
|
|
+ * @param {String} id 支付id
|
|
|
+ * @return {Object} 关闭订单结果
|
|
|
+ */
|
|
|
+ async closeOrder(id) {
|
|
|
+ const data = await this.model.findById(id);
|
|
|
+ if (!data) throw new BusinessError(ErrorCode.DATA_NOT_EXIST, '未找到要退款的支付数据');
|
|
|
+ const res = await this.payService.close(data.order_no);
|
|
|
+ return res;
|
|
|
+ }
|
|
|
+
|
|
|
+ getOrderNo() {
|
|
|
+ return `ONCAPP${moment().format('YYYYMMDDHHmmss')}-${_.random(1, 999999)}`;
|
|
|
}
|
|
|
}
|
|
|
|