微信支付(前端流程)及遇到的坑

支付中的微信支付在上线中出了问题,反思了下原因:

1.测试时因为不能在测试环境支付,所以就没有测试,自己也没有再去验证。(即使是无法测试环境测的,没有把握也还是要自己测一遍,最起码代码要全,流程假数据能走通)

2.微信支付分普通浏览器支付和微信浏览器调起微信支付。其中微信浏览器调起微信支付会比较麻烦

3.微信浏览器调起微信支付需要商户配置允许的支付链接,否则会提示支付的链接无效。

———————————————————————————————————————

下面就是如何进行的微信支付

可参考的微信支付的官网文档链接

https://pay.weixin.qq.com/wiki/doc/api/jsapi.php?chapter=7_3

https://pay.weixin.qq.com/wiki/doc/api/jsapi.php?chapter=7_7&index=6

  1. 首先要在微信商户平台(pay.weixin.qq.com)上配支付的链接,否则在实际操作中,最后支付时提示“当前页面的ULR未注册”。

  2. 支付时,接口中要求传用户openid,而获取openid则需要在公众平台设置获取openid的域名,只有被设置过的域名才是一个有效的获取openid的域名,否则将获取失败。(这也是为什么测试环境无法测试的原因,因为域名不同)

  3. 对于前端来说,首先页面要做的第一步分辨是否是微信浏览器还是普通浏览器

    if(navigator.userAgent.indexOf("MicroMessenger")>-1){//微信浏览器
        terminalType=3;
    }else if(/Android|webOS|iPhone|iPod|BlackBerry/i.test(navigator.userAgent)) {//普通浏览器
        terminalType=2;
    }

     

  4.  当发现是微信浏览器后区分是IOS还是安卓手机,分别请求不同的链接(相当于调用接口)

    if (navigator.userAgent.indexOf("MicroMessenger") > -1) { //微信浏览器
        if (!!navigator.userAgent.match(/\(i[^;]+;( U;)? CPU.+Mac OS X/)) { //ios
            window.location.href = "https://open.weixin.qq.com/connect/oauth2/authorize?appid=xxxxxxxxx&redirect_uri=https://执行支付页面.html&response_type=code&scope=snsapi_base&state=1#wechat_redirect";
        } else {//安卓手机
            window.location.href = "https://open.weixin.qq.com/connect/oauth2/authorize?appid=xxxxxxxxx&redirect_uri=https://执行支付页面.html%0A&response_type=code&scope=snsapi_base&state=123#wechat_redirect";
        }
    } 

    这里其实我没懂为什么区分IOS还是安卓,上网看的案例没有区分安卓还是IOS,但是之前的是这么写的,而且这样确实可以成功,所以还是照着之前的逻辑没有动。

这个链接其实是个Get方法请求的接口。关于这个链接(接口)的相关配置参数可以参考这个链接

https://www.cnblogs.com/hejun26/p/9908887.html,里面讲的很详细。

5.请求上述链接(接口)后会得到一个返回链接:https://充值页面.html?code=xxxxxxxxxxxxx&state=123

这个链接里有code参数,利用一个函数getQueryString得到,(注意:获得的参数不包括state=123部分哦)

code = getQueryString("code");

//获得url参数
function getQueryString(name) {
    var reg = new RegExp("(^|&)" + name + "=([^&]*)(&|$)", "i");
    var r = window.location.search.substr(1).match(reg);
    if (r != null) return unescape(r[2]);
    return null;
}

6.对于我就是前台传包括code的一些参数给后台。对于后台,把code传进去获得返回值

String url = "https://api.weixin.qq.com/sns/oauth2/access_token?appid="+ WECHAT_ACCOUNT_APPID +"&secret="+WECHAT_ACCOUNT_SECRET + "&code=" + code + "&grant_type=" + WECHAT_ACCOUNT_GRANTTYPE ;

7.前端获得后端返回值后,得到appid,timeStamp,noceStr,package,paySign这几个参数,进行判断,执行以下代码

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(appid,timeStamp,nonceStr,package,paySign);
}

onBridgeReady: function(appId, timeStamp, nonceStr, package, paySign) {
    WeixinJSBridge.invoke(
        'getBrandWCPayRequest', {
            "appId": appId, //公众号名称,由商户传入
            "timeStamp": timeStamp, //时间戳,自1970年以来的秒数
            "nonceStr": nonceStr, //随机串
            "package": package,
            "signType": "MD5", //微信签名方式:
            "paySign": paySign //微信签名
        },
        function(res) {
            if (res.err_msg == "get_brand_wcpay_request:ok") {
                // 使用以上方式判断前端返回,微信团队郑重提示:
                //res.err_msg将在用户支付成功后返回ok,但并不保证它绝对可靠。
                window.location.href = "支付成功跳转页面";
            }
        }
    );
}

 

其中碰到的问题

1.自测的时候,想页面调试,但是微信浏览器的链接无法在电脑打开。就是下面的这个链接

https://open.weixin.qq.com/connect/oauth2/authorize?appid=XXXXXXXXX&redirect_uri=https://ABC.html%0A&response_type=code&scope=snsapi_base&state=123#wechat_redirect

这种类型的链接是无法在普通浏览器(电脑端)打开的,在电脑上下载微信开发者工具,然后再打开。会提示要公众号绑定你的开发者微信号。(我没绑定,实际上我把链接传手机上,用手机打开,然后复制链接,获得Get方法请求这个微信链接的返回值。怕麻烦的童鞋可以这样试试,但是只限于线上环境存在https://ABC.html这个页面才可以)。

2.在微信开发者工具里模拟支付时,最后 WeixinJSBridge.invoke会报错:chooseWXPay:fail, the permission value is offline verifying,但是实际上用真机的时候可以调通。

3.前端传后台时需要一个cip参数,用来放用户的位置和IP信息,这里我们用的是http://pv.sohu.com/cityjson?ie=utf-8这个链接直接获得。在测试环境里引入这个链接没有问题。



cip = returnCitySN.cip;

但在实际线上环境里会报错,因为我们的域名是https,在https里引入http现在被判断为不合法,[ HTTPS页面里动态的引入HTTP资源,比如引入一个js文件,会被直接block掉的。在HTTPS页面里通过AJAX的方式请求HTTP资源,也会被直接block掉的。]

参考链接:https://www.cnblogs.com/webARM/p/5728695.html

网上有的解决方法是引入方式改为:

但是在电脑端微信开发者工具上,我测试的时候发现依然报错:https://pv.sohu.com/cityjson?ie=utf-8 net::ERR_CONNECTION_ABORTED; Uncaught ReferenceError: returnCitySN is not defined

不过在实际的手机上可以正常运行。

你可能感兴趣的:(前端)