node.js开发微信公众号(signature验证,access_token生成,事件接收,api调用)

2018-11-0910:35:19WEB前端开发Comments3,049 views字数 3432阅读模式

如何用node.js开发微信公众号。主要内容包括signature的验证,access_token的生成,微信事件的接收,还有各种api的调用。文章源自菜鸟学院-https://www.cainiaoxueyuan.com/gcs/7769.html

准备工作

开发前需要安装好node.js,因为我是基于express框架开发的,所以装了express(框架按自己的需求选择),需要有一个微信公众号,不管是订阅号还是服务号都可以(没有的话可以用测试公众号),还需要一个公网能访问的服务器。基本的配置就这些,后面有需要的再补充。接下来,开始讲如何开发。文章源自菜鸟学院-https://www.cainiaoxueyuan.com/gcs/7769.html

一、微信公众平台配置

登录微信公众平台,没有公众号的话注册一个测试公众号(不会的点这里,扫码登录即可)。 进入到公众平台,你会看到如下界面:文章源自菜鸟学院-https://www.cainiaoxueyuan.com/gcs/7769.html

node.js开发微信公众号(signature验证,access_token生成,事件接收,api调用)

基本配置

进入到公众平台首页,首先会有一个测试号信息的appID,appsecret;并且appIDappsecret是不可以修改的(自己注册公众号的appsecret是可以重置的,操作很简单,这里不做说明);文章源自菜鸟学院-https://www.cainiaoxueyuan.com/gcs/7769.html

接口配置

接口配置信息这个模块,首次进来的是空的,需要自己配置;这里需要配置两个参数,一个是URL,还有一个是Token;如果不知道怎么配置,具体的可以看微信的wiki文档,我这里也给大家说一下我配置的时候遇到的一些坑吧!文章源自菜鸟学院-https://www.cainiaoxueyuan.com/gcs/7769.html

首先,点击修改的时候,会变成如下界面:文章源自菜鸟学院-https://www.cainiaoxueyuan.com/gcs/7769.html

node.js开发微信公众号(signature验证,access_token生成,事件接收,api调用)

注意点:文章源自菜鸟学院-https://www.cainiaoxueyuan.com/gcs/7769.html

  • URL参数说明: url填的是一个公网上部署好的接口地址(是真实存在已经部署好能够请求的接口),接口必须以http://https://开头,仅支持80端口和443端口。
  • Token参数说明: token填的是自己定义的一个标识,需要注意的一点就是这边配置好了以后,在上面那个url的接口里面设置的token需要和这个保持一致,不然配置是不会成功的。

具体的配置指南戳这里文章源自菜鸟学院-https://www.cainiaoxueyuan.com/gcs/7769.html

当你点击提交的时候,会发送一个get请求到你刚刚填写的URL地址,并且会带上4个参数,分别是:signature,timestamp,echostr,nonce,然后在服务端验证配置是否通过;
如果配置成功,则会有如下成功提示:文章源自菜鸟学院-https://www.cainiaoxueyuan.com/gcs/7769.html

node.js开发微信公众号(signature验证,access_token生成,事件接收,api调用)

如果配置失败,则会有如下失败提示:文章源自菜鸟学院-https://www.cainiaoxueyuan.com/gcs/7769.html

node.js开发微信公众号(signature验证,access_token生成,事件接收,api调用)

接口配置到这里就完成了。文章源自菜鸟学院-https://www.cainiaoxueyuan.com/gcs/7769.html

JS接口安全域名

这个配置主要是为了能够调js-sdk接口配置的,只有在该域名下,开发才能调用微信js接口(像调用二维码,上传预览文件等功能),文档也写的比较详细,这里不做过多说明。文章源自菜鸟学院-https://www.cainiaoxueyuan.com/gcs/7769.html

微信官方JS-SDK文档戳这里文章源自菜鸟学院-https://www.cainiaoxueyuan.com/gcs/7769.html

到这里,微信公众平台的配置就差不多了,接下来就可以开始服务端的开发了。文章源自菜鸟学院-https://www.cainiaoxueyuan.com/gcs/7769.html

二、node服务端开发配置

还记得微信公众平台配置的时候填写的urltoken值吗?这里就用到了,来看下面一段代码:文章源自菜鸟学院-https://www.cainiaoxueyuan.com/gcs/7769.html

const bodyParser = require('body-parser'); //处理请求参数

server.get("/", function (req, res) {
    var token = "xxxx";
    var signature = req.query.signature;
    var timestamp = req.query.timestamp;
    var echostr = req.query.echostr;
    var nonce = req.query.nonce;

    var oriArray = new Array();
    oriArray[0] = nonce;
    oriArray[1] = timestamp;
    oriArray[2] = token;
    oriArray.sort();

    var original = oriArray.join('');
    var sha = sha1(original)

    if (signature === sha) {
        //验证成功
        res.send(echostr)
    } else {
        //验证失败
        res.send({ "message": "error" })
    }

});
复制代码

