微信菜单自定义推送事件是一个post方式提交的请求, 该post的URL是进入“服务器配置(用于接收用户信息)”配置的URL中。
在成为开发者时的验证URL有效性,是进入URL的get方式。 而菜单自定义推送事件是进入URL的POST方式。
菜单的推送事件,发送的请求是xml格式的String, 在java端首先要把String转化成xml,读取里面的参数,然后对相应的逻辑,最后返回的也是xml格式的String,这样微信才知道要怎么显示消息。
String 与xml的转化可以用dom4j
/* * Copyright 2012-2012 imeiya.com All right reserved. This software is the * confidential and proprietary information of imeiya.com ("Confidential * Information"). You shall not disclose such Confidential Information and shall * use it only in accordance with the terms of the license agreement you entered * into with imeiya.com. */ package com.lehuo.app.ju.weixin; import java.io.IOException; import java.io.InputStream; import java.io.PrintWriter; import java.io.UnsupportedEncodingException; import java.util.Date; import java.util.HashMap; import java.util.List; import java.util.Map; import javax.servlet.http.HttpServletRequest; import javax.servlet.http.HttpServletResponse; import org.dom4j.Document; import org.dom4j.Element; import org.dom4j.io.SAXReader; import org.springframework.stereotype.Controller; import org.springframework.ui.ModelMap; import org.springframework.web.bind.annotation.RequestMapping; import org.springframework.web.bind.annotation.RequestMethod; import com.lehuo.app.ju.tb.TbBaseAction; /** * 类IndexAction.java的实现描述:TODO 类实现描述 * @author chenyao 2014-1-17 上午10:43:33 */ @Controller public class IndexAction extends TbBaseAction{ @RequestMapping(value="/index.html", method = RequestMethod.GET) public void doGet(HttpServletRequest request, HttpServletResponse response, ModelMap model) throws IOException { String echostr = request.getParameter("echostr"); response.getWriter().write(echostr); } @RequestMapping(value="/index.html", method = RequestMethod.POST) public void doPost(HttpServletRequest request, HttpServletResponse response) throws UnsupportedEncodingException { // 将请求、响应的编码均设置为UTF-8(防止中文乱码) request.setCharacterEncoding("UTF-8"); response.setCharacterEncoding("UTF-8"); // 调用核心业务类接收消息、处理消息 String respMessage = processRequest(request); // 响应消息 PrintWriter out; try { out = response.getWriter(); out.write(respMessage); out.close(); } catch (IOException e) { e.printStackTrace(); } } private String processRequest(HttpServletRequest request) { String respMessage = null; try {// 默认返回的文本消息内容 String respContent = "请求处理异常,请稍候尝试!"; Map<String, String> requestMap = parseXml(request); // 发送方帐号(open_id) String fromUserName = requestMap.get("FromUserName");; // 公众帐号 String toUserName = requestMap.get("ToUserName"); // 消息类型 String msgType = requestMap.get("MsgType"); // 回复文本消息 TextMessage textMessage = new TextMessage(); textMessage.setToUserName(fromUserName); textMessage.setFromUserName(toUserName); textMessage.setCreateTime(new Date()); textMessage.setMsgType(MessageUtil.RESP_MESSAGE_TYPE_TEXT); textMessage.setFuncFlag(0); // 文本消息 if (msgType.equals(MessageUtil.REQ_MESSAGE_TYPE_TEXT)) { respContent = "您发送的是文本消息!"; } // 图片消息 else if (msgType.equals(MessageUtil.REQ_MESSAGE_TYPE_IMAGE)) { respContent = "您发送的是图片消息!"; } // 地理位置消息 else if (msgType.equals(MessageUtil.REQ_MESSAGE_TYPE_LOCATION)) { respContent = "您发送的是地理位置消息!"; } // 链接消息 else if (msgType.equals(MessageUtil.REQ_MESSAGE_TYPE_LINK)) { respContent = "您发送的是链接消息!"; } // 音频消息 else if (msgType.equals(MessageUtil.REQ_MESSAGE_TYPE_VOICE)) { respContent = "您发送的是音频消息!"; } // 事件推送 else if (msgType.equals(MessageUtil.REQ_MESSAGE_TYPE_EVENT)) { // 事件类型 String eventType = requestMap.get("Event"); // 订阅 if (eventType.equals(MessageUtil.EVENT_TYPE_SUBSCRIBE)) { respContent = "谢谢您的关注!"; } // 取消订阅 else if (eventType.equals(MessageUtil.EVENT_TYPE_UNSUBSCRIBE)) { // TODO 取消订阅后用户再收不到公众号发送的消息,因此不需要回复消息 } // 自定义菜单点击事件 else{ String eventKey = requestMap.get("EventKey"); respContent = "event"+eventKey==null?"":eventKey+"__eventType"+eventType; // TODO 自定义菜单权没有开放,暂不处理该类消息 EventKey /* if(eventKey.equalsIgnoreCase("20_PROMANAGE")){ respContent = "项目管理"; } else if(eventKey.equalsIgnoreCase("30_ORGANIZATION")){ respContent = "机构运作"; } else if(eventKey.equalsIgnoreCase("01_WAITING")){ respContent = "待办工单"; } else if(eventKey.equalsIgnoreCase("02_FINISH")){ respContent = "已办工单"; } else if(eventKey.equalsIgnoreCase("03_MYJOB")){ respContent = "我的工单"; } else if(eventKey.equalsIgnoreCase("04_MESSAGEBOX")){ respContent = "公告消息箱"; } else if(eventKey.equalsIgnoreCase("05_SIGN")){ respContent = "签到"; }*/ } } textMessage.setContent(respContent); respMessage = Object2XmlString(textMessage); } catch (Exception e) { e.printStackTrace(); } return respMessage; } @SuppressWarnings("unchecked") private Map<String, String> parseXml(HttpServletRequest request) throws Exception { // 将解析结果存储在HashMap中 Map<String, String> map = new HashMap<String, String>(); InputStream is = request.getInputStream(); SAXReader reader = new SAXReader(); Document doc = reader.read(is); Element root = doc.getRootElement(); List<Element> list = root.elements(); // 遍历所有子节点 for (Element el : list){ map.put( el.getName(), el.getText()); } // 释放资源 is.close(); is = null; return map; } /** * 将对象转换为xml字符串 */ public String Object2XmlString(Object object) { return "<xml><ToUserName><![CDATA[测试账号]]></ToUserName><FromUserName><![CDATA[测试账号]]></FromUserName><CreateTime>12345678</CreateTime><MsgType><![CDATA[text]]></MsgType><Content><![CDATA[试试看效果]]></Content></xml>"; } }