Selaa lähdekoodia

add wsd brideg server

stanley-king 4 vuotta sitten
vanhempi
commit
f49961705a

+ 0 - 10
client_req.puml

@@ -1,10 +0,0 @@
-@startuml
-UI -> TalkEngine: Authentication Request
-TalkEngine -> Accessor
-Accessor -> TalkEngine : result,message
-
-TalkEngine -> Observer : Protocol,message->database
-
-
-
-@enduml

+ 2 - 1
data/config/dev/base.ini.php

@@ -106,4 +106,5 @@ $config['return_address'] = ['address' => '上海市金山区朱吕公路7335号
 $config['area_version'] = 5;
 $config['appjump_prefix'] = 'xyzshop://www.xyzshops.com';
 
-$config['client_setting'] = ['running' => 174,'home' => 0];
+$config['client_setting'] = ['running' => 174,'home' => 0];
+$config['wsd_bradge_port'] = 60987;

+ 3 - 1
data/config/prod/base.ini.php

@@ -105,4 +105,6 @@ $config['area_version'] = 5;
 
 $config['appjump_prefix'] = 'xyzshop://www.xyzshops.com';
 
-$config['client_setting'] = ['running' => 174,'home' => 0];
+$config['client_setting'] = ['running' => 174,'home' => 0];
+
+$config['wsd_bradge_port'] = 60987;

+ 3 - 1
data/config/test/base.ini.php

@@ -103,4 +103,6 @@ $config['return_address'] = ['address' => '上海市金山区朱吕公路7335号
 $config['area_version'] = 5;
 
 $config['appjump_prefix'] = 'xyzshop://www.xyzshops.com';
-$config['client_setting'] = ['running' => 174,'home' => 0];
+$config['client_setting'] = ['running' => 174,'home' => 0];
+
+$config['wsd_bradge_port'] = 60988;

+ 14 - 0
docker-compose-dev.yml

@@ -73,6 +73,20 @@ services:
     depends_on:
       - "redisrv"
 
+  wsdsrv:
+    image: php-zts-debug:7.3.18
+    ports:
+      - "60987:60987"
+    volumes:
+      - $PWD/conf/etc/localtime:/etc/localtime:ro
+      - $PWD:/var/www/html
+      - /Volumes/Transcend/upload:/var/www/html/data/upload
+      - $PWD/conf/php/php-debug.ini:/usr/local/etc/php/php.ini
+    links:
+      - redisrv
+    container_name: "panda-wsd"
+    command: [php,"/var/www/html/wsd_bridge.php"]
+
   searcher:
     image: php-zts-debug:7.3.18
     volumes:

+ 17 - 0
docker-compose.yml

@@ -81,6 +81,23 @@ services:
       - "docker.hostip:172.17.0.1"
       - "eth.hostip:172.26.105.125"
 
+  wsdsrv:
+    image: php-zts-debug:7.3.18
+    ports:
+      - "60987:60987"
+    volumes:
+      - $PWD/conf/etc/localtime:/etc/localtime:ro
+      - $PWD:/var/www/html
+      - /mnt/upload:/var/www/html/data/upload
+      - $PWD/conf/php/php.ini:/usr/local/etc/php/php.ini
+    links:
+      - redisrv
+    container_name: "panda-wsd"
+    command: [php,"/var/www/html/wsd_bridge.php"]
+    extra_hosts:
+      - "docker.hostip:172.17.0.1"
+      - "eth.hostip:172.26.105.125"
+
   searcher:
     image: php-zts-debug:7.3.18
     volumes:

+ 20 - 0
helper/event/util.php

@@ -37,6 +37,26 @@ class util
         return $listen_fd;
     }
 
+    static public function listen_block($host,$port)
+    {
+        $listen_fd = socket_create(AF_INET, SOCK_STREAM, SOL_TCP);
+
+        if(!socket_set_option($listen_fd, SOL_SOCKET, SO_REUSEADDR, 1)) {
+            Log::record("socket_set_option 地址重用失败.",Log::DEBUG);
+            return false;
+        }
+        if(!socket_bind($listen_fd, $host, $port)) {
+            echo "无法绑定socket {$host} : {$port},请退出之前进程.\n";
+            return false;
+        }
+        if(!socket_listen($listen_fd)) {
+            echo "无法监听socket,请退出之前进程.\n";
+            return false;
+        }
+
+        return $listen_fd;
+    }
+
     static function fork_child($callback, $params)
     {
         if (($pid = pcntl_fork()) === 0)

+ 62 - 45
helper/rbridge/wsd/Bridge.php

@@ -5,49 +5,71 @@ require_once(BASE_HELPER_PATH . '/rbridge/wsd/config.php');
 require_once(BASE_HELPER_PATH . '/refill/RefillFactory.php');
 
 use rbridge\IBridge;
+use rbridge\wsd\config;
 use refill\RefillFactory;
 use refill_proxy;
 use Log;
 use member_info;
 use Exception;
-use rbridge\wsd\config;
 
 class Bridge implements IBridge
 {
     public function add($params)
     {
-        if($this->verify($params) === false) {
-            return [false,"签名不成功"];
+        if ($this->verify($params) === false) {
+            return json_encode($this->errbody("签名不成功",$params));
         }
 
         $action = $params['action'];
         $chargeType = intval($params['chargeType']);
 
-        if($action != 'CZ') {
-            return [false,"不支持该业务"];
+        if ($action != 'CZ') {
+            return json_encode($this->errbody("不支持该业务",$params));
         }
 
         //业务类型
         //0:话费 1:Q币 2:QQ会员 3:游戏
         //4:水电气 5:流量 6:票务 7:固话 8:宽带 9:油卡
-        if($chargeType !== 0 && $chargeType !== 9) {
-            return false;
+        if ($chargeType !== 0 && $chargeType !== 9) {
+            return json_encode($this->errbody("不支持该类型业务",$params));
+
         }
 
         $mchid = config::MCHID;
-        Model('merchant_query')->add_info(config::MCHID,$params['chargeId'],json_encode($params));
+        Model('merchant_query')->add_info(config::MCHID, $params['chargeId'], json_encode($params));
         $mchinfo = Model('merchant')->getMerchantInfo(['mchid' => $mchid]);
         $userid = intval($mchinfo['admin_id']);
-        [$code,$msg] = RefillFactory::instance()->add($mchid,$userid,$params['chargeCash'],$params['chargeAcct'],$params['chargeId'],config::MCH_NOTIFY_URL);
+        [$code, $msg] = RefillFactory::instance()->add($mchid, $userid, $params['chargeCash'], $params['chargeAcct'], $params['chargeId'], config::MCH_NOTIFY_URL);
 
-        $ret = $this->retbody($code,$msg,$params);
+        $ret = $this->retbody($code, $msg, $params);
         return json_encode($ret);
     }
 
-    private function retbody($code,$msg,$params)
+    private function errbody($msg,$params)
     {
         //交易结果 0:未处理 1:充值成功 2:充值结果不确定 3:充值失败
-        if($code === true) {
+        $retCode = 3;
+        $retDetail = $msg;
+
+        $result = [
+            'action' => 'CZ',
+            'chargeId' => $params['chargeId'],
+            'retCode' => $retCode,
+            'retDetail' => $retDetail,
+            'retRsn' => $params['retRsn']];
+
+        $body = "{$params['chargeId']}{$retCode}{$params['retRsn']}" . config::BridgeKey;
+        $sign = md5($body);
+        $result['sign'] = $sign;
+
+        return $result;
+
+    }
+
+    private function retbody($code, $msg, $params)
+    {
+        //交易结果 0:未处理 1:充值成功 2:充值结果不确定 3:充值失败
+        if ($code === true) {
             $retCode = 0;
             $retDetail = '定单已接收';
         } else {
@@ -58,9 +80,9 @@ class Bridge implements IBridge
         $result = [
             'action' => 'CZ',
             'chargeId' => $params['chargeId'],
-            'retCode'  => $retCode,
+            'retCode' => $retCode,
             'retDetail' => $retDetail,
-            'retRsn' => $params['retRsn'] ];
+            'retRsn' => $params['retRsn']];
 
         $body = "{$params['chargeId']}{$retCode}{$params['retRsn']}" . config::BridgeKey;
         $sign = md5($body);
@@ -72,30 +94,27 @@ class Bridge implements IBridge
     public function notify($params)
     {
         $proxy = new refill_proxy(config::MCH_KEY);
-        [$verify,$data] = $proxy->notify($params);
+        [$verify, $data] = $proxy->notify($params);
         $mchid = config::MCHID;
 
-        if($verify)
-        {
+        if ($verify) {
             $body = $this->notify_body($data);
-            if($body === false) {
+            if ($body === false) {
                 return true;
             }
 
             $header = ['Content-Type: application/json'];
-            $resp = http_post_data(config::BridgeNotifyURL,$body,$header);
+            $resp = http_post_data(config::BridgeNotifyURL, $body, $header);
 
-            if($resp === false) {
+            if ($resp === false) {
                 $url = config::BridgeNotifyURL;
-                Log::record("通知mchid = {$mchid} {$url}失败",Log::ERR);
+                Log::record("通知mchid = {$mchid} {$url}失败", Log::ERR);
                 return false;
-            }
-            else {
+            } else {
                 return true;
             }
-        }
-        else {
-            Log::record("内部回调签名错误 mchid = {$mchid}",Log::ERR);
+        } else {
+            Log::record("内部回调签名错误 mchid = {$mchid}", Log::ERR);
             return false;
         }
     }
@@ -104,14 +123,13 @@ class Bridge implements IBridge
     private function notify_body($params)
     {
         $mch_ordersn = $params['order_sn'];
-        $query_info = Model('merchant_query')->query_info(config::MCHID,$mch_ordersn);
-        if(empty($query_info)) {
+        $query_info = Model('merchant_query')->query_info(config::MCHID, $mch_ordersn);
+        if (empty($query_info)) {
             $mchid = config::MCHID;
-            Log::record("查不到mchid={$mchid},mch_order:{$mch_ordersn}的原始订单信息",Log::ERR);
+            Log::record("查不到mchid={$mchid},mch_order:{$mch_ordersn}的原始订单信息", Log::ERR);
             return false;
-        }
-        else {
-            $query_info = json_decode($query_info['request'],true);
+        } else {
+            $query_info = json_decode($query_info['request'], true);
         }
 
         $success = $params['state'] == 'SUCCESS';
@@ -124,9 +142,9 @@ class Bridge implements IBridge
             "retDetail" => $retCode == 1 ? "充值成功" : "充值失败",
             "retRsn" => $query_info['retRsn'],
             "userContent" => "",
-            "retCost" => number_format($this->getCost(config::MCHID,$mch_ordersn),3),
-            "retBalance" => number_format($this->getBalance(config::MCHID),3),
-            "retCash" => number_format($query_info['chargeCash'],3)
+            "retCost" => number_format($this->getCost(config::MCHID, $mch_ordersn), 3),
+            "retBalance" => number_format($this->getBalance(config::MCHID), 3),
+            "retCash" => number_format($query_info['chargeCash'], 3)
         ];
         $sign = md5("{$body['chargeId']}{$body['retCode']}{$body['retRsn']}" . config::BridgeKey);
         $body['sign'] = $sign;
@@ -140,22 +158,21 @@ class Bridge implements IBridge
             $mchinfo = Model('merchant')->getMerchantInfo(['mchid' => $mchid]);
             $userid = intval($mchinfo['admin_id']);
             $info = new member_info($userid);
-            return round($info->available_predeposit(),3);
-        }
-        catch(Exception $ex) {
-            Log::record("Bridge getBalance mchid={$mchid} what : {$ex->getMessage()}",Log::ERR);
+            return round($info->available_predeposit(), 3);
+        } catch (Exception $ex) {
+            Log::record("Bridge getBalance mchid={$mchid} what : {$ex->getMessage()}", Log::ERR);
             return 0.000;
         }
     }
-    private function getCost($mchid,$mch_ordersn)
+
+    private function getCost($mchid, $mch_ordersn)
     {
         $refill_order = Model('refill_order');
-        $items = $refill_order->getOrderInfo(['mchid' => $mchid,'mch_order' => $mch_ordersn,'inner_status' => 0]);
-        if(!empty($items)) {
+        $items = $refill_order->getOrderInfo(['mchid' => $mchid, 'mch_order' => $mch_ordersn, 'inner_status' => 0]);
+        if (!empty($items)) {
             $order = $items[0];
             return $order['mch_amount'];
-        }
-        else {
+        } else {
             return 0;
         }
     }
@@ -163,7 +180,7 @@ class Bridge implements IBridge
     private function verify($params)
     {
         //md5(chargeId + chargeAcct + var1 + var2 + var3 + var4 + chargeCash + md5key)
-        $keys = ['chargeId','chargeAcct','var1','var2','var3','var4','chargeCash'];
+        $keys = ['chargeId', 'chargeAcct', 'var1', 'var2', 'var3', 'var4', 'chargeCash'];
         $body = "";
         foreach ($keys as $key) {
             $body .= $params[$key] ?? "";

+ 38 - 10
test/TestRBridge.php

@@ -21,14 +21,7 @@ class TestRBridge extends TestCase
         Base::run_util();
     }
 
-    public function testSurAdd()
-    {
-        $input = '{"action":"CZ","chargeId":196,"chargeAcct":"13530017201","chargeCash":100.000,"chargeType":0,"amount":1,"faceValue":100.000,"var1":"","var2":"","var3":"","var4":"","productSn":0,"nbrArea":"广东省深圳-移动","cardSn":"","cardPassword":"","agentAcct":"","agentPass":"","cardId":0,"retRsn":"0","sign":"3c90ed55aa363a22cd86746f34eeedb0"}';
-        $params = json_decode($input,true);
-        $ret = rbridge\RBridgeFactory::instance()->add('shr',$params);
-    }
-
-    public function testWSDAdd()
+    private function getParams()
     {
         $params = ["action" => "CZ",
             "chargeId" => $this->make_sn(),
@@ -50,7 +43,42 @@ class TestRBridge extends TestCase
             "cardId" => 0,
             "retRsn" => "0"];
         $params['sign'] = $this->sign($params);
-        $resp = http_post_data(BASE_SITE_URL . "/mobile/bridge_shr.php",json_encode($params),['Content-Type: application/json']);
+
+        return $params;
+    }
+
+    public function testWSDAdd()
+    {
+
+        $resp = http_post_data(BASE_SITE_URL . "/mobile/bridge_shr.php",json_encode($this->getParams()),['Content-Type: application/json']);
+    }
+
+    public function testTCPAdd()
+    {
+        $params = $this->getParams();
+        $this->send(json_encode($params));
+
+
+    }
+
+    public function send($body)
+    {
+        global $config;
+        $port = $config['wsd_bradge_port'];
+
+        $sock = socket_create(AF_INET, SOCK_STREAM, SOL_TCP);
+        if(socket_connect($sock, "192.168.1.220", $port))
+        {
+            socket_write($sock,$body);
+            $resp = socket_read($sock,1024);
+        }
+    }
+
+    public function testSurAdd()
+    {
+        $input = '{"action":"CZ","chargeId":196,"chargeAcct":"13530017201","chargeCash":100.000,"chargeType":0,"amount":1,"faceValue":100.000,"var1":"","var2":"","var3":"","var4":"","productSn":0,"nbrArea":"广东省深圳-移动","cardSn":"","cardPassword":"","agentAcct":"","agentPass":"","cardId":0,"retRsn":"0","sign":"3c90ed55aa363a22cd86746f34eeedb0"}';
+        $params = json_decode($input,true);
+        $ret = rbridge\RBridgeFactory::instance()->add('shr',$params);
     }
 
     public function testCallBack()
@@ -73,7 +101,7 @@ class TestRBridge extends TestCase
         foreach ($keys as $key) {
             $body .= $params[$key] ?? "";
         }
-        $body .= 'bff0378ea5ef0d5d';
+        $body .= 'ac59f54faf1ffcc1';
         $sign = md5($body);
 
         return $sign;

+ 0 - 2
test/TestRefill.php

@@ -281,8 +281,6 @@ class TestRefill extends TestCase
             'notifyurl'=> 'https://qzcz.edusahoo.com.cn/index/index/callback'];
 
         $resp = $this->send_md5(BASE_SITE_URL . '/mobile/index.php',$params);
-
-
     }
 
     protected function check_empty($value)

+ 121 - 0
wsd_bridge.php

@@ -0,0 +1,121 @@
+<?php
+
+use rbridge\wsd\config;
+
+define('APP_ID', 'bridge-wsd');
+define('BASE_ROOT_PATH', str_replace('\\', '/', dirname(__FILE__)));
+
+require_once(BASE_ROOT_PATH . '/global.php');
+require_once(BASE_ROOT_PATH . '/fooder.php');
+require_once(BASE_ROOT_PATH . '/helper/event_looper.php');
+require_once(BASE_CORE_PATH . '/framework/function/http.php');
+
+
+global $config;
+$port = $config['wsd_bradge_port'];
+
+
+class WSDBridge
+{
+    private $mListenPort;
+    const KEY = 'ac59f54faf1ffcc1';
+
+    public function __construct($port)
+    {
+        $this->mListenPort = $port;
+    }
+
+    public function looper()
+    {
+        $fd = event\util::listen_block("0.0.0.0", $this->mListenPort);
+        if ($fd === false) {
+            Log::record("Cannot Listen on port = {$this->mListenPort}", Log::DEBUG);
+            return false;
+        }
+
+        while (true)
+        {
+            if (($client = socket_accept($fd)) !== false) {
+                Log::record("Client {$client} has connected", Log::DEBUG);
+                socket_set_option($client, SOL_SOCKET, SO_RCVTIMEO, ['sec' => 8, 'usec' => 0]);
+
+                $body = $this->read_order($client);
+                if($body !== false) {
+                    $response = $this->relay_request($body);
+                    socket_write($client,$response);
+                }
+                socket_close($client);
+            }
+        }
+    }
+
+    private function relay_request($body)
+    {
+        $url = BASE_SITE_URL . "/mobile/bridge_shr.php";
+        $headers = ['Content-Type: application/json'];
+
+        $resp = http_post_data($url,$body,$headers);
+        if($resp === false) {
+            Log::record("Net error.",Log::ERR);
+            return $this->err_body($body);
+        }
+        else {
+            return $resp;
+        }
+    }
+
+    private function err_body($body)
+    {
+        $params = json_decode($body);
+
+        //交易结果 0:未处理 1:充值成功 2:充值结果不确定 3:充值失败
+        $retCode = 3;
+        $retDetail = "服务维护中.....";
+
+        $result = [
+            'action' => 'CZ',
+            'chargeId' => $params['chargeId'],
+            'retCode'  => $retCode,
+            'retDetail' => $retDetail,
+            'retRsn' => $params['retRsn'] ];
+
+        $body = "{$params['chargeId']}{$retCode}{$params['retRsn']}" . WSDBridge::KEY;
+        $sign = md5($body);
+        $result['sign'] = $sign;
+
+        return json_encode($result);
+    }
+
+    private function read_order($client)
+    {
+        $content = '';
+        while (true)
+        {
+            $buf = socket_read($client, 1024);
+            if ($buf === false) {
+                $error = socket_strerror(socket_last_error($client));
+                Log::record("read_order err:{$error}", Log::ERR);
+                return false;
+            } else {
+                $content .= $buf;
+            }
+
+            if ($this->isbody($content)) {
+                return $content;
+            }
+
+            if(strlen($content) >  1024) {
+                return false;
+            }
+        }
+    }
+
+    private function isbody($content)
+    {
+        $ret = json_decode($content, true);
+        return ($ret !== false);
+    }
+}
+
+$brider = new WSDBridge($port);
+$brider->looper();