| 123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335 | 'use strict';/** * * * @author Mai * @date 2018/7/16 * @version */const auditConst = require('../const/audit').flow;module.exports = app => {    class MeasureAudit extends app.BaseService {        /**         * 构造函数         *         * @param {Object} ctx - egg全局变量         * @return {void}         */        constructor(ctx) {            super(ctx);            this.tableName = 'measure_audit';        }        /**         * 获取 中间计量 审核人信息         *         * @param {uuid} mid - 中间计量id         * @param {Number} auditorId - 审核人id         * @param {Number} times - 第几次审批         * @return {Promise<*>}         */        async getAuditor(mid, auditorId, times = 1) {            const sql = 'SELECT ma.*, pa.`name`, pa.`company`, pa.`role`, pa.`mobile`, pa.`telephone` ' +                'FROM ?? AS ma, ?? AS pa ' +                'WHERE ma.`mid` = ? and ma.`audit_id` = ? and ma.`times` = ?' +                '    and ma.`audit_id` = pa.`id`';            const sqlParam = [this.tableName, this.ctx.service.projectAccount.tableName, mid, auditorId, times];            return await this.db.queryOne(sql, sqlParam);        }        /**         * 获取 中间计量 审核人列表信息         *         * @param {uuid} mid - 中间计量id         * @param {Number} times - 第几次审批         * @return {Promise<*>}         */        async getAuditors(mid, times = 1) {            const sql = 'SELECT ma.*, pa.`name`, pa.`company`, pa.`role`, pa.`mobile`, pa.`telephone` ' +                'FROM ?? AS ma, ?? AS pa ' +                'WHERE ma.`mid` = ? and ma.`times` = ?' +                '    and ma.`audit_id` = pa.`id` and ma.`order` > 0';            const sqlParam = [this.tableName, this.ctx.service.projectAccount.tableName, mid, times];            return await this.db.query(sql, sqlParam);        }        /**         * 获取 中间计量 当前审核人         *         * @param {uuid} mid - 中间计量id         * @param {Number} times - 第几次审批         * @return {Promise<*>}         */        async getCurAuditor(mid, times = 1) {            const sql = 'SELECT ma.`audit_id`, pa.`name`, pa.`company`, pa.`role`, pa.`mobile`, pa.`telephone`, ma.`times`, ma.`order`, ma.`status`, ma.`opinion`, ma.`begin_time`, ma.`end_time` ' +                'FROM ?? AS ma, ?? AS pa ' +                'WHERE ma.`mid` = ? and ma.`status` = ? and ma.`times` = ?' +                '    and ma.`audit_id` = pa.`id`';            const sqlParam = [this.tableName, this.ctx.service.projectAccount.tableName, mid, auditConst.status.checking, times];            return await this.db.queryOne(sql, sqlParam);        }        /**         * 获取 中间计量 最新审核顺序         *         * @param {uuid} mid - 中间计量id         * @param {Number} times - 第几次审批         * @return {Promise<number>}         */        async getNewOrder(mid, times = 1) {            const sql = 'SELECT Max(??) As max_order FROM ?? Where `mid` = ? and `times` = ? and `order` > 0';            const sqlParam = ['order', this.tableName, mid, times];            const result = await this.db.queryOne(sql, sqlParam);            return result && result.max_order ? result.max_order + 1 : 1;        }        /**         * 新增审核人         *         * @param {Number} tenderId - 标段id         * @param {uuid} mid - 中间计量id         * @param {Number} auditorId - 审核人id         * @param {Number} times - 第几次审批         * @return {Promise<number>}         */        async addAuditor(tenderId, mid, auditorId, times = 1) {            const newOrder = await this.getNewOrder(mid, times);            const data = {                tender_id: tenderId,                mid,                audit_id: auditorId,                times,                order: newOrder,                status: auditConst.status.uncheck,            };            const result = await this.db.insert(this.tableName, data);            return result.effectRows = 1;        }        /**         * 移除审核人时,同步其后审核人order         * @param transaction - 事务         * @param {uuid} mid - 中间计量id         * @param {Number} auditorId - 审核人id         * @param {Number} times - 第几次审批         * @return {Promise<*>}         * @private         */        async _syncOrderByDelete(transaction, mid, order, times) {            this.initSqlBuilder();            this.sqlBuilder.setAndWhere('mid', {                value: this.db.escape(mid),                operate: '=',            });            this.sqlBuilder.setAndWhere('order', {                value: order,                operate: '>=',            });            this.sqlBuilder.setAndWhere('times', {                value: times,                operate: '=',            });            this.sqlBuilder.setUpdateData('order', {                value: 1,                selfOperate: '-',            });            const [sql, sqlParam] = this.sqlBuilder.build(this.tableName, 'update');            const data = await transaction.query(sql, sqlParam);            return data;        }        /**         * 移除审核人         *         * @param {uuid} mid - 中间计量id         * @param {Number} auditorId - 审核人id         * @param {Number} times - 第几次审批         * @return {Promise<boolean>}         */        async deleteAuditor(mid, auditorId, times = 1) {            const transaction = await this.db.beginTransaction();            try {                const condition = { mid, audit_id: auditorId, times };                const auditor = await this.getDataByCondition(condition);                if (!auditor) {                    throw '该审核人不存在';                }                await this._syncOrderByDelete(transaction, mid, auditor.order, times);                await transaction.delete(this.tableName, condition);                await transaction.commit();            } catch (err) {                await transaction.rollback();                throw err;            }            return true;        }        _sumBills(bills) {            const result = { deal: 0, qc: 0 };            for (const b of bills) {                result.deal = result.deal + (b.deal_totalprice ? b.deal_totalprice : 0);                result.qc = result.qc + (b.qc_totalprice ? b.qc_totalprice : 0);            }            return result;        }        /**         * 拷贝原报的历史数据         *         * @param transacation - 事务         * @param {uuid} mid - 中间计量         * @param {Number} times - 次数         * @return {Promise<void>}         * @private         */        async _copyReportBillsHistory(transacation, mid, times) {            const bills = await this.ctx.service.measureBills.getAllDataByCondition({ where: { mid } });            const sum = this._sumBills(bills);            const history = await this.getDataByCondition({ mid, times, order: 0 });            if (history) {                await transacation.update(this.tableName, {                    id: history.id,                    bills: JSON.stringify(bills),                    deal_sum: sum.deal,                    qc_sum: sum.qc,                });            } else {                const measure = await this.ctx.service.measure.getDataByCondition({ mid });                await transacation.insert(this.tableName, {                    tender_id: measure.tender_id,                    mid,                    times,                    order: 0,                    audit_id: measure.user_id,                    status: 0,                    bills: JSON.stringify(bills),                    deal_sum: sum.deal,                    qc_sum: sum.qc,                });            }            return sum;        }        /**         * 开始审批         *         * @param {uuid} mid - 中间计量id         * @param {Number} times - 第几次审批         * @return {Promise<boolean>}         */        async start(mid, times = 1) {            const audit = await this.getDataByCondition({ mid, times, order: 1 });            if (!audit) {                throw '审核人信息错误';            }            const transaction = await this.db.beginTransaction();            try {                // 记录历史数据                const sum = await this._copyReportBillsHistory(transaction, mid, times);                // 更新审核人状态                await transaction.update(this.tableName, {                    id: audit.id,                    status: auditConst.status.checking,                    begin_time: new Date(),                });                // 改变中间计量状态                await transaction.update(this.ctx.service.measure.tableName, {                    times,                    status: auditConst.status.checking,                    deal_sum: sum.deal,                    qc_sum: sum.qc,                }, { where: { mid } });                await transaction.commit();            } catch (err) {                await transaction.rollback();                throw err;            }            return true;        }        /**         * 审批         * @param {uuid} mid - 中间计量id         * @param {auditConst.status.checked|auditConst.status.checkNo} checkType - 审批结果         * @param {Number} times - 第几次审批         * @return {Promise<void>}         */        async check(mid, checkType, opinion, times = 1) {            if (checkType !== auditConst.status.checked && checkType !== auditConst.status.checkNo) {                throw '提交数据错误';            }            const transaction = await this.db.beginTransaction();            try {                // 整理当前流程审核人状态更新                const time = new Date();                const audit = await this.getDataByCondition({ mid, times, status: auditConst.status.checking });                if (!audit) {                    throw '审核数据错误';                }                // 更新当前审核流程                const bills = await this.ctx.service.measureBills.getAllDataByCondition({ where: { mid } });                const sum = this._sumBills(bills);                await transaction.update(this.tableName, {                    id: audit.id,                    status: checkType,                    opinion,                    end_time: time,                    bills: JSON.stringify(bills),                    deal_sum: sum.deal,                    qc_sum: sum.qc,                });                const measureTable = this.ctx.service.measure.tableName;                if (checkType === auditConst.status.checked) {                    const nextAudit = await this.getDataByCondition({ mid, times, order: audit.order + 1 });                    // 无下一审核人表示,审核结束                    if (nextAudit) {                        await transaction.update(this.tableName, { id: nextAudit.id, status: auditConst.status.checking, begin_time: time });                        await transaction.update(measureTable, { deal_sum: sum.deal, qc_sum: sum.qc }, { where: { mid } });                    } else {                        // 同步标段信息                        await transaction.update(measureTable, { status: checkType, deal_sum: sum.deal, qc_sum: sum.qc }, { where: { mid } });                    }                } else {                    // 同步标段信息                    await transaction.update(measureTable, { times: times + 1, status: checkType, deal_sum: sum.deal, qc_sum: sum.qc }, { where: { mid } });                    // 拷贝新一次审核流程列表                    const auditors = await this.getAllDataByCondition({                        where: { mid, times },                        columns: ['tender_id', 'order', 'audit_id', 'mid'],                    });                    for (const a of auditors) {                        a.times = times + 1;                        a.status = auditConst.status.uncheck;                    }                    await transaction.insert(this.tableName, auditors);                }                await transaction.commit();            } catch (err) {                await transaction.rollback();                throw err;            }        }        /**         * 获取审核人需要审核的标段列表         *         * @param auditorId         * @return {Promise<*>}         */        async getAuditTender(auditorId) {            const sql = 'SELECT ma.`audit_id`, ma.`times`, ma.`order`, ma.`begin_time`, t.`id`, t.`name`, t.`project_id`, t.`type`, t.`user_id` ' +                'FROM ?? AS ma, ?? AS t ' +                'WHERE ma.`audit_id` = ? and ma.`status` = ?' +                '    and ma.`tender_id` = t.`id`';            const sqlParam = [this.tableName, this.ctx.service.tender.tableName, auditorId, auditConst.status.checking];            return await this.db.query(sql, sqlParam);        }    }    return MeasureAudit;};
 |