微信开发系列(五)_消息,事件的处理

本文详细介绍如何处理微信公众号接收到的各种消息类型,包括文本、图片、语音等,并介绍如何响应不同类型的用户事件,如点击按钮、扫码等。文章还提供了具体的Java实现代码示例。

摘要生成于 C知道 ,由 DeepSeek-R1 满血版支持, 前往体验 >

来自微信端的事件可以有多种

1:文本消息

2:图片消息

3:语音消息

4:点击按钮事件

5:扫码事件等等

用户发送的消息或者事件  都是以xml的形式发送给我们开发者的(也就是服务器端) 我们也是以xml的格式返回去的

这是开发者文档点击打开链接


所有首先 我们得把用户的消息给获取并解析了(我给出一个工具类类  )

可以看出就是把传过来的request直接传进去就ok了

 public static Map<String,String> xmlToMap(HttpServletRequest request) throws IOException, DocumentException{
	  //用List列表的方式来解析xml,详细见http://www.jb51.net/article/42323.htm
	  Map<String, String> map =new HashMap<String,String>();  //把客户端传过来的xml数据转换成map格式的数据
	  
	  SAXReader reader =new SAXReader();
	  
	  
	  InputStream ins=request.getInputStream();//从request中获取输入流
	  Document doc =reader.read(ins);// 弄成文本???Xml
		
	  Element root =doc.getRootElement();
	  List<Element> list =root.elements();//获取子节点元素
		//list相当于一个变量,List则是标明是何种变量,这样来理解
		for(Element e :list){
		   map.put(e.getName(), e.getText());	                 //将遍历的结果保存到集合中
		}
	    ins.close();
	    return map;
	  
  }
然后当然就是获取map里面的数据了

所以我们得根据他们的类型(是文字 还在图片 还是点击 ,,)

Map<String ,String> map =BaseMessageUtil.xmlToMap(req);  //把服务器传过来的xml格式的数据转换成map
			String fromUserName =map.get("FromUserName");//发送方帐号(一个OpenID)
			String toUserName =map.get("ToUserName");//开发者微信号
			String msgType =map.get("MsgType");//text
			String content =map.get("Content");//文本消息内容
请注意 图片的msgtype是image

             文字的msgtype是text

             语音的msgtype是voice

             .....................

但是事件的msgtype都是event (包括点击事件click 关注事件 扫码事件) 区分他们的唯一标示是 他们的map里面有一个event字段 可以将他们区分

获取 String eventType = map.get("Event");   //事件的类型



好了事件获取完毕就开始一一回击吧

刚刚说过 回复也要包装成xml返回的

所以制作完回复消息后就要转换成xml了再输出到微信端【out.print(message);】

消息的制作就以图文消息为例

首先新建一个基本消息父类

package com.po;

public class BaseMessage {
	private String ToUserName;//微信号
	 private String FromUserName;//用户的openID
	 private long CreateTime;//创建时间
	 private String MsgType;//消息类型
	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;
	}
}
图文消息类


一个总图文(PicNews)消息里面可以包含多个图文消息(PicNewsMessage)

package com.po;

public class PicNews {
  private String Title;
  private String Description;
  private String PicUrl;
  private String Url;
public String getTitle() {
	return Title;
}
public void setTitle(String title) {
	Title = title;
}
public String getDescription() {
	return Description;
}
public void setDescription(String description) {
	Description = description;
}
public String getPicUrl() {
	return PicUrl;
}
public void setPicUrl(String picUrl) {
	PicUrl = picUrl;
}
public String getUrl() {
	return Url;
}
public void setUrl(String url) {
	Url = url;
}
}


package com.po;

import java.util.List;

public class PicNewsMessage extends BaseMessage{    //图文消息的基本设置
    private int ArticleCount;
    private List<PicNews> Articles;//该集合中存放的是PicNews对象,每个对象都代表着一条图文消息
	public int getArticleCount() {
		return ArticleCount;
	}
	public void setArticleCount(int articleCount) {
		ArticleCount = articleCount;
	}
	public List<PicNews> getArticles() {
		return Articles;
	}
	public void setArticles(List<PicNews> articles) {
		Articles = articles;
	}
}
返回的时候只要填写数据就ok了
填写好了之后就要把PicNewsMessage 对象转化成xml了
话不多说  转化的代码(这是图文消息的转化)
<pre name="code" class="java">
 public static String PicNewsMessageToXml(PicNewsMessage picNewsMessage){
 //返回一个Xml
 XStream xstream = new XStream();
 xstream.alias("xml", picNewsMessage.getClass());
 xstream.alias("item", new PicNews().getClass());//<articles>下根为<items>
 return xstream.toXML(picNewsMessage);
}

 

把转化完的消息放在message中out一下就到微信端了

再把微信servlet代码贴上去
<pre name="code" class="java">package com.servlet;

import java.io.IOException;
import java.io.PrintWriter;
import java.sql.SQLException;
import java.util.Date;
import java.util.Map;

import javax.servlet.ServletException;
import javax.servlet.http.HttpServlet;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;

import org.dom4j.DocumentException;

import com.po.TextMessage;
import com.util.CheckUtil;
import com.util.BaseMessageUtil;
import com.util.ImageMessageUtil;
import com.util.MusicMessageUtil;
import com.util.PicNewsMessageUtil;
import com.util.TextMessageUtil;
import com.util.WeixinUtil;
import com.xt.util.UserUtil;

