业务场景
应公司需求,需要在项目中接入支付宝h5支付,微信h5支付和微信公众号支付功能,本编主要讲述支付踩坑和h5支付后跳转的回调问题
微信h5支付
微信h5支付时需要校验下单域名,微信从referer中获取到后与微信后台中设置的支付域名进行校验,若不符则不能支付成功,报错如下
后端希望由前端在下单时传入referer瞒过微信校验,然而前端并不能直接改变’源’,所以只能尽可能在保证代码逻辑的前提下,发布到测试环境(微信校验的referer域名)去测试支付,
下单成功的返回值如下"https://wx.tenpay.com/cgi-bin/mmpayweb-bin/checkmweb?prepay_id=wx20161110163838f231619da20804912345&package=1037687096&redirect_url=https%3A%2F%2Fwww.wechatpay.com.cn
",redirect_url可由前端自行拼接,作为支付成功后的回调地址,其中"?"后的参数选需要使用encodeURIComponent
进行转码,否则参数会被删除,回调只有域名,血淋淋的教训-…-
楼主回调如下
var url = "https://" + window.location.host + "/dev/?id=1
url = encodeURIComponent(url)
window.location.href = res.h5Pay + "&redirect_url=" + url
res.h5Pay为下单成功未拼接redirect_url的返回值,可参考微信官方文档
微信公众号支付
微信公众号支付比较无脑,走流程就行,登录=>token=>下单=>支付
下单成功后会返回微信支付所需要的参数,传入微信支付方法中就ok,详细说明可参考微信官方文档
function weixinPay (params) {
WeixinJSBridge.invoke(
'getBrandWCPayRequest',
{
"appId": params.appId, //公众号名称,由商户传入
"timeStamp": params.timeStamp, //时间戳,自1970年以来的秒数
"nonceStr": params.nonceStr, //随机串
"package": params.package,
"signType": params.signType, //微信签名方式
"paySign": params.paySign //微信签名
},
function(res) {
if (res.err_msg === "get_brand_wcpay_request:ok") {
console.log('支付成功')
} else if (res.err_msg === "get_brand_wcpay_request:cancel") {
console.log('取消支付')
} else if (res.err_msg === "get_brand_wcpay_request:fail") {
console.log('支付失败')
}
}
)
}
注:在此告诫前端的小伙伴们,不要在微信公众号支付的成功回调中调后端的方法去通知后端该订单已支付,微信统一下单文档中有介绍后端如何配置微信支付成功后的异步回调,由于微信公众号支付成功后不会刷新页面,所以可以在res.err_msg === "get_brand_wcpay_request:ok
时做一些前端的逻辑处理
支付宝h5支付
相对来说,支付宝的h5支付还是比较友好的,不需要校验referer,回调支付后回调地址也没提供前端拼接的方法,对前端来说只是调了个下单接口,打开支付宝支付,完成支付后只需要处理下页面刷新的问题就可以,本人下单成功后代码如下
window.location.href = res.alipay_str
对比微信h5支付少了redirect_url的转码和拼接
首次发文,有错请指出,会及时纠正