1. 程式人生 > >支付介面的注意事項

支付介面的注意事項

1、php的ini檔案要開啟php_openssl的支援

2、微信支付回撥成功後要先向微信發起查詢訂單介面,確保訂單是付款的,而不是惡意模擬請求,查詢微信後臺存在該訂單的時候,再處理自己的邏輯

3、支付寶支付成功回撥的時候,要判斷支付的金額是否和資料庫的金額一致,一致才能認為付款成功,避免模擬請求的

4、微信支付的呼叫方法

(1) 微信api生成隨機字串

function wechatRandomStr()
{
   return  md5(time().mt_rand(0,1000));
}

(2)生成微信sign簽名

function createWechatSign($arr)
{
    ksort($arr);
    return strtoupper(md5(urldecode(http_build_query($arr) . '&key='.WECHAT_PARTNER_KEY)));
}

(3)生成xml陣列

function createXml($arr)
{
    $xml="<xml>\n";
    foreach ($arr as $key => $value) {
        $xml.="<".$key."><![CDATA[".trim($value)."]]></".$key.">\n";
    }
    $xml.="</xml>";
    return $xml;
}
(4) 資料生成xml格式,返回xml格式的資料
function curlWechatApi($uri,$xmlData)
{
    $ch = curl_init();
    $header = array('Content-type: text/xml');
    curl_setopt($ch, CURLOPT_URL, $uri);
    curl_setopt($ch, CURLOPT_HTTPHEADER, $header);
    curl_setopt($ch, CURLOPT_POST, 1);
    curl_setopt($ch, CURLOPT_POSTFIELDS, $xmlData);
    curl_setopt($ch, CURLOPT_SSL_VERIFYPEER, false);
    curl_setopt($ch, CURLOPT_RETURNTRANSFER, 1);
    curl_setopt($ch, CURLOPT_HEADER, 0);
    $res = simplexml_load_string(curl_exec($ch),null, LIBXML_NOCDATA);
    curl_close($ch);
    return $res;
}

(5)微信查詢訂單

function orderQuery($wechatOrderID,$orderID)
{
    $arr = array(
        'appid' => WECHAT_APP_ID,//appid微信開放平臺稽核通過的應用APPID
        'mch_id'=> WECHAT_MCH_ID,//mch_id微信支付分配的商戶號
        'transaction_id'    =>sprintf('%s',$wechatOrderID),
        'out_trade_no'  =>sprintf('%s',$orderID),
        'nonce_str' =>wechatRandomStr()
    );
    $arr['sign'] = createWechatSign($arr);
    $dataStr = createXml($arr);
    return curlWechatApi(WECHAT_ORDERQUERY_URI,$dataStr);
}

(6)統一下單的介面

function prepayOrder($out_trade_no){
	$out_trade_no = $_REQUEST['out_trade_no'];	//接收訂單號
	訂單號的合法合理性判斷
	//構造一個微信訂單
    	$order=array(
        	"body" => 商品描述,
        	"appid" => WECHAT_APP_ID,
       	 	'attach'=> 附加資料(店鋪名稱),
        	"device_info" => 裝置號(APP-001),
        	"mch_id" => WECHAT_MCH_ID,
        	"nonce_str" => wechatRandomStr(),
        	"notify_url" => WECHAT_NOTIFY_URL,
        	"out_trade_no" => $out_trade_no,
       		// "spbill_create_ip" => $this->input->ip_address(),  //APP傳過來
        	"spbill_create_ip" => $_SERVER["REMOTE_ADDR"],
        	"total_fee" => intval(商品價格*100),//注意:前方有坑!!!最小單位是分,跟支付寶不一樣。1表示1分錢。只能是整形。
        	"trade_type" => 'APP'
    	);
	$order['sign'] = createWechatSign($order);
	$xml = createXml($order);
	$result = curlWechatApi(WECHAT_UNIFIEDORDER_URL,$xml);
	//判斷是否在微信後臺成功生成一個訂單
	if($result->return_code == 'SUCCESS' && $result->result_code == 'SUCCESS'){
		$prepay=array(
            	    "noncestr" => $result->nonce_str,
            	    "prepayid" => $result->prepay_id,//上一步請求微信伺服器得到nonce_str和prepay_id引數。
            	    "appid"=>WECHAT_APP_ID,
            	    "package"=>"Sign=WXPay",
            	    "partnerid"=>WECHAT_MCH_ID,
            	    "timestamp"=>sprintf('%s',time()),
        	);
        	$prepay['sign'] = createWechatSign($prepay);
        	$prepay['success'] = true;
	}
	else{
		
		$prepay=array(
            	     "success" => false,
            	     "noncestr"=>"",
            	     "prepayid"=>"",
            	     "appid"=>WECHAT_APP_ID,
            	     "package"=>"Sign=WXPay",
            	     "partnerid"=>WECHAT_MCH_ID,
            	     "timestamp"=>"".time(),
		     "sign" => "",
            	     "return_msg"=>sprintf('%s',$result->return_msg)
        	);




	}
	return $prepay;
}

(7)微信支付通知回撥
function notify(){
	$xml = file_get_contents('php://input');
	$result = simplexml_load_string($xml,null,LIBXML_NOCDATA);
	//判斷引數是否合理,微信訂單是否存在
	if(is_object($result) && property_exits($result,'transaction_id') && property_exists($result,'out_trade_no')
	{
		$wechatOrderInfo = orderOquery($result->transaction_id,$result->out_trade_no);
		//微信訂單不存在,終止執行,並進行日誌記錄
		if($wechatOrderInfo->return_code != 'SUCCESS' || $wechatChatOrderInfo->trade_state != 'SUCCESS')
		{
			addLog($xml,'微信訂單不存在',json_encode($wechetOrderInfo));
			$str = "<xml><return_code><![CDATA[SUCCESS]]></return_code><return_msg><![CDATA[OK]]></return_msg></xml>";
			echo $str;
			exit();
		}
	}
	//判斷訂單在資料庫中是否已經付款,付款終止(省略)
	if($wechatOrderInfo->return_code == 'SUCCESS' && $wechatOrderInfo->result_code == 'SUCCESS'){
		//處理業務邏輯
	}
	//失敗處理
}