public class WeixinServlet extends HttpServlet {
    
	
	/**
	 * 
	 */
	private static final long serialVersionUID = 1L;
	@Override
    protected void doGet(HttpServletRequest req, HttpServletResponse resp)
    		throws ServletException, IOException {  //验证方式为get
    	String signature = req.getParameter("signature");
    	String timestamp = req.getParameter("timestamp");
    	String nonce = req.getParameter("nonce");
    	String echostr = req.getParameter("echostr");
    	
    	PrintWriter out = resp.getWriter();
    	if(CheckUtil.checkSignature(signature, timestamp, nonce)){
    		out.print(echostr);
    	}
    	
    }
     protected void doPost(HttpServletRequest req ,HttpServletResponse resp) throws IOException {
    	 
    	 req.setCharacterEncoding("UTF-8");
    	 resp.setCharacterEncoding("UTF-8");
    	 
    	 /**
    	  * out是输出字符流,即servlet接受到request请求后,
    	  * servlet使用out来返回结果,不管客户端是什么(浏览器或者httpclient 或者别的serlvet等等),
    	  * 它都和客户端建立一个流输出管道,然后把字符流输出给请求端。
          */
    	 PrintWriter out =resp.getWriter(); 
		 
		    
    	 try {
			Map<String ,String> map =BaseMessageUtil.xmlToMap(req);  //把服务器传过来的xml格式的数据转换成map
			String fromUserName =map.get("FromUserName");//发送方帐号(一个OpenID)
			String toUserName =map.get("ToUserName");//开发者微信号
			String msgType =map.get("MsgType");//text
			String content =map.get("Content");//文本消息内容
			//String 
			
			//判断该消息是否为文本消息
			String message =null;
			if(BaseMessageUtil.MESSAGE_TEXT.equals(msgType)){  //发过来的时文本消息时
				if("1".equals(content)){  //回复文本消息
					System.out.println(this+"用户输入的是1");
//					message = TextMessageUtil.initText(toUserName, fromUserName, TextMessageUtil.firstMenu(fromUserName)); 
					message = PicNewsMessageUtil.initPicNewsMessage(toUserName, fromUserName,12);
				}else if("2".equals(content)){  //回复图文消息
					//message = PicNewsMessageUtil.initPicNewsMessage(toUserName, fromUserName);
					 
				}else if("3".equals(content)){  //回复图片消息
					message = ImageMessageUtil.initImageMessage(toUserName, fromUserName);
				}else if("4".equals(content)){  //回复音乐消息
					message = MusicMessageUtil.initMusicMessage(toUserName, fromUserName);
				}
				else if("5".equals(content)){  //回复文本消息
					message = TextMessageUtil.initText(toUserName, fromUserName,TextMessageUtil.threeMenu());
				}
				else if("?".equals(content)||"?".equals(content)){ //菜单
					message = TextMessageUtil.initText(toUserName, fromUserName, TextMessageUtil.menuText(fromUserName));
				}else if(content.startsWith("翻译")){
					String word = content.replaceAll("^翻译", "").trim();
					if("".equals(word)){
						message = TextMessageUtil.initText(toUserName, fromUserName,TextMessageUtil.threeMenu());
					}else{
						//message = TextMessageUtil.initText(toUserName, fromUserName, WeixinUtil.translate(word));//翻译
					}
				}
				
			/**	   
				   text.setFromUserName(toUserName);
				   text.setToUserName(fromUserName);
				   text.setMsgType("text");
				   text.setCreateTime(new Date().getTime());
				   text.setContent("您发送的消息是:"+content);
				   TextMessage text =new TextMessage();
				   message = TextMessageUtil.textMessageToXml(text);
				 
				*/
				
			}else if(BaseMessageUtil.MESSAGE_EVENT.equals(msgType)){  //当发过来的是事件
				
				String eventType = map.get("Event");   //点击事件的类型
				if(BaseMessageUtil.MESSAGE_SUBSCRIBE.equals(eventType)){  //调出主菜单
					message = TextMessageUtil.initText(toUserName, fromUserName, TextMessageUtil.menuText(fromUserName));
					UserUtil userUtil=new UserUtil();
					try {
						userUtil.saveUser(fromUserName);//关注的时候往数据库里面插入用户的信息
					} catch (ClassNotFoundException | SQLException e) {
						// TODO Auto-generated catch block
						e.printStackTrace();
					}
				}else if(BaseMessageUtil.MESSAGE_CLICK.equals(eventType)){  //点击事件时,推送图文消息
					int Key = Integer.parseInt(map.get("EventKey"));  //得到按钮的key值
					message = PicNewsMessageUtil.initPicNewsMessage(toUserName, fromUserName,Key);
					
				}else if(BaseMessageUtil.MESSAGE_VIEW.equals(eventType)){  //链接事件
					System.out.println("你点击了ViewButton");
					message = TextMessageUtil.initText(toUserName, fromUserName, TextMessageUtil.menuText(fromUserName));
//					String url = map.get("EventKey"); 
//					message = TextMessageUtil.initText(toUserName, fromUserName, url);
				}else if(BaseMessageUtil.MESSAGE_SCANCODE.equals(eventType)){  //扫码事件,推送消息
					
					String key =map.get("EventKey");
					System.out.println(key);
					//message = TextMessageUtil.initText(toUserName, fromUserName, key);

				}else if(BaseMessageUtil.MESSAGE_LOCATION.equals(eventType)){
					String label = map.get("Label");
					message = TextMessageUtil.initText(toUserName, fromUserName, label);
				}
				else if(BaseMessageUtil.MESSAGE_SCAN.equals(eventType)){
					String scene_id = map.get("EventKey");
					System.out.println(scene_id);
					
				}
				
				
				
				
            }
			
			//System.out.println(message);
			
			out.print(message);
		} catch (IOException e) {
			// TODO Auto-generated catch block
			e.printStackTrace();
		} catch (DocumentException e) {
			// TODO Auto-generated catch block
			e.printStackTrace();
		}
    	 finally{
    		 out.close();
    		 
    	 }
	}
}


 

评论 1
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值