weapp_tender_controller.js 16 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252
  1. 'use strict';
  2. const auditConst = require('../const/audit');
  3. const measureType = require('../const/tender').measureType;
  4. const advanceConst = require('../const/advance');
  5. const status = require('../const/audit').advance.status;
  6. const shenpiConst = require('../const/shenpi');
  7. const stdConst = require('../const/standard');
  8. const _ = require('lodash');
  9. module.exports = app => {
  10. class WeappTenderController extends app.BaseController {
  11. async listManage(ctx) {
  12. try {
  13. const projectId = ctx.query.projectId;
  14. if (!projectId) {
  15. ctx.body = { err: 1, msg: '缺少projectId参数', data: null };
  16. return;
  17. }
  18. const accountInfo = ctx.session.sessionUser;
  19. const userPermission = accountInfo !== undefined && accountInfo.permission !== '' ? JSON.parse(accountInfo.permission) : null;
  20. if (userPermission !== null && userPermission.tender !== undefined && userPermission.tender.indexOf('1') !== -1) {
  21. const subProject = await this.ctx.service.subProject.getDataById(projectId);
  22. const tenderList = await this.ctx.service.tender.getList('', userPermission, ctx.session.sessionUser.is_admin, '', subProject);
  23. for (const tender of tenderList) {
  24. // 查询当前审批期以及状态
  25. const stage = await this.ctx.service.stage.getLastestStage(tender.id, true);
  26. tender.stage_order = stage && stage.order ? stage.order : null;
  27. tender.stage_status = stage && stage.status ? stage.status : null;
  28. }
  29. const categoryData = await this.ctx.service.category.getAllCategory(subProject);
  30. const renderData = {
  31. categoryData,
  32. tenderList,
  33. };
  34. ctx.body = { err: 0, msg: '', data: renderData };
  35. } else {
  36. ctx.body = { err: 1, msg: '您没有管理权限', data: null };
  37. }
  38. } catch (err) {
  39. this.log(err);
  40. ctx.body = { err: 1, msg: err.toString(), data: null };
  41. }
  42. }
  43. async detail(ctx) {
  44. try {
  45. const tender = ctx.tender.data;
  46. let bCalcTp = ctx.tender.data.user_id === ctx.session.sessionUser.accountId && (
  47. ctx.tender.ledger_status === auditConst.ledger.status.checkNo || ctx.tender.ledger_status === auditConst.ledger.status.uncheck);
  48. const stages = await ctx.service.stage.getValidStages(ctx.tender.id);
  49. const lastStage = stages.length > 0 ? stages[0] : null; // await ctx.service.stage.getLastestStage(ctx.tender.id);
  50. const [change_tp, change_p_tp, change_n_tp, change_valuation_tp, change_unvaluation_tp] = await ctx.service.change.getChangeTp(ctx.tender.id);
  51. tender.change_tp = change_tp;
  52. tender.change_p_tp = change_p_tp;
  53. tender.change_n_tp = change_n_tp;
  54. tender.change_valuation_tp = change_valuation_tp;
  55. tender.change_unvaluation_tp = change_unvaluation_tp;
  56. if (lastStage) {
  57. await this.ctx.service.stage.checkStageGatherData(lastStage, ctx.session.sessionUser.is_admin);
  58. if ((!bCalcTp) && tender.measure_type === measureType.gcl.value) {
  59. bCalcTp = lastStage.status !== auditConst.stage.status.checked && !lastStage.readOnly;
  60. }
  61. if (bCalcTp) {
  62. const sum = await this.ctx.service.ledger.addUp({ tender_id: ctx.tender.id/* , is_leaf: true*/ });
  63. tender.total_price = sum.total_price;
  64. tender.deal_tp = sum.deal_tp;
  65. }
  66. tender.sum = ctx.tender.info.calc_type === 'tp' ? ctx.helper.add(tender.total_price, tender.change_valuation_tp) : ctx.helper.add(tender.total_price, tender.change_tp);
  67. tender.gather_tp = ctx.helper.sum([lastStage.contract_tp, lastStage.qc_tp, lastStage.pc_tp]);
  68. tender.end_contract_tp = ctx.helper.sum([lastStage.contract_tp, lastStage.pre_contract_tp, lastStage.contract_pc_tp]);
  69. tender.end_qc_tp = ctx.helper.sum([lastStage.qc_tp, lastStage.pre_qc_tp, lastStage.qc_pc_tp]);
  70. tender.end_positive_qc_tp = ctx.helper.sum([lastStage.positive_qc_tp, lastStage.pre_positive_qc_tp, lastStage.positive_qc_pc_tp]);
  71. tender.end_negative_qc_tp = ctx.helper.sum([lastStage.negative_qc_tp, lastStage.pre_negative_qc_tp, lastStage.negative_qc_pc_tp]);
  72. tender.end_gather_tp = ctx.helper.add(tender.end_contract_tp, tender.end_qc_tp);
  73. tender.pre_gather_tp = ctx.helper.add(lastStage.pre_contract_tp, lastStage.pre_qc_tp);
  74. tender.yf_tp = lastStage.yf_tp;
  75. tender.sf_tp = lastStage.sf_tp;
  76. tender.qc_ratio = ctx.helper.mul(ctx.helper.div(tender.end_qc_tp, ctx.tender.info.deal_param.contractPrice, 2), 100);
  77. tender.pre_ratio = ctx.helper.mul(ctx.helper.div(tender.pre_gather_tp, tender.sum, 2), 100);
  78. tender.cur_ratio = ctx.helper.mul(ctx.helper.div(tender.gather_tp, tender.sum, 2), 100);
  79. tender.other_tp = ctx.helper.sub(ctx.helper.sub(tender.sum, tender.pre_gather_tp), tender.gather_tp);
  80. tender.other_ratio = Math.max(0, 100 - tender.pre_ratio - tender.cur_ratio);
  81. tender.end_yf_tp = ctx.helper.add(lastStage.yf_tp, lastStage.pre_yf_tp);
  82. tender.end_sf_tp = ctx.helper.add(lastStage.sf_tp, lastStage.pre_sf_tp);
  83. tender.undone_tp = ctx.helper.sub(ctx.helper.sub(ctx.helper.add(tender.total_price, change_tp), tender.end_contract_tp), tender.end_qc_tp);
  84. } else {
  85. if (bCalcTp) {
  86. const sum = await this.ctx.service.ledger.addUp({ tender_id: ctx.tender.id/* , is_leaf: true*/ });
  87. tender.total_price = sum.total_price;
  88. tender.deal_tp = sum.deal_tp;
  89. }
  90. tender.sum = ctx.helper.add(tender.total_price, tender.change_tp);
  91. }
  92. // const monthProgress = [];
  93. // for (const s of stages) {
  94. // if (s.s_time) {
  95. // let progress = monthProgress.find(function(x) {
  96. // return x.month === s.s_time;
  97. // });
  98. // if (!progress) {
  99. // progress = { month: s.s_time };
  100. // monthProgress.push(progress);
  101. // }
  102. // progress.tp = ctx.helper.add(ctx.helper.add(progress.tp, s.contract_tp), s.qc_tp);
  103. // }
  104. // }
  105. // monthProgress.sort(function(x, y) {
  106. // return Date.parse(x.month) - Date.parse(y.month);
  107. // });
  108. // let sum = 0;
  109. // for (const p of monthProgress) {
  110. // p.ratio = ctx.helper.mul(ctx.helper.div(p.tp, tender.sum, 4), 100);
  111. // sum = ctx.helper.add(sum, p.tp);
  112. // p.end_tp = sum;
  113. // p.end_ratio = ctx.helper.mul(ctx.helper.div(p.end_tp, tender.sum, 4), 100);
  114. // }
  115. ctx.body = {
  116. code: 0, msg: '', data: {
  117. tender,
  118. // monthProgress,
  119. // stagesEcharts: JSON.parse(JSON.stringify(stages)).reverse(),
  120. },
  121. };
  122. } catch (error) {
  123. this.log(error);
  124. ctx.body = { code: -1, msg: error.toString(), data: null };
  125. }
  126. }
  127. async advanceList(ctx) {
  128. try {
  129. const { advanceType } = ctx.query;
  130. const typeCol = advanceConst.typeCol.find(x => x.type === Number(advanceType));
  131. if (!typeCol) {
  132. ctx.body = { code: -1, msg: '预付款类型错误', data: null };
  133. return;
  134. }
  135. const { decimal } = ctx.tender.info;
  136. const advancePayTotal = ctx.tender.info.deal_param[typeCol.key + 'Advance'];
  137. const advances = await ctx.service.advance.getAdvanceList(ctx.tender.id, typeCol.type, decimal.pay ? decimal.payTp : decimal.tp, advancePayTotal);
  138. ctx.body = { code: 0, msg: '', data: advances };
  139. } catch (error) {
  140. this.log(error);
  141. ctx.body = { code: -1, msg: error.toString(), data: null };
  142. }
  143. }
  144. async advanceDetail(ctx) {
  145. try {
  146. const { id } = ctx.query;
  147. const advance = await this.service.advance.getDataById(id);
  148. if (!advance) {
  149. throw '预付款数据错误';
  150. }
  151. advance.user = await this.service.projectAccount.getAccountInfoById(advance.uid);
  152. // 读取审核人列表数据
  153. advance.auditors = await this.service.advanceAudit.getAuditors(advance.id, advance.times);
  154. advance.curAuditor = await this.service.advanceAudit.getCurAuditor(advance.id, advance.times);
  155. // 根据状态判断是否需要更新审批人列表
  156. if ((advance.status === status.uncheck || advance.status === status.checkNo) && ctx.tender.info.shenpi.advance !== shenpiConst.sp_status.sqspr) {
  157. const shenpi_status = this.ctx.tender.info.shenpi.advance;
  158. // 进一步比较审批流是否与审批流程设置的相同,不同则替换为固定审批流或固定的终审
  159. const auditList = await this.service.advanceAudit.getAllDataByCondition({ where: { vid: advance.id, times: advance.times }, orders: [['order', 'asc']] });
  160. const auditIdList = _.map(auditList, 'audit_id');
  161. if (shenpi_status === shenpiConst.sp_status.gdspl) {
  162. const shenpiList = await this.service.shenpiAudit.getAllDataByCondition({ where: { tid: advance.tid, sp_type: shenpiConst.sp_type.advance, sp_status: shenpi_status } });
  163. const shenpiIdList = _.map(shenpiList, 'audit_id');
  164. // 判断2个id数组是否相同,不同则删除原审批流,切换成固定的审批流
  165. if (!_.isEqual(auditIdList, shenpiIdList)) {
  166. await this.service.advanceAudit.updateNewAuditList(advance, shenpiIdList);
  167. }
  168. } else if (shenpi_status === shenpiConst.sp_status.gdzs) {
  169. const shenpiInfo = await this.service.shenpiAudit.getDataByCondition({ tid: advance.tid, sp_type: shenpiConst.sp_type.advance, sp_status: shenpi_status });
  170. // 判断最后一个id是否与固定终审id相同,不同则删除原审批流中如果存在的id和添加终审
  171. if (shenpiInfo && shenpiInfo.audit_id !== _.last(auditIdList)) {
  172. await this.service.advanceAudit.updateLastAudit(advance, auditList, shenpiInfo.audit_id);
  173. } else if (!shenpiInfo) {
  174. // 不存在终审人的状态下这里恢复为授权审批人
  175. this.ctx.tender.info.shenpi.advance = shenpiConst.sp_status.sqspr;
  176. }
  177. }
  178. }
  179. advance.advancePayTotal = ctx.tender.info.deal_param[ advanceConst.typeCol[advance.type].key + 'Advance'];
  180. const times = advance.status === auditConst.advance.status.checkNo ? advance.times - 1 : advance.times;
  181. if (advance.status === auditConst.advance.status.checkNo) {
  182. advance.curAuditor = await ctx.service.advanceAudit.getAuditorByStatus(advance.id, advance.status, times);
  183. advance.auditors = await ctx.service.advanceAudit.getAuditors(advance.id, times);
  184. }
  185. // 因为上报人不在审核列表里面单独添加进去
  186. // advance.auditors.unshirt({
  187. // audit_id: advance.uid,
  188. // name: advance.user.name,
  189. // company: advance.user.company,
  190. // create_time: advance.pay_time,
  191. // end_time: advance.auditors.length ? advance.auditors[0].create_time : null,
  192. // mobile: '',
  193. // })
  194. ctx.body = { code: 0, msg: '', data: { advance } };
  195. } catch (error) {
  196. this.log(error);
  197. ctx.body = { code: -1, msg: error.toString(), data: null };
  198. }
  199. }
  200. async reviseDetail(ctx) {
  201. try {
  202. const { rid } = ctx.query;
  203. const revise = rid
  204. ? await ctx.service.ledgerRevise.getRevise(ctx.tender.id, rid)
  205. : ctx.service.ledgerRevise.getLastestRevise(ctx.tender.id);
  206. revise.preHis = revise.pre_his_id ? await ctx.service.ledgerHistory.getDataById(revise.pre_his_id) : null;
  207. revise.curHis = revise.his_id ? await ctx.service.ledgerHistory.getDataById(revise.his_id) : null;
  208. await ctx.service.reviseAudit.loadReviseUser(revise);
  209. await ctx.service.reviseAudit.loadReviseAuditViewData(revise);
  210. const GclGather = require('../lib/gcl_gather');
  211. const gclGatherModal = new GclGather.gclCompareGather(this.ctx);
  212. const spec = {zlj: stdConst.zlj, jrg: stdConst.jrg};
  213. spec.zlj.deal_bills_tp = ctx.tender.info.deal_param.zanLiePrice;
  214. gclGatherModal.init(ctx.tender.info.chapter, spec);
  215. const reviseBillsData = revise.readOnly && revise.curHis
  216. ? await ctx.helper.loadLedgerDataFromOss(revise.curHis.bills_file)
  217. : await ctx.service.reviseBills.getAllDataByCondition({ where: { tender_id: ctx.tender.id } });
  218. const revisePosData = revise.readOnly && revise.curHis
  219. ? await this.ctx.helper.loadLedgerDataFromOss(revise.curHis.pos_file)
  220. : await ctx.service.revisePos.getAllDataByCondition({ where: { tid: ctx.tender.id } });
  221. const price = await this.ctx.service.revisePrice.getAllDataByCondition({ where: { rid: revise.id } });
  222. gclGatherModal.gatherReviseLedgerData(reviseBillsData, revisePosData, { prefix: 'new_' }, price, ctx.tender.info.decimal);
  223. const billsData = revise.preHis ? await this.ctx.helper.loadLedgerDataFromOss(revise.preHis.bills_file) : [];
  224. const posData = revise.preHis ? await this.ctx.helper.loadLedgerDataFromOss(revise.preHis.pos_file) : [];
  225. gclGatherModal.gatherLedgerData(billsData, posData, { prefix: 'org_' });
  226. revise.chapterList = gclGatherModal.chapterData();
  227. revise.new_tp = gclGatherModal.otherChapter.hj.new_total_price || 0;
  228. revise.org_tp = gclGatherModal.otherChapter.hj.org_total_price || 0;
  229. ctx.body = { code: 0, msg: '', data: { revise } };
  230. } catch(error) {
  231. ctx.log(error);
  232. ctx.body = { code: -1, msg: error.toString(), data: null };
  233. }
  234. }
  235. }
  236. return WeappTenderController;
  237. };