getRefundDetail($event['finder_shop_aftersale_status_update']['after_sale_order_id']); // 判断是否有同步当前退款,没有的话那么就需要记录 $status = $resp['after_sale_order']['status'] ?? null; switch ($status) { case RefundEnum::AFTER_SALE_STATUS_USER_CANCELD: // 用户取消申请 $refund = $this->cancel($resp['after_sale_order'] ?? []); break; case RefundEnum::AFTER_SALE_STATUS_MERCHANT_PROCESSING: // 商家受理中 // $this->create($resp['after_sale_order'] ?? []); break; case RefundEnum::AFTER_SALE_STATUS_MERCHANT_REJECT_REFUND: // 商家拒绝退款 $refund = $this->reject($resp['after_sale_order'] ?? []); break; case RefundEnum::AFTER_SALE_STATUS_MERCHANT_REJECT_RETURN: // 商家拒绝退货退款 $refund = $this->reject($resp['after_sale_order'] ?? []); break; case RefundEnum::AFTER_SALE_STATUS_USER_WAIT_RETURN: // 待买家退货 $refund = $this->agree($resp['after_sale_order'] ?? []); break; case RefundEnum::AFTER_SALE_STATUS_RETURN_CLOSED: // 退货退款关闭 $refund = $this->cancel($resp['after_sale_order'] ?? []); break; case RefundEnum::AFTER_SALE_STATUS_MERCHANT_WAIT_RECEIPT: // 待商家收货 $refund = $this->buyerShip($resp['after_sale_order'] ?? []); break; case RefundEnum::AFTER_SALE_STATUS_MERCHANT_OVERDUE_REFUND: // 商家逾期未退款 break; case RefundEnum::AFTER_SALE_STATUS_MERCHANT_REFUND_SUCCESS: // 退款完成 break; case RefundEnum::AFTER_SALE_STATUS_MERCHANT_RETURN_SUCCESS: // 退货退款完成 break; case RefundEnum::AFTER_SALE_STATUS_PLATFORM_REFUNDING: // 平台退款中 break; case RefundEnum::AFTER_SALE_STATUS_PLATFORM_REFUND_FAIL: // 平台退款失败 break; case RefundEnum::AFTER_SALE_STATUS_USER_WAIT_CONFIRM: // 待用户确认 break; case RefundEnum::AFTER_SALE_STATUS_MERCHANT_REFUND_RETRY_FAIL: // 商家打款失败,客服关闭售后 $refund = $this->cancel($resp['after_sale_order'] ?? []); break; case RefundEnum::AFTER_SALE_STATUS_MERCHANT_FAIL: // 售后关闭 $refund = $this->cancel($resp['after_sale_order'] ?? []); break; } if (!empty($refund)) { $refund->content = $resp['after_sale_order']; if (!$refund->save()) { // 修改数据 throw new \Exception($refund->getErrorMessage()); } } } /** * 申请售后 * @return void * @throws \Exception */ protected function create(array $resp) { if (empty($resp)) throw new \Exception("售后订单数据为空"); // 取出订单 $user_id = UserInfo::find()->where(['mall_id' => $this->mall_id]) ->andWhere(['openid' => $resp['openid']])->select('user_id')->scalar(); if (empty($user_id)) throw new \Exception("用户不存在: {$resp['openid']}"); // $order_ids = WechatVideoShopOrder::find() // ->where(['third_order_id' => $resp['order_id']])->select('order_id')->column(); // if (empty($order_ids)) throw new \Exception("订单不存在: {$resp['order_id']}"); $orders = WechatVideoShopOrder::lists([ 'where' => [ ['third_order_id' => $resp['order_id']] ], 'index' => 'order_id', 'select'=> 'order_id, content' ]); // SKU ID 不一致 if (empty($orders)) throw new \Exception("订单不存在: {$resp['order_id']}"); $order_id = 0; $sku_id = 0; foreach ($orders as $key => $order) { $content = Json::decode($order['content']); // 找出包含 $resp['product_info']['sku_id'] 的那一行数据 $product_infos = $content['order_detail']['product_infos']; $tmp_skus = array_column($product_infos, "out_sku_id", "sku_id"); if (!empty($tmp_skus[$resp['product_info']['sku_id']])) { $order_id = $key; $sku_id = $tmp_skus[$resp['product_info']['sku_id']]; } } if (empty($order_id)) throw new \Exception("未找到相关SKU: {$resp['product_info']['sku_id']}"); // 取出订单商品ID $orderDetail = OrderDetail::getOne([ ['order_id' => $order_id], ['goods_attr_id' => $sku_id], ['user_id' => $user_id] ]); if (empty($orderDetail)) throw new \Exception("订单详情不存在: $sku_id"); // order_detail_id, shipping_status, pic_list, reason, refund_price, remark, type // 获取media $pic_list = []; if (!empty($resp['details']['media_id_list'])) { foreach ($resp['details']['media_id_list'] as $mediaId) { $mediaModel = new GetMediaModel(); $mediaModel->media_id = $mediaId; $pic_list[] = WechatRequestHelper::accessTokenAndToArray(new GetMediaRequest([]), $mediaModel); } } $params['user_id'] = $user_id; $params['mall_id'] = $this->mall_id; $params['order_detail_id'] = $orderDetail->id; $params['pic_list'] = Json::encode($pic_list); $params['refund_price'] = bcmul($resp['refund_info']['amount'], 0.01, 2); $params['reason'] = $resp['reason_text'] ?? '未知理由'; $params['shipping_status'] = $orderDetail->order_status == OrderStatusEnum::PAY ? 0 : 1; // 是否已经发货 $params['type'] = $resp['type'] == 'REFUND' ? 1 : 2; // 售后类型:1=仅退款,2=退货退款,3=换货 // 售后类型。REFUND:退款;RETURN:退货退款。 $params['remark'] = "{$resp['details']['desc']}, 联系电话: [{$resp['details']['tel_number']}]"; // 退货数量 // 退款金额 $where = [ ['=', 'order_detail_id', $params['order_detail_id']], ['=', 'user_id', $user_id], ['=', 'mall_id', $this->mall_id], ['>', 'step_status', 0], ['<>', 'refund_status', RefundStatusEnum::REVOKE] ]; $order_refund_model = OrderRefund::getOne($where, true); if ($order_refund_model) throw new \Exception('该订单商品已经申请过售后'); $res = OrderRefund::feedback($params); if (!$res) throw new \Exception(OrderRefund::getStaticError()); // 这里需要怎么处理呢? $refundModel = new WechatVideoShopRefund(); $refundModel->mall_id = $this->mall_id; $refundModel->shop_id = $this->shop_id; $refundModel->user_id = $user_id; $refundModel->order_id = $orderDetail->order_id; $refundModel->third_refund_id = $resp['after_sale_order_id']; $refundModel->third_order_id = $resp['order_id']; $refundModel->refund_id = $res->id; $refundModel->content = $resp; $refundModel->refund_certificates = !empty($resp['details']['media_id_list']) ? $resp['details']['media_id_list'] : []; $refundModel->refund_desc = $resp['details']['desc']; if (!$refundModel->save()) { throw new \Exception($refundModel->getErrorMessage()); } // 触发事件 $event = new OrderRefundEvent(); $event->mall_id = $this->mall_id; $order_detail['order_detail_id'] = $params['order_detail_id']; $order_detail['id'] = $res->id; $order_detail['operator_id'] = 0; $order_detail['operator_name'] = OrderCallbackService::OPERATOR_NAME; Yii::$app->services->events->dispatch($event, $order_detail, $event->listeners); } /** * @param $third_refund_id * @return WechatVideoShopRefund * @throws \Exception */ protected function getLocalRefund($third_refund_id) { $refund = WechatVideoShopRefund::getOne([ ['third_refund_id' => $third_refund_id] ]); if (empty($refund)) throw new \Exception("退款单号不存在: {$third_refund_id}"); return $refund; } /** * 取消售后 * @return WechatVideoShopRefund * @throws \Exception */ protected function cancel(array $resp) { $refund = $this->getLocalRefund($resp['after_sale_order_id']); $params['mall_id'] = $this->mall_id; $params['user_id'] = $refund->user_id; $params['id'] = $refund->refund_id; $res = OrderRefund::cancelRefund($params); if ($res === false) throw new \Exception(OrderRefund::getStaticError()); return $refund; } /** * 买家发货 * @return WechatVideoShopRefund * @throws \Exception */ protected function buyerShip(array $resp) { $refund = $this->getLocalRefund($resp['after_sale_order_id']); $params['mall_id'] = $this->mall_id; $params['user_id'] = $refund->user_id; // 快递公司 $company = WechatVideoShopExpressCompany::getOne([ ['delivery_id' => $resp['return_info']['delivery_id']] ]); $params['express'] = !empty($company) ? $company->delivery_name : "其他"; // 默认其他快递 $params['express_id'] = !empty($company) ? $company->company_id : 10000; // 默认其他快递 // 快递单号 $params['express_no'] = $resp['return_info']['waybill_id']; $params['id'] = $refund->refund_id; $res = OrderRefundStep::refundSend($params); if ($res === false) throw new \Exception(OrderRefundStep::getStaticError()); return $refund; } /** * 买家收货 - 买家不需要收货 * @return WechatVideoShopRefund * @throws \Exception */ protected function buyerSing(array $resp) { $refund = $this->getLocalRefund($resp['after_sale_order_id']); $params['mall_id'] = $this->mall_id; $params['user_id'] = $refund->user_id; $params['id'] = $refund->refund_id; $res = OrderRefundStep::refundTakeDelivery($params); if ($res === false) throw new \Exception(OrderRefundStep::getStaticError()); return $refund; } /** * 卖家发货 - 卖家不需要发货 * @return WechatVideoShopRefund * @throws \Exception */ protected function sellerShip(array $resp) { // 卖家发货 $refund = $this->getLocalRefund($resp['after_sale_order_id']); $this->handle([ 'id' => $refund->refund_id, 'step_status' => -1 ]); return $refund; } /** * 同意售后 * @return WechatVideoShopRefund * @throws \Exception */ protected function agree(array $resp) { $refund = $this->getLocalRefund($resp['after_sale_order_id']); $params = []; switch ($resp['type']) { case 'REFUND': // id: 108 // step_status: 6 $params['step_status'] = RefundStatusEnum::STEP_6; $params['id'] = $refund->refund_id; break; case 'RETURN': // address_type: 1 // consignee: 林锦豪 // mobile: 13246824705 // address: 广州市白云区永平街永泰学山塘街81号A2栋618 // express_id: // saler_express: // saler_express_no: // customer_name: // id: 105 // step_status: 2 $shop = WechatVideoShop::getOne([ ['id' => $refund->shop_id] ]); $params = [ 'address_type' => 2, 'consignee' => $shop->contact_person, 'mobile' => $shop->phone, 'address' => "{$shop->province}{$shop->city}{$shop->district}{$shop->address}", 'id' => $refund->refund_id, 'step_status' => RefundStatusEnum::STEP_2, // 第几步,如果是仅退款是第几步,如果是退货退款那么是第几步 ]; break; } if (empty($params)) throw new \Exception("退款类型未找到: {$resp['type']}"); $this->handle($params); return $refund; } /** * 拒绝售后 * @return WechatVideoShopRefund * @throws \Exception */ protected function reject(array $resp) { // id: 106 // step_status: -1 $refund = $this->getLocalRefund($resp['after_sale_order_id']); $this->handle([ 'id' => $refund->refund_id, 'step_status' => RefundStatusEnum::REFUSE ]); return $refund; } /** * @param array $params * @return void * @throws \Exception */ protected function handle(array $params) { // 退货地址 $address = ['consignee' => $params['consignee'] ?? '','mobile' => $params['mobile'] ?? '','address' => $params['address'] ?? '']; // 换货物流信息 $express = ['saler_express' => $params['saler_express'] ?? '', 'saler_express_no' => $params['saler_express_no'] ?? '', 'customer_name' => $params['customer_name'] ?? '']; $data = [ 'id' => $params['id'], 'step_status' => $params['step_status'], // 在这里处理 'address' => $address, 'express' => $express, 'is_async' => true, // 不退钱 'is_trigger_update_event' => true, ]; $logic = new OrderRefundLogic(); $res = $logic->execute($this->mall_id, $data); if (!$res) throw new \Exception($logic->getError()); } /** * 卖家收货 * @return WechatVideoShopRefund * @throws \Exception */ protected function sellerSing(array $resp) { $refund = $this->getLocalRefund($resp['after_sale_order_id']); $this->handle([ 'id' => $refund->refund_id, 'step_status' => 4 ]); return $refund; } /** * @param $after_sale_order_id * @param array $config * @return array * @throws \Exception */ public function getRefundDetail($after_sale_order_id, array $config = []) { $refundInfoModel = new RefundInfoModel(); $refundInfoModel->after_sale_order_id = $after_sale_order_id; $resp = WechatRequestHelper::accessTokenAndToArray(new RefundInfoRequest(!empty($config) ? $config : $this->config), $refundInfoModel); if (empty($resp['after_sale_order'])) throw new \Exception('获取售后详情失败'); return $resp; } /** * @param array $config * @return void * @throws \Exception */ public function syncCreate(array $config) { try { $this->mall_id = $config['mall_id']; $this->shop_id = $config['id']; $resp = $this->getRefundDetail($config['after_sale_order_id'], $config); $this->create($resp['after_sale_order'] ?? []); } catch (\Exception $e) { \Yii::error(FormatHelper::exception($e, __METHOD__)); } } }