stanley-king 3 years atrás
parent
commit
8f805fa500

+ 76 - 0
helper/refill/api/xyz/suning/RefillCallBack.php

@@ -0,0 +1,76 @@
+<?php
+namespace refill\sctongqian;
+require_once(BASE_HELPER_RAPI_PATH . '/sctongqian/config.php');
+
+use refill;
+use Log;
+
+class RefillCallBack implements refill\IRefillCallBack
+{
+    public function verify($params): bool
+    {
+        $sign = $this->sign($params);
+        if ($params['Sign'] == $sign) {
+            return true;
+        } else {
+            return false;
+        }
+    }
+
+    private function sign($params)
+    {
+        $content = config::APP_KEY . $params['TimesTamp'] . $params['MOrderID'] . $params['OrderID'] . $params['State'] . $params['ChargeAccount'];
+        $content .= $params['BuyCount'] . config::App_Secret;
+        return strtoupper(md5($content));
+    }
+
+    public function notify($params)
+    {
+        $status = intval($params['State']);
+        $order_sn = $params['MOrderID'];
+
+        $order_info = Model('vr_order')->getOrderInfo(['order_sn' => $order_sn]);
+        if (empty($order_info)) {
+            return [false, false, false,false];
+        }
+        $order_id = $order_info['order_id'];
+
+        if ($status === 2)
+        {
+            $card_info = $params['CardInfo'];
+            if(!empty($card_info))
+            {
+                $result = $this->rsa_decode($params['CardInfo']);
+                if (empty($result)) {
+                    $data['ret_state'] = 2;
+                    $data['card_info'] = '回调解密,解密失败';
+                } else {
+                    $data['ret_state'] = 1;
+                    $data['card_info'] = $result;
+                }
+                Model('thrid_refill')->edit_third($order_id, $data);
+            }
+
+            return [$order_id, true, false,true];
+        }
+        elseif ($status === 3) {
+            return [$order_id, false, true,true];
+        }
+        else {
+            return [$order_id, false, false,false];
+        }
+    }
+
+    private function rsa_decode($encrypted)
+    {
+        $ret = openssl_private_decrypt(base64_decode($encrypted), $decrypted, config::PRIVATE_KEY);
+        if ($ret) {
+            $result = json_decode($decrypted, true);
+            return $result;
+        } else {
+            $err = openssl_error_string();
+            Log::record("sctongqian callback openssl_private_decrypt error={$err}",Log::ERR);
+            return false;
+        }
+    }
+}

+ 217 - 0
helper/refill/api/xyz/suning/RefillPhone.php

