在准备工作中,我们已经完成准备工作,接下来就是进行开发啦,应该怎么来开发呢??容我想想。。。我觉得我们可以直接让用户的消息发送到微信的消息,转到我们自己的服务器上面!!感觉好厉害的样子
1.首先写 验证程序啦,这第一步的工作呢,就是验证数据是不是来源于微信端的,如果不是来自微信服务器端的,那就安逸了。。。,废话不多说,直接上代码
1.1这个是微信端页面的配置
1.2 验证微信数据来源
//获取token
string Token = string.Format("{0}", ConfigurationManager.AppSettings["ToKen"]);//这个,简单来说,就是我们自己的钥匙,用来验证的钥匙,需要和微信端填写的一模一样,我这里直接在Web.config里面进行配置就行,见上图
[HttpGet]
public ActionResult Index(string signature, string timestamp, string nonce, string echostr)//相关字段信息我们可以直接上微信文档了解,这里就不一一列举了
{
string[] ArrTmp = { Token, timestamp, nonce };
Array.Sort(ArrTmp); //字典排序
string tmpStr = string.Join("", ArrTmp);
tmpStr = FormsAuthentication.HashPasswordForStoringInConfigFile(tmpStr, "SHA1");//这个就是SHA1加密
tmpStr = tmpStr.ToLower();
if (signature == tmpStr) // 如果从微信传入的数据和我们的数据不一样,那就表示传入的数据不一定是从微信传入的数据,就不能返回echostr参数
{
return Content(echostr);
}
else
{
ReturnInfo<SessionInfo> returnSessionInfo = GetSessionUserInfo();
if (returnSessionInfo.Code != 1)
{
//返回失败信息到页面
return RedirectToAction("Index", "Error"); ;
}
return View();
}
}
备注:在公司开发可能会遇到跨域问题,推荐使用工具ngnork,可实现内外网穿透
2.消息的获取
2.1消息去重,使用msgid排重
static List<BaseMsg> _queue = new List<BaseMsg>();
//消息去重
if (_queue == null)
{
_queue = new List<BaseMsg>();
}
else if (_queue.Count >= 50)
{
_queue = _queue.Where(q => { return q.CreateTime.AddSeconds(20) > DateTime.Now; }).ToList();//保留20秒内未响应的消息
}
2.2消息的获取
Stream requestStream = System.Web.HttpContext.Current.Request.InputStream;
byte[] requestByte = new byte[requestStream.Length];
requestStream.Read(requestByte, 0, (int)requestStream.Length);
string requestStr = Encoding.UTF8.GetString(requestByte);
//封装请求类
XmlDocument requestDocXml = new XmlDocument();
requestDocXml.LoadXml(requestStr);
XmlElement rootElement = requestDocXml.DocumentElement;
XElement xdoc = XElement.Parse(requestStr);
var msgtype = xdoc.Element("MsgType").Value.ToUpper();
var FromUserName = xdoc.Element("FromUserName").Value;
var MsgId = xdoc.Element("MsgId").Value;
var CreateTime = xdoc.Element("CreateTime").Value;
if (msgtype != "event" && msgtype != "link" && msgtype != "location")
{
if (_queue.FirstOrDefault(m => { return m.MsgFlag == MsgId; }) == null)
{
_queue.Add(new BaseMsg
{
CreateTime = DateTime.Now,
FromUser = FromUserName,
MsgFlag = MsgId
});
}
else
{
return "";
}
}
else
{
return "";
}
接下来就是通过解析rootElement 来获取对应字段的消息了
如:string strFormUserName = rootElement.SelectSingleNode("FromUserName").InnerText;
然后把数据保存至数据库,整个消息接受和保存的数据流程就走完了