当普通微信用户向公众账号发消息时,微信服务器将post消息的xml数据包到开发者填写的url上。
请注意:
- 1、关于重试的消息排重,推荐使用msgid排重。
- 2、微信服务器在五秒内收不到响应会断掉连接,并且重新发起请求,总共重试三次。假如服务器无法保证在五秒内处理并回复,可以直接回复空串,微信服务器不会对此作任何处理,并且不会发起重试。详情请见“发送消息-被动回复消息”。
- 3、为了保证更高的安全保障,开发者可以在公众平台凯发网娱乐官网下载官网的开发者中心处设置消息加密。开启加密后,用户发来的消息会被加密,公众号被动回复用户的消息也需要加密(但开发者通过客服接口等api调用形式向用户发送消息,则不受影响)。关于消息加解密的详细说明,请见“消息加解密说明”。
各消息类型的推送xml数据包结构如下:
文本消息
1348831860 1234567890123456
图片消息
1348831860 1234567890123456
语音消息
1357290913 1234567890123456
请注意,开通语音识别后,用户每次发送语音给公众号时,微信会在推送的语音消息xml数据包中,增加一个recongnition字段 (注:由于客户端缓存,开发者开启或者关闭语音识别功能,对新关注者立刻生效,对已关注用户需要24小时生效。开发者可以重新关注此帐号进行测试)。开启语音识别后的语音xml数据包如下:
1357290913 1234567890123456
多出的字段中,format为语音格式,一般为amr,recognition为语音识别结果,使用utf8编码。
视频消息
1357290913 1234567890123456
小视频消息
1357290913 1234567890123456
地理位置消息
1351776360 23.134521 113.358803 20 1234567890123456
链接消息
1351776360 <![cdata[公众平台凯发网娱乐官网下载官网链接]]> 1234567890123456
接上篇,看responsexml(poststring);方法如下
////// 获取用户发送的消息 /// /// private void responsexml(string poststring) { //使用xmldocument加载信息结构 xmldocument xmldoc = new xmldocument(); xmldoc.loadxml(poststring); xmlelement rootelement = xmldoc.documentelement;//获取文档的根 xmlnode msgtype = rootelement.selectsinglenode("msgtype"); //获取消息的文本类型 requestxml requestxml = new requestxml();//声明实例,获取各个属性并赋值 requestxml.tousername = rootelement.selectsinglenode("tousername").innertext;//公众号 requestxml.fromusername = rootelement.selectsinglenode("fromusername").innertext;//用户 requestxml.createtime = rootelement.selectsinglenode("createtime").innertext;//创建时间 requestxml.msgtype = msgtype.innertext;//消息类型 ///对消息的不同类型进行赋值 if (requestxml.msgtype == "text") { //赋值文本信息内容 requestxml.content = rootelement.selectsinglenode("content").innertext; } if (requestxml.msgtype.trim() == "location") { ///赋值地理位置纬度,经度,地图缩放比例,地理位置说明 requestxml.location_x = rootelement.selectsinglenode("location_x").innertext; requestxml.location_y = rootelement.selectsinglenode("location_y").innertext; requestxml.scale = rootelement.selectsinglenode("scale").innertext; requestxml.label = rootelement.selectsinglenode("label").innertext; } if (requestxml.msgtype.trim().tolower() == "event") { ///赋值事件名称和事件key值 requestxml.eventname = rootelement.selectsinglenode("event").innertext; requestxml.eventkey = rootelement.selectsinglenode("eventkey").innertext; } if (requestxml.msgtype.trim().tolower() == "voice") { ///赋值语音识别结果,赋值之前一定要记得在开发者模式下,把语音识别功能开启,否则获取不到 requestxml.recognition = rootelement.selectsinglenode("recognition").innertext; } responsemsg(requestxml); }
语音识别功能开启如下:
requestxml是我单独创建的一个类,该类声明了消息中常用的属性字段,如下:
////// 接收消息的实体类 /// public class requestxml { private string tousername = string.empty; ////// 本公众号 /// public string tousername{get;set;} ////// 用户微信号 /// public string fromusername{get;set;} ////// 创建时间 /// public string createtime{get;set;} ////// 信息类型 /// public string msgtype{get;set;} ////// 信息内容 /// public string content{get;set;} /*以下为事件类型的消息特有的属性*/ ////// 事件名称 /// public string eventname{get;set;} ////// 事件值 /// public string eventkey { get; set; } /*以下为图文类型的消息特有的属性*/ ////// 图文消息的个数 /// public int articlecount { get; set; } ////// 图文消息的标题 /// public string title { get; set; } ////// 图文消息的简介 /// public string description { get; set; } ////// 图文消息图片的链接地址 /// public string picurl { get; set; } ////// 图文消息详情链接地址 /// public string url { get; set; } ////// 图文消息集合 /// public listarticles { get; set;} /*以下为地理位置类型的消息特有的属性*/ /// /// 地理位置纬度 /// public string location_x { get; set; } ////// 地理位置经度 /// public string location_y { get; set; } ////// 地图缩放比例 /// public string scale { get; set; } ////// 地图位置说明 /// public string label { get; set; } ////// 语音消息特有字段 /// public string recognition { get; set; } }
继续关注 responsemsg(requestxml);方法如下
private void responsemsg(requestxml requestxml) { string msgtype = requestxml.msgtype; try { //根据消息类型判断发送何种类型消息 switch (msgtype) { case "text": sendtextcase(requestxml);//发送文本消息 break; case "event"://发送事件消息 if (!string.isnullorwhitespace(requestxml.eventname) && requestxml.eventname.tostring().trim().equals("subscribe")) { sendwelcomemsg(requestxml);//关注时返回的图文消息 } else if (!string.isnullorwhitespace(requestxml.eventname) && requestxml.eventname.tostring().trim().equals("click")) { sendeventmsg(requestxml);//发送事件消息 } break; case "voice": sendvoicemsg(requestxml);//发送语音消息 break; case "location"://发送位置消息 sendmapmsg(requestxml); break; default: break; } } catch (exception ex) { httpcontext.current.response.write(ex.tostring()); } }
先来关注发送文本消息,sendtextcase(requestxml);//发送文本消息
////// 发送文本 /// /// private void sendtextcase(requestxml requestxml) { string responsecontent = formattextxml(requestxml.fromusername, requestxml.tousername, requestxml.content); httpcontext.current.response.contenttype = "text/xml"; httpcontext.current.response.contentencoding = encoding.utf8; httpcontext.current.response.write(responsecontent); httpcontext.current.response.end(); }
formattextxml方法制定格式
////// 返回格式化的xml格式内容 /// /// 公众号 /// 用户号 /// 回复内容 ///private string formattextxml(string p1, string p2, string p3) { return " "; } " datetime.now.subtract(new datetime(1970, 1, 1, 8, 0, 0)).totalseconds.tostring() " 1
这样就能实现消息的应答,如果用户点击的按钮,如下代码:
case "event"://发送事件消息 if (!string.isnullorwhitespace(requestxml.eventname) && requestxml.eventname.tostring().trim().equals("subscribe")) { sendwelcomemsg(requestxml);//关注时返回的图文消息 } else if (!string.isnullorwhitespace(requestxml.eventname) && requestxml.eventname.tostring().trim().equals("click")) { sendeventmsg(requestxml);//发送事件消息 } break; ////// 发送响应事件消息 /// /// private void sendeventmsg(requestxml requestxml) { string keystr = requestxml.eventkey.tostring(); switch (keystr) { case "mypay": sendpaydetails(requestxml);//发送薪资账单 break; case "tianqiyubao": sendweatermessage(requestxml);//发送天气预报 break; case "kaixinyixiao": sendkaixinmessage(requestxml);//发送开心一笑结果集 break; case "updatemessage": sendupdatemessage(requestxml);//发送修改信息链接 break; case "yuangonghuodong": sendyuangonghuodong(requestxml);//发送学生活动 break; case "yuangongtongzhi": sendyuangongtongzhi(requestxml);//发送员工通知 break; case "youwenbida": sendwenti(requestxml);//发送员工提交问题链接 break; case "mywen": sendwentilist(requestxml);//发送问题列表链接 break; case "phoneserices": sendkefumessage(requestxml);//接入客服 break; default: string responsecontent = string.empty; responsecontent = formattextxml(requestxml.fromusername, requestxml.tousername,"此功能暂未开放!敬请期待!"); httpcontext.current.response.contenttype = "text/xml"; httpcontext.current.response.contentencoding = encoding.utf8; httpcontext.current.response.write(responsecontent); httpcontext.current.response.end(); break; } }
sendwelcomemsg(requestxml);//关注时返回的图文消息
////// 发送关注时的图文消息 /// /// private void sendwelcomemsg(requestxml requestxml) { string responsecontent = string.empty; string newdate = datetime.now.subtract(new datetime(1970, 1, 1, 8, 0, 0)).totalseconds.tostring(); string purlfilename = "http://www.51sjk.com/upload/articles/1/0/133/133331_20200730132044686.jpg"; responsecontent = string.format(message_news_main, requestxml.fromusername, requestxml.tousername, newdate, "1", string.format(message_news_item, "欢迎关注德桥员工服务中心", "苏州德桥人力资源创立于2002年...", purlfilename, "http://www.deqiaohr.com.cn/weixin/wxgsjianjie.aspx")); httpcontext.current.response.contenttype = "text/xml"; httpcontext.current.response.contentencoding = encoding.utf8; httpcontext.current.response.write(responsecontent); httpcontext.current.response.end(); }
message_news_main 和message_news_item是图文消息格式化
////// 返回图文消息主体 /// public static string message_news_main { get { return @""; } } /// {2} {3} {4} /// 返回图文消息项 /// public static string message_news_item { get { return @"- "; } } ///
<![cdata[{0}]]> /// 发送响应语音识别结果 /// /// private void sendvoicemsg(requestxml requestxml) { string responsecontent = formattextxml(requestxml.fromusername, requestxml.tousername, "您刚才说的语音消息识别结果为:" requestxml.recognition.tostring()); httpcontext.current.response.contenttype = "text/xml"; httpcontext.current.response.contentencoding = encoding.utf8; httpcontext.current.response.write(responsecontent); httpcontext.current.response.end(); }
精彩专题分享:asp.net微信开发教程汇总,欢迎大家学习。
以上就是关于asp.net微信开发的第二篇,针对消息应答进行学习,之后会有更新更多关于asp.net微信开发的文章,希望大家持续关注。