@@ -0,0 +1,217 @@
+<?php
+
+namespace refill\suning;
+
+require_once(BASE_HELPER_RAPI_PATH . '/suning/config.php');
+
+use refill;
+use Log;
+
+class RefillPhone extends refill\IRefillPhone
+{
+    public function __construct($cfgs)
+    {
+        parent::__construct($cfgs);
+    }
+
+    public function goods($quality,int $amount,int $card_type,$other)
+    {
+        [$goods_id, $price] = parent::goods($quality,$amount,$card_type,$other);
+        if($goods_id <= 0) return [0,0];
+
+        $store_id = $this->mStoreID;
+        $pcode = $other['product_code'];
+        $thrid_refill = Model('thrid_refill');
+        $product = $thrid_refill->getProviderProduct($store_id,$goods_id,$pcode);
+        if(empty($product)) {
+            Log::record("cannot find provider's produce where name={$this->mName}, goods_id = {$goods_id} pcode={$pcode}",Log::ERR);
+            return [0,0];
+        } else {
+            return [$goods_id,ncPriceFormat($product['channel_amount'])];
+        }
+    }
+
+    private function req_params(string $order_sn, string $product_code,$quantity)
+    {
+        $params['partner'] = config::PARTNER;
+        $params['service'] = 'cardSaleAgent';
+        $params['format'] = 'json';
+        $params['orderTime'] = time();
+        $params['ProductCode'] = $product_code;
+        $params['BuyCount'] = $quantity;
+        $params['MOrderID'] = $order_sn;
+        $params['CustomerIP'] = config::API_IP;
+        $params['IsCallback'] = 1;
+        $params['CallBackUrl'] = config::NOTIFY_URL;
+        $params['Version'] = '1.0';
+        return $params;
+    }
+
+    private function getProductCode($goods_id,$sys_pcode)
+    {
+        $thrid_refill = Model('thrid_refill');
+        $product = $thrid_refill->getProviderProduct($this->mStoreID,$goods_id,$sys_pcode);
+        if (empty($product)) {
+            return false;
+        } else {
+            return $product['channel_code'];
+        }
+    }
+
+    //直充提单
+    public function add($card_no, $card_type, $amount, $params)
+    {
+        if(empty($card_no)) {
+            return $this->cardkey_add($params);
+        } else {
+            return $this->direct_add($card_no, $params);
+        }
+    }
+
+    private function direct_add($card_no, $params)
+    {
+        $order_sn = $params['order_sn'];
+        $goods_id = intval($params['goods_id']);
+        $product_code = $this->getProductCode($goods_id,$params['product_code']);
+
+        Model('thrid_refill')->edit_third($params['order_id'], ['chcode' => $product_code]);
+        $quantity = intval($params['quantity']);
+
+        $params = $this->req_params($order_sn,$product_code,$quantity);
+
+        $params['ChargeAccount'] = $card_no;
+        $params['ChargeAccountType'] = 1;//账号类型1 手机号,2 QQ号,3 微信号
+
+        $sign = $this->sign($params);
+        $params['Sign'] = $sign;
+
+        $resp = http_request(config::ORDER_URL, $params);
+        if (empty($resp)) {
+            return [false, '网络错误', true];
+        }
+        else
+        {
+            Log::record($resp, Log::DEBUG);
+            $resp = json_decode($resp, true);
+            if (empty($resp)) {
+                return [false, '网络错误', true];
+            } elseif ($resp['Code'] == 999) {
+                return [true, $resp['OrderModel']['OrderId'], false];
+            } else {
+                return [false, $resp['Msg'], false];
+            }
+        }
+    }
+
+    private function cardkey_add($params)
+    {
+        $order_sn = $params['order_sn'];
+        $goods_id = intval($params['goods_id']);
+        $product_code = $this->getProductCode($goods_id,$params['product_code']);
+        Model('thrid_refill')->edit_third($params['order_id'], ['chcode' => $product_code]);
+
+        $quantity = intval($params['quantity']);
+        $params = $this->req_params($order_sn,$product_code,$quantity);
+
+        $params['PublicKey'] = config::PUBLIC_KEY;
+        $sign = $this->sign($params);
+        $params['Sign'] = $sign;
+
+        $resp = http_request(config::CARD_ORDER_URL, $params);
+        if (empty($resp)) {
+            return [false, '网络错误', true];
+        }
+        else
+        {
+            Log::record($resp, Log::DEBUG);
+            $resp = json_decode($resp, true);
+            if (empty($resp)) {
+                return [false, '网络错误', true];
+            } elseif ($resp['Code'] == 999) {
+                return [true, $resp['OrderModel']['OrderId'], false];
+            } else {
+                return [false, $resp['Msg'], false];
+            }
+        }
+    }
+
+    public function query($refill_info)
+    {
+        $params['AppKey'] = config::APP_KEY;
+        $params['TimesTamp'] = time();
+        $params['MOrderID'] = $refill_info['order_sn'];
+        $params['Version'] = '1.0';
+
+        $content = config::APP_KEY . $params['TimesTamp'] . $params['Version'] . $params['MOrderID'] . config::App_Secret;
+        $params['Sign'] = strtoupper(md5($content));
+
+        $resp = http_request(config::QUERY_URL, $params);
+
+        if (empty($resp)) {
+            return [false, '网络错误'];
+        }
+        else
+        {
+            Log::record($resp, Log::DEBUG);
+            $resp = json_decode($resp, true);
+            if (empty($resp)) {
+                return [false, '网络错误'];
+            }
+            elseif ($resp['Code'] == 999)
+            {
+                $status = intval($resp['Data']['OrderState']);
+                if ($status === 2)
+                {
+                    if(!empty($resp['Data']['CardData'])) {
+                        $result = $this->rsa_decode($resp['Data']['CardData']);
+                        if (empty($result)) {
+                            $data['ret_state'] = 2;
+                            $data['card_info'] = '查询接口,解密失败';
+                        } else {
+                            $data['ret_state'] = 1;
+                            $data['card_info'] = $result;
+                        }
+                        Model('thrid_refill')->edit_third($refill_info['order_id'], $data);
+                    }
+                    $order_state = ORDER_STATE_SUCCESS;
+                }
+                elseif ($status === 3) {
+                    $order_state = ORDER_STATE_CANCEL;
+                }
+                elseif (in_array($status, [1,4])) {
+                    $order_state = ORDER_STATE_SEND;
+                }
+                else {
+                    return [false, $resp['Message']];
+                }
+
+                return [true, $order_state];
+            }
+            else
+            {
+                return [false, $resp['Message']];
+            }
+        }
+    }
+
+    private function rsa_decode($encrypted)
+    {
+        $ret = openssl_private_decrypt(base64_decode($encrypted), $decrypted, config::PRIVATE_KEY);
+        if ($ret) {
+            $result = json_decode($decrypted, true);
+            return $result;
+        } else {
+            $err = openssl_error_string();
+            Log::record("sctongqian callback openssl_private_decrypt error={$err}", Log::ERR);
+            return false;
+        }
+    }
+
+    private function sign($params)
+    {
+        $content = config::APP_KEY . $params['BuyCount'] . $params['CallBackUrl'] . $params['ChargeAccount'] . $params['CustomerIP'] . $params['MOrderID'];
+        $content .= $params['ProductCode'] . $params['TimesTamp'] . $params['Version'] . config::App_Secret;
+        return strtoupper(md5($content));
+    }
+
+}

