model = new InvoicePool(); } public function create(){ $params = $this->request->param(["is_comon"=>0,"buy_id"=>"","buyNo"=>"",'companyNo'=>"","relaComNo"=>"","invtype"=>"", "email"=>"","remark"=>"","exam_remark"=>"","orderArr"=>[]],"post","trim"); $validate = $this->validate($params,[ "is_comon|是否通用订单"=>"require|in:0,1", "buy_id|买方信息"=>"requireIf:is_comon,0|number", "buyNo|买方信息"=>"requireIf:is_comon,1|max:255", "invtype|发票类型"=>"require|in:".implode(",",array_keys(\app\cxinv\model\Invoice::$invoiceType)), "orderArr|开票订单信息"=>"require|array" ]); if($validate!==true) return error($validate); if($params["is_comon"]==0){ $buyer = Customerinvoice::where(["id"=>$params["buy_id"],"is_del"=>0])->findOrEmpty(); }else{ $buyer = CompanyInfo::where(["companyNo"=>$params["buyNo"],"is_del"=>0])->field("invoice_title,company_license invoice_code,company_address invoice_addr, mobile invoice_mobile,bank_name invoice_bank,bankNo invoice_bankNo")->findOrEmpty(); } if($buyer->isEmpty()) return error("购买方发票信息不存在"); $companyNo = $this->level==1? $params["companyNo"]:$params["relaComNo"]; if($companyNo=="") return error("业务公司不能为空"); $seller = CompanyInfo::where(["companyNo"=>$companyNo,"is_del"=>0])->findOrEmpty(); if($seller->isEmpty()) return error("销售方发票信息不存在"); $platform_type =""; $invNo = makeNo("INV"); $invfee=array_sum(array_column($params["orderArr"],'inv_fee')); if(in_array($params["invtype"],['fully_digitalized_special_electronic','fully_digitalized_normal_electronic'])){ //全电发票限制金额 if (floatval($invfee) > 10000000) { return error('开票面额不能超过一千万元'); } } else {//其他发票限制金额 if ($seller['denomination'] != '' && floatval($invfee) > intval($seller['denomination']) * 10000) { return error( "开票面额不能超过{$seller['denomination']}万元"); } } $assoc =[]; foreach ($params["orderArr"] as $key=>$order){ $Valid= $this->validate($order,[ "sequenceNo|订单号"=>"require", "inv_fee|开票金额"=>"require|float|gt:0", ]); if($Valid!==true) return error($Valid); $orderInfo = QrdInfo::where(["sequenceNo"=>$order["sequenceNo"],"is_del"=>0])->findOrEmpty(); if($orderInfo->isEmpty()) return error("{$order["sequenceNo"]}订单信息不存在"); if($orderInfo->statu==2) return error("{$order["sequenceNo"]}订单不参与对账"); if($orderInfo->winv_fee< $order["inv_fee"]) return error("{$order["sequenceNo"]}订单待开票金额不足"); if($orderInfo->is_comon!=$params["is_comon"]) return error("{$order["sequenceNo"]}类型不匹配"); $isCategory = Good::where(["spuCode"=>$orderInfo->goodNo,"status"=>2])->findOrEmpty(); if($isCategory->isEmpty()) return error("{$order["sequenceNo"]}商品未确认开票类目"); if($platform_type==""){ $platform_type = $orderInfo->platform_type; }else{ if($platform_type!=$orderInfo->platform_type) return error("{$order["sequenceNo"]}订单平台类型不一致"); } $ascc[]=[ "assocNo"=>makeNo("AS",str_pad(strval($key+1),4,"0",STR_PAD_LEFT)), "apply_id"=>$this->uid, "apply_name"=>$this->uname, "type"=>1, "orderCode"=>$orderInfo['sequenceNo'], "customerNo"=>$orderInfo['customerNo'], "viceCode"=>$invNo, "order_total"=>$orderInfo['totalPrice'], "vice_total"=>$invfee, "cancel_fee"=>$order['inv_fee'], "status"=>1, "addtime"=>date("Y-m-d H:i:s"), "updatetime"=>date("Y-m-d H:i:s") ]; $invoice_good[]=[ "invNo"=>$invNo, "orderCode"=>$orderInfo['sequenceNo'], "goodNo"=>$orderInfo['goodNo'], "goodName"=>$isCategory['inv_good_name']??$orderInfo['goodName'] , "catName"=>$isCategory['inv_cat_name']??$orderInfo['thirdCat'], "catNo"=>$isCategory['inv_cat_code']??"", "goodPrice"=>$orderInfo['goodPrice'], "unitName"=>$orderInfo['goodUnit'], "goodNum"=>bcdiv($order["inv_fee"],$orderInfo['goodPrice'],8), "specInfo"=>$orderInfo['sequenceNo'], "totalPrice"=>$order['inv_fee'], "totalTax"=>$order['inv_fee'], "tax"=>$isCategory['inv_tax']??$orderInfo['tax'], "is_discount"=>$isCategory['is_discount']??0, "addTax"=>$isCategory['addTax']??'', "inv_tag"=>$isCategory['inv_tag']??"", "taxPrice"=>round($order['inv_fee']*($isCategory['inv_tax']??$orderInfo['tax']),2), ]; } $inv=[ "invNo"=>$invNo, "inv_value"=>$invfee, "inv_out"=> $companyNo, "inv_company"=> $seller['invoice_title']??"", "apply_id"=>$this->uid, "apply_name"=>$this->uname, "inv_type"=>$params["invtype"],//发票类型 专用 普通 电子专用 电子普通 全电子票 "open_type"=>0, //开票类型 金税开票 金税线下 纯线下 "platform_type"=>0, //开票类型 金税开票 金税线下 纯线下 "is_ticket"=>$seller['out_ticket'], //是否支持金税开票 "company_type"=> $buyer['company_type']??'01', //类型01 企业,02 机关事业单位,03 个人, 04 其他 "remark"=>$params["remark"], //申请备注 "exam_remark"=>$params["exam_remark"], //审核备注 "ainv_fee"=>0,//已核销金额 "winv_fee"=>$invfee,//未核销金额 'is_comon'=> $params["is_comon"],//是否通用订单 , "status"=>1,// 带财务审核 "is_del"=>0, "email"=>$params["email"], ]; $invinfo=[ "buyer_title"=>$buyer['invoice_title'], "buyer_code"=>$buyer['invoice_code'], "buyer_addr"=>$buyer['invoice_addr'], "buyer_mobile"=>$buyer['invoice_mobile'], "buyer_bank"=>$buyer['invoice_bank'], "buyer_bankNo"=>$buyer['invoice_bankNo'], "seller_title"=>$seller['company_name'], "seller_code"=>$seller['company_license'], "seller_addr"=>$seller['company_address'], "seller_mobile"=>$seller['mobile'], "seller_bank"=>$seller['bank_name'], "seller_bankNo"=>$seller['bankNo'], "invNo"=>$invNo, "voider"=>$seller['voider'], "payee"=>$seller['payee'], "drawer"=>$seller['drawer'], "reviewer"=>$seller['reviewer'], "ownerPlace"=>$seller['ownerPlace'], "addtime"=>date("Y-m-d H:i:s") ]; $this->model->startTrans(); try{ $create = $this->model->create($inv); if($create->isEmpty()) throw new \Exception("发票创建失败"); $up= $create->PoolInfo()->save($invinfo); if($up===false) throw new \Exception("发票信息创建失败"); $create->assoc()->saveAll($ascc); $create->InvoiceGood()->saveAll($invoice_good); foreach ($params["orderArr"] as $order){ $orderInfo = QrdInfo::where(["sequenceNo"=>$order["sequenceNo"],"is_del"=>0])->findOrEmpty(); if($orderInfo->isEmpty()) throw new \Exception("{$order["sequenceNo"]}订单信息不存在"); if($orderInfo->statu==2) throw new \Exception("{$order["sequenceNo"]}订单不参与对账"); if($orderInfo->winv_fee< $order["inv_fee"]) throw new \Exception("{$order["sequenceNo"]}订单待开票金额不足"); $up= $orderInfo->save([ "winv_fee"=>bcsub($orderInfo->winv_fee,$order["inv_fee"],2), "inv_fee"=>bcadd($orderInfo->inv_fee,$order["inv_fee"],2), "inv_status"=>2, "status"=>1, ]); if($up===false) throw new \Exception("订单信息更新失败"); } $this->model->commit(); }catch (\Exception $e){ $this->model->rollback(); return error($e->getMessage()); } event("report_code",["type"=>"add","key"=>"invNo","value"=>$invNo,"main"=>['key'=>'qrdNo','value'=>array_column($params["orderArr"],'sequenceNo')]]); return success("开票成功",["invNo"=>$invNo]); } }