Bladeren bron

1. 刷新token
2. 顺丰授权回调与取消授权回调

shizhongqi 8 maanden geleden
bovenliggende
commit
6acaa04d80

+ 7 - 3
app-ghs/controllers/DeliveryController.php

@@ -521,8 +521,12 @@ class DeliveryController extends BaseController
 
         $ds = new DispatchService($this->mainId, $platform);
         $ret = $ds->getCancelReasonList($orderId);
-
-        util::success($ret);
+        if($ret['code'] == 0){
+            util::success($ret['data']);
+        }else{
+            Yii::error('获取订单取消原因:'.json_encode($ret));
+            util::fail($ret['msg']);
+        }
     }
 
 
@@ -643,7 +647,7 @@ class DeliveryController extends BaseController
     {
         $post = Yii::$app->request->post();
         $cbh = new \common\components\delivery\platform\shunfeng\CallBackHandler();
-        $ret = $cbh->handle($post);// 1.配送状态更改  2.订单完成  3.顺丰原因取消  4.订单配送异常  5.骑士撤单  6.自动建店回调
+        $ret = $cbh->handle($post);// 各回调处理
         if($ret) {
             return $this->asJson(['error_code' => 0, 'error_msg' => 'success']);
         } else {

+ 8 - 0
app-ghs/controllers/DeliveryShopController.php

@@ -61,4 +61,12 @@ class DeliveryShopController extends BaseController
         $deliveryAuthToken->save();
         util::success(['balance'=>$balance]);
     }
+
+    public function actionStore()
+    {
+        $get = Yii::$app->request->get();
+        $platform = $get['platform'];
+
+        $ShopService = new ShopService($this->mainId, $platform);
+    }
 }

+ 1 - 0
common/components/delivery/platform/fengniao/Fengniao.php

@@ -3,6 +3,7 @@ namespace common\components\delivery\platform\fengniao;
 
 
 use common\components\delivery\helpers\SignHelper;
+use Yii;
 
 class Fengniao
 {

+ 102 - 0
common/components/delivery/platform/shunfeng/CallBackHandler.php

@@ -1,6 +1,7 @@
 <?php
 namespace common\components\delivery\platform\shunfeng;
 
+use bizGhs\express\classes\DeliveryAuthTokenClass;
 use bizGhs\express\classes\GhsDeliveryOrderClass;
 use bizGhs\order\classes\OrderClass;
 use Yii;
@@ -56,6 +57,14 @@ class CallBackHandler
                 case 'rider_recall':
                     // 骑士撤单回调
                     return $this->handleRiderRecall($data);
+
+                case 'bindnotify':
+                    // 授权状态回调
+                    return $this->handleBindNotify($data);
+
+                case 'cancelbindnotify':
+                    // 取消授权状态回调
+                    return $this->handleCancelBindNotify($data);
                     
                 default:
                     Yii::warning('未知的顺丰回调类型: ' . $urlIndex, 'shunfeng-callback');
@@ -320,6 +329,99 @@ class CallBackHandler
         
         return true;
     }
