一、server 端
1.配置授权目录地址
授权目录地址即为我们支付页面的的地址的上一级目录
(如为Vue项目, 你的路由中有锚点,"/#/" 也算一级目录)
2. 创建请求参数
创建请求参数,仔细阅读微信文档, 尤其是每个字段的《描述》
A. 创建生成签名参数
SortedMap<Object, Object> parameters = new TreeMap<Object, Object>();
parameters.put("appid","XXXXXXXXX");// 公众账号id
parameters.put("mch_id", "XXXXXX");// 商户号
parameters.put("nonce_str", "b1089cb0231011e7b7e1484520356fdc");// 随机字符串
parameters.put("body", "测试商家-商品类目");// 商品详情
parameters.put("detail", "在线购物");// 商品描述
parameters.put("trade_type", "JSAPI");// 交易类型 trade_type=JSAPI时(即公众号支付),必须传OpenId,
parameters.put("sign_type", "MD5");// 商户订单号
parameters.put("fee_type", "CNY");// 商户订单号
parameters.put("out_trade_no", "20161909105959000000111RT8");// 商户订单号
parameters.put("total_fee", "1");// 金钱
parameters.put("device_info","WEB"); // 设备号, pc或公众号支付传WEB
parameters.put("notify_url", "https://baidu.com/");// 支付成功回调地址
parameters.put("spbill_create_ip", "127.0.0.1");// 终端IP,
parameters.put("openid", "o0pcHVtc");// 用户OpenId
B.生成签名 MD5
微信签名算法:根据(上传参数的key-value加上key-支付秘钥 )来生成签名
C. 将生成的签名在加入 parameters对象中
parameters.put("sign", "上面生成的签名");// 商户订单号
将 parameters 对象转换为XML, 你也可以选择手动拼接为XML
3. 统一下单
请求 https://api.mch.weixin.qq.com/pay/unifiedorder 传入XML ,
此处注意, 传给WX的XML数据与生成签名的数据保持一致, 否则会导致签名不合法
4. 统一下单成功
{
"return_code":"SUCCESS",
"return_msg":"OK",
"appid":"w70ec43b",
"mch_id":"10000100",
"nonce_str":"IITRi8Ilz1Jc",
"openid":"oUjWeS6o",
"sign":"7972F",
"result_code":"SUCCESS",
"prepay_id":"wx20779950874",
"trade_type":"JSAPI"
}
此处我们能用到的 就只有 "prepay_id":"wx209950874", 这一条数据,
5. 创建h5支付对象
此处只会用到统一下单成功 返回的 "prepay_id"数据,其它数据看看就行了; 也与统一下单创建的 parameters无关
SortedMap<Object, Object> web_parameters = new TreeMap<Object, Object>();
web_parameters.put("appId", "appId");
//时间, 微信要求的时间是10位到秒, getTime是13位到毫米
web_parameters.put("timeStamp", (new Date().getTime()+"").substring(0,10));
//从新生成的的随机字符串, 与统一下单的随机字符和统一下单成功返回的随机字符串都没有关系
web_parameters.put("nonceStr", "");
// 将统一下单成功返回的 "prepay_id":"wx209950874", 传入,
web_parameters.put("package", "prepay_id="+map.get("prepay_id"));
web_parameters.put("signType", "MD5");
再次生成签名 web_parameters+支付秘钥key生成, 逻辑与统一下单相同
web_parameters.put("paySign", WxComUtil.createSignMD5(UTF8, web_parameters, "支付秘钥")); //加入由 web_parameters 生成的 签名
将 web_parameters 对象返回给 前端
6.支付成功回调
支付成功后微信会主动请求你的notify_url回调地址, 只需解析微信参入的XML参数,做相应处理即可
二、H5端·
将server端传入的参数 一一对应填入,WeixinJSBridge对象为微信浏览器内置对象,只需调用该方法即可,
function onBridgeReady(){
WeixinJSBridge.invoke(
'getBrandWCPayRequest', {
"appId":"w43b", //公众号名称,由商户传入
"timeStamp":"134", //时间戳,自1970年以来的秒数
"nonceStr":"e61463ccfbbb444", //随机串
"package":"prepay_id=u802345jgfjsdfgsdg888",
"signType":"MD5", //微信签名方式:
"paySign":"70EA57FADD89" //微信签名
},
function(res){
if(res.err_msg == "get_brand_wcpay_request:ok" ) {} // 使用以上方式判断前端返回,微信团队郑重提示:res.err_msg将在用户支付成功后返回 ok,但并不保证它绝对可靠。
}
);
}
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();
}
问题
1. 路径url 未注册, 检查第一步配置的授权目录
2. 签名错误, 检查生成签名的参数, 与请求wx的参数是否一致