美文网首页node微信支付
基于nodejs后端微信支付接口

基于nodejs后端微信支付接口

作者: 伯纳乌的追风少年 | 来源:发表于2018-10-19 14:37 被阅读0次

本文不谈框架,不谈代码组织结构,只谈怎么实现,

1,微信移动端支付流程如下:

这个流程可以微信app支付文档找到,最重要的就是统一下单这个接口,可以简化一下这个接口,简化后的流程如下:

app给后端传:金额total_fee,32位的商户订单号out_trade_no,支付成功后的回调地址notify_url 这最基本的3个参数,后端通过微信的统一下单接口https://api.mch.weixin.qq.com/pay/unifiedorder 生成一些参数,在返回给app端,app根据这些参数再加上微信授权,调起微信支付,支付成功后返回到商家app,微信后台自动检测是否支出成功,成功后调用app传给微信后端的回调地址notify_url接口,app后端在回调地址的接口中处理什么数据库改写操作,发消息等等的动作。

nodejs需要的一些包:

"dependencies": {
    "crypto": "^1.0.1",
    "express": "^4.16.3",
    "request": "^2.85.0",
    "xmlreader": "^0.2.3"
  }

xmlreader处理xml的工具包,crypto数据加密包

2,工具类util.js

var xmlreader = require("xmlreader");
var fs = require("fs");
 
 
var wxpay = {
 
    //把金额转为分
    getmoney: function (money) {
        return parseFloat(money) * 100;
    },
 
    // 随机字符串产生函数  
    createNonceStr: function () {
        return Math.random().toString(36).substr(2, 15);
    },
 
    // 时间戳产生函数  
    createTimeStamp: function () {
        return parseInt(new Date().getTime() / 1000) + '';
    },
 
    //签名加密算法
    paysignjsapi: function (appid, body, mch_id, nonce_str, notify_url, out_trade_no, spbill_create_ip, total_fee, trade_type, mchkey) {
        var ret = {
            appid: appid,
            mch_id: mch_id,
            nonce_str: nonce_str,
            body: body,
            notify_url: notify_url,
            out_trade_no: out_trade_no,
            spbill_create_ip: spbill_create_ip,
            total_fee: total_fee,
            trade_type: trade_type
        };
        console.log('ret==', ret);
        var string = raw(ret);
        var key = mchkey;
        string = string + '&key=' + key;
        console.log('string=', string);
        var crypto = require('crypto');
        return crypto.createHash('md5').update(string, 'utf8').digest('hex').toUpperCase();
    },
    //签名加密算法,第二次的签名
    paysignjsapifinal: function (appid,mch_id,prepayid,noncestr,timestamp,mchkey) {
        var ret = {
            appid: appid,
            partnerid: mch_id,
            prepayid: prepayid,
            package: 'Sign=WXPay',
            noncestr: noncestr,
            timestamp: timestamp,
        };
        console.log('retretret==', ret);
        var string = raw(ret);
        var key = mchkey;
        string = string + '&key=' + key;
        console.log('stringstringstring=', string);
        var crypto = require('crypto');
        return crypto.createHash('md5').update(string, 'utf8').digest('hex').toUpperCase();
    },
    getXMLNodeValue: function (xml) {
        // var tmp = xml.split("<"+node_name+">");
        // console.log('tmp',tmp);
        // var _tmp = tmp[1].split("</"+node_name+">");
        // console.log('_tmp',_tmp);
        // return _tmp[0];
        xmlreader.read(xml, function (errors, response) {
            if (null !== errors) {
                console.log(errors)
                return;
            }
            console.log('长度===', response.xml.prepay_id.text().length);
            var prepay_id = response.xml.prepay_id.text();
            console.log('解析后的prepay_id==',prepay_id);
            return prepay_id;
        });
    }
 
}
function raw(args) {
    var keys = Object.keys(args);
    keys = keys.sort()
    var newArgs = {};
    keys.forEach(function (key) {
        newArgs[key] = args[key];
    });
    var string = '';
    for (var k in newArgs) {
        string += '&' + k + '=' + newArgs[k];
    }
    string = string.substr(1);
    return string;
}
 
module.exports = wxpay;

3,调用app.js

appid,appsecret是微信开放平台的数据,mchid是微信对应的商户平台id,mchkey是商户平台陪的安全秘钥。

var express = require('express');
var request = require('request');
var xmlreader = require("xmlreader");
var fs = require("fs");
 
var app = express();
 
var wxpay = require('./util');
 
 
var appid     = 'wx28f86efd25cc3312';
var appsecret = 'b8687555bf947b1947b62767c448723';
var mchid     = '1499403456'
var mchkey    = '8r435jVd7yA0354nsvkxb4cN3x7Se4322';
var wxurl     = 'http://XXXXXXXXX/weixinNotify.action';
 
