CheckService.php 79 KB

12345678910111213141516171819202122232425262728293031323334353637383940414243444546474849505152535455565758596061626364656667686970717273747576777879808182838485868788899091929394959697989910010110210310410510610710810911011111211311411511611711811912012112212312412512612712812913013113213313413513613713813914014114214314414514614714814915015115215315415515615715815916016116216316416516616716816917017117217317417517617717817918018118218318418518618718818919019119219319419519619719819920020120220320420520620720820921021121221321421521621721821922022122222322422522622722822923023123223323423523623723823924024124224324424524624724824925025125225325425525625725825926026126226326426526626726826927027127227327427527627727827928028128228328428528628728828929029129229329429529629729829930030130230330430530630730830931031131231331431531631731831932032132232332432532632732832933033133233333433533633733833934034134234334434534634734834935035135235335435535635735835936036136236336436536636736836937037137237337437537637737837938038138238338438538638738838939039139239339439539639739839940040140240340440540640740840941041141241341441541641741841942042142242342442542642742842943043143243343443543643743843944044144244344444544644744844945045145245345445545645745845946046146246346446546646746846947047147247347447547647747847948048148248348448548648748848949049149249349449549649749849950050150250350450550650750850951051151251351451551651751851952052152252352452552652752852953053153253353453553653753853954054154254354454554654754854955055155255355455555655755855956056156256356456556656756856957057157257357457557657757857958058158258358458558658758858959059159259359459559659759859960060160260360460560660760860961061161261361461561661761861962062162262362462562662762862963063163263363463563663763863964064164264364464564664764864965065165265365465565665765865966066166266366466566666766866967067167267367467567667767867968068168268368468568668768868969069169269369469569669769869970070170270370470570670770870971071171271371471571671771871972072172272372472572672772872973073173273373473573673773873974074174274374474574674774874975075175275375475575675775875976076176276376476576676776876977077177277377477577677777877978078178278378478578678778878979079179279379479579679779879980080180280380480580680780880981081181281381481581681781881982082182282382482582682782882983083183283383483583683783883984084184284384484584684784884985085185285385485585685785885986086186286386486586686786886987087187287387487587687787887988088188288388488588688788888989089189289389489589689789889990090190290390490590690790890991091191291391491591691791891992092192292392492592692792892993093193293393493593693793893994094194294394494594694794894995095195295395495595695795895996096196296396496596696796896997097197297397497597697797897998098198298398498598698798898999099199299399499599699799899910001001100210031004100510061007100810091010101110121013101410151016101710181019102010211022102310241025102610271028102910301031103210331034103510361037103810391040104110421043104410451046104710481049105010511052105310541055105610571058105910601061106210631064106510661067106810691070107110721073107410751076107710781079108010811082108310841085108610871088108910901091109210931094109510961097109810991100110111021103110411051106110711081109111011111112111311141115111611171118111911201121112211231124112511261127112811291130113111321133113411351136113711381139114011411142114311441145114611471148114911501151115211531154115511561157115811591160116111621163116411651166116711681169117011711172117311741175117611771178117911801181118211831184118511861187118811891190119111921193119411951196119711981199120012011202120312041205120612071208120912101211121212131214121512161217121812191220122112221223122412251226122712281229123012311232123312341235123612371238123912401241124212431244124512461247124812491250125112521253125412551256125712581259126012611262126312641265126612671268126912701271127212731274127512761277127812791280128112821283128412851286128712881289129012911292129312941295129612971298129913001301130213031304130513061307130813091310131113121313131413151316131713181319132013211322132313241325132613271328132913301331133213331334133513361337133813391340134113421343134413451346134713481349135013511352135313541355135613571358135913601361136213631364136513661367136813691370137113721373137413751376137713781379138013811382138313841385138613871388138913901391139213931394139513961397139813991400140114021403140414051406140714081409141014111412141314141415141614171418141914201421142214231424142514261427142814291430143114321433143414351436143714381439144014411442144314441445144614471448144914501451145214531454145514561457145814591460146114621463146414651466146714681469147014711472147314741475147614771478147914801481148214831484148514861487148814891490149114921493149414951496149714981499150015011502150315041505150615071508150915101511151215131514151515161517151815191520152115221523152415251526152715281529153015311532153315341535153615371538153915401541154215431544154515461547154815491550155115521553155415551556155715581559156015611562156315641565156615671568156915701571157215731574157515761577157815791580158115821583158415851586158715881589159015911592159315941595159615971598159916001601160216031604160516061607160816091610161116121613161416151616161716181619162016211622162316241625162616271628162916301631163216331634163516361637163816391640164116421643164416451646164716481649165016511652165316541655165616571658165916601661166216631664166516661667166816691670167116721673167416751676167716781679168016811682168316841685168616871688168916901691169216931694169516961697169816991700170117021703170417051706170717081709171017111712171317141715171617171718171917201721172217231724172517261727172817291730173117321733173417351736173717381739174017411742174317441745174617471748174917501751175217531754175517561757175817591760176117621763176417651766176717681769177017711772177317741775177617771778177917801781178217831784178517861787178817891790179117921793179417951796179717981799180018011802180318041805180618071808180918101811181218131814181518161817181818191820182118221823182418251826182718281829183018311832183318341835183618371838183918401841184218431844184518461847184818491850185118521853185418551856185718581859186018611862186318641865186618671868186918701871187218731874187518761877187818791880188118821883188418851886188718881889189018911892189318941895189618971898189919001901190219031904190519061907190819091910191119121913191419151916191719181919192019211922192319241925192619271928192919301931193219331934193519361937193819391940194119421943194419451946194719481949195019511952195319541955195619571958195919601961196219631964196519661967196819691970197119721973197419751976197719781979198019811982198319841985198619871988198919901991199219931994199519961997199819992000200120022003200420052006200720082009201020112012201320142015201620172018201920202021202220232024202520262027202820292030203120322033203420352036203720382039204020412042204320442045204620472048204920502051
  1. <?php
  2. namespace App\Service;
  3. use App\Model\Construction;
  4. use App\Model\ConstructionProductInfo;
  5. use App\Model\Customer;
  6. use App\Model\Depart;
  7. use App\Model\Employee;
  8. use App\Model\InOutRecord;
  9. use App\Model\Inventory;
  10. use App\Model\InventorySub;
  11. use App\Model\InvoiceOrder;
  12. use App\Model\InvoiceOrderInfo;
  13. use App\Model\OrderInventoryStock;
  14. use App\Model\OrderOperation;
  15. use App\Model\OutBoundOrder;
  16. use App\Model\OutBoundOrderInfo;
  17. use App\Model\PaymentReceipt;
  18. use App\Model\PaymentReceiptInfo;
  19. use App\Model\ProductInventory;
  20. use App\Model\ProductInventorySet;
  21. use App\Model\PurchaseOrder;
  22. use App\Model\PurchaseOrderInfo;
  23. use App\Model\PurchaseOrderSpecial;
  24. use App\Model\PurchaseOrderSpecialInfo;
  25. use App\Model\ReturnExchangeOrder;
  26. use App\Model\ReturnExchangeOrderProductInfo;
  27. use App\Model\SalesOrder;
  28. use App\Model\SalesOrderInfo;
  29. use App\Model\SalesOrderOtherFee;
  30. use App\Model\SalesOrderProductInfo;
  31. use App\Model\SeeRange;
  32. use App\Model\SportsBag;
  33. use App\Model\Storehouse;
  34. use App\Model\Supplier;
  35. use Illuminate\Support\Facades\DB;
  36. class CheckService extends Service
  37. {
  38. //特殊操作数
  39. const minus_one = -1;//跳出库存流水
  40. //审批操作对应的数值
  41. const one = 1; //收货
  42. const two = 2; //发货
  43. const three = 3; //采购单入库
  44. const four = 4; //合同公司完结
  45. const five = 5; //施工单
  46. const six = 6; //退换货单
  47. const seven = 7; //采购单确认
  48. const eight = 8; //合同确认
  49. const nine = 9; //合同客户完结
  50. const ten = 10; //收付款确认
  51. const eve = 11; //接受派单
  52. const twl = 12; //活动包
  53. const thi = 13; //虚拟采购单
  54. const fourteen = 14; //盘点
  55. const fifteen = 15; //放弃门店派单
  56. const sixteen = 16; //出库单审核
  57. //中文对照
  58. public $map = [
  59. self::one => '收货单',
  60. self::two => '发货单',//确认后出库
  61. self::three => '采购单入库',//确认后入库
  62. self::four => '公司完结', // 安装件 合同完结
  63. self::five => '施工单',//确认后出库
  64. self::six => '退换货单',//确认后出库或出库入库
  65. self::seven => '采购单确认',
  66. self::eight => '合同确认',
  67. self::nine => '合同客户完结',
  68. self::ten => '收付款确认',
  69. self::eve => '接受门店派单',
  70. self::twl => '活动包',
  71. self::thi => '虚拟采购单',
  72. self::fourteen => '盘点单',
  73. self::fifteen => '放弃门店派单',
  74. self::sixteen => '出库单审核',
  75. ];
  76. //入库操作
  77. public static $in_opt = [
  78. self::three,
  79. ];
  80. //出库操作
  81. public static $out_opt = [
  82. self::two,
  83. self::five,
  84. self::sixteen,
  85. ];
  86. const TYPE_ONE = 1;//通过
  87. const TYPE_TWO = 2;//不通过
  88. const TYPE_THREE = 3;//通过后驳回
  89. //改为待审核状态 校验
  90. public static $opt_1case_check = [
  91. // self::five => 'checkConstruction',//施工单
  92. ];
  93. //改为待审核状态
  94. public static $opt_1case = [
  95. self::two => 'waitInvoice',//发货单
  96. // self::three => 'waitPurchase',//采购单 入库
  97. self::five => 'waitConstruction',//施工单
  98. self::six => 'waitReturnExchange',//退换货单
  99. self::seven => 'waitPurchaseConfirm', //采购单确认
  100. self::eight => 'waitSales', // 合同安装件 合同确认
  101. self::ten => 'waitPaymentReceipt', //收付款确认
  102. self::twl => 'waitSportsBag', //活动包确认
  103. self::thi => 'waitPurchaseSpecial', //虚拟采购单
  104. self::fourteen => 'waitInventory', //盘点单
  105. self::sixteen => 'waitOut', //出库单
  106. ];
  107. public static $finished = [
  108. self::three => 'confirmPurchaseOrder',//采购单 入库
  109. self::four => 'settleSalesOrder', // 合同 安装件 合同公司完结
  110. self::nine => 'settleSalesOrderCustomer', // 合同 安装件 合同客户完结
  111. self::eve => 'settleSalesOrderConfirm', // 合同 安装件 合同接收
  112. self::fifteen => 'settleSalesOrderConfirmBack', // 合同 安装件 合同接收后放弃
  113. ];
  114. //单据操作
  115. public static $opt_case = [
  116. self::two => 'confirmInvoiceOrder',
  117. // self::three => 'confirmPurchaseOrder',
  118. self::five => 'confirmConstruction',
  119. self::six => 'confirmReturnExchangeOrder',
  120. self::seven => 'confirmPurchaseOrderState',
  121. self::eight => 'confirmSales', // 合同 安装件 合同确认
  122. self::ten => 'confirmPaymentReceipt', // 确认收付款单
  123. self::twl => 'confirmSportsBag', // 确认活动包
  124. self::thi => 'confirmPurchaseSpecial', //虚拟采购单
  125. self::fourteen => 'confirmInventory', //盘点单
  126. self::sixteen => 'confirmOut', //出库单
  127. ];
  128. //单据库存流水
  129. public static $record = [
  130. // self::two => 'recordInvoiceOrder',
  131. self::three => 'recordPurchaseOrder',
  132. // self::five => 'recordConstruction',
  133. self::six => 'recordReturnExchangeOrder',
  134. self::fourteen => 'recordInventory',
  135. self::sixteen => 'recordOut',
  136. ];
  137. //自动生成
  138. public static $create = [
  139. self::seven => 'createPurchaseOrderSales', //分社合同生成
  140. self::four => 'createPurchaseOrder', // 派给分社的合同 公司完结以后生成虚拟采购单
  141. ];
  142. //自动生成的删除
  143. public static $create_del = [
  144. self::seven => 'delCreatePurchaseOrderSales', //分社合同生成(删除)
  145. // self::four => 'delCreatePurchaseOrder', // 派给分社的合同确认以后生成虚拟采购单
  146. ];
  147. //审核通过后 弃审
  148. public static $opt_case_reject = [
  149. self::four => 'reject_sales', // 合同
  150. // self::three => 'reject_purchase', //采购入库
  151. self::seven => 'reject_purchase_confirm', //采购确认驳回
  152. self::five => 'reject_construction',//施工单
  153. self::six => 'reject_return_exchange',//退换货
  154. self::ten => 'reject_payment_receipt',//收付款单
  155. self::twl => 'reject_sports_bag',//活动包
  156. self::thi => 'reject_purchase_special',//虚拟采购单
  157. ];
  158. //审核通过后 驳回 产生流水
  159. public static $reject_record = [
  160. // self::five => 'reject_record_construction', //施工单驳回
  161. self::three => 'reject_record_purchase', //采购
  162. self::six => 'reject_record_return_exchange',//退换货
  163. ];
  164. //旅程日志 同意
  165. public static $operation_order = [
  166. self::eight => OrderOperation::three, //合同确认
  167. self::two => OrderOperation::eight, //发货单确认
  168. self::six => OrderOperation::nine, //退换货审核
  169. self::five => OrderOperation::eve, //施工单
  170. self::seven => OrderOperation::thi,//采购单确认
  171. self::three => OrderOperation::fourteen,//采购单入库
  172. self::ten => OrderOperation::twenty_one,//收付款单
  173. self::twl => OrderOperation::twenty_one,//收付款单
  174. self::thi => OrderOperation::twenty_nine,//虚拟采购单
  175. ];
  176. //旅程日志 驳回
  177. public static $operation_order_reject = [
  178. self::four => OrderOperation::four, //合同弃审
  179. self::six => OrderOperation::ten, //退换货弃审
  180. self::five => OrderOperation::twl, //施工单弃审
  181. self::three => OrderOperation::fif,//采购单入库弃审
  182. self::seven => OrderOperation::twenty,//采购单确认弃审
  183. self::ten => OrderOperation::twenty_two,//收付款单
  184. self::twl => OrderOperation::twenty_eight,//活动包
  185. self::thi => OrderOperation::thirty,//虚拟采购单
  186. ];
  187. //校验 不需要了
  188. public function checkConstruction($data, $user){
  189. $order = Construction::where('del_time',0)
  190. ->where('order_number',$data['order_number'])
  191. ->first();
  192. if(empty($order)) return [false,'施工单不存在或已被删除'];
  193. $order = $order->toArray();
  194. //总社id
  195. $head = $user['head'] ?? [];
  196. $head = $head['id'] ?? 0;
  197. //分社自己的施工单 直接返回
  198. if($order['top_depart_id'] != $head) return [true, ''];
  199. //不校验库存
  200. if($user['is_check_stock'] == ProductInventorySet::type_two) return [true,''];
  201. //施工单产品
  202. $sub = ConstructionProductInfo::where('construction_id',$order['id'])
  203. ->where('del_time',0)
  204. ->get()->toArray();
  205. if(empty($sub)) return [false,'施工单产品不存在或已被删除'];
  206. $product_submit = $product_id = [];
  207. foreach ($sub as $value){
  208. $product_id[] = $value['product_id'];
  209. $key = $value['product_id'] . ',' . $value['storehouse_id'];
  210. if(isset($product_save[$key])){
  211. $product_submit[$key] += $value['number'];
  212. }else{
  213. $product_submit[$key] = $value['number'];
  214. }
  215. }
  216. //比较库存
  217. list($status,$msg) = (new ProductInventoryService())->compareStock($user,$product_id, $product_submit, []);
  218. if(! $status) return [false, $msg];
  219. //锁定库存
  220. // ProductInventoryService::changeLockNumber($user,$product_submit);
  221. return [true, ''];
  222. }
  223. //改为待审核---------------------------------
  224. public function waitInvoice($data){
  225. $model = InvoiceOrder::where('id',$data['id'])
  226. ->where('del_time',0)
  227. ->first();
  228. if(empty($model)) return [false, '发货单不存在或已被删除'];
  229. if($model->state != InvoiceOrder::STATE_ZERO) return [false, '请确认发货单状态,操作失败'];
  230. InvoiceOrder::where('del_time',0)->where('id',$data['id'])
  231. ->update(['state' => InvoiceOrder::STATE_ONE]);
  232. return [true, $model->toArray()];
  233. }
  234. public function waitPurchaseConfirm($data){
  235. $model = PurchaseOrder::where('id',$data['id'])
  236. ->where('del_time',0)
  237. ->first();
  238. if(empty($model)) return [false,'采购单不存在或已被删除'];
  239. if(! in_array($model->state, [PurchaseOrder::State_minus_one,PurchaseOrder::STATE_ZERO])) return [false, '请确认采购单状态,操作失败'];
  240. //待确认
  241. PurchaseOrder::where('id',$data['id'])->update(['state' => PurchaseOrder::STATE_ONE]);
  242. return [true, $model->toArray()];
  243. }
  244. public function waitPurchase($data){
  245. $model = PurchaseOrder::where('id',$data['id'])
  246. ->where('del_time',0)
  247. ->first();
  248. if(empty($model)) return [false, '采购订单不存在或已被删除'];
  249. if($model->state != PurchaseOrder::STATE_TWO) return [false, '请确认采购订单状态,操作失败'];
  250. //待入库
  251. PurchaseOrder::where('del_time',0)->where('id',$data['id'])
  252. ->update(['state' => PurchaseOrder::STATE_Three]);
  253. return [true, $model->toArray()];
  254. }
  255. public function waitPurchaseSpecial($data){
  256. $model = PurchaseOrderSpecial::where('id',$data['id'])
  257. ->where('del_time',0)
  258. ->first();
  259. if(empty($model)) return [false, '虚拟采购订单不存在或已被删除'];
  260. if($model->state > PurchaseOrderSpecial::STATE_ZERO) return [false, '请确认虚拟采购订单状态,操作失败'];
  261. //待入库
  262. PurchaseOrderSpecial::where('del_time',0)->where('id',$data['id'])
  263. ->update(['state' => PurchaseOrder::STATE_ONE]);
  264. return [true, $model->toArray()];
  265. }
  266. public function waitInventory($data){
  267. $model = Inventory::where('id',$data['id'])
  268. ->where('del_time',0)
  269. ->first();
  270. if(empty($model)) return [false, '盘点单不存在或已被删除'];
  271. if($model->state > Inventory::STATE_ZERO) return [false, '请确认盘点单状态,操作失败'];
  272. //待入库
  273. Inventory::where('del_time',0)->where('id',$data['id'])
  274. ->update(['state' => Inventory::STATE_ONE]);
  275. return [true, $model->toArray()];
  276. }
  277. public function waitOut($data){
  278. $model = OutBoundOrder::where('id',$data['id'])
  279. ->where('del_time',0)
  280. ->first();
  281. if(empty($model)) return [false, '出库单不存在或已被删除'];
  282. if($model->state > OutBoundOrder::STATE_ZERO) return [false, '请确认出库单状态,操作失败'];
  283. //待入库
  284. OutBoundOrder::where('del_time',0)->where('id',$data['id'])
  285. ->update(['state' => OutBoundOrder::STATE_ONE]);
  286. return [true, $model->toArray()];
  287. }
  288. public function waitConstruction($data){
  289. $model = Construction::where('id',$data['id'])
  290. ->where('del_time',0)
  291. ->first();
  292. if(empty($model)) return [false, '施工单不存在或已被删除'];
  293. if(! in_array($model->state, [Construction::State_minus_one,Construction::STATE_ZERO])) return [false, '请确认施工单状态,操作失败'];
  294. //待确认
  295. Construction::where('del_time',0)->where('id',$data['id'])
  296. ->update(['state' => Construction::STATE_ONE]);
  297. return [true, $model->toArray()];
  298. }
  299. public function waitReturnExchange($data){
  300. $model = ReturnExchangeOrder::where('id',$data['id'])
  301. ->where('del_time',0)
  302. ->first();
  303. if(empty($model)) return [false, '退换货单不存在或已被删除'];
  304. if(! in_array($model->state, [ReturnExchangeOrder::State_minus_one,ReturnExchangeOrder::State_zero])) return [false, '请确认退换货单状态,操作失败'];
  305. //待确认
  306. ReturnExchangeOrder::where('del_time',0)->where('id',$data['id'])
  307. ->update(['state' => ReturnExchangeOrder::State_one]);
  308. return [true, $model->toArray()];
  309. }
  310. public function waitSales($data){
  311. $model = SalesOrder::where('id', $data['id'])
  312. ->where('del_time',0)
  313. ->first();
  314. if(empty($model)) return [false, '合同不存在或已被删除'];
  315. //安装件
  316. if(! in_array($model->state, [SalesOrder::State_minus_one,SalesOrder::State_zero])) return [false, '请确认合同状态,操作失败'];
  317. SalesOrder::where('del_time',0)->where('id',$data['id'])
  318. ->update(['state' => SalesOrder::State_one]);
  319. return [true, $model->toArray()];
  320. }
  321. public function waitPaymentReceipt($data){
  322. $model = PaymentReceipt::where('id', $data['id'])
  323. ->where('del_time',0)
  324. ->first();
  325. if(empty($model)) return [false, '收付款单不存在或已被删除'];
  326. if(! in_array($model->state, [PaymentReceipt::State_minus_one,PaymentReceipt::STATE_ZERO])) return [false, '请确认收付款单状态,操作失败'];
  327. PaymentReceipt::where('del_time',0)->where('id',$data['id'])
  328. ->update(['state' => PaymentReceipt::STATE_ONE]);
  329. return [true, $model->toArray()];
  330. }
  331. public function waitSportsBag($data){
  332. $model = SportsBag::where('id', $data['id'])
  333. ->where('del_time',0)
  334. ->first();
  335. if(empty($model)) return [false, '活动包不存在或已被删除'];
  336. if(! in_array($model->state, [SportsBag::State_minus_one,SportsBag::STATE_ZERO])) return [false, '请确认活动包状态,操作失败'];
  337. SportsBag::where('del_time',0)->where('id',$data['id'])
  338. ->update(['state' => PaymentReceipt::STATE_ONE]);
  339. return [true, $model->toArray()];
  340. }
  341. //改为待审核---------------------------------
  342. //自动生成-----------------------------------
  343. //总社派给分社的合同 完成生成虚拟采购单
  344. public function createPurchaseOrder($order,$user){
  345. //快递件
  346. if($order['sales_order_type'] == SalesOrder::Order_type_two) return [true,''];
  347. //不是总公司的合同
  348. $head = $user['head'] ?? [];
  349. $head = $head['id'] ?? 0; //总社id
  350. if($head != $order['top_depart_id']) return [true, ''];
  351. $see = SeeRange::where('del_time',0)
  352. ->where('data_id',$order['id'])
  353. ->where('data_type',SeeRange::type_seven)
  354. ->where('type',SeeRange::data_three)
  355. ->first();
  356. if(empty($see)) return [false, '未找到指派分社信息'];
  357. $depart_id = $see->param_id;//指派的分社
  358. //总社指派给自己
  359. if($depart_id == $head) return [true, ''];
  360. //获取指派分社时候的金额
  361. $fee = SalesOrderOtherFee::where('del_time',0)
  362. ->where('sales_order_id',$order['id'])
  363. ->first();
  364. if(empty($fee)) return [false, '未找到指派分社时填写的金额'];
  365. $fee = $fee->toArray();
  366. $order_number = (new OrderNoService())->createOrderNumber(PurchaseOrderSpecial::prefix);
  367. $storehouse = Storehouse::where('depart_id',$head)->value('id');
  368. $product = SalesOrderProductInfo::where('del_time',0)
  369. ->where('sales_order_id',$order['id'])
  370. ->select('product_id','number','retail_price')
  371. ->get()->toArray();
  372. //退货的差异
  373. $returnExchange_map = [];
  374. $returnExchange = ReturnExchangeOrder::where('del_time',0)
  375. ->where('type',ReturnExchangeOrder::Order_type)
  376. ->where('data_id',$order['id'])
  377. ->select('id')
  378. ->get()->toArray();
  379. $return_product = ReturnExchangeOrderProductInfo::where('del_time',0)
  380. ->where('return_exchange_id',array_column($returnExchange,'id'))
  381. ->select('product_id','number')
  382. ->get()->toArray();
  383. foreach ($return_product as $value){
  384. if(isset($returnExchange_map[$value['product_id']])){
  385. $returnExchange_map[$value['product_id']] += $value['number'];
  386. }else{
  387. $returnExchange_map[$value['product_id']] = $value['number'];
  388. }
  389. }
  390. $product_map = $rate = [];
  391. $total = 0;
  392. foreach ($product as $key => $value){
  393. $return_number = 0;
  394. if(isset($returnExchange_map[$value['product_id']])) $return_number = $returnExchange_map[$value['product_id']];
  395. $number = $value['number'];
  396. if($return_number >= $value['number']) {
  397. unset($product[$key]);
  398. continue;
  399. }else{
  400. $number = bcsub($number,$return_number,2);
  401. $product[$key]['number'] = $number;
  402. }
  403. $total += $number * $value['retail_price'];
  404. if(isset($product_map[$value['product_id']])){
  405. $product_map[$value['product_id']] += $value['retail_price'] * $number;
  406. }else{
  407. $product_map[$value['product_id']] = $value['retail_price'] * $number;
  408. }
  409. }
  410. foreach ($product_map as $key => $value){
  411. $rate[$key] = bcdiv($value, $total, 2);
  412. }
  413. try {
  414. DB::beginTransaction();
  415. $model = new PurchaseOrderSpecial();
  416. $model->order_number = $order_number;
  417. $model->sales_order_id = $order['id'];
  418. $model->supplier = $depart_id;
  419. $model->type = $order['type'];
  420. $model->depart_id = $head;
  421. $model->top_depart_id = $head;
  422. $model->crt_id = Employee::SPECIAL_ADMIN;
  423. $model->purchase_id = Employee::SPECIAL_ADMIN;
  424. $model->purchase_total = $fee['other_fee_1'] ?? 0;
  425. $model->storehouse_id = $storehouse ?? 0;
  426. $model->save();
  427. if(empty($model->id)) return [false,'采购单主信息生成失败'];
  428. $purchase_order_id = $model->id;
  429. $insert = [];$product_total = 0;
  430. foreach ($product as $value){
  431. $rate_tmp = $rate[$value['product_id']] ?? 0;
  432. $price = bcdiv(bcmul($rate_tmp, $fee['other_fee_1'],2), $value['number'],2);
  433. $product_total += $price * $value['number'];
  434. $insert[] = [
  435. 'purchase_order_special_id' => $purchase_order_id,
  436. 'product_id' => $value['product_id'],
  437. 'order_number' => $order_number,
  438. 'number' => $value['number'],
  439. 'price' => $price,
  440. 'storehouse_id' => $storehouse,
  441. ];
  442. }
  443. PurchaseOrderSpecialInfo::insert($insert);
  444. PurchaseOrderSpecial::where('id',$purchase_order_id)->update(['total' => $product_total]);
  445. $insert_see[] = [
  446. 'data_id' => $purchase_order_id, // 虚拟采购单
  447. 'data_type' => SeeRange::type_ten,
  448. 'param_id' => $depart_id, //门店id
  449. 'type' => SeeRange::data_three,
  450. 'crt_time' => time(),
  451. ];
  452. if(! empty($insert_see)) SeeRange::insert($insert_see);
  453. DB::commit();
  454. }catch (\Throwable $exception){
  455. DB::rollBack();
  456. if (str_contains($exception->getMessage(), '1062') || str_contains($exception->getMessage(), 'Duplicate entry')) {
  457. return [false, '网络波动,请重新操作!'];
  458. }
  459. return [false, $exception->getMessage()];
  460. }
  461. return [true, ''];
  462. }
  463. //分社向总社采购 生成 分社订货合同
  464. public function createPurchaseOrderSales($order,$user){
  465. //没有供应商 不创建合同
  466. if(empty($order['supplier'])) return [true, ''];
  467. //总公司的采购单 不创建合同
  468. $head = $user['head'] ?? [];
  469. $head = $head['id'] ?? 0; //总社id
  470. if($head == $order['top_depart_id']) return [true, ''];
  471. //分社公司的采购单 不向总供应商采购 不创建合同
  472. $is_create = Supplier::where('id',$order['supplier'])->value('is_main');
  473. if(empty($is_create)) return [true, ''];
  474. // $customer_short_name = Depart::where('id',$order['top_depart_id'])->value('id') ?? "";
  475. $prefix = SalesOrder::$prefix[SalesOrder::Model_type_two];
  476. $order_number = OrderNoService::createSalesOrderNumber($prefix);
  477. $product = PurchaseOrderInfo::where('del_time',0)
  478. ->where('purchase_order_id',$order['id'])
  479. ->get()->toArray();
  480. if(empty($product)) return [false, '采购订单产品数据不能为空'];
  481. try{
  482. DB::beginTransaction();
  483. $time = time();
  484. $model = new SalesOrder();
  485. $model->model_type = SalesOrder::Model_type_two;
  486. $model->sales_order_type = SalesOrder::Order_type_two;
  487. $model->customer_id = Customer::special_id;
  488. $model->order_number = $order_number;
  489. $model->crt_id = $order['crt_id'];
  490. $model->depart_id = $head;
  491. $model->top_depart_id = $head;
  492. $model->other_fee = $order['other_fee'];
  493. $model->discount_fee = $order['discount_fee'];
  494. $model->contract_fee = $order['purchase_total'];
  495. $model->contact_order_no = $order['order_number'];
  496. $model->sign_time = $time;
  497. $model->save();
  498. $sales_order_id = $model->id;
  499. //产品字典
  500. $product_map = (new ProductService())->getProductDetail(array_column($product,'product_id'));
  501. $insert = [];
  502. $product_total = 0;
  503. foreach ($product as $value){
  504. $tmp = $product_map[$value['product_id']] ?? [];
  505. $product_total += $value['price'] * $value['number'];
  506. $insert[] = [
  507. 'sales_order_id' => $sales_order_id,
  508. 'product_id' => $value['product_id'],
  509. 'number' => $value['number'],
  510. 'basic_type_id' => $value['basic_type_id'],
  511. 'price' => $value['price'],
  512. 'cost' => $tmp['cost'] ?? 0,
  513. 'retail_price' => $tmp['retail_price'] ?? 0,
  514. 'final_amount' => $value['price'] * $value['number'],
  515. ];
  516. }
  517. $bool = SalesOrderProductInfo::insert($insert);
  518. if(! $bool) return [false,'合同生成失败!'];
  519. //反写数据
  520. $tmp = $product_total + $order['other_fee'];
  521. $tmp = $tmp > 0 ? $tmp : 1;
  522. $rate = ($product_total + $order['other_fee'] - $order['discount_fee']) / $tmp;
  523. SalesOrder::where('id',$sales_order_id)->update([
  524. 'product_total' => $product_total,
  525. 'rate' => $rate
  526. ]);
  527. //生成付款单
  528. $model = new PaymentReceipt();
  529. $model->order_number = (new OrderNoService())->createOrderNumber(PaymentReceipt::prefix);
  530. $model->data_type = PaymentReceipt::data_type_one;
  531. $model->type = PaymentReceipt::type_one;
  532. $model->crt_id = $user['id'];
  533. $model->depart_id = $head;
  534. $model->top_depart_id = $head;
  535. $model->save();
  536. $insert = [];
  537. $insert[] = [
  538. 'payment_receipt_id' => $model->id,
  539. 'data_type' => PaymentReceipt::type_one,
  540. 'data_order_no' => $order_number,
  541. 'data_order_type' => PaymentReceipt::data_type_one,
  542. 'amount' => $order['purchase_total'],
  543. 'type' => PaymentReceiptInfo::type_three,
  544. 'crt_time' => $time,
  545. ];
  546. PaymentReceiptInfo::insert($insert);
  547. DB::commit();
  548. }catch (\Throwable $exception){
  549. DB::rollBack();
  550. if (str_contains($exception->getMessage(), '1062') || str_contains($exception->getMessage(), 'Duplicate entry')) {
  551. return [false, '网络波动,请重新操作!'];
  552. }
  553. return [false ,$exception->getMessage()];
  554. }
  555. return [true,''];
  556. }
  557. //自动生成-----------------------------------
  558. //自动生成删除
  559. //分社订货合同删除
  560. public function delCreatePurchaseOrderSales($data, $order){
  561. $sale_order = SalesOrder::where('del_time',0)
  562. ->where('contact_order_no',$order['order_number'])
  563. ->select('id','order_number')
  564. ->get()->toArray();
  565. if(empty($sale_order)) return [true,''];
  566. foreach ($sale_order as $value){
  567. list($status, $msg) = (new SalesOrderService())->salesOrderDel(['id' => $value['id']]);
  568. if(! $status) return [false,$msg];
  569. list($status, $msg) = (new PaymentReceiptService())->customerDel(['id' => $value['id']]);
  570. if(! $status) return [false,$msg];
  571. }
  572. return [true, ''];
  573. }
  574. //自动生成删除
  575. public function confirmSportsBag($data){
  576. $model = SportsBag::where('order_number',$data['order_number'])
  577. ->where('del_time',0)
  578. ->first();
  579. if(empty($model)) return [false, '活动包不存在或已被删除'];
  580. if($model->state != SportsBag::STATE_ONE) return [false, '请确认活动包状态,操作失败'];
  581. if($data['type'] == self::TYPE_ONE){
  582. //通过
  583. $model->state = SportsBag::STATE_TWO;
  584. $model->save();
  585. }else{
  586. //驳回
  587. $model->state = SportsBag::State_minus_one;
  588. $model->save();
  589. }
  590. return [true, $model->toArray()];
  591. }
  592. public function confirmPaymentReceipt($data){
  593. $model = PaymentReceipt::where('order_number',$data['order_number'])
  594. ->where('del_time',0)
  595. ->first();
  596. if(empty($model)) return [false, '收付款单不存在或已被删除'];
  597. if($model->state != PaymentReceipt::STATE_ONE) return [false, '请确认收付款单状态,操作失败'];
  598. if($data['type'] == self::TYPE_ONE){
  599. //通过
  600. $model->state = PaymentReceipt::STATE_TWO;
  601. $model->save();
  602. }else{
  603. //驳回
  604. $model->state = PaymentReceipt::State_minus_one;
  605. $model->save();
  606. }
  607. return [true, $model->toArray()];
  608. }
  609. public function confirmInvoiceOrder($data){
  610. $model = InvoiceOrder::where('order_number',$data['order_number'])
  611. ->where('del_time',0)
  612. ->first();
  613. if(empty($model)) return [false, '发货单不存在或已被删除'];
  614. if($model->state != InvoiceOrder::STATE_ONE) return [false, '请确认发货单状态,操作失败'];
  615. $send_data = [];
  616. if($data['type'] == self::TYPE_ONE){
  617. //通过
  618. $model->state = InvoiceOrder::STATE_TWO;
  619. $model->save();
  620. $sale = SalesOrder::where('id',$model->sales_order_id)->first();
  621. if($sale['sales_order_type'] == SalesOrder::Order_type_one){
  622. //安装件更新发货状态
  623. SalesOrder::where('id',$model->sales_order_id)
  624. ->update(['invoice_state' => SalesOrder::invoice_one]);
  625. }else{
  626. //快递件更新 单据状态 发货状态
  627. SalesOrder::where('id',$model->sales_order_id)
  628. ->update([
  629. 'state' => SalesOrder::State2_one,
  630. 'invoice_state' => SalesOrder::invoice_one
  631. ]);
  632. }
  633. //分社采购单更新发货状态
  634. if(! empty($sale->contact_order_no)) {
  635. $purchase = PurchaseOrder::where('order_number',$sale->contact_order_no)->where('del_time', 0)->first();
  636. if(! empty($purchase)){
  637. $purchase = $purchase->toArray();
  638. if(in_array($purchase['order_type'], [PurchaseOrder::Order_type_three, PurchaseOrder::Order_type_four])) {
  639. //提醒创建人
  640. $emp_tmp = Employee::where('id', $purchase['crt_id'])->value('emp_name');
  641. $send_data[] = [
  642. 'employee_id' => $purchase['crt_id'],
  643. 'type' => 2,
  644. 'state' => 0,
  645. 'menu_id' => 45,
  646. 'order_number' => $purchase['order_number'],
  647. 'tmp_data' => [
  648. $purchase['order_number'],
  649. "分社采购单",
  650. '已发货',
  651. $emp_tmp,
  652. date('Y-m-d H:i:s'),
  653. ],
  654. ];
  655. }
  656. }
  657. PurchaseOrder::where('order_number',$sale->contact_order_no)->update(['invoice_state' => PurchaseOrder::invoice_state_one]);
  658. }
  659. }else{
  660. //驳回
  661. $model->state = InvoiceOrder::STATE_ZERO;
  662. $model->save();
  663. }
  664. (new OaService())->sendWxOaCheckMessage($send_data);
  665. return [true, $model->toArray()];
  666. }
  667. public function recordInvoiceOrder($data, $order){
  668. $result = InvoiceOrderInfo::where('del_time',0)
  669. ->where('order_number',$order['order_number'])
  670. ->get()->toArray();
  671. if(empty($result)) return [false,'发货单产品信息不存在或已被删除'];
  672. $insert = [];
  673. $time = time();
  674. foreach ($result as $value){
  675. $key = $value['product_id'] . $value['storehouse_id'];
  676. if(isset($insert[$key])){
  677. $insert[$key]['number'] += -($value['number']);
  678. }else{
  679. $insert[$key] = [
  680. 'product_id' => $value['product_id'],
  681. 'number' => -($value['number']),
  682. 'order_type' => InvoiceOrder::prefix,
  683. 'order_number' => $order['order_number'],
  684. 'crt_time' => $time,
  685. 'storehouse_id' => $value['storehouse_id'],
  686. 'depart_id' => $order['depart_id'],
  687. 'top_depart_id' => $order['top_depart_id'],
  688. 'price' => $value['price'],
  689. ];
  690. }
  691. }
  692. $insert = array_values($insert);
  693. $bool = InOutRecord::insert($insert);
  694. if(! $bool) return [false,'流水写入失败'];
  695. return [true,''];
  696. }
  697. public function confirmPurchaseOrderState($data){
  698. $model = PurchaseOrder::where('order_number',$data['order_number'])
  699. ->where('del_time',0)
  700. ->first();
  701. if(empty($model)) return [false,'采购单不存在或已被删除'];
  702. if($model->state != PurchaseOrder::STATE_ONE) return [false,'请确认采购单状态,操作失败'];
  703. if($data['type'] == self::TYPE_ONE){
  704. $model->state = PurchaseOrder::STATE_TWO;
  705. $model->save();
  706. }else{
  707. //驳回
  708. $model->state = PurchaseOrder::State_minus_one;
  709. $model->save();
  710. }
  711. return [true, $model->toArray()];
  712. }
  713. public function confirmPurchaseOrder($data,$user){
  714. $model = PurchaseOrder::where('order_number',$data['order_number'])
  715. ->where('del_time',0)
  716. ->first();
  717. if(empty($model)) return [false, '采购订单不存在或已被删除'];
  718. if($model->state != PurchaseOrder::STATE_TWO) return [false, '请确认采购订单状态,操作失败'];
  719. $model->state = PurchaseOrder::STATE_Four;
  720. $model->save();
  721. return [true, $model->toArray()];
  722. }
  723. public function recordPurchaseOrder($data, $order){
  724. $result = PurchaseOrderInfo::where('del_time',0)
  725. ->where('order_number',$order['order_number'])
  726. ->get()->toArray();
  727. if(empty($result)) return [false,'采购单产品信息不存在或已被删除'];
  728. $insert = [];
  729. $time = time();
  730. foreach ($result as $value){
  731. $key = $value['product_id'] . $value['storehouse_id'];
  732. if(isset($insert[$key])){
  733. $insert[$key]['number'] += $value['number'];
  734. }else{
  735. $insert[$key] = [
  736. 'product_id' => $value['product_id'],
  737. 'number' => $value['number'],
  738. 'order_type' => PurchaseOrder::prefix,
  739. 'order_number' => $order['order_number'],
  740. 'crt_time' => $time,
  741. 'storehouse_id' => $value['storehouse_id'],
  742. 'depart_id' => $order['depart_id'],
  743. 'top_depart_id' => $order['top_depart_id'],
  744. 'price' => $value['price'],
  745. ];
  746. }
  747. }
  748. $insert = array_values($insert);
  749. $bool = InOutRecord::insert($insert);
  750. if(! $bool) return [false,'流水写入失败'];
  751. return [true,''];
  752. }
  753. public function confirmPurchaseSpecial($data){
  754. $model = PurchaseOrderSpecial::where('order_number',$data['order_number'])
  755. ->where('del_time',0)
  756. ->first();
  757. if(empty($model)) return [false,'虚拟采购订单不存在或已被删除'];
  758. if($model->state != PurchaseOrderSpecial::STATE_ONE) return [false,'请确认虚拟采购订单状态,操作失败'];
  759. if($data['type'] == self::TYPE_ONE){
  760. $model->state = PurchaseOrderSpecial::STATE_TWO;
  761. $model->save();
  762. }else{
  763. //驳回
  764. $model->state = PurchaseOrderSpecial::State_minus_one;
  765. $model->save();
  766. }
  767. return [true, $model->toArray()];
  768. }
  769. public function confirmConstruction($data){
  770. $model = Construction::where('order_number',$data['order_number'])
  771. ->where('del_time',0)
  772. ->first();
  773. if(empty($model)) return [false, '施工单不存在或已被删除'];
  774. if($model->state != Construction::STATE_ONE) return [false, '请确认施工单状态,操作失败'];
  775. if($data['type'] == self::TYPE_ONE){
  776. $model->state = Construction::STATE_TWO;
  777. $model->save();
  778. //已下施工
  779. SalesOrder::where('id',$model->sales_order_id)->update(['state' => SalesOrder::State_five]);
  780. }else{
  781. //驳回
  782. $model->state = Construction::State_minus_one;
  783. $model->save();
  784. }
  785. return [true, $model->toArray()];
  786. }
  787. public function recordConstruction($data, $order){
  788. //仅施工不需要库存流水
  789. if($order['model_type'] == Construction::Model_type_two) return [true, self::minus_one];
  790. $result = ConstructionProductInfo::where('del_time',0)
  791. ->where('construction_id',$order['id'])
  792. ->get()->toArray();
  793. if(empty($result)) return [false,'施工单产品信息不存在或已被删除'];
  794. $insert = [];
  795. $time = time();
  796. foreach ($result as $value){
  797. $key = $value['product_id'] . $value['storehouse_id'];
  798. if(isset($insert[$key])){
  799. $insert[$key]['number'] += -($value['number']);
  800. }else{
  801. $insert[$key] = [
  802. 'product_id' => $value['product_id'],
  803. 'number' => -($value['number']),
  804. 'order_type' => Construction::$prefix[$order['model_type']] ?? '',
  805. 'order_number' => $order['order_number'],
  806. 'crt_time' => $time,
  807. 'storehouse_id' => $value['storehouse_id'],
  808. 'depart_id' => $order['depart_id'],
  809. 'top_depart_id' => $order['top_depart_id'],
  810. 'price' => $value['price'],
  811. ];
  812. }
  813. }
  814. $insert = array_values($insert);
  815. $bool = InOutRecord::insert($insert);
  816. if(! $bool) return [false,'流水写入失败'];
  817. return [true,''];
  818. }
  819. public function confirmReturnExchangeOrder($data){
  820. $model = ReturnExchangeOrder::where('order_number',$data['order_number'])
  821. ->where('del_time',0)
  822. ->first();
  823. if(empty($model)) return [false, '退换货单不存在或已被删除'];
  824. if($model->state != ReturnExchangeOrder::State_one) return [false, '请确认退换货单状态,操作失败'];
  825. if($data['type'] == self::TYPE_ONE){
  826. $model->state = ReturnExchangeOrder::State_two;
  827. $model->save();
  828. // if($model->data_type == ReturnExchangeOrder::Order_type){
  829. // SalesOrder::where('id', $model->data_id)->update([
  830. // 'state' => SalesOrder::State_six
  831. // ]);
  832. // }
  833. }else{
  834. //驳回
  835. $model->state = ReturnExchangeOrder::State_minus_one;
  836. $model->save();
  837. }
  838. return [true, $model->toArray()];
  839. }
  840. public function recordReturnExchangeOrder($data, $order){
  841. if($order['model_type'] == ReturnExchangeOrder::Model_type_three) return [true, self::minus_one];
  842. // if($order['type'] == ReturnExchangeOrder::Order_type){
  843. // //快递件不记录流水
  844. // $sales_order_type = SalesOrder::where('id',$order['data_id'])->value('sales_order_type');
  845. // if($sales_order_type == SalesOrder::Order_type_two) return [true, self::minus_one];
  846. // }
  847. //合同 退货
  848. $map = [];
  849. if($order['type'] == ReturnExchangeOrder::Order_type){
  850. //查找 出库数据的产品
  851. $product = OutBoundOrderInfo::where('del_time',0)
  852. ->where('data_id', $order['data_id'])
  853. ->where('type', OutBoundOrder::out_type_one)
  854. ->whereColumn('number','>','return_number')
  855. ->select('id','product_id','number','return_number')
  856. ->get()->toArray();
  857. foreach($product as $value){
  858. $map[$value['product_id']][] = $value;
  859. }
  860. }
  861. $result = ReturnExchangeOrderProductInfo::where('del_time',0)
  862. ->where('return_exchange_id',$order['id'])
  863. ->get()->toArray();
  864. if(empty($result)) return [false,'退换货单产品信息不存在或已被删除'];
  865. $insert = $update =[];
  866. $time = time();
  867. foreach ($result as $value){
  868. $key = $value['product_id'] . $value['storehouse_id'];
  869. $prefix = ReturnExchangeOrder::$prefix[$value['return_or_exchange']] ?? '';
  870. if($value['return_or_exchange'] == ReturnExchangeOrderProductInfo::type_one){
  871. //退货
  872. if($order['type'] == ReturnExchangeOrder::Order_type){
  873. $number = 0;
  874. //合同出库数量
  875. $out_array = $map[$value['product_id']] ?? [];
  876. if(empty($out_array)){
  877. //未出库 这个退货不需要加回来 不需要流水
  878. continue;
  879. } else{
  880. foreach ($out_array as $out){
  881. if($value['number'] <= 0) continue;
  882. //剩余能退数量
  883. $out_number = bcsub($out['number'], $out['return_number']);
  884. if($out_number >= $value['number']) {
  885. $number = bcadd($value['number'], $number);
  886. $value['number'] = 0;
  887. $t = $value['number'];
  888. }else{
  889. $number = bcadd($out_number, $number);
  890. $value['number'] = bcsub($value['number'], $out_number);
  891. $t = $out_number;
  892. }
  893. //更新数据
  894. $update[] = [
  895. 'id' => $out['id'],
  896. 'return_number' => bcadd($out['return_number'], $t),
  897. ];
  898. }
  899. }
  900. }else{
  901. // 采购
  902. $number = -($value['number']);
  903. }
  904. if(isset($insert[$key])){
  905. $insert[$key]['number'] += $number;
  906. }else{
  907. $insert[$key] = [
  908. 'product_id' => $value['product_id'],
  909. 'number' => $number,
  910. 'order_type' => $prefix,
  911. 'order_number' => $order['order_number'],
  912. 'crt_time' => $time,
  913. 'storehouse_id' => $value['storehouse_id'],
  914. 'depart_id' => $order['depart_id'],
  915. 'top_depart_id' => $order['top_depart_id'],
  916. 'price' => $value['return_exchange_price'],
  917. ];
  918. }
  919. }
  920. }
  921. $insert = array_values($insert);
  922. if(empty($insert)) return [true, self::minus_one];
  923. $bool = InOutRecord::insert($insert);
  924. if(! $bool) return [false,'流水写入失败'];
  925. if(! empty($update)){
  926. foreach ($update as $value){
  927. OutBoundOrderInfo::where('id', $value['id'])
  928. ->update(['return_number' => $value['return_number']]);
  929. }
  930. }
  931. return [true,''];
  932. }
  933. public function confirmInventory($data){
  934. $model = Inventory::where('order_number',$data['order_number'])
  935. ->where('del_time',0)
  936. ->first();
  937. if(empty($model)) return [false,'盘点单不存在或已被删除'];
  938. if($model->state != Inventory::STATE_ONE) return [false,'请确认盘点单状态,操作失败'];
  939. if($data['type'] == self::TYPE_ONE){
  940. $model->state = Inventory::STATE_TWO;
  941. $model->save();
  942. }else{
  943. //驳回
  944. $model->state = Inventory::State_minus_one;
  945. $model->save();
  946. }
  947. return [true, $model->toArray()];
  948. }
  949. public function confirmOut($data){
  950. $model = OutBoundOrder::where('order_number',$data['order_number'])
  951. ->where('del_time',0)
  952. ->first();
  953. if(empty($model)) return [false,'出库单不存在或已被删除'];
  954. if($model->state != OutBoundOrder::STATE_ONE) return [false,'请确认出库单状态,操作失败'];
  955. if($data['type'] == self::TYPE_ONE){
  956. $model->state = OutBoundOrder::STATE_TWO;
  957. $model->save();
  958. }else{
  959. //驳回
  960. $model->state = OutBoundOrder::State_minus_one;
  961. $model->save();
  962. }
  963. return [true, $model->toArray()];
  964. }
  965. public function recordInventory($data, $order){
  966. $result = InventorySub::where('del_time',0)
  967. ->where('inventory_id',$order['id'])
  968. ->get()->toArray();
  969. if(empty($result)) return [false,'盘点单明细信息不存在或已被删除'];
  970. $prefix = Inventory::prefix;
  971. $insert = [];
  972. $time = time();
  973. foreach ($result as $value){
  974. $key = $value['product_id'] . $value['storehouse_id'];
  975. $number = $value['final_num'];
  976. if(isset($insert[$key])){
  977. $insert[$key]['number'] += $number;
  978. }else{
  979. $insert[$key] = [
  980. 'product_id' => $value['product_id'],
  981. 'number' => $number,
  982. 'order_type' => $prefix,
  983. 'order_number' => $order['order_number'],
  984. 'crt_time' => $time,
  985. 'storehouse_id' => $value['storehouse_id'],
  986. 'depart_id' => $order['depart_id'],
  987. 'top_depart_id' => $order['top_depart_id'],
  988. 'price' => $value['price'],
  989. ];
  990. }
  991. }
  992. $bool = InOutRecord::insert($insert);
  993. if(! $bool) return [false,'流水写入失败'];
  994. return [true,''];
  995. }
  996. public function recordOut($data, $order){
  997. $result = OutBoundOrderInfo::where('del_time',0)
  998. ->where('out_bound_id',$order['id'])
  999. ->get()->toArray();
  1000. if(empty($result)) return [false,'出库单明细信息不存在或已被删除'];
  1001. $prefix = OutBoundOrder::prefix;
  1002. $insert = [];
  1003. $time = time();
  1004. foreach ($result as $value){
  1005. $key = $value['product_id'] . $value['storehouse_id'];
  1006. $number = -($value['number']);
  1007. if(isset($insert[$key])){
  1008. $insert[$key]['number'] += $number;
  1009. }else{
  1010. $insert[$key] = [
  1011. 'product_id' => $value['product_id'],
  1012. 'number' => $number,
  1013. 'order_type' => $prefix,
  1014. 'order_number' => $order['order_number'],
  1015. 'crt_time' => $time,
  1016. 'storehouse_id' => $value['storehouse_id'],
  1017. 'depart_id' => $order['depart_id'],
  1018. 'top_depart_id' => $order['top_depart_id'],
  1019. 'price' => $value['price'],
  1020. ];
  1021. }
  1022. }
  1023. $bool = InOutRecord::insert($insert);
  1024. if(! $bool) return [false, '流水写入失败'];
  1025. return [true, ''];
  1026. }
  1027. public function settleSalesOrder($data,$user){
  1028. $model = SalesOrder::where('order_number', $data['order_number'])
  1029. ->where('del_time',0)
  1030. ->first();
  1031. if(empty($model)) return [false, '合同不存在或已被删除'];
  1032. //安装件
  1033. if($model->state <= SalesOrder::State_four || $model->state >= SalesOrder::State_seven) return [false, '请确认合同状态,操作失败'];
  1034. SalesOrder::where('del_time',0)->where('order_number',$data['order_number'])
  1035. ->update(['state' => SalesOrder::State_seven]);
  1036. $time = time();
  1037. $insert = [];
  1038. $new = [];
  1039. if(! empty($data['img'])){
  1040. foreach ($data['img'] as $value){
  1041. $insert[] = [
  1042. 'sales_order_id' => $model->id,
  1043. 'data_id' => 0,
  1044. 'type' => SalesOrderInfo::type_seven,
  1045. 'file' => $value,
  1046. 'crt_time' => $time,
  1047. ];
  1048. $new[] = $value;
  1049. }
  1050. }
  1051. if(! empty($data['mark'])){
  1052. $insert[] = [
  1053. 'sales_order_id' => $model->id,
  1054. 'data_id' => $user['id'],
  1055. 'type' => SalesOrderInfo::type_eight,
  1056. 'file' => $data['mark'],
  1057. 'crt_time' => $time,
  1058. ];
  1059. }
  1060. if(! empty($insert)) SalesOrderInfo::insert($insert);
  1061. return [true, ['file' => $new, 'order' => $model->toArray()]];
  1062. }
  1063. public function settleSalesOrderCustomer($data,$user){
  1064. $model = SalesOrder::where('order_number', $data['order_number'])
  1065. ->where('del_time',0)
  1066. ->first();
  1067. if(empty($model)) return [false, '合同不存在或已被删除'];
  1068. if(empty($data['img'])) return [false,'图片不能为空'];
  1069. //安装件
  1070. if($model->state != SalesOrder::State_seven) return [false, '请确认合同状态,操作失败'];
  1071. SalesOrder::where('del_time',0)->where('order_number',$data['order_number'])
  1072. ->update(['state' => SalesOrder::State_eight]);
  1073. SalesOrderInfo::insert([
  1074. 'sales_order_id' => $model->id,
  1075. 'type' => SalesOrderInfo::type_six,
  1076. 'file' => $data['img'],
  1077. 'crt_time' => time(),
  1078. ]);
  1079. return [true, $model->toArray()];
  1080. }
  1081. public function settleSalesOrderConfirm($data,$user){
  1082. $model = SalesOrder::where('order_number', $data['order_number'])
  1083. ->where('del_time',0)
  1084. ->first();
  1085. if(empty($model)) return [false, '合同不存在或已被删除'];
  1086. //安装件
  1087. if($model->state != SalesOrder::State_four) return [false, '请确认合同状态,操作失败'];
  1088. $model->is_confirm = 1;
  1089. $model->save();
  1090. $depart = SeeRange::where('del_time',0)
  1091. ->where('data_id', $model->id)
  1092. ->where('data_type',SeeRange::type_seven)
  1093. ->where('type',SeeRange::data_three)
  1094. ->first();
  1095. if(! empty($depart)){
  1096. $depart = $depart->toArray();
  1097. $channel_id = Depart::where('id',$depart->param_id)->value('channel_id');
  1098. if(! empty($channel_id)){
  1099. $emp_name = Employee::where('id',$channel_id)->value('emp_name');
  1100. $send_data[] = [
  1101. 'employee_id' => $channel_id,
  1102. 'type' => 2,
  1103. 'state' => 0,
  1104. 'menu_id' => 37,
  1105. 'order_number' => $model->order_number,
  1106. 'tmp_data' => [
  1107. $model->order_number,
  1108. "派单合同",
  1109. "门店接收派单",
  1110. $emp_name,
  1111. date('Y-m-d H:i:s'),
  1112. ],
  1113. ];
  1114. (new OaService())->sendWxOaCheckMessage($send_data);
  1115. }
  1116. }
  1117. return [true, $model->toArray()];
  1118. }
  1119. public function settleSalesOrderConfirmBack($data,$user){
  1120. $model = SalesOrder::where('order_number', $data['order_number'])
  1121. ->where('del_time',0)
  1122. ->first();
  1123. if(empty($model)) return [false, '合同不存在或已被删除'];
  1124. //安装件
  1125. if($model->state != SalesOrder::State_four) return [false, '请确认合同状态,操作失败'];
  1126. //校验施工
  1127. $bool = Construction::where('del_time',0)
  1128. ->where('sales_order_id', $model->id)
  1129. ->exists();
  1130. if($bool) return [false,'合同已生成施工单,操作失败'];
  1131. if($model->is_confirm != 1) return [false, '合同未接受派单,操作失败'];
  1132. $model->is_confirm = 0;
  1133. $model->save();
  1134. //单据状态还原
  1135. SalesOrder::where('del_time',0)->where('id', $model->id)->update([
  1136. 'state' => SalesOrder::State_three,
  1137. 'dispatch_time_second' => 0,
  1138. 'dispatch_time_second_id' => 0,
  1139. ]);
  1140. SeeRange::where('del_time',0)
  1141. ->where('data_id', $model->id)
  1142. ->where('data_type',SeeRange::type_seven)
  1143. ->where('type',SeeRange::data_three)
  1144. ->update(['del_time' => time()]);
  1145. return [true, $model->toArray()];
  1146. }
  1147. public function confirmSales($data){
  1148. $model = SalesOrder::where('order_number', $data['order_number'])
  1149. ->where('del_time',0)
  1150. ->first();
  1151. if(empty($model)) return [false, '合同不存在或已被删除'];
  1152. if($model->state != SalesOrder::State_one) return [false, '请确认合同状态,操作失败'];
  1153. if($data['type'] == self::TYPE_ONE){
  1154. $state = SalesOrder::State_three;
  1155. if(in_array($model->model_type,[SalesOrder::Model_type_four,SalesOrder::Model_type_seven])){
  1156. //线上订单 补贴订单
  1157. $state = SalesOrder::State_two;
  1158. }
  1159. $model->state = $state;
  1160. $model->save();
  1161. }else{
  1162. $model->state = SalesOrder::State_minus_one;
  1163. $model->save();
  1164. }
  1165. return [true, $model->toArray()];
  1166. }
  1167. public function reject_sales($data){
  1168. $model = SalesOrder::where('order_number', $data['order_number'])
  1169. ->where('del_time',0)
  1170. ->first();
  1171. if(empty($model)) return [false, '合同不存在或已被删除'];
  1172. if($model->out_state > SalesOrder::out_zero) return [false, '合同已提交出库,操作失败'];
  1173. //安装件
  1174. if(in_array($model->model_type,[SalesOrder::Model_type_four,SalesOrder::Model_type_seven])){
  1175. //线上订单 补贴订单
  1176. if($model->state != SalesOrder::State_two) return [false, '请确认合同状态,操作失败'];
  1177. }else{
  1178. //除线上订单 补贴订单 之外
  1179. if($model->state != SalesOrder::State_three) return [false, '请确认合同状态,操作失败'];
  1180. }
  1181. //未确认
  1182. $model->state = SalesOrder::State_zero;
  1183. $model->save();
  1184. return [true, $model->toArray()];
  1185. }
  1186. public function reject_purchase($data){
  1187. $model = PurchaseOrder::where('order_number', $data['order_number'])
  1188. ->where('del_time',0)
  1189. ->first();
  1190. if(empty($model)) return [false, '采购单不存在或已被删除'];
  1191. //安装件
  1192. if($model->state != PurchaseOrder::STATE_Four) return [false, '请确认采购单状态,操作失败'];
  1193. $model->state = PurchaseOrder::STATE_TWO;
  1194. $model->save();
  1195. return [true, $model->toArray()];
  1196. }
  1197. public function reject_purchase_special($data){
  1198. $model = PurchaseOrderSpecial::where('order_number', $data['order_number'])
  1199. ->where('del_time',0)
  1200. ->first();
  1201. if(empty($model)) return [false, '虚拟采购订单不存在或已被删除'];
  1202. //安装件
  1203. if($model->state != PurchaseOrderSpecial::STATE_TWO) return [false, '请确认虚拟采购订单状态,操作失败'];
  1204. $model->state = PurchaseOrder::STATE_ZERO;
  1205. $model->save();
  1206. return [true, $model->toArray()];
  1207. }
  1208. public function reject_purchase_confirm($data){
  1209. $model = PurchaseOrder::where('order_number', $data['order_number'])
  1210. ->where('del_time',0)
  1211. ->first();
  1212. if(empty($model)) return [false, '采购单不存在或已被删除'];
  1213. //安装件
  1214. if($model->state != PurchaseOrder::STATE_TWO) return [false, '请确认采购单状态,操作失败'];
  1215. $model->state = PurchaseOrder::STATE_ZERO;
  1216. $model->save();
  1217. return [true, $model->toArray()];
  1218. }
  1219. public function reject_construction($data){
  1220. $model = Construction::where('order_number', $data['order_number'])
  1221. ->where('del_time',0)
  1222. ->first();
  1223. if(empty($model)) return [false, '施工单不存在或已被删除'];
  1224. //安装件
  1225. if($model->state != Construction::STATE_TWO) return [false, '请确认施工单状态,操作失败'];
  1226. $model->state = Construction::STATE_ZERO;
  1227. $model->save();
  1228. return [true, $model->toArray()];
  1229. }
  1230. public function reject_payment_receipt($data){
  1231. $model = PaymentReceipt::where('order_number', $data['order_number'])
  1232. ->where('del_time',0)
  1233. ->first();
  1234. if(empty($model)) return [false, '收付款单不存在或已被删除'];
  1235. if($model->state != PaymentReceipt::STATE_TWO) return [false, '请确认收付款单状态,操作失败'];
  1236. $model->state = PaymentReceipt::STATE_ZERO;
  1237. $model->save();
  1238. return [true, $model->toArray()];
  1239. }
  1240. public function reject_sports_bag($data){
  1241. $model = SportsBag::where('order_number', $data['order_number'])
  1242. ->where('del_time',0)
  1243. ->first();
  1244. if(empty($model)) return [false, '活动包不存在或已被删除'];
  1245. if($model->state != SportsBag::STATE_TWO) return [false, '请确认活动包状态,操作失败'];
  1246. $model->state = SportsBag::STATE_ZERO;
  1247. $model->save();
  1248. return [true, $model->toArray()];
  1249. }
  1250. public function reject_return_exchange($data){
  1251. $model = ReturnExchangeOrder::where('order_number', $data['order_number'])
  1252. ->where('del_time',0)
  1253. ->first();
  1254. if(empty($model)) return [false, '退换货单不存在或已被删除'];
  1255. if($model->state != ReturnExchangeOrder::State_two) return [false, '请确认退换货单状态,操作失败'];
  1256. $model->state = ReturnExchangeOrder::State_zero;
  1257. $model->save();
  1258. return [true, $model->toArray()];
  1259. }
  1260. public function reject_record_construction($data,$order){
  1261. //仅施工不需要库存流水
  1262. if($order['model_type'] == Construction::Model_type_two) return [true, self::minus_one];
  1263. //获取单据最新数据时间 正常施工数据
  1264. $crt_time = 0;
  1265. $latest = InOutRecord::where('del_time',0)
  1266. ->where('order_number',$data['order_number'])
  1267. ->where('number','<',0)
  1268. ->select('crt_time')
  1269. ->orderBy('crt_time', 'desc')
  1270. ->first();
  1271. if(! empty($latest)) $crt_time = $latest->crt_time;
  1272. $result = InOutRecord::where('del_time',0)
  1273. ->where('crt_time',$crt_time)
  1274. ->where('order_number',$data['order_number'])
  1275. ->where('number','<',0)
  1276. ->select('product_id','storehouse_id','number','depart_id','order_number','top_depart_id','order_type','price')
  1277. ->get()->toArray();
  1278. if(empty($result)) return [false,'施工出库流水数据未找到'];
  1279. //生成对冲数据
  1280. $time = time();
  1281. foreach ($result as $key => $value){
  1282. $result[$key]['number'] = abs($value['number']);
  1283. $result[$key]['crt_time'] = $time;
  1284. }
  1285. $bool = InOutRecord::insert($result);
  1286. if(! $bool) return [false,'流水写入失败'];
  1287. //写入流水
  1288. return [true, ''];
  1289. }
  1290. public function reject_record_purchase($data,$order){
  1291. //获取单据最新数据时间 正常采购入库数据
  1292. $crt_time = 0;
  1293. $latest = InOutRecord::where('del_time',0)
  1294. ->where('order_number',$data['order_number'])
  1295. ->where('number','>',0)
  1296. ->select('crt_time')
  1297. ->orderBy('crt_time', 'desc')
  1298. ->first();
  1299. if(! empty($latest)) $crt_time = $latest->crt_time;
  1300. $result = InOutRecord::where('del_time',0)
  1301. ->where('crt_time',$crt_time)
  1302. ->where('order_number',$data['order_number'])
  1303. ->where('number','>',0)
  1304. ->select('product_id','storehouse_id','number','depart_id','order_number','top_depart_id','order_type','price')
  1305. ->get()->toArray();
  1306. if(empty($result)) return [false,'采购入库流水数据未找到'];
  1307. //生成对冲数据
  1308. $time = time();
  1309. foreach ($result as $key => $value){
  1310. $result[$key]['number'] = - $value['number'];
  1311. $result[$key]['crt_time'] = $time;
  1312. }
  1313. $bool = InOutRecord::insert($result);
  1314. if(! $bool) return [false,'流水写入失败'];
  1315. //写入流水
  1316. return [true, ''];
  1317. }
  1318. public function reject_record_return_exchange($data,$order){
  1319. if($order['model_type'] == ReturnExchangeOrder::Model_type_three) return [true, self::minus_one];
  1320. //获取单据最新数据时间 正常退换货流水数据
  1321. $crt_time = 0;
  1322. $latest = InOutRecord::where('del_time',0)
  1323. ->where('order_number',$data['order_number'])
  1324. ->select('crt_time')
  1325. ->orderBy('crt_time', 'desc')
  1326. ->first();
  1327. if(! empty($latest)) $crt_time = $latest->crt_time;
  1328. $result = InOutRecord::where('del_time',0)
  1329. ->where('crt_time',$crt_time)
  1330. ->where('order_number',$data['order_number'])
  1331. ->select('product_id','storehouse_id','number','depart_id','order_number','top_depart_id','order_type','price')
  1332. ->get()->toArray();
  1333. if(empty($result)) return [true, self::minus_one];
  1334. //生成对冲数据
  1335. $time = time();
  1336. foreach ($result as $key => $value){
  1337. $result[$key]['number'] = - $value['number'];
  1338. $result[$key]['crt_time'] = $time;
  1339. }
  1340. $bool = InOutRecord::insert($result);
  1341. if(! $bool) return [false, '流水写入失败'];
  1342. //写入流水
  1343. return [true, ''];
  1344. }
  1345. public function getOrderDetail($data,$user){
  1346. if(empty($data['order_number'])) return [false,'必传参数不能为空'];
  1347. $array = [];
  1348. foreach (Construction::$prefix as $value){
  1349. $array[$value] = "\App\Service\\ConstructionService";
  1350. }
  1351. foreach (ReturnExchangeOrder::$prefix as $value){
  1352. $array[$value] = "\App\Service\\ReturnExchangeOrderService";
  1353. }
  1354. foreach (SalesOrder::$prefix as $value){
  1355. $array[$value] = "\App\Service\\SalesOrderService";
  1356. }
  1357. $status = true;
  1358. $msg = [];
  1359. foreach ($array as $key => $value){
  1360. if(strpos($data['order_number'],$key) !== false) {
  1361. list($status, $msg) = (new $value)->detail($data);
  1362. return [$status, $msg];
  1363. }
  1364. }
  1365. if(strpos($data['order_number'],PurchaseOrder::prefix) !== false){
  1366. $service = "\App\Service\\PurchaseOrderService";
  1367. list($status, $msg) = (new $service)->detail($data,$user);
  1368. return [$status, $msg];
  1369. }
  1370. return [$status, $msg];
  1371. }
  1372. public function checkAll($data,$user){
  1373. if(empty($data['id']) || empty($data['order_number'])|| empty($data['opt_case'])) return [false,'必传参数不能为空或者参数值错误!'];
  1374. list($status,$msg) = $this->limitingSendRequestBackgExpire($data['order_number'].$data['opt_case']);
  1375. if(! $status) return [false,$msg];
  1376. //走审批流 单据校验
  1377. $function_check = self::$opt_1case_check[$data['opt_case']] ?? '';
  1378. //走审批流 单据状态改为待审批方法
  1379. $function = self::$opt_1case[$data['opt_case']] ?? '';
  1380. //单据不走审批流
  1381. $function2 = self::$finished[$data['opt_case']] ?? '';
  1382. try{
  1383. DB::beginTransaction();
  1384. //不走审批流,更新完直接返回
  1385. if($function2) {
  1386. list($bool,$msg) = $this->$function2($data,$user);
  1387. if($bool) {
  1388. $file = [];
  1389. if(isset($msg['order'])){
  1390. $order = $msg['order'];
  1391. $file = $msg['file'];
  1392. } else{
  1393. $order = $msg;
  1394. }
  1395. list($bool,$err) = $this->createRecordAndInventoryMy($data,$user,$order);
  1396. if($bool){
  1397. DB::commit();
  1398. if(! empty($file)) return [true, ['file' => ['new' => $file]]];
  1399. return [true, ''];
  1400. }else{
  1401. DB::rollBack();
  1402. return [false, $err];
  1403. }
  1404. }else{
  1405. DB::rollBack();
  1406. return [false, $msg];
  1407. }
  1408. }
  1409. //需要审批流,校验
  1410. if($function_check){
  1411. list($bool,$msg) = $this->$function_check($data, $user);
  1412. if(! $bool){
  1413. DB::rollBack();
  1414. return [false, $msg];
  1415. }
  1416. }
  1417. //需要审批流,从未审核变成待审核
  1418. if($function){
  1419. list($bool,$msg) = $this->$function($data);
  1420. if(! $bool){
  1421. DB::rollBack();
  1422. return [false, $msg];
  1423. }
  1424. //创建审批流
  1425. $args = [
  1426. 'order_no' => $data['order_number'],
  1427. 'menu_id' => $data['menu_id'] ?? 0,
  1428. 'opt_case' => $data['opt_case'],
  1429. 'order' => $msg,
  1430. ];
  1431. $oa = new OaService($user);
  1432. list($bool,$msg) = $oa->createOaOrder($args);
  1433. if(! $bool) {
  1434. DB::rollBack();
  1435. if($msg) return [false,$msg];
  1436. }
  1437. }
  1438. DB::commit();
  1439. return [true, ''];
  1440. }catch (\Throwable $exception){
  1441. DB::rollBack();
  1442. return [false, $exception->getMessage() . $exception->getFile(). $exception->getLine()];
  1443. }
  1444. }
  1445. //更新库存
  1446. public function changeInventory($data,$order,$user){
  1447. $number_symbol = "";
  1448. if(in_array($data['opt_case'],self::$in_opt)){
  1449. $number_symbol = ">";
  1450. }elseif (in_array($data['opt_case'],self::$out_opt)){
  1451. $number_symbol = "<";
  1452. }
  1453. //获取单据最新数据时间 正常审核的数据
  1454. $latest = InOutRecord::where('del_time',0)
  1455. ->where('order_number',$order['order_number'])
  1456. ->when(! empty($number_symbol), function ($query) use ($number_symbol) {
  1457. return $query->where('number', $number_symbol,0);
  1458. })
  1459. ->select('crt_time')
  1460. ->orderBy('crt_time', 'desc')
  1461. ->first();
  1462. $model = InOutRecord::where('del_time',0)
  1463. ->where('order_number',$order['order_number'])
  1464. ->when(! empty($number_symbol), function ($query) use ($number_symbol) {
  1465. return $query->where('number', $number_symbol,0);
  1466. })
  1467. ->select('number','crt_time','product_id','storehouse_id','top_depart_id');
  1468. if(! empty($latest)) {
  1469. $t = $latest->toArray();
  1470. $model->where('crt_time',$t['crt_time']);
  1471. }
  1472. $record = $model->get()->toArray();
  1473. if (empty($record)) return [false,'流水记录不存在'];
  1474. $top_depart_id = Storehouse::where('id', $order['storehouse_id'])->value('top_depart_id');
  1475. $result = $lock_number = [];
  1476. foreach ($record as $value){
  1477. $key = $value['product_id'] . $value['storehouse_id'];
  1478. if(isset($result[$key])){
  1479. $result[$key]['number'] += $value['number'];
  1480. }else{
  1481. $result[$key] = [
  1482. 'product_id' => $value['product_id'],
  1483. 'number' => $value['number'],
  1484. 'crt_time' => $value['crt_time'],
  1485. 'storehouse_id' => $value['storehouse_id'],
  1486. 'top_depart_id' => $top_depart_id,
  1487. ];
  1488. }
  1489. if($value['number'] < 0){
  1490. if(isset($lock_number[$key])){
  1491. $lock_number[$key] += $value['number'];
  1492. }else{
  1493. $lock_number[$key] = $value['number'];
  1494. }
  1495. }
  1496. }
  1497. //是否校验库存 是的话锁定数量要更新(根据当前操作人所在门店是否校验库存)
  1498. // $lock = $user['is_check_stock'];
  1499. $lock = ProductInventorySet::type_one;
  1500. $for_lock = OrderInventoryStock::where('order_number',$order['order_number'])
  1501. ->where('del_time',0)
  1502. ->orderBy('id','desc')
  1503. ->first();
  1504. if(! empty($for_lock)) {
  1505. $for_lock = $for_lock->toArray();
  1506. $lock = $for_lock['is_check_stock'];
  1507. }
  1508. $result = array_values($result);
  1509. foreach ($result as $key => $value){
  1510. $keys = $value['product_id'] . $value['storehouse_id'];
  1511. $m = ProductInventory::where('product_id',$value['product_id'])
  1512. ->where('storehouse_id',$value['storehouse_id'])
  1513. ->select('product_id','number','storehouse_id')
  1514. ->first();
  1515. if(empty($m)){
  1516. ProductInventory::insert($result[$key]);
  1517. }else{
  1518. //锁定数量
  1519. $lock_number_tmp = 0;
  1520. if($lock == ProductInventorySet::type_one && ! empty($lock_number[$keys])) $lock_number_tmp = $lock_number[$keys];
  1521. ProductInventory::where('product_id',$m->product_id)
  1522. ->where('storehouse_id',$m->storehouse_id)
  1523. ->lockForUpdate()
  1524. ->update([
  1525. 'number' => DB::raw('number + ('. $value['number'] . ')'),
  1526. 'lock_number' => DB::raw('lock_number + ('. $lock_number_tmp . ')')
  1527. ]);
  1528. }
  1529. }
  1530. return [true,''];
  1531. }
  1532. //业务单据审批通过后 驳回 更新库存
  1533. public function changeInventoryReject($data,$order,$user){
  1534. $number_symbol = "";
  1535. if(in_array($data['opt_case'],self::$in_opt)){
  1536. $number_symbol = "<";
  1537. }elseif (in_array($data['opt_case'],self::$out_opt)){
  1538. $number_symbol = ">";
  1539. }
  1540. //获取单据最新数据时间 正常审核的数据
  1541. $latest = InOutRecord::where('del_time',0)
  1542. ->where('order_number',$order['order_number'])
  1543. ->when(! empty($number_symbol), function ($query) use ($number_symbol) {
  1544. return $query->where('number', $number_symbol,0);
  1545. })
  1546. ->select('crt_time')
  1547. ->orderBy('crt_time', 'desc')
  1548. ->first();
  1549. $model = InOutRecord::where('del_time',0)
  1550. ->where('order_number',$order['order_number'])
  1551. ->when(! empty($number_symbol), function ($query) use ($number_symbol) {
  1552. return $query->where('number', $number_symbol,0);
  1553. })
  1554. ->select('number','crt_time','product_id','storehouse_id','top_depart_id');
  1555. if(! empty($latest)) {
  1556. $t = $latest->toArray();
  1557. $model->where('crt_time',$t['crt_time']);
  1558. }
  1559. $record = $model->get()->toArray();
  1560. if (empty($record)) return [false,'流水记录不存在'];
  1561. $top_depart_id = Storehouse::where('id', $order['storehouse_id'])->value('top_depart_id');
  1562. $result = $lock_number = [];
  1563. foreach ($record as $value){
  1564. $key = $value['product_id'] . $value['storehouse_id'];
  1565. if(isset($result[$key])){
  1566. $result[$key]['number'] += $value['number'];
  1567. }else{
  1568. $result[$key] = [
  1569. 'product_id' => $value['product_id'],
  1570. 'number' => $value['number'],
  1571. 'crt_time' => $value['crt_time'],
  1572. 'storehouse_id' => $value['storehouse_id'],
  1573. 'top_depart_id' => $top_depart_id,
  1574. ];
  1575. }
  1576. if($value['number'] > 0){
  1577. if(isset($lock_number[$key])){
  1578. $lock_number[$key] += $value['number'];
  1579. }else{
  1580. $lock_number[$key] = $value['number'];
  1581. }
  1582. }
  1583. }
  1584. //是否校验库存 是的话锁定数量要更新(根据当前操作人所在门店是否校验库存)
  1585. $lock = $user['is_check_stock'];
  1586. $result = array_values($result);
  1587. foreach ($result as $key => $value){
  1588. $keys = $value['product_id'] . $value['storehouse_id'];
  1589. $m = ProductInventory::where('product_id',$value['product_id'])
  1590. ->where('storehouse_id',$value['storehouse_id'])
  1591. ->select('product_id','number','storehouse_id')
  1592. ->first();
  1593. if(empty($m)){
  1594. ProductInventory::insert($result[$key]);
  1595. }else{
  1596. //锁定数量
  1597. $lock_number_tmp = 0;
  1598. if($lock == ProductInventorySet::type_one && ! empty($lock_number[$keys])) $lock_number_tmp = $lock_number[$keys];
  1599. ProductInventory::where('product_id',$m->product_id)
  1600. ->where('storehouse_id',$m->storehouse_id)
  1601. ->lockForUpdate()
  1602. ->update([
  1603. 'number' => DB::raw('number + ('. $value['number'] . ')'),
  1604. 'lock_number' => DB::raw('lock_number + ('. $lock_number_tmp . ')')
  1605. ]);
  1606. }
  1607. }
  1608. return [true,''];
  1609. }
  1610. public function createRecordAndInventory($data = []){
  1611. if(empty($data['type']) || empty($data['opt_case']) || empty($data['order_number'])) return [false, '传递参数缺少'];
  1612. $user = $data['user_data'] ?? [];
  1613. if($data['type'] == self::TYPE_THREE){
  1614. //通过后弃审
  1615. if(! isset(self::$opt_case_reject[$data['opt_case']])) return [false, '该操作不存在'];
  1616. //具体方法
  1617. $function = self::$opt_case_reject[$data['opt_case']];
  1618. //流水
  1619. $function2 = self::$reject_record[$data['opt_case']] ?? '';
  1620. //自动生成删除
  1621. $function3 = self::$create_del[$data['opt_case']] ?? '';
  1622. try{
  1623. DB::beginTransaction();
  1624. //更新单据的状态
  1625. list($bool,$msg) = $this->$function($data);
  1626. if(! $bool){
  1627. DB::rollBack();
  1628. return [false, $msg];
  1629. }
  1630. $order = $msg;
  1631. if($function3){
  1632. list($boolean,$msg) = $this->$function3($data,$order);
  1633. if(! $boolean) {
  1634. DB::rollBack();
  1635. return [false, $msg];
  1636. }
  1637. }
  1638. if($function2) {
  1639. //流水
  1640. list($boolean,$msg) = $this->$function2($data,$order);
  1641. if(! $boolean) {
  1642. DB::rollBack();
  1643. return [false, $msg];
  1644. }
  1645. if($msg != self::minus_one){
  1646. //库存
  1647. list($bool,$msg) = $this->changeInventoryReject($data,$order,$user);
  1648. if(! $bool){
  1649. DB::rollBack();
  1650. return [false, $msg];
  1651. }
  1652. }
  1653. }
  1654. if(! empty(self::$operation_order_reject[$data['opt_case']])){
  1655. $type = self::$operation_order_reject[$data['opt_case']];
  1656. (new OrderOperationService())->add([
  1657. 'order_number' => $order['order_number'],
  1658. 'msg' => OrderOperation::$type[$type],
  1659. 'type' => $type
  1660. ],$user);
  1661. }
  1662. DB::commit();
  1663. return [true, ''];
  1664. }catch (\Throwable $exception){
  1665. DB::rollBack();
  1666. return [false, $exception->getMessage() . $exception->getLine() . $exception->getFile()];
  1667. }
  1668. }else{
  1669. //具体方法
  1670. $function = self::$opt_case[$data['opt_case']] ?? "";
  1671. $record = self::$record[$data['opt_case']] ?? "";
  1672. $create = self::$create[$data['opt_case']] ?? "";
  1673. try{
  1674. DB::beginTransaction();
  1675. list($bool,$msg) = $this->$function($data);
  1676. if(! $bool){
  1677. DB::rollBack();
  1678. return [false, $msg];
  1679. }
  1680. $order = $msg;
  1681. if($data['type'] == self::TYPE_ONE){
  1682. if($record) {
  1683. //流水
  1684. list($bool,$msg) = $this->$record($data, $order);
  1685. if(! $bool) {
  1686. DB::rollBack();
  1687. return [false, $msg];
  1688. }
  1689. if($msg != self::minus_one){
  1690. //库存
  1691. list($bool,$msg) = $this->changeInventory($data, $order, $user);
  1692. if(! $bool) {
  1693. DB::rollBack();
  1694. return [false, $msg];
  1695. }
  1696. }
  1697. }
  1698. if($create) {
  1699. list($bool,$msg) = $this->$create($order,$user);
  1700. if(! $bool) {
  1701. DB::rollBack();
  1702. return [false, $msg];
  1703. }
  1704. }
  1705. }
  1706. if(! empty(self::$operation_order[$data['opt_case']])){
  1707. $user = $data['user_data'] ?? [];
  1708. $type = self::$operation_order[$data['opt_case']];
  1709. (new OrderOperationService())->add([
  1710. 'order_number' => $order['order_number'],
  1711. 'msg' => OrderOperation::$type[$type],
  1712. 'type' => $type
  1713. ],$user);
  1714. }
  1715. DB::commit();
  1716. return [true, ''];
  1717. }catch (\Throwable $exception){
  1718. DB::rollBack();
  1719. return [false, $exception->getMessage() . $exception->getLine() . $exception->getFile()];
  1720. }
  1721. }
  1722. }
  1723. //不需要走审批流 直接调用
  1724. public function createRecordAndInventoryMy($data = [],$user = [],$order = []){
  1725. if(! empty($data['type']) && $data['type'] == self::TYPE_THREE){
  1726. }else{
  1727. //具体方法
  1728. $record = self::$record[$data['opt_case']] ?? "";
  1729. $create = self::$create[$data['opt_case']] ?? "";
  1730. try{
  1731. DB::beginTransaction();
  1732. if($record) {
  1733. //流水
  1734. list($bool,$msg) = $this->$record($data, $order);
  1735. if(! $bool) {
  1736. DB::rollBack();
  1737. return [false, $msg];
  1738. }
  1739. if($msg != self::minus_one){
  1740. //库存
  1741. list($bool,$msg) = $this->changeInventory($data, $order, $user);
  1742. if(! $bool) {
  1743. DB::rollBack();
  1744. return [false, $msg];
  1745. }
  1746. }
  1747. }
  1748. if($create) {
  1749. list($bool,$msg) = $this->$create($order,$user);
  1750. if(! $bool) {
  1751. DB::rollBack();
  1752. return [false, $msg];
  1753. }
  1754. }
  1755. if(! empty(self::$operation_order[$data['opt_case']])){
  1756. $type = self::$operation_order[$data['opt_case']];
  1757. (new OrderOperationService())->add([
  1758. 'order_number' => $order['order_number'],
  1759. 'msg' => OrderOperation::$type[$type],
  1760. 'type' => $type
  1761. ],$user);
  1762. }
  1763. DB::commit();
  1764. return [true, ''];
  1765. }catch (\Throwable $exception){
  1766. DB::rollBack();
  1767. return [false, $exception->getMessage() . $exception->getLine() . $exception->getFile()];
  1768. }
  1769. }
  1770. }
  1771. public function orderInventoryInsert($insert){
  1772. if(empty($insert['order_number'])) return;
  1773. $model = new OrderInventoryStock();
  1774. $model->order_number = $insert['order_number'];
  1775. $model->is_check_stock = $insert['is_check_stock'];
  1776. $model->save();
  1777. }
  1778. }