// +---------------------------------------------------------------------- declare (strict_types=1); namespace app\store\model; use app\store\model\Setting as SettingModel; use app\store\service\User as UserService; use app\store\model\OrderGoods as OrderGoodsModel; use app\store\model\Order as OrderModel; // use app\common\model\order\RefundHis as RefundHisModel; // use app\common\model\order\RefundHis; use app\common\model\RefundCompensate as RefundCompensateModel; // use app\common\enum\order\refund\RefundType as RefundTypeEnum; // use app\common\enum\order\refund\AuditStatus as AuditStatusEnum; // use app\common\enum\order\refund\RefundStatus as RefundStatusEnum; // use app\common\enum\order\refund\FinanceRefundStatus as FinanceRefundStatusEnum; use app\common\exception\BaseException; use app\common\service\Kuaidi as KuaidiService; // use app\store\model\OrderGoods; use app\common\service\Order as OrderService; use app\common\service\store\User as StoreUserService; use app\common\model\User as UserModel; use app\common\model\RefundCompensateHis as RefundCompensateHisModel; use app\api\model\card\UserRiceCard as UserRiceCardModel; use app\api\model\card\UserRiceCardConsume; use app\common\service\order\Refund as RefundService; /** * 售后补偿单模型 * Class OrderRefund * @package app\api\model */ class RefundCompensate extends RefundCompensateModel { /** * 隐藏字段 * @var array */ protected $hidden = [ // 'store_id', // 'update_time' ]; /** * 追加字段 * @var array */ protected $append = [ 'state_text', // 售后补偿单状态 // 'dfh_time', // 待用户发货倒计时 ]; /** * 添加补偿单 * @param array $data * @return bool * @throws \think\db\exception\DataNotFoundException * @throws \think\db\exception\DbException * @throws \think\db\exception\ModelNotFoundException */ public function edit(array $data) { $user = StoreUserService::getLoginInfo(); $real_name = $user['user']['real_name']??''; // $data['refund_number'] = OrderService::createOrderNoPrefix('TKBC'); // // $data['order_id'] = $data['order_id']??0; // $data['submit_zy'] = $real_name; // // 事务处理 $this->transaction(function () use ($data) { // 添加 $this->save($data); }); return true; } /** * 添加补偿单 * @param array $data * @return bool * @throws \think\db\exception\DataNotFoundException * @throws \think\db\exception\DbException * @throws \think\db\exception\ModelNotFoundException */ public function add(array $data){ $user = StoreUserService::getLoginInfo(); $real_name = $user['user']['real_name']??''; $data['refund_number'] = OrderService::createOrderNoPrefix('TKBC'); // $data['order_id'] = $data['order_id']??0; $data['submit_zy'] = $real_name; // // 事务处理 $this->transaction(function () use ($data) { // 添加 $this->save($data); }); return true; } // /** // * 售后补偿单状态文字描述 // * @param $value // * @param $data // * @return string // */ public function getStateTextAttr($value, $data) { // 已完成 if(!isset($data['status'])){ return ['value'=>0,'name'=>'进行中']; } if ($data['status'] == 0&&$data['audit_status_zg']==0) { return ['value'=>1,'name'=>'待主管审核']; } // 已取消 if ($data['finance_refund']==0&&$data['audit_status_zg']==10) { return ['value'=>2,'name'=>'待退款']; } // 待专员修改 if ($data['status'] == 0&&$data['audit_status_zg']==20) { return ['value'=>3,'name'=>'待专员修改']; } // 已关闭 if ($data['status'] == 40) { return ['value'=>4,'name'=>'已关闭']; } // 已退款 if ($data['status'] == 20&&$data['finance_refund']==10) { return ['value'=>5,'name'=>'已退款']; } return ['value'=>0,'name'=>'进行中']; } /** * 获取售后补偿单列表 财务 * @param * @return \think\Paginator * @throws \app\common\exception\BaseException * @throws \think\db\exception\DbException */ public function getFinanceList(array $param=[]) { // 检索查询条件 $filter = []; $filter = $this->getFinanceFilter($param); // 售后补偿单状态 // $state > -1 && $filter[] = ['status', '=', $state]; // 当前用户ID // $userId = UserService::getCurrentLoginUserId(); // 查询列表记录 return $this->alias('refund')->field('refund.*, order.order_no,order.order_id,order.create_time as order_create_time,order.user_id,user.nick_name,user.mobile')->with(['orderData','orderGoods.image']) ->where($filter)->where('audit_status_zg',10) //主管同意 ->leftJoin('orderGoods', 'orderGoods.order_goods_id = refund.order_goods_id') ->leftjoin('order', 'order.order_id = refund.order_id') ->join('user', 'user.user_id = order.user_id') ->leftJoin('provider', 'provider.provider_id = orderGoods.provider_id') // ->where('user_id', '=', $userId) ->order(['refund.create_time' => 'desc']) ->paginate(15) ->each(function($item) { $mobile = UserModel::where('user_id',$item['user_id'])->value("mobile"); $item['orderData']['mobile'] = $mobile; $item['type'] = 'finance'; $item['orderData']['pay_type_text'] = '微信'; $pay_type_text ='微信'; if($item['orderData']['pay_price']>0&& $item['orderData']['rice_card_id']>0){ $pay_type_text = '微信+现金卡'; } if($item['orderData']['pay_price']==0&&$item['orderData']['rice_card_id']>0){ $pay_type_text = '现金卡'; } $item['pay_type_text'] = $pay_type_text; }); } /** * 补偿退款订单列表 * @return array * @throws \think\db\exception\DataNotFoundException * @throws \think\db\exception\DbException * @throws \think\db\exception\ModelNotFoundException */ public function refundsExport($param){ $filter = $this->getFinanceFilter($param); // 获取列表数据 $list = $this->alias('refund')->field('refund.*, order.order_no,order.order_id,order.create_time as order_create_time,order.user_id,user.nick_name,user.mobile') ->with(['orderData','orderGoods.image']) ->where($filter)->where('audit_status_zg',10) //主管同意 ->leftJoin('orderGoods', 'orderGoods.order_goods_id = refund.order_goods_id') ->leftjoin('order', 'order.order_id = refund.order_id') ->join('user', 'user.user_id = order.user_id') ->leftJoin('provider', 'provider.provider_id = orderGoods.provider_id') ->order(['refund.create_time' => 'desc']) ->select(); $data['header'] = ['序号', '退款单编号','订单编号','配送方式', '商品名称','规格','品牌','退款金额','申请时间','退款状态', '会员昵称','会员手机号','微信交易流水号']; $data['filename'] = '售后补偿退款单列表导出'; $data['data'] = []; foreach ($list as $key=>$arr){ $new_list['key'] = $key+1; $new_list['refund_number'] = $arr['refund_number']; $new_list['order_no'] = $arr['orderData']['order_no']; $new_list['delivery_type'] = $arr['orderData']['delivery_type']==10?'普通配送':'门店自提'; $new_list['goods_name'] = $arr['orderGoods']['goods_name']; $new_list['goods_props'] = $arr['orderGoods']['goods_props'][0]['value']['name']??'-'; $new_list['supplier'] = $arr['orderGoods']['supplier'] ?: '-'; $new_list['refund_money'] = $arr['refund_money']; $new_list['create_time'] = $arr['create_time']; $new_list['finance_refund_text'] = $arr['state_text']['name']; $new_list['nick_name'] = $arr['nick_name']; $new_list['mobile'] = $arr['mobile']; $new_list['transaction_id'] = $arr['transaction_id'] ?: '-'; $data['data'][] = $new_list; } return $data; } /** * 检索查询条件 * @param array $param * @return array */ private function getFinanceFilter(array $param = []): array { // 默认查询条件 $params = $this->setQueryDefaultValue($param, [ 'finance_refund' => -1, // 关键词类型 (10订单号 20会员昵称 30会员ID) // 'searchValue' => '', // 关键词内容 // 'refundType' => -1, // 售后类型 // 'refundStatus' => -1, // 售后单状态 // 'betweenTime' => [], // 申请时间 // 'delivery_type' =>-1 //配送方式(10快递配送 20门店自提) 'supplier' => '', // 供应商品牌 'type' => -1, // 退款类型 10-退货退款 30-仅退款 'transaction_id' => '',// 微信交易流水号 ]); // 检查查询条件 $filter = []; // //配送方式 (10快递配送 20门店自提) isset($params['delivery_type'])&&$params['delivery_type']>-1 && $filter[] = ['order.delivery_type', '=', (int)$params['delivery_type']]; // 售后单编号 !empty($params['refund_number']) && $filter[] = ['refund.refund_number', 'like', '%'.$params['refund_number'].'%']; // 退款状态 $params['finance_refund']>-1 && $filter[] = ['refund.finance_refund', '=', $params['finance_refund']]; // 订单编号 !empty($params['order_no']) && $filter[] = ['order.order_no', 'like', '%'.$params['order_no'].'%']; // // 供应商名称 !empty($params['provider_name']) && $filter[] = ['provider.provider_name', 'like', '%'.$params['provider_name'].'%']; //手机号码 !empty($params['mobile']) && $filter[] = ['user.mobile', 'like', "%{$params['mobile']}%"]; //退款人姓名: !empty($params['nick_name']) && $filter[] = ['user.nick_name', 'like', "%{$params['nick_name']}%"]; // 申请时间 if (!empty($params['betweenTime'])) { $times = between_time_format($params['betweenTime']); $filter[] = ['refund.create_time', '>=', $times['start_time']]; $filter[] = ['refund.create_time', '<',$times['end_time']]; } !empty($params['supplier']) && $filter[] = ['order_goods.supplier', 'like', "%{$params['supplier']}%"]; !empty($params['transaction_id']) && $filter[] = ['refund.transaction_id', 'like', "%{$params['transaction_id']}%"]; return $filter; } /** * 获取售后补偿单列表 * @param * @return \think\Paginator * @throws \app\common\exception\BaseException * @throws \think\db\exception\DbException */ public function getList(array $param=[]) { // 检索查询条件 $filter = []; $filter = $this->getFilter($param); // 售后补偿单状态 // $state > -1 && $filter[] = ['status', '=', $state]; // 当前用户ID // $userId = UserService::getCurrentLoginUserId(); // 查询列表记录 return $this->alias('refund')->field('refund.*, order.order_no,order.order_id,order.create_time as order_create_time,order.user_id')->with(['orderData','orderGoods.image']) ->where($filter) ->leftJoin('orderGoods', 'orderGoods.order_goods_id = refund.order_goods_id') ->leftjoin('order', 'order.order_id = refund.order_id') ->join('user', 'user.user_id = order.user_id') ->leftJoin('provider', 'provider.provider_id = orderGoods.provider_id') // ->where('user_id', '=', $userId) ->order(['refund.create_time' => 'desc']) ->paginate(15) ->each(function($item) { $mobile = UserModel::where('user_id',$item['user_id'])->value("mobile"); $item['orderData']['mobile'] = $mobile; }); } /** * 检索查询条件 * @param array $param * @return array */ private function getFilter(array $param = []): array { // 默认查询条件 $params = $this->setQueryDefaultValue($param, [ // 'searchType' => '', // 关键词类型 (10订单号 20会员昵称 30会员ID) // 'searchValue' => '', // 关键词内容 // 'refundType' => -1, // 售后类型 // 'refundStatus' => -1, // 售后单状态 // 'betweenTime' => [], // 申请时间 // 'delivery_type' =>-1 //配送方式(10快递配送 20门店自提) ]); // 检查查询条件 $filter = []; // //配送方式 (10快递配送 20门店自提) isset($params['delivery_type'])&&$params['delivery_type']>-1 && $filter[] = ['order.delivery_type', '=', (int)$params['delivery_type']]; // 售后单编号 !empty($params['refund_number']) && $filter[] = ['refund.refund_number', 'like', '%'.$params['refund_number'].'%']; !empty($params['submit_zy']) && $filter[] = ['refund.submit_zy', 'like', '%'.$params['submit_zy'].'%']; // // 订单编号 !empty($params['order_no']) && $filter[] = ['order.order_no', 'like', '%'.$params['order_no'].'%']; // // 供应商名称 !empty($params['provider_name']) && $filter[] = ['provider.provider_name', 'like', '%'.$params['provider_name'].'%']; // //手机号码 !empty($params['mobile']) && $filter[] = ['user.mobile', 'like', "%{$params['mobile']}%"]; //售后状态 if(isset($params['refund_status']) && $params['refund_status'] > 0){ $this->statusValue($params['refund_status'],$filter); } // 订单时间 if (!empty($params['betweenTime'])) { $times = between_time($params['betweenTime']); $filter[] = ['order.create_time', '>=', $times['start_time']]; $filter[] = ['order.create_time', '<',$times['end_time'] + 86400]; } return $filter; } private function statusValue($refundStatus,&$filter){ switch ($refundStatus){ case 1://待主管审核 $filter[] = ['refund.status', '=',0]; //进行中 $filter[] = ['refund.audit_status_zg', '=',0]; //等待专员审核 break; case 2://待退款 $filter[] = ['refund.finance_refund', '=', 0]; $filter[] = ['refund.audit_status_zg', '=', 10]; break; case 3://待专员修改 $filter[] = ['refund.status', '=', 0]; $filter[] = ['refund.audit_status_zg', '=', 20]; break; case 4://关闭 $filter[] = ['refund.status', '=', 40]; break; case 5://已退款 $filter[] = ['refund.status', '=', 20]; $filter[] = ['refund.finance_refund', '=', 10]; break; } return $filter; } /** * 获取当前用户的售后单详情 * @param int $orderRefundId 售后单ID * @param bool $isWith 是否关联 * @return static|null * @throws BaseException */ public static function getDetail(int $id,$addWith=[]) { // 关联查询 $with = ['orderGoods' => ['image'],'his']; if($addWith){ $with = array_merge($with,$addWith); } // 获取记录 $detail = static::detail(['id' => $id], $with); if (empty($detail)) throwError('未找到该售后补偿单'); return $detail; } /** * 主管审核 * @param array $data * @return bool */ public function auditzg(array $data): bool { if ($data['audit_status_zg'] ==20&& empty($data['refuse_desc_zg'])) { $this->error = '请输入拒绝原因'; return false; } $this->transaction(function () use ($data) { $user = StoreUserService::getLoginInfo(); $real_name = $user['user']['real_name']??''; $id = (int)$this['id']; if($data['audit_status_zg'] == 10) { (new RefundCompensateHisModel())->add($id,$real_name,'同意补偿',''); } if($data['audit_status_zg'] == 20) { (new RefundCompensateHisModel())->add($id,$real_name,'拒绝',$data['refuse_desc_zg']); } $this->save($data); }); return true; } //关闭售后单 public function close(array $data=[]): bool { $user = StoreUserService::getLoginInfo(); $real_name = $user['user']['real_name']??''; //售后单已关闭 if($this['status']==20){ $this->error = '售后补偿单已完成,不能关闭吧'; return false; } //售后单已完成 if($this['status']==40){ $this->error = '售后补偿单已关闭,不要重复操作'; return false; } $data['status'] = 40; $this->transaction(function () use ($data) { $this->save($data); // (new RefundCompensateHisModel())->add($id,$real_name,'关闭',$data['refuse_desc_zg']); }); return true; } public function getError(){ return $this->error; } /** * 财务退款 * @return bool */ public function refund(): bool { if ($this['refund_money'] <= 0) { $this->error = '退款金额不能小于0'; return false; } // 事务处理 $this->transaction(function () { $refund_money = floatval($this['refund_money']); $order_goods = OrderGoodsModel::where("order_goods_id",$this['order_goods_id'])->find(); $wx_pay = floatval($order_goods['total_pay_price']); $rice_card_pay = floatval($order_goods['rice_card_money']); $ret_wx_pay = 0; $ret_rice_card_money = 0; if($rice_card_pay<=0&&$wx_pay>=$refund_money){ $ret_wx_pay = $refund_money; $ret_rice_card_money = 0; } if($rice_card_pay>0){ if($rice_card_pay>=$refund_money){ $ret_rice_card_money = $refund_money; $ret_wx_pay = 0; } if($rice_card_pay<$refund_money){ $ret_rice_card_money = $rice_card_pay; $ret_wx_pay = $refund_money- $ret_rice_card_money; } } //更新售后单状态 // var_dump($ret_rice_card_money); // var_dump($ret_wx_pay); // die(); $order = OrderModel::where("order_id",$this['order_id'])->find(); $ret_wx_pay = round($ret_wx_pay,2); $this->save([ 'status' => 20, 'finance_refund' => 10, 'finance_refund_time' => time(), 'out_refund_no' => time(), 'ret_wx_pay'=>$ret_wx_pay, 'ret_rice_card_money'=>$ret_rice_card_money ]); if ($ret_wx_pay > 0) { // 执行原路退款 $refund_ret = (new RefundService)->execute($order, $this['refund_number'], $ret_wx_pay); if ($refund_ret['status'] == 200) { $this->save([ 'transaction_id' => $refund_ret['data']['transaction_id'] // 微信退款交易号 ]); } } if ($ret_rice_card_money>0) { // 订单商品有使用现金卡 // 验证余额 $riceCard = UserRiceCardModel::getValidRiceCardDetail($order_goods['rice_card_id']); if(empty($riceCard)){ $this->error = '找不到米卡'; return false; } if ($ret_rice_card_money + $riceCard['balance'] > $riceCard['face_value']) { $this->error = "现金卡退还金额异常"; return false; } // 写入现金卡流水明细 $order_amount = $order_goods['total_pay_price']+$order_goods['rice_card_money']; // 写入现金卡流水明细 // var_dump($ret_rice_card_money); UserRiceCardConsume::addExtra($riceCard, $order['order_no'],$order_amount, $ret_rice_card_money,1, '售后退款'); // 退还现金卡金额 UserRiceCardModel::setIncByField($order_goods['rice_card_id'], 'balance', $ret_rice_card_money); $riceCard->effect_state = 1; // 改为 生效 $riceCard->save(); } }); return true; } }