app.get('/',(req,res)=>{
    
    //首先拿到前端传过来的参数
    let orderCode = req.query.orderCode;
    let money     = req.query.money;
    let orderID   = req.query.orderID;
 
    console.log('APP传过来的参数是',orderCode+'----'+money+'------'+orderID+'----'+appid+'-----'+appsecret+'-----'+mchid+'-----'+mchkey);
 
    //首先生成签名sign
    appid
    let mch_id = mchid;
    let nonce_str = wxpay.createNonceStr();
    let timestamp = wxpay.createTimeStamp();
    let body = '测试微信支付';
    let out_trade_no = orderCode;
    let total_fee = wxpay.getmoney(money);
    let spbill_create_ip = req.connection.remoteAddress;
    let notify_url = wxurl;
    let trade_type = 'APP';
 
    let sign = wxpay.paysignjsapi(appid,body,mch_id,nonce_str,notify_url,out_trade_no,spbill_create_ip,total_fee,trade_type,mchkey);
 
    console.log('sign==',sign);
 
    //组装xml数据
    var formData  = "<xml>";
    formData  += "<appid>"+appid+"</appid>";  //appid
    formData  += "<body><![CDATA["+"测试微信支付"+"]]></body>";
    formData  += "<mch_id>"+mch_id+"</mch_id>";  //商户号
    formData  += "<nonce_str>"+nonce_str+"</nonce_str>"; //随机字符串,不长于32位。
    formData  += "<notify_url>"+notify_url+"</notify_url>";
    formData  += "<out_trade_no>"+out_trade_no+"</out_trade_no>";
    formData  += "<spbill_create_ip>"+spbill_create_ip+"</spbill_create_ip>";
    formData  += "<total_fee>"+total_fee+"</total_fee>";
    formData  += "<trade_type>"+trade_type+"</trade_type>";
    formData  += "<sign>"+sign+"</sign>";
    formData  += "</xml>";
 
    console.log('formData===',formData);
 
    var url = 'https://api.mch.weixin.qq.com/pay/unifiedorder';
 
    request({url:url,method:'POST',body: formData},function(err,response,body){
        if(!err && response.statusCode == 200){
            console.log(body);
 
            xmlreader.read(body.toString("utf-8"), function (errors, response) {
                if (null !== errors) {
                    console.log(errors)
                    return;
                }
                console.log('长度===', response.xml.prepay_id.text().length);
                var prepay_id = response.xml.prepay_id.text();
                console.log('解析后的prepay_id==',prepay_id);
 
 
                //将预支付订单和其他信息一起签名后返回给前端
                let finalsign = wxpay.paysignjsapifinal(appid,mch_id,prepay_id,nonce_str,timestamp,mchkey);
 
                res.json({'appId':appid,'partnerId':mchid,'prepayId':prepay_id,'nonceStr':nonce_str,'timeStamp':timestamp,'package':'Sign=WXPay','sign':finalsign});
 
            });
 
 
        }
    });
 
})
 
 
app.listen(3000,()=>{
    console.log('服务器启动了....');
});

相关文章

  • 基于nodejs后端微信支付接口

    本文不谈框架,不谈代码组织结构,只谈怎么实现, 1,微信移动端支付流程如下: 这个流程可以微信app支付文档找到,...

  • python3实现微信支付和提现

    微信支付--V3接口 小程序支付 前提:前端获取微信用户的临时code值给到后端,后端根据code值调用微信API...

  • 微信公众号支付

    微信公众号支付使用的是JSAPI支付,后端调用微信支付demo中统一下单的接口获取支付参数返回给前端,在公众号中直...

  • 微信pc端扫码支付前后端流程(Nodejs)

    大致流程 不必须事先微信登录, 前端准备好支付后, 告诉后端, 后台发送本次交易的数据到微信联合支付接口, 返回...

  • nodejs 微信支付 (koa 框架)

    nodejs实现微信支付,koa框架的接入流程,此文档通过测试,在小程序/微信公众号的后端代码中使用, 已经用于生...

  • JSSDK调用

    微信JS-SDK是微信公众号平台面向网页开发这提供基于微信内的网页开发工具包。 接口大类分为:分享接口、微信支付、...

  • 详解微信公众号支付开发

    前言 由于学校有个项目类似轻松筹,基于微信支付,便深入了解微信支付流程及其接口调用,其业务流程有些繁琐,但其策略是...

  • PHP支付接口教程,详解微信支付(三)

    微信APP支付 接口申请 微信APP支付和其他支付接口最大的不同在于——申请方式无论是JS支付、PC支付还是WEB...

  • 重构 - Http请求方式重写

    背景 后端基于 restful 建议,定义了 patch, put 等请求方法,但是微信小程序,支付宝小程序却没有...

  • nodejs 微信支付

    微信支付比较简单 基本的步骤一、app前端获取统一下单(服务器提供) 二、拿到获取到的数据调用微信sdk支付 三、...

网友评论

    本文标题:基于nodejs后端微信支付接口

    本文链接:https://www.haomeiwen.com/subject/zswyzftx.html