1、需求:由于公司微信公衆号新增充值業務,是以需要在公衆号裡h5頁面裡接入微信支付
2、分析:其實微信支付開發文檔寫的很詳細,隻要按照步驟一步一步來,基本問題不大,但我還是遇到了形形色色大大小小的坑,在此記錄,希望有相似需求的小夥伴有所收獲~
① 首先确認公衆号支付的定義(截圖來自微信商戶平台)
![](https://img.laitimes.com/img/_0nNw4CM6IyYiwiM6ICdiwiIwczLcVmds92czlGZvwVP9EUTDZ0aRJkSwk0LcxGbpZ2LcBDM08CXlpXazRnbvZ2LcRlMMVDT2EWNvwFdu9mZvwVP9cXT4VlaONTQU1EM4wmYwhGWhxGZzwEMW1mY1RzRapnTtxkb5ckYplTeMZTTINGMShUYvwFd4VGdvwlMvw1ayFWbyVGdhd3P5MTOxcDM1ETNyATM4EDMy8CX0Vmbu4GZzNmLn9Gbi1yZtl2Lc9CX6MHc0RHaiojIsJye.jpg)
② 業務流程(圖檔來自微信商戶平台)
③ 要想完成這個功能,需要業務辦理人員、背景api人員及前端h5人員共同的合作,每一環都很重要。在此僅大部分從前端角度出發,如何根據以上流程圖一步步完成這個需求。
3、過程
業務申請(業務申請工作由業務辦理人員負責,不包括在以上的流程圖中,但卻是所有業務的基礎)
① 申請公衆号
前往公衆平台注冊公衆号,選擇帳号類型為服務号、或政府/媒體訂閱号,并完成微信認證。 前往申請
② 送出資料
填寫申請單(售賣商品場景請選擇“公衆号”),并按指引完成賬戶驗證。立即申請 填寫指引
③ 簽署協定
資料稽核通過後,需線上完成協定簽署,以獲得正式交易權限和各項産品能力。 簽約指引
④ 綁定場景
登入公衆平台,确認商戶号和公衆号的綁定關系。 綁定指引
平台相關設定(平台相關設定,也是後面接口能順利調通息息相關,不然會報各種錯)
① 設定授權域名
開發公衆号支付時,在統一下單接口中要求必傳使用者openid,而擷取openid則需要您在公衆平台設定擷取openid的域名,隻有被設定過的域名才是一個有效的擷取openid的域名,否則将擷取失敗。
重點:
- 這裡隻用填寫域名,不用添加http或https協定,不然會報錯“域名或路徑格式不正确,請參考注意事項” ;
- 上傳txt檔案後,必須外網可以通路的到,不然會報錯“無法通路‘你域名’指向的web伺服器(或虛拟主機)的目錄,請檢查網絡設定”。
② 設定JSAPI支付授權目錄
公衆号支付在請求支付的時候會校驗請求來源是否有在商戶平台做了配置,是以必須確定支付目錄已經正确的被配置,否則将驗證失敗,請求支付不成功。
重點:
- 這裡填寫的不僅是域名,且必須包括協定(http或https都不能寫錯),不然在調取微信支付元件時拿到的回調參數res.err_msg會為:get_brand_wcpay_request:fail,即:調取微信支付元件失敗!
③ 設定 IP白名單
通過appId及appSecret調用擷取access_token及openId接口時,需要設定通路來源IP為白名單。
重點:
- 由于擷取openId的接口由服務端調用,則需将你伺服器ip位址填進去,包括測試環境與正式環境
- 如若未設定IP白名單,則會報“擷取微信公衆号授權失敗,請稍後重試!錯誤代碼-40164”,
④ 綁定開發者微信号
在微信開發者工具調試公衆号頁面時,要求開發者微信号與公衆号建立綁定關系。
第一步:微信網頁授權
要調起的支付元件,必須先經過使用者網頁授權,擷取使用者對于公衆号的openId
① 使用者同意授權,擷取code
引導使用者打開如下連結:
https://open.weixin.qq.com/connect/oauth2/authorize?appid=APPID&redirect_uri=REDIRECT_URI&response_type=code&scope=SCOPE&state=STATE#wechat_redirect
參數說明:
如果使用者同意授權(即:打開上面的授權連結),頁面将跳轉至: redirect_uri/?code=CODE&state=STATE
code說明 :
code作為換取access_token的票據,每次使用者授權帶上的code将不一樣;
code隻能使用一次,5分鐘未被使用自動過期。
在重定向的頁面使用 getUrlParams 函數即可,擷取到code,然後通過接口傳給服務端
getUrlParams (name) {
let reg = new RegExp('(^|&)' + name + '=([^&]*)(&|$)', 'i')
let params = window.location.search.substr(window.location.search.indexOf('?') + 1)
let r = params.match(reg)
return r !== null ? decodeURI(r[2]) : null
}
② 通過code換取網頁授權openId
由于涉及到敏感參數,這一步由服務端實作,請求方法:
https://api.weixin.qq.com/sns/oauth2/access_token?appid=APPID&secret=SECRET&code=CODE&grant_type=authorization_code
參數說明:
正确時傳回的JSON資料包如下:
到這裡,我們便經過了使用者網頁授權,擷取到了使用者對于公衆号的openId(微信使用者在商戶對應appid下的唯一辨別)
第二步:服務端調取微信API統一下單接口
接口連結:
https://api.mch.weixin.qq.com/pay/unifiedorder
其中一個必傳的參數就是上面擷取到的:openId
這裡參數太多,我就不一一列舉了,可以自己看文檔。
我們需要的提供幾個重要資料為:
① appid (公衆賬号ID):參數
② mch_id(商戶号):參數
③ appkey(api安全密鑰):生成簽名sign必要字元串(key設定路徑:微信商戶平台(pay.weixin.qq.com)–>賬戶設定–>API安全–>密鑰設定)
正确時傳回的字段如下:
到這裡,我們便擷取到了前端h5調起支付元件的重要資料:nonceStr、package、paySign
,再加上appId、timeStamp、signType,用json包裹後返給前端h5。
第三步:微信内H5調起支付
① 由于微信WeixinJSBridge内置對象加載需要一定的時間,是以必須等WeixinJSBridge内置對象加載完成後才可以調起支付元件,不然會報錯:“WeixinJSBridge is undefined”,如下:
if (typeof WeixinJSBridge == "undefined"){
if( document.addEventListener ){
document.addEventListener('WeixinJSBridgeReady', onBridgeReady, false);
}else if (document.attachEvent){
document.attachEvent('WeixinJSBridgeReady', onBridgeReady);
document.attachEvent('onWeixinJSBridgeReady', onBridgeReady);
}
}else{
onBridgeReady();
}
② 調起函數:WeixinJSBridge.invoke(‘getBrandWCPayRequest’, option, callback)
參數如下(均為從服務端傳回):
// 參數 data 為服務端傳回json
function onBridgeReady(data){
WeixinJSBridge.invoke(
'getBrandWCPayRequest', {
appId: data.appId, // 公衆号id
timeStamp: data.timeStamp, // 時間戳
nonceStr: data.nonceStr, // 随機串
package: data.package, // 訂單詳情擴充字元串
signType: data.signType, // 微信簽名方式
paySign: data.paySign // 微信簽名
},
function(res){
if(res.err_msg == "get_brand_wcpay_request:ok" ){
//res.err_msg将在使用者支付成功後傳回ok,這時調取你本身服務端業務查詢,若已支付成功,則跳轉成功頁面,展示給使用者。
}
});
}
③ 調起支付元件成功表現:
④ 傳回結果說明:
到這裡,res.err_msg将在使用者支付成功後傳回ok,這時調取你本身服務端業務查詢,若已支付成功,則跳轉成功頁面,展示給使用者,至此,公衆号微信支付功能實作 ~