还记得上面说点击提交的时候会发一个get请求吗?还说会带signature,timestamp,echostr,nonce四个参数。就是在这个接口中,判断配置是否成功的,来看下这个get请求具体做了什么事情。文章源自菜鸟学院-https://www.cainiaoxueyuan.com/gcs/7769.html

  1. 定义一个token值,需要和公众平台配置的token保持一致。
  2. 通过req.query.xxx获取请求传过来的4个参数。
  3. nonce,timestamp,token添加到一个数组中,并用sort()排序,然后把这个数组用join("")拼接成一个字符串。
  4. sha1加密生成一个密匙,最后判断通过sha1生成的signature和参数带过来的signature是否一致,一致则配置成功,不一致则配置失败。

具体可以看官方文档(文档示例是php的),文档地址 戳这里文章源自菜鸟学院-https://www.cainiaoxueyuan.com/gcs/7769.html

到这里微信开发的公众号配置和node服务端配置就完成了,接下来可以开始愉快的开发啦!文章源自菜鸟学院-https://www.cainiaoxueyuan.com/gcs/7769.html

三、用户信息处理

首先问一个问题,当用户关注公众号,发送消息的时候,开发者在哪里能接收到这些消息,并做相应的回复呢?
答案是微信公众平台配置的URLpost请求,如果说该URL的get请求是为了配置用的,那么post请求就是为了处理用户信息。文章源自菜鸟学院-https://www.cainiaoxueyuan.com/gcs/7769.html

来看下面一段代码文章源自菜鸟学院-https://www.cainiaoxueyuan.com/gcs/7769.html

var parseString = require('xml2js').parseString;

server.post("/", function (req, res) {
    try {
        var buffer = [];
        //监听 data 事件 用于接收数据
        req.on('data', function (data) {
            buffer.push(data);
        });
        //监听 end 事件 用于处理接收完成的数据
        req.on('end', function () {
            //输出接收完成的数据
            parseString(Buffer.concat(buffer).toString('utf-8'), { explicitArray: false }, function (err, result) {
                if (err) {
                    //打印错误信息
                    console.log(err);
                } else {
                    //打印解析结果
                    result = result.xml;
                    var toUser = result.ToUserName; //接收方微信
                    var fromUser = result.FromUserName;//发送仿微信
                    //判断是否是事件类型
                    if (result.Event) {
                        //处理事件类型
                        switch (result.Event) {
                            case "subscribe":
                                //关注公众号
                                break;
                            default:
                                
                        }
                    } else {
                        //处理消息类型
                        switch (result.MsgType) {
                            case "text":
                                //处理文本消息
                                break;
                            case "image":
                                //处理图片消息
                                break;
                            case "voice":
                                //处理语音消息
                                break;
                            case "video":
                                //处理视频消息
                                break;
                            case "shortvideo":
                                //处理小视频消息
                                break;
                            case "location":
                                //处理发送地理位置
                                break;
                            case "link":
                                //处理点击链接消息
                                break;
                            default:
                                
                        }
                    }
                }
            })
        });
    } catch (err) {
        res.send(err);
    }
});
复制代码

通过上面这段代码,可以看出,所有的消息处理都是在一个post中处理,大致的流程是服务端会接收一段固定格式xml的字符串,具体格式如下:文章源自菜鸟学院-https://www.cainiaoxueyuan.com/gcs/7769.html

<xml>
    <ToUserName><![CDATA[${toUser}]]></ToUserName>  //接收方
    <FromUserName><![CDATA[${fromUser}]]></FromUserName>  //发送方
    <CreateTime>${new Date().getTime()}</CreateTime>  //发送时间
    <Event>< ![CDATA[VIEW] ]></Event>    //事件类型
    <MsgType><![CDATA[text]]></MsgType>  //消息类型
    <Content><![CDATA[${content}]]></Content>  //内容
</xml>;
复制代码

当接收到xml消息后,用xml2js解析xml,根据EventMsgType做事件类型的判断,并做相应的处理,最后,res.send(xml)发送数据的时候也是要一个xml格式的数据,要注意的一点是,ToUserNameFromUserName不要弄错就可以了!文章源自菜鸟学院-https://www.cainiaoxueyuan.com/gcs/7769.html

作者:西瓜太郎酱
链接:https://juejin.im/post/5be3af8ae51d4554b54b0a0d
来源:掘金
著作权归作者所有。商业转载请联系作者获得授权,非商业转载请注明出处。文章源自菜鸟学院-https://www.cainiaoxueyuan.com/gcs/7769.html

文章源自菜鸟学院-https://www.cainiaoxueyuan.com/gcs/7769.html
  • 本站内容整理自互联网,仅提供信息存储空间服务,以方便学习之用。如对文章、图片、字体等版权有疑问,请在下方留言,管理员看到后,将第一时间进行处理。
  • 转载请务必保留本文链接:https://www.cainiaoxueyuan.com/gcs/7769.html

Comment

匿名网友 填写信息

:?: :razz: :sad: :evil: :!: :smile: :oops: :grin: :eek: :shock: :???: :cool: :lol: :mad: :twisted: :roll: :wink: :idea: :arrow: :neutral: :cry: :mrgreen:

确定