material_bills.js 8.5 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229
  1. 'use strict';
  2. /**
  3. * 期计量 数据模型
  4. *
  5. * @author Mai
  6. * @date 2018/8/13
  7. * @version
  8. */
  9. const auditConst = require('../const/audit').material;
  10. const materialConst = require('../const/material');
  11. const MaterialCalculator = require('../lib/material_calc');
  12. module.exports = app => {
  13. class MaterialBills extends app.BaseService {
  14. /**
  15. * 构造函数
  16. *
  17. * @param {Object} ctx - egg全局变量
  18. * @return {void}
  19. */
  20. constructor(ctx) {
  21. super(ctx);
  22. this.tableName = 'material_bills';
  23. }
  24. /**
  25. * 添加工料
  26. * @return {void}
  27. */
  28. async add() {
  29. if (!this.ctx.tender || !this.ctx.material) {
  30. throw '数据错误';
  31. }
  32. const newBills = {
  33. tid: this.ctx.tender.id,
  34. mid: this.ctx.material.id,
  35. in_time: new Date(),
  36. };
  37. // 新增工料
  38. const result = await this.db.insert(this.tableName, newBills);
  39. if (result.affectedRows !== 1) {
  40. throw '新增工料数据失败';
  41. }
  42. return await this.getDataById(result.insertId);
  43. }
  44. /**
  45. * 删除工料
  46. * @param {int} id 工料id
  47. * @return {void}
  48. */
  49. async del(id) {
  50. if (!this.ctx.tender || !this.ctx.material) {
  51. throw '数据错误';
  52. }
  53. // 判断t_type是否为费用,且存在quantity,m_spread值
  54. const transaction = await this.db.beginTransaction();
  55. try {
  56. const mbInfo = await this.getDataById(id);
  57. await transaction.delete(this.tableName, { id });
  58. let m_tp = this.ctx.material.m_tp;
  59. if (mbInfo.t_type === materialConst.t_type[1].value && mbInfo.quantity !== null && mbInfo.m_spread !== null) {
  60. // 金额发生变化,则重新计算本期金额
  61. m_tp = await this.calcMaterialMTp(transaction);
  62. }
  63. await transaction.commit();
  64. return m_tp;
  65. } catch (err) {
  66. await transaction.rollback();
  67. throw err;
  68. }
  69. }
  70. /**
  71. * 修改工料信息
  72. * @param {Object} data 工料内容
  73. * @return {void}
  74. */
  75. async save(data) {
  76. if (!this.ctx.tender || !this.ctx.material) {
  77. throw '数据错误';
  78. }
  79. delete data.in_time;
  80. delete data.m_tp;
  81. // 判断是否可修改
  82. // 判断t_type是否为费用
  83. const transaction = await this.db.beginTransaction();
  84. try {
  85. await transaction.update(this.tableName, data);
  86. const m_tp = await this.calcMaterialMTp(transaction);
  87. await transaction.commit();
  88. return m_tp;
  89. } catch (err) {
  90. await transaction.rollback();
  91. throw err;
  92. }
  93. }
  94. /**
  95. * 修改工料信息
  96. * @param {Object} data 工料内容
  97. * @return {void}
  98. */
  99. async saveDatas(datas) {
  100. if (!this.ctx.tender || !this.ctx.material) {
  101. throw '数据错误';
  102. }
  103. // 判断是否可修改
  104. // 判断t_type是否为费用
  105. const transaction = await this.db.beginTransaction();
  106. try {
  107. for (const data of datas) {
  108. delete data.in_time;
  109. delete data.m_tp;
  110. // console.log(data);
  111. await transaction.update(this.tableName, data);
  112. }
  113. // console.log(datas);
  114. // await transaction.update(this.tableName, datas);
  115. const m_tp = await this.calcMaterialMTp(transaction);
  116. await transaction.commit();
  117. return m_tp;
  118. } catch (err) {
  119. await transaction.rollback();
  120. throw err;
  121. }
  122. }
  123. /**
  124. * 更新新一期的quantity和截止上期金额并返回本期总金额
  125. * @param transaction
  126. * @param tid
  127. * @param mid
  128. * @returns {Promise<number>}
  129. */
  130. async updateNewMaterial(transaction, tid, mid, ctx, stage_id) {
  131. const materialBillsData = await this.getAllDataByCondition({ where: { tid } });
  132. let m_tp = 0;
  133. const materialCalculator = new MaterialCalculator(ctx, stage_id, ctx.tender.info);
  134. for (const mb of materialBillsData) {
  135. const one_tp = await this.calcQuantityByMB(transaction, mid, mb, materialCalculator);
  136. m_tp = this.ctx.helper.add(m_tp, one_tp);
  137. }
  138. return m_tp;
  139. }
  140. /**
  141. * 修改quantity,m_spread值和返回单条调差金额(新增一期)
  142. * @param transaction
  143. * @param mid
  144. * @param mb
  145. * @returns {Promise<*>}
  146. */
  147. async calcQuantityByMB(transaction, mid, mb, materialCalculator) {
  148. if (mb.t_type === materialConst.t_type[0].value) {
  149. const sql = 'SELECT SUM(`gather_qty`*`quantity`) as quantity FROM ' + this.ctx.service.materialList.tableName + ' WHERE `mid`=? AND `mb_id`=? AND `is_join`=1';
  150. const sqlParam = [mid, mb.id];
  151. const mb_quantity = await transaction.queryOne(sql, sqlParam);
  152. console.log(mb_quantity);
  153. // 取历史期记录获取截止上期调差金额
  154. const updateData = {
  155. id: mb.id,
  156. quantity: this.ctx.helper.round(mb_quantity.quantity, 3),
  157. pre_tp: mb.quantity && mb.m_spread !== null ? this.ctx.helper.round(this.ctx.helper.add(mb.pre_tp, this.ctx.helper.mul(mb.quantity, mb.m_spread)), 2) : mb.pre_tp,
  158. };
  159. await transaction.update(this.tableName, updateData);
  160. return await this.ctx.helper.round(this.ctx.helper.mul(mb_quantity.quantity, mb.m_spread), 2);
  161. } else if (mb.t_type === materialConst.t_type[1].value) {
  162. const quantity = await materialCalculator.calculateExpr(mb.expr);
  163. const updateData = {
  164. id: mb.id,
  165. quantity: quantity !== 0 && quantity !== null ? this.ctx.helper.round(quantity, 3) : null,
  166. pre_tp: mb.quantity && mb.m_spread !== null ? this.ctx.helper.round(this.ctx.helper.add(mb.pre_tp, this.ctx.helper.mul(mb.quantity, mb.m_spread)), 2) : mb.pre_tp,
  167. };
  168. await transaction.update(this.tableName, updateData);
  169. return await this.ctx.helper.round(this.ctx.helper.mul(quantity, mb.m_spread), 2);
  170. }
  171. }
  172. /**
  173. * 修改 expr和quantity值,返回本期金额和单条数据
  174. * @param data
  175. * @returns {Promise<void>}
  176. */
  177. async updateFYQuantity(data) {
  178. if (!this.ctx.tender || !this.ctx.material) {
  179. throw '数据错误';
  180. }
  181. const transaction = await this.db.beginTransaction();
  182. try {
  183. const mbInfo = await this.getDataById(data.id);
  184. await transaction.update(this.tableName, data);
  185. let m_tp = this.ctx.material.m_tp;
  186. if (mbInfo.quantity !== data.quantity) {
  187. m_tp = await this.calcMaterialMTp(transaction);
  188. }
  189. await transaction.commit();
  190. const returnData = {
  191. m_tp,
  192. info: await this.getDataById(data.id),
  193. }
  194. return returnData;
  195. } catch (err) {
  196. await transaction.rollback();
  197. throw err;
  198. }
  199. }
  200. // 更改计算总金额并返回值
  201. async calcMaterialMTp(transaction) {
  202. // 金额发生变化,则重新计算本期金额
  203. const sql = 'SELECT SUM(`m_spread`*`quantity`) as total_price FROM ' + this.tableName + ' WHERE `tid` = ?';
  204. const sqlParam = [this.ctx.tender.id];
  205. const tp = await transaction.queryOne(sql, sqlParam);
  206. console.log(tp);
  207. const updateData2 = {
  208. id: this.ctx.material.id,
  209. m_tp: tp.total_price,
  210. };
  211. await transaction.update(this.ctx.service.material.tableName, updateData2);
  212. return tp.total_price;
  213. }
  214. }
  215. return MaterialBills;
  216. };