+
+    /**
+     * 处理顺丰授权成功回调
+     *
+     * @param array $data
+     * @return bool
+     */
+    private function handleBindNotify($data)
+    {
+        $sign = Yii::$app->request->get('sign');
+        Yii::info('顺丰授权状态回调(sign=' . ($sign ?? '') . '): ' . json_encode($data, JSON_UNESCAPED_UNICODE), 'shunfeng-callback');
+
+        $mainId = isset($data['out_shop_id']) ? (int)$data['out_shop_id'] : 0;
+        $shopId = isset($data['shop_id']) ? (string)$data['shop_id'] : '';
+
+        if ($mainId <= 0 || $shopId === '') {
+            Yii::error('顺丰授权状态回调参数缺失: ' . json_encode($data, JSON_UNESCAPED_UNICODE), 'shunfeng-callback');
+            return false;
+        }
+
+        $payload = [
+            'mainId' => $mainId,
+            'platform' => 'shunfeng',
+            'shopId' => $shopId,
+            'authType' => 'all_store',
+            'accessToken' => $data['access_token'] ?? '',
+            'refreshToken' => $data['refresh_token'] ?? '',
+            'expiresAt' => isset($data['expires_at']) ? (int)$data['expires_at'] : 0,
+        ];
+
+        $existing = DeliveryAuthTokenClass::getByCondition(
+            ['mainId' => $mainId, 'platform' => 'shunfeng'],
+            false,
+            false,
+            'id'
+        );
+
+        if ($existing && isset($existing['id'])) {
+            DeliveryAuthTokenClass::updateById($existing['id'], [
+                'shopId' => $payload['shopId'],
+                'authType' => $payload['authType'],
+                'accessToken' => $payload['accessToken'],
+                'refreshToken' => $payload['refreshToken'],
+                'expiresAt' => $payload['expiresAt'],
+            ]);
+        } else {
+            DeliveryAuthTokenClass::add($payload);
+        }
+
+        return true;
+    }
+
+    /**
+     * 处理顺丰取消授权回调
+     *
+     * @param array $data
+     * @return bool
+     */
+    private function handleCancelBindNotify($data)
+    {
+        $sign = Yii::$app->request->get('sign');
+        Yii::info('顺丰取消授权状态回调(sign=' . ($sign ?? '') . '): ' . json_encode($data, JSON_UNESCAPED_UNICODE), 'shunfeng-callback');
+
+        $mainId = isset($data['out_shop_id']) ? (int)$data['out_shop_id'] : 0;
+        if ($mainId <= 0) {
+            Yii::error('顺丰取消授权回调缺少 out_shop_id: ' . json_encode($data, JSON_UNESCAPED_UNICODE), 'shunfeng-callback');
+            return false;
+        }
+
+        if (!empty($data['app_id'])) {
+            $auth = new Auth();
+            if ((string)$auth->getAppKey() !== (string)$data['app_id']) {
+                Yii::warning('顺丰取消授权回调 app_id 不匹配: ' . json_encode($data, JSON_UNESCAPED_UNICODE), 'shunfeng-callback');
+                return false;
+            }
+        }
+
+        $condition = [
+            'mainId' => $mainId,
+            'platform' => 'shunfeng',
+        ];
+
+        if (!empty($data['shop_id'])) {
+            $condition['shopId'] = (string)$data['shop_id'];
+        }
+
+        $deleted = DeliveryAuthTokenClass::deleteByCondition($condition);
+        if ($deleted === 0) {
+            Yii::warning('顺丰取消授权回调未删除任何记录: ' . json_encode($data, JSON_UNESCAPED_UNICODE), 'shunfeng-callback');
+        }
+
+        return true;
+    }
     
     /**
      * 转换顺丰订单状态到系统配送状态

+ 36 - 0
common/components/delivery/services/DispatchService.php

@@ -40,6 +40,13 @@ class DispatchService
                         $this->adapters['shunfeng'] = new ShunfengAdapter($pt['accessToken'], $pt['shopId']);
                         break;
                 }
+
+                //检测 token 是否即将过期
+                $tokenExpireTime = $pt['expireAt'];
+                if ($tokenExpireTime < time() + 86400 * 5) {
+                    Yii::info('刷新 token: ' . $pt['platform'] . ',refreshToken: ' . $pt['refreshToken'] . ',merchantId: ' . $pt['merchantId']);
+                    $this->refreshToken($pt['platform'], $pt['refreshToken'], ['merchantId' => $pt['merchantId']]);
+                }
             }
         } else {
             $authPlatform = DeliveryAuthTokenClass::getByCondition(['mainId'=>$mainId, 'platform'=>$platform]);
@@ -61,6 +68,10 @@ class DispatchService
                     break;
             }
             $this->platformName = $platform;
+            if($authPlatform['expireAt'] < time() + 86400 * 5) {    
+                Yii::info('刷新 token: ' . $platform . ',refreshToken: ' . $authPlatform['refreshToken'] . ',merchantId: ' . $authPlatform['merchantId']);
+                $this->refreshToken($platform, $authPlatform['refreshToken'], ['merchantId' => $authPlatform['merchantId']]);
+            }
         }
     }
 
@@ -565,4 +576,29 @@ class DispatchService
         $ap = $this->adapters[$platform];
         return $ap->cityList();
     }
+
+    /**
+     * 刷新 token
+     */
+    public function refreshToken($platform, $refreshToken, $data=[])
+    {
+        switch($platform) {
+            case 'shansong':
+                $auth = new \common\components\delivery\platform\shansong\Auth();
+                $auth->refreshAccessToken($refreshToken);
+                break;
+            case 'huolala':
+                $auth = new \common\components\delivery\platform\huolala\Auth();
+                $auth->refreshAccessToken($refreshToken);
+                break;
+            case 'fengniao':
+                $auth = new \common\components\delivery\platform\fengniao\Auth();
+                $auth->refreshAccessToken($refreshToken, $data['merchantId']);
+                break;
+            case 'shunfeng':
+                $auth = new \common\components\delivery\platform\shunfeng\Auth();
+                $auth->refreshAccessToken($refreshToken);
+                break;
+        }
+    }
 }

+ 8 - 0
common/components/delivery/services/ShopService.php

@@ -92,4 +92,12 @@ class ShopService
         }
         return $ret['balance'];
     }
+
+    /**
+     * 获取商家的所有门店
+     */
+    public function getMerchantStores()
+    {
+        
+    }
 }

+ 1 - 1
common/components/delivery/services/adapter/FengniaoAdapter.php

@@ -697,7 +697,7 @@ class FengniaoAdapter extends Fengniao implements Adapter
             return [
                 'code' => 0,
                 'data' => [
-                    'cancel_reason_list' => $cancelReasonList,
+                    'reasonList' => $cancelReasonList,
                 ]
             ];
         }

+ 4 - 12
common/components/delivery/services/adapter/HuolalaAdapter.php

@@ -529,29 +529,21 @@ class HuolalaAdapter extends Huolala implements Adapter
             $reasonList = [];
             if (!empty($respData['reason']) && is_array($respData['reason'])) {
                 foreach ($respData['reason'] as $reason) {
-                    // 处理子原因
-                    $subReasons = [];
                     if (!empty($reason['sub_reason']) && is_array($reason['sub_reason'])) {
                         foreach ($reason['sub_reason'] as $subReason) {
-                            $subReasons[] = [
-                                'id' => (int)($subReason['id'] ?? 0),
-                                'sub_name' => $subReason['sub_name'] ?? '',
+                            $reasonList[] = [
+                                'order_cancel_code' => (int)($subReason['id'] ?? 0),
+                                'order_cancel_desc' => $subReason['name'] ?? '',
                             ];
                         }
                     }
-                    
-                    $reasonList[] = [
-                        'id' => $reason['id'],
-                        //'name' => $reason['name'] ?? '',
-                        'name' => $subReasons,
-                    ];
                 }
             }
             
             return [
                 'code' => 0,
                 'data' => [
-                    'reason' => $reasonList,
+                    'reasonList' => $reasonList,
                 ]
             ];
         }