+ 54 - 0
helper/refill/api/xyz/suning/config.php

@@ -0,0 +1,54 @@
+<?php
+
+namespace refill\suning;
+
+class config
+{
+    //正式地址及正式账号信息
+    const ORDER_URL = 'http://video.api.sctongqian.com/Order/DirectOrder';//直充订单提交地址
+    const CARD_ORDER_URL = 'http://video.api.sctongqian.com/Order/CardOrder';//卡密订单提交地址
+    const QUERY_URL= 'http://video.api.sctongqian.com/Business/QueryOrder';
+
+
+    const PARTNER = 'YZKJ';
+
+    const APP_KEY= 211394768;
+    const App_Secret = 'vA+24E7SOUWPAIHvNMdXyw==';
+
+    //沙箱环境账号
+//    const ORDER_URL = 'http://182.150.21.90:8050/Order/DirectOrder';//直充订单提交地址
+//    const CARD_ORDER_URL = 'http://182.150.21.90:8050/Order/CardOrder';//卡密订单提交地址
+//    const QUERY_URL= 'http://182.150.21.90:8050/Business/QueryOrder';
+//    const APP_KEY= 211394658;
+//    const App_Secret = 'ZZV9akQWGkmR0ln6zOGmsQ==';
+
+    const NOTIFY_URL = BASE_SITE_URL . "/racc/callback/lingzh/sctongqian.php";
+    const API_IP = NET_IP;
+
+    const PUBLIC_KEY = <<<heredoc
+-----BEGIN RSA PUBLIC KEY-----
+MIGJAoGBAJZPPaJkFbdhTmSqc3aNSLTOXA3PpEZ8aZflS0h5ZTF7NSm3cGBBMZ2K
+giFAhf4CoqYpeUGiq5iFIfRvLLihidocr8QAlTuVdwUv7dWc0BP3bWWwK3j7re0m
+Pu0xhetm8hmyF6UWQxr+4D+tiWtLj1NZEv6ZPf6d4XSgxDpFGtq1AgMBAAE=
+-----END RSA PUBLIC KEY-----
+heredoc;
+
+    const PRIVATE_KEY = <<<heredoc
+-----BEGIN OPENSSH PRIVATE KEY-----
+b3BlbnNzaC1rZXktdjEAAAAABG5vbmUAAAAEbm9uZQAAAAAAAAABAAAAlwAAAAdzc2gtcn
+NhAAAAAwEAAQAAAIEAlk89omQVt2FOZKpzdo1ItM5cDc+kRnxpl+VLSHllMXs1KbdwYEEx
+nYqCIUCF/gKipil5QaKrmIUh9G8suKGJ2hyvxACVO5V3BS/t1ZzQE/dtZbArePut7SY+7T
+GF62byGbIXpRZDGv7gP62Ja0uPU1kS/pk9/p3hdKDEOkUa2rUAAAIQSSgusUkoLrEAAAAH
+c3NoLXJzYQAAAIEAlk89omQVt2FOZKpzdo1ItM5cDc+kRnxpl+VLSHllMXs1KbdwYEExnY
+qCIUCF/gKipil5QaKrmIUh9G8suKGJ2hyvxACVO5V3BS/t1ZzQE/dtZbArePut7SY+7TGF
+62byGbIXpRZDGv7gP62Ja0uPU1kS/pk9/p3hdKDEOkUa2rUAAAADAQABAAAAgDZc7IbKOg
+x8FhVUjLQo/03dgO/B1MFlh+9XD/ZjaZUO4bh3zx4RFjfLe6s5If0vyNHeGCwEAJoGNLSq
+bPtN+YQqi3GIYEgscHCQYrsa/TMEn4Svrd+1VRoxYrPN+zgpTf1MXcPW22xr2K433u+f4l
+M19Dmi/G3u5mY0lorAyzPBAAAAQQCq6lRGiMBLuO46a4Cw5KWarqWH63B0Dlp/mry7ugnL
+GeBOhYJmzlA5sMWpTg3XyzOxez11Oo+nUn2ByF+XrLcdAAAAQQDF42SO61xOpf5qVN84XV
+s1wcNcJxuhPhet43A8VqAo8MC4f522Lp3/4B1Uf/hwzAx5Gg2tkFnx8eXobsvceG1lAAAA
+QQDCcwggFzrz6BiNE4Tqmz6TDOuH13wyXqUXGgO3fjibIoJCwSo+KggqhlPUM7zDWSbhns
+NJd7JPEi6j+lOvY0sRAAAAGnN0YW5sZXkta2luZ0BTdGFubGV5TWFjcHJv
+-----END OPENSSH PRIVATE KEY-----
+heredoc;
+}

BIN
helper/refill/api/xyz/suning/苏宁卡API销售接口说明v1.6.1.pdf


+ 5 - 0
test/TestTime.php

@@ -173,4 +173,9 @@ class TestTime extends TestCase
         $y = md5($x);
     }
 
+    public function testSuning()
+    {
+        $x = date("YmdHis",time());
+    }
+
 }