排行榜 统计
  • 建站日期:2020-07-15
  • 文章总数:63 篇
  • 评论总数:1454 条
  • 分类总数:6 个
  • 最后更新:2023年03月28日
原创精品教程

Node.js关于微信支付V3版相关处理方法

本文阅读 3 分钟
首页 精品教程 正文

Node.js关于微信支付V3版相关处理方法

今天给大家写一个关于Node.js接入微信支付V3接口时一些毕竟复杂的点,主要就是请求签名Authorization、调起支付签名、回调参数解密等。

请求签名Authorization

​在微信支付V3接口中,商户需要使用自身的私钥对API URL、消息体等关键数据的组合进行SHA-256 with RSA签名。请求的签名信息通过HTTP头Authorization传递,具体说明可以去看签名生成指南。没有携带签名或者签名验证不通过的请求,都不会被执行,并返回401 Unauthorized 。

那么如何生成这个Authorization呢,这个请求头,最麻烦的地方就是如何去生成

signature,其中我们使用jsrsasign模块来进行SHA256 with RSA加密,可以查看如下代码:


const {KJUR, hextob64} = require('jsrsasign')
​
rsaSign(content, privateKey, hash='SHA256withRSA'){
    const signature = new KJUR.crypto.Signature({
            alg: hash,
            prvkeypem: privateKey
        })
    signature.updateString(content)
    const signData = signature.sign()
    // 将内容转成base64
    return hextob64(signData)
}
​
//调用这个函数
let signature = this.rsaSign(`${method}\n${pathname}\n${timestamp}\n${onece_str}\n${bodyParamsStr}\n`,this.private_key,'SHA256withRSA')
​
//获取到signature后就可以获取到Authorization了
 let Authorization = `WECHATPAY2-SHA256-RSA2048 mchid="${mchid}",nonce_str="${onece_str}",timestamp="${timestamp}",signature="${signature}",serial_no="${serial_no}"`
​

其中mchid:商户号,onece_str:随机字符,timestamp:时间戳,serial_no:商户API证书序列号。这样在请求时在请求头里加入就可以了,如下:

 headers:{
     'Content-Type':'application/json',
     'Accept':'application/json',
     'Authorization':Authorization
}

调起支付签名

通过上述请求后可以得到预支付交易会话标识prepay_id,然后我们需要再次进行签名,用于调起微信支付,代码如下:


paysign(options) { 
     let timeStamp = this.createTimeStamp(), //时间戳
         nonceStr = this.randomString(), //32位随机数
         Ppackage = `prepay_id=${options}`, //prepay_id
         signType = 'RSA'; //加签方式
     let PpaySign = `${this.appId}\n${timeStamp}\n${nonceStr}\n${Ppackage}\n`; //需要加签的字段拼接
     let cryptStr = this.rsaSign(PpaySign, this.privateKey, 'SHA256withRSA'); //生成签名
     let paySign = cryptStr;
     return {
         timeStamp,
         nonceStr,
         package: Ppackage,
         signType,
         paySign
     };
}

​这里的rsaSign()函数就是上文提到的加密函数,只是这里的content参数有所不同而已,这样我们就可以直接调用起微信支付了。

回调参数解密

微信支付的回调都是需要验证解密之后才可以得到订单数据的,所以解密也是比较复杂的地方,这里我们使用crypto模块,对参数进行解密,代码如下:


const crypto = require("crypto");
​
 decode(params) {
        const AUTH_KEY_LENGTH = 16;
        // ciphertext = 密文,associated_data = 填充内容, nonce = 位移
        const { ciphertext, associated_data, nonce } = params;
        // 密钥
        const key_bytes = Buffer.from(this.apiv3_private_key, 'utf8');
        // 位移
        const nonce_bytes = Buffer.from(nonce, 'utf8');
        // 填充内容
        const associated_data_bytes = Buffer.from(associated_data, 'utf8');
        // 密文Buffer
        const ciphertext_bytes = Buffer.from(ciphertext, 'base64');
        // 计算减去16位长度
        const cipherdata_length = ciphertext_bytes.length - AUTH_KEY_LENGTH;
        // upodata
        const cipherdata_bytes = ciphertext_bytes.slice(0, cipherdata_length);
        // tag
        const auth_tag_bytes = ciphertext_bytes.slice(cipherdata_length, ciphertext_bytes.length);
        const decipher = crypto.createDecipheriv(
            'aes-256-gcm', key_bytes, nonce_bytes
        );
        decipher.setAuthTag(auth_tag_bytes);
        decipher.setAAD(Buffer.from(associated_data_bytes));
​
        const output = Buffer.concat([
            decipher.update(cipherdata_bytes),
            decipher.final(),
        ]);
        return output;
}

其中就是params回调返回值里的resource参数,这样就可以得到回调返回的信息了。

更多内容可以去关注我的公众号:阳光艺创站

原创文章,作者:小创果,如若转载,请注明出处:http://www.i4qq.com/jpjc/nodejsgywxzfv3.html
Typecho小程序接入百度登录详细教程
« 上一篇 06-27
Node.js中常见的参数字典升序排序及拼接
下一篇 » 07-19

发表评论

成为第一个评论的人

作者信息

热门文章

标签TAG

热评文章