123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284 |
- <?php
- /**
- * Created by PhpStorm.
- * User: z-yang
- * Date: 2017/12/9
- * Time: 12:02
- */
- namespace App\Libs\Pay\Merchants;
- use Illuminate\Support\Facades\Storage;
- use App\Libs\PayClient;
- use Log;
- class LianLianPay
- {
- private $appid;
- private $oid_partner;
- public $private_key_path;
- public $public_key_path;
- public $key;
- private $api_url;
- private $PayClient;
- private $sign_type;
- private $col_oidpartner;
- public function __construct($config=[])
- {
-
- $this->appid = $config['appid'];
- $this->oid_partner = $config['oid_partner'];
- $this->api_url = $config['api_url'];
- $this->key = $config['key'];
- $this->private_key_path = $config['private_key_path'];
- $this->public_key_path = $config['public_key_path'];
- $this->sign_type = 'RSA';
- $this->col_oidpartner = $config['col_oidpartner'];
- }
- function send($data)
- {
- $uid = json_decode($data['remark'],true)['uid'];
- $request_data = [
- 'no_order'=>$data['trade_no'],
- 'oid_partner'=>$this->oid_partner,
- 'appid'=>$this->appid,
- 'openid'=>$data['openid'],
- 'busi_partner'=>'101001',
- 'money_order'=>$data['price']/100,
- 'user_id'=>$uid,
- "col_oidpartner"=>$this->col_oidpartner,
- 'dt_order'=>date('YmdHis'),
- 'notify_url'=>env('LIANLIAN_PAY_CALL_BACK_URL'),
- 'pay_type'=>'W',
- 'risk_item'=>'',
- 'sign_type'=>$this->sign_type,
- ];
- $request_data['risk_item'] = json_encode([
- 'frms_ware_category'=>'1004',
- 'user_info_mercht_userno'=>$uid,
- 'user_info_dt_register'=>'20171112103052',
- 'user_info_bind_phone'=>'18606947570'
- ]);
- $request_data = $this->buildRequestPara($request_data);
- $result = $this->getHttpResponseJSON($this->api_url,$request_data);
- \Log::info('lianlian res---------------------');
- \Log::info($result);
- $res = json_decode($result,true);
- if ($res['ret_code'] == '0000') {
- //$pay_data = json_decode($res["payLoad"], true);
- return $res["payLoad"];
- }else{
- return $res;
- }
- }
- /**
- * 生成要请求给连连支付的参数数组
- * @param $para_temp
- * @return
- */
- function buildRequestPara($para_temp) {
- //除去待签名参数数组中的空值和签名参数
- $para_filter = $this->paraFilter($para_temp);
- //对待签名参数数组排序
- $para_sort = $this->argSort($para_filter);
- //生成签名结果
- $mysign = $this->buildRequestMysign($para_sort);
- //签名结果与签名方式加入请求提交参数组中
- $para_sort['sign'] = $mysign;
- $para_sort['sign_type'] = strtoupper(trim($this->sign_type));
- foreach ($para_sort as $key => $value) {
- $para_sort[$key] = $value;
- }
- return $para_sort;
- //return urldecode(json_encode($para_sort));
- }
- /**
- * 除去数组中的空值和签名参数
- * @param $para
- * return 去掉空值与签名参数后的新签名参数组
- */
- function paraFilter($para) {
- $para_filter = array();
- while (list ($key, $val) = each ($para)) {
- if($key == "sign" || $val == "")continue;
- else $para_filter[$key] = $para[$key];
- }
- return $para_filter;
- }
- /**
- * 对数组排序
- * @param $para
- * return 排序后的数组
- */
- function argSort($para) {
- ksort($para);
- reset($para);
- return $para;
- }
- /**
- * 生成签名结果
- * @param $para_sort
- * return 签名结果字符串
- */
- function buildRequestMysign($para_sort) {
- //把数组所有元素,按照“参数=参数值”的模式用“&”字符拼接成字符串
- $prestr = $this->createLinkstring($para_sort);
- $mysign = "";
- switch (strtoupper(trim($this->sign_type))) {
- case "MD5" :
- $mysign = $this->md5Sign($prestr, $this->key);
- break;
- case "RSA" :
- $private_key = Storage::disk('public')->get($this->private_key_path);
- $mysign = $this->Rsasign($prestr, $private_key);
- break;
- default :
- $mysign = "";
- }
- return $mysign;
- }
- /**
- * 把数组所有元素,按照“参数=参数值”的模式用“&”字符拼接成字符串
- * @param $para
- * return 拼接完成以后的字符串
- */
- public function createLinkstring($para) {
- $arg = "";
- while (list ($key, $val) = each ($para)) {
- $arg.=$key."=".$val."&";
- }
- //去掉最后一个&字符
- $arg = substr($arg,0,count($arg)-2);
- //file_put_contents("log.txt","转义前:".$arg."\n", FILE_APPEND);
- //如果存在转义字符,那么去掉转义
- if(get_magic_quotes_gpc()){$arg = stripslashes($arg);}
- //file_put_contents("log.txt","转义后:".$arg."\n", FILE_APPEND);
- return $arg;
- }
- /**
- * 签名字符串
- * @param $prestr 需要签名的字符串
- * @param $key 私钥
- * return 签名结果
- */
- public function md5Sign($prestr, $key) {
- $prestr = $prestr ."&key=". $key;
- return md5($prestr);
- }
- /**
- * 签名验证
- * @param $prestr
- * @param $sign
- * @param $key
- * @return bool
- */
- public function md5Verify($prestr, $sign, $key) {
- $prestr = $prestr ."&key=". $key;
- $mysgin = md5($prestr);
- if($mysgin == $sign) {
- return true;
- }
- else {
- return false;
- }
- }
- /**RSA签名
- * $data签名数据(需要先排序,然后拼接)
- * 签名用商户私钥,必须是没有经过pkcs8转换的私钥
- * 最后的签名,需要用base64编码
- * return Sign签名
- */
- public function Rsasign($data,$priKey) {
- //转换为openssl密钥,必须是没有经过pkcs8转换的私钥
- $res = openssl_get_privatekey($priKey);
- //调用openssl内置签名方法,生成签名$sign
- openssl_sign($data, $sign, $res,OPENSSL_ALGO_MD5);
- //释放资源
- openssl_free_key($res);
- //base64编码
- $sign = base64_encode($sign);
- return $sign;
- }
- /**RSA验签
- * $data待签名数据(需要先排序,然后拼接)
- * $sign需要验签的签名,需要base64_decode解码
- * 验签用连连支付公钥
- * return 验签是否通过 bool值
- */
- public function Rsaverify($data, $sign) {
- \Log::info('Rsaverify param is');
- \Log::info($data);
- \Log::info($sign);
- //读取连连支付公钥文件
- $pubKey = Storage::disk('public')->get($this->public_key_path);
- \Log::info($pubKey);
- //转换为openssl格式密钥
- //$res = openssl_get_publickey($pubKey);
- $res = openssl_pkey_get_public($pubKey);
- \Log::info('public key--is');
- \Log::info($res);
- //调用openssl内置方法验签,返回bool值
- $result = openssl_verify($data, base64_decode($sign), $res,OPENSSL_ALGO_MD5);
- //释放资源
- openssl_free_key($res);
- //返回资源是否成功
- return $result;
- }
- /**
- *
- * 签名验证
- */
- public function rsaCheck($data){
- $sign = $data['sign'];
- $no_sign_data = $this->argSort($this->paraFilter($data));
- //$private_key = Storage::disk('public')->get($this->private_key_path);
- //$check_sing = $this->Rsasign($this->createLinkstring($no_sign_data),$private_key);
- $res = $this->Rsaverify($this->createLinkstring($no_sign_data),$sign);
- \Log::info('lianlian-----------------check');
- \Log::info($res);
- return $res;
- }
- public function getHttpResponseJSON($url, $para) {
- $json = json_encode($para);
- $curl = curl_init($url);
- curl_setopt($curl, CURLOPT_SSL_VERIFYPEER, false); //信任任何证书
- curl_setopt($curl, CURLOPT_CUSTOMREQUEST, "POST");
- curl_setopt($curl, CURLOPT_POSTFIELDS, $json);
- curl_setopt($curl, CURLOPT_RETURNTRANSFER, true);
- curl_setopt($curl, CURLOPT_HTTPHEADER, array(
- 'Content-Type: application/json',
- 'Content-Length: ' . strlen($json))
- );
- $responseText = curl_exec($curl);
- curl_close($curl);
- return $responseText;
- }
- }
|