• 微信公众号开发(2)---消息的接收发送


    在微信公众号开发(1)中,我们进行了GET请求方法的开发编写,能够使微信与我们的服务器进行了关系的绑定,接下来我们进行开发接收用户消息与一些事件的回复;

           开发必要了解:在我们微信与我们的服务器进行了关系的绑定后,微信会将用户所发过来的消息以及事件会以XML的格式POST请求的方式发送给我们的服务器,所以我们需要开发POST请求的接口,接收用户的消息,我们可以根据用户的消息进行一些关键字回复,以及关注后的回复推送,微信事件里有很多功能,这里只进行开发关键字回复以及关注事件,其他的顺藤摸瓜按照微信文档完全可以开发出来,一样的套路----

      1.为了方便开发,我先引入进来微信常用的接口和事件的常量,以及Xml转Map的工具类代码附上(红色部分我们需要配置成我们后台的参数):

    package com.wx.project.util;
    
    public class WxParamConfig {
        
        public static final String TOKEN="chenyuesong";//为微信后台配置的token
        public static final String APPID="wx426aad126775582c";//为微信后台的appid
        public static final String ACCESS_TOKEN="https://api.weixin.qq.com/cgi-bin/token?grant_type=client_credential&appid=APPID&secret=APPSECRET";//微信获取TOKEN地址
        public static final String SEND_TEMPLATE="https://api.weixin.qq.com/cgi-bin/message/template/send?access_token=ACCESS_TOKEN";//模板发送地址
        public static final String USER_INFO="https://api.weixin.qq.com/sns/userinfo?access_token=ACCESS_TOKEN&openid=OPENID&lang=zh_CN";//获取用户信息
        public static final String MENU="https://api.weixin.qq.com/cgi-bin/menu/create?access_token=ACCESS_TOKEN";//微信菜单管理创建
        public static final String LOGIN="https://open.weixin.qq.com/connect/oauth2/authorize?appid=APPID&redirect_uri=REDIRECT_URI&response_type=code&scope=SCOPE&state=STATE#wechat_redirect";//微信公众号login地址,获取code
        public static final String USER_TOKEN="https://api.weixin.qq.com/sns/oauth2/access_token?appid=APPID&secret=SECRET&code=CODE&grant_type=authorization_code";//通过code获取token票据
        
        /*
         * 微信提供的事件类型
         */
        public static final String MESSAGE_TEXT="text";
        public static final String MESSAGE_IMAGE="image";
        public static final String MESSAGE_NEWS="news";//图文消息
        public static final String MESSAGE_VIDEO="video";
        public static final String MESSAGE_VOICE="voice";
        public static final String MESSAGE_LINK="link";
        public static final String MESSAGE_LOCATION="location";
        public static final String MESSAGE_EVENT="event";
        public static final String MESSAGE_SUBSCRIBE="subscribe";//消息关注
        public static final String MESSAGE_UNSUBSCRIBE="unsubscribe";//取消关注
        public static final String MESSAGE_CLICK="click";//菜单点击
        public static final String MESSAGE_VIEW="view";//view菜单点击
        
        
    
    }

       

      xml转Map 工具类(在我的常用工具类中有这个工具类):---> https://www.cnblogs.com/iscys/p/9501155.html

      

      2.进行POST方法的编写---->接收到微信的XML数据流---->xml转Map工具类进行数据的读取判断----->开发者自己的逻辑---->返回给微信数据----->发送成功

        <1>  Controller层的代码,我将业务逻辑的判断回复放在了Service层,来更加真实模拟开发环境  

    /*
         * 微信消息事件配置逻辑,微信公众号用户发出的请求都会进入POST方法进行接收,我们可以进行消息的回复,以及图文消息等等
         * 需要注意的是数据的接收与回复都是XML的数据格式
         */
        @RequestMapping(value="/wxopen" ,method=RequestMethod.POST)
        public void MsgResponse(HttpServletRequest request,HttpServletResponse response) throws Exception { 
            /*
             * 可以以来数据库内容进行动态的回复判断
             */
            //接收消息,将微信XML数据流消息转换为MAP数据格式
            Map<String,String> map=WxParseXmlUtil.xmlTOMap(request);
            String ToUserName =map.get("ToUserName");
            String FromUserName =map.get("FromUserName");//获取发送消息方的微信号
            String  MsgType =map.get("MsgType");//消息的类型
            String Content =map.get("Content");//消息内容,我们根据消息的内容与消息的类型进行动态的实现自己的业务逻辑
            //业务逻辑的实现在Service层,返回XML字符串
            String contentXml=msgResponse.autoResponse(map);
            System.out.println(contentXml);
            PrintWriter writer=null;
            try {
            writer=response.getWriter();
            writer.write(contentXml);
            }
            catch (IOException e) {
                // TODO Auto-generated catch block
                e.printStackTrace();
            }
            finally {
                if(writer !=null) {
                    writer.close();
                }
        }
        
        }

        <2>.service 层代码,为了方便我们这里不进行数据库内容的获取

    public String autoResponse(Map<String, String> map) {
            
            String ToUserName =map.get("ToUserName");//接收方的微信公众号;
            String FromUserName =map.get("FromUserName");//获取发送消息方的微信号
            String  MsgType =map.get("MsgType");//消息的类型
            String Content =map.get("Content");//消息内容
            String xmlStr =null;
            //用户关注时候的事件,用户关注时候微信或给我们XML中带有 <MsgType>event</MsgType><Event>subscribe</Event>
             if(WxParamConfig.MESSAGE_EVENT.equals(MsgType)) {
                 if(WxParamConfig.MESSAGE_SUBSCRIBE.equals(map.get("Event"))) {
                    //List<Map> content= msgmapper.getContentByWxType(WxParamConfig.MESSAGE_SUBSCRIBE);
    
                     //文本消息回复
                     String content ="这是关注后的文本消息发送";
                     xmlStr = textMessage(content,ToUserName,FromUserName);
                     }
    
    }
             return xmlStr;
        }
    
    
        //文本消息类型的消息
        public  String textMessage(Object textContent, String toUserName, String fromUserName) {
            String content =(String) textContent;
            TextMessage  text =new TextMessage();
            text.setContent(content);
            text.setToUserName(fromUserName);
            text.setFromUserName(toUserName);
            text.setMsgType(WxParamConfig.MESSAGE_TEXT);
            text.setCreateTime(new Date().getTime());
            String xmlStr=WxParseXmlUtil.poToXML(text);
            return xmlStr;
        }
        

     TextMessage 文本消息enity

    package com.wx.project.entity;
    
    public class TextMessage {
    
    
        /**
         * 文本消息模板,详情请参考wechat
         */
        private String ToUserName;
        private String FromUserName;
        private long CreateTime;
        private String MsgType;
        private String Content;
        private int MsgId;
        public String getToUserName() {
            return ToUserName;
        }
        public void setToUserName(String toUserName) {
            ToUserName = toUserName;
        }
        public String getFromUserName() {
            return FromUserName;
        }
        public void setFromUserName(String fromUserName) {
            FromUserName = fromUserName;
        }
        public long getCreateTime() {
            return CreateTime;
        }
        public void setCreateTime(long createTime) {
            CreateTime = createTime;
        }
        public String getMsgType() {
            return MsgType;
        }
        public void setMsgType(String msgType) {
            MsgType = msgType;
        }
        public String getContent() {
            return Content;
        }
        public void setContent(String content) {
            Content = content;
        }
        public int getMsgId() {
            return MsgId;
        }
        public void setMsgId(int msgId) {
            MsgId = msgId;
        }
    }

      

      

      

      

    原创打造,多多指教
  • 相关阅读:
    Flask-SQLAlchemy 学习总结
    ubuntu安装redis
    PostgreSQL在Ubuntu上安装指南
    Linux(Ubuntu)下MySQL的安装与配置
    python wechat_sdk间接性的出现错误OfficialAPIError: 40001,说access_token已过期或者不是最新的。
    django不要设置datetime字段auto_now=True
    python 装饰器和 functools 模块
    关于 Python Iterator 协议的一点思考
    python中的enumerate函数
    8 种常被忽视的 SQL 错误用法
  • 原文地址:https://www.cnblogs.com/iscys/p/9508953.html
Copyright © 2020-2023  润新知