先申請微信公衆號的受權,找到或配置幾個關鍵的信息(開發者ID、開發者密碼、IP白名單、令牌和消息加解密密鑰等)。服務器
開發者ID:固定的;微信
開發者密碼:本身掃一下就能夠看到;async
IP白名單:設置本身配置服務器的地址;ide
服務器地址(URL):稍後詳解;post
令牌:隨便寫,按規則;測試
消息加解密密鑰:隨便寫,或者隨機生成;spa
服務器地址(URL)應該怎麼配置呢?圖片上的配置的地址是:http://www.nidie.com.cn/wechat ,那麼它對應的控制器應該是怎麼樣子的呢?code
在這裏,我使用了第三方的包,須要經過 Nuget 來安裝:blog
<package id="Senparc.Weixin" version="4.22.1" targetFramework="net471" /> <package id="Senparc.Weixin.MP" version="14.14.0" targetFramework="net471" /> <package id="Senparc.Weixin.MP.MVC" version="5.4.5" targetFramework="net471" />
接下來新建一個 WeChatController.cs:繼承
using System.Threading.Tasks; using System.Web.Mvc; using Senparc.Weixin.MP; using Senparc.Weixin.MP.Entities.Request; using Senparc.Weixin.MP.MvcExtension; using Wen.MvcDemo.Application.WeChat.MessageHandlers.CustomMessageHandlers; using Wen.MvcDemo.Infrastructure.Configuration; namespace Wen.MvcDemo.Web.Controllers { /// <summary> /// 微信 /// </summary> public class WeChatController : Controller { #region private static field private static readonly string AppId = ApplicationSettingsFactory.GetApplicationSettings().WeChatAppId; private static readonly string EncodingAesKey = ApplicationSettingsFactory.GetApplicationSettings().WeChatEncodingAesKey; private static readonly string Token = ApplicationSettingsFactory.GetApplicationSettings().WeChatToken; #endregion private static field /// <summary> /// 微信後臺驗證地址 /// </summary> /// <param name="signature"></param> /// <param name="timestamp"></param> /// <param name="nonce"></param> /// <param name="echostr"></param> /// <returns></returns> [HttpGet] public ActionResult Index(string signature, string timestamp, string nonce, string echostr) { return Content(echostr); } /// <summary> /// 處理用戶發送消息後 /// </summary> /// <param name="postModel"></param> /// <returns></returns> [HttpPost] public async Task<ActionResult> Index(PostModel postModel) { //校驗簽名 if (!CheckSignature.Check(postModel.Signature, postModel.Timestamp, postModel.Nonce, Token)) return new WeixinResult("參數錯誤!"); postModel.AppId = AppId; postModel.EncodingAESKey = EncodingAesKey; postModel.Token = Token; //接收消息,自定義 MessageHandler,對微信請求進行處理 var messageHandler = new CustomMessageHandler(Request.InputStream, postModel); //執行微信處理過程 await messageHandler.ExecuteAsync(); //返回處理結果 return new FixWeixinBugWeixinResult(messageHandler); } } }
代碼分析:
裏面主要包含了三個靜態字段和兩個 Index 方法。
其中靜態字段對應的就是基本配置信息裏面對應的幾個參數,日常都是寫入配置文件中來進行讀取。
其中一個標識特性爲 HttpGet 的 Index 方法,它是用來經過服務器地址(URL)驗證的,當你成功部署到你的服務器後,再點擊提交認證就能夠經過了。注意的是,須要將代碼先提交到服務器,再進行提交確認。
可能你看到該方法好像只返回 return Content(echostr); 這麼簡單的代碼感到質疑:這能行嗎?「我」記得官方文檔好像要調用很複雜的方法進行校驗才行的!?
上圖就是官方文檔,可是我只關心經過配置提交認證,也就是我用紅圈着色的部分,即原樣返回 echostr 參數內容便可。
第二個是實現 Post 請求的 Index 方法,在這裏我進行了簽名校驗(也就是上圖文檔的校驗邏輯),由於使用了第三方庫,咱們知道傳哪些參數過去就能夠了,簽名經過後就是讀取請求信息並進行後續處理的步驟了。
在上面的處理請求信息的代碼中,我自定義了一個類 CustomMessageHandler 來處理消息。
using System; using System.Collections.Generic; using System.IO; using System.Linq; using System.Text; using System.Threading.Tasks; using System.Xml.Linq; using Senparc.Weixin.MP.AppStore; using Senparc.Weixin.MP.AppStore.Utility; using Senparc.Weixin.MP.Entities; using Senparc.Weixin.MP.Entities.Request; using Senparc.Weixin.MP.MessageHandlers; namespace Wen.MvcDemo.Application.WeChat.MessageHandlers.CustomMessageHandlers { /// <summary> /// 自定義消息處理 /// </summary> public class CustomMessageHandler : MessageHandler<CustomMessageContext> { public CustomMessageHandler(Stream inputStream, PostModel postModel = null, int maxRecordCount = 0, DeveloperInfo developerInfo = null) : base(inputStream, postModel, maxRecordCount, developerInfo) { } public CustomMessageHandler(XDocument requestDocument, PostModel postModel = null, int maxRecordCount = 0, DeveloperInfo developerInfo = null) : base(requestDocument, postModel, maxRecordCount, developerInfo) { } public CustomMessageHandler(RequestMessageBase requestMessageBase, PostModel postModel = null, int maxRecordCount = 0, DeveloperInfo developerInfo = null) : base(requestMessageBase, postModel, maxRecordCount, developerInfo) { } /// <summary> /// 默認 /// </summary> /// <param name="requestMessage"></param> /// <returns></returns> public override IResponseMessageBase DefaultResponseMessage(IRequestMessageBase requestMessage) { var responseMessage = base.CreateResponseMessage<ResponseMessageText>(); //ResponseMessageText也能夠是News等其餘類型 responseMessage.Content = $"您好,目前使用的微信公衆號仍處於開發階段,現已接入了【圖靈機器人】,您能夠嘗試和他(她)交流。"; return responseMessage; } } }
CustomMessageHandler 類繼承了 MessageHandler 類,而後重寫了 DefaultResponseMessage() 方法,返回固定的文本值。base.CreateResponseMessage<T>() 方法能夠返回多種不一樣類型的結果值,如:
ResponseMessageText - 對應文本消息 ResponseMessageNews - 對應圖文消息 ResponseMessageMusic - 對應音樂消息 ResponseMessageXXX - 其餘類型以此類推
上述方法只是一種默認的消息處理,咱們也能夠專門針對不一樣的請求類型作出不一樣的迴應,好比重寫 OnTextRequest(),其它重載須要本身觀察基類成員:
/// <summary> /// 文本請求 /// </summary> /// <param name="requestMessage"></param> /// <returns></returns> public override IResponseMessageBase OnTextRequest(RequestMessageText requestMessage) { var responseMessage = base.CreateResponseMessage<ResponseMessageText>(); responseMessage.Content = $"您剛纔發送的文字信息是:{requestMessage.Content}。"; //\r\n用於換行,requestMessage.Content即用戶發過來的文字內容 return responseMessage; }
由於在繼承 MessageHandler<T> 類的同時,我建立了一個 CustomMessageContext 自定義消息上下文的類,該類內容以下,並無包含其它方法,直接繼承 MessageContext<IRequestMessageBase, IResponseMessageBase> 便可:
using Senparc.Weixin.Context; using Senparc.Weixin.MP.Entities; namespace Wen.MvcDemo.Application.WeChat.MessageHandlers.CustomMessageHandlers { /// <summary> /// 自定義消息上下文 /// </summary> public class CustomMessageContext : MessageContext<IRequestMessageBase, IResponseMessageBase> { } }
這樣,就完成了全部代碼的編寫,如今咱們再次把代碼部署好以後就能夠開始進行測試了。
由於我除了部署本身的站點以外,還接入了【圖靈機器人】回覆,因此你看到了兩條信息。