.net开发微信公众号(4)-获取AccessToken

  获取AccessToken

  今天主要介绍一下AccessToken的获取方式,这个是调用其他接口的基础。

  首先看下微信开发文档上是如何定义AccessToken的。

  access_token是公众号的全局唯一票据,公众号调用各接口时都需使用access_token。开发者需要进行妥善保存。access_token的存储至少要保留512个字符空间。access_token的有效期目前为2个小时,需定时刷新,重复获取将导致上次获取的access_token失效。

  公众平台的API调用所需的access_token的使用及生成方式说明:

  1、为了保密appsecrect,第三方需要一个access_token获取和刷新的中控服务器。而其他业务逻辑服务器所使用的access_token均来自于该中控服务器,不应该各自去刷新,否则会造成access_token覆盖而影响业务;
  2、目前access_token的有效期通过返回的expire_in来传达,目前是7200秒之内的值。中控服务器需要根据这个有效时间提前去刷新新access_token。在刷新过程中,中控服务器对外输出的依然是老access_token,此时公众平台后台会保证在刷新短时间内,新老access_token都可用,这保证了第三方业务的平滑过渡;
  3、access_token的有效时间可能会在未来有调整,所以中控服务器不仅需要内部定时主动刷新,还需要提供被动刷新access_token的接口,这样便于业务服务器在API调用获知access_token已超时的情况下,可以触发access_token的刷新流程。
  
  以上就是微信开发文档上内容,看完之后总结一下就是说了三点内容:  
  1、access_token很重要,是公众号的全局唯一票据,每次调用其他API的时候都要传这个参数。  
  2、2小时失效一次并且每日的总调用次数有上限,不能每次调用其他API都从新获取。  
  3、建议弄一个中控服务器来干获取这个事。

   好,AccessToken是个什么玩意我们弄清楚了,接下来就要想如何获取它了。由于AccessToken取一次能用两小时且获取次数有上限这两个特点,我也参考了一些网上其他人的做法,总结了以下几种方式:

  1、用单例模式写一个全局的访问方法来获取,获取之后放在内存中。调用时候判断一下上次取的时间差是不是大于两小时,如果大于就从取一次,如果不大于就直接返回上次取的值。

  2、程序启动的时候启动一个线程定时取出AccessToken,然后存在本地xml或者数据库里。获取的时候直接从xml或者数据库里直接读取就行。

  3、单独写一个程序来提供AccessToken。这是微信推荐的方式,在.net上其实就是写一个Windows服务或Wcf来干这个事。

  我选的是第一种方式来做,开发比较简单而且容易理解。但是如果你需要把这个AccessToken保存下来的话也可以写到文件中或数据库里。第二种方式个人觉得不是很稳定,因为线程本身并不好控制。第三种是比较稳妥的方式,但比较麻烦,还要维护两个程序的运行状态。

  下面是微信开发文档给出的接口调用及返回值说明:

  

  

  下面的就是单例模式的类:

 1 using Service.Common.Utility;
 2 using System;
 3 using System.Collections.Generic;
 4 using System.Linq;
 5 using System.Text;
 6 using System.Threading.Tasks;
 7 
 8 namespace Service.Wechat.Common
 9 {
10     /* 单例模式
11      * 全局使用同一个Access_Token,每隔7200秒(2小时)微信服务器刷新一下
12      * 为了保证正常使用,程序每隔7000秒获取一次Access_Token
13      */
14     public class AccessToken
15     {
16         private AccessToken() { } //私有化构造函数
17         public static readonly AccessToken Instance = new AccessToken(); //C#的单例模式
18         private string Access_Token = string.Empty;
19         private long last = 0;
20         public string GetAccessToken()
21         {
22             long Now = UtilityFunc.GetTimeStamp();//获取一个Unix时间戳
23             if(Now-last>7000)
24             {
25                 var result = WeApiRequest.GetAccessToken();
26                 if (result.IsSuccess)
27                 {
28                     Access_Token = result.Info;
29                     last = Now;
30                     return Access_Token;
31                 }else
32                 {
33                     return "err";
34                 }
35 
36             }
37             else
38             {
39                 return Access_Token;
40             }
41         }
42     }
43 }

  

  这段是调用API的代码:

 1         public static WeApiRequestResult GetAccessToken()
 2         {
 3             WeApiRequestResult result = new WeApiRequestResult() { IsSuccess = false, Info = string.Empty };
 4             string errMsg = string.Empty;
 5             string appid = WeConst.AppID;//成为开发者时生成的AppID,在微信开发者中心里有
 6             string secret = WeConst.AppSecret;//成为开发者时生成的AppSecret,在微信开发者中心里有
 7             string url = "https://api.weixin.qq.com/cgi-bin/token?grant_type=client_credential&appid=" + appid + "&secret=" + secret;
 8             string requsetResult = HttpUtility.Request(HttpUtility.HTTP_GET, url, string.Empty, ref errMsg);
 9             if (!string.IsNullOrEmpty(errMsg))
10             {
11                 WeLogger.Error("方法名:GetAccessToken(),请求Access_Token失败,错误信息:" + errMsg);
12                 result.Info = errMsg;
13                 return result;
14             }
15             string token = UtilityFunc.GetJsonValueByKey(requsetResult, "access_token");
16             if (string.IsNullOrEmpty(token))
17             {
18                 WeLogger.Error("方法名:GetAccessToken(),请求Access_Token发送完成,但未取回Access_Token值,错误信息:" + requsetResult);
19                 result.Info = requsetResult;
20                 return result;
21             }
22             result.IsSuccess = true;
23             result.Info = token;
24             return result;
25         }

  这段是所有调用接口方法的返回值类,就是上面那个方法的返回值类:

1     /// <summary>
2     /// 调用接口方法的返回值类
3     /// </summary>
4     public class WeApiRequestResult
5     {
6         public bool IsSuccess { get; set; }
7         public string Info { get; set; }
8         public object data { get; set; }
9     }

  里面还有个http请求的方法和json操作的方法,各位小伙伴自己封装一下好,我就不在这里贴代码了,比较多。

  总结一下:

  总结获取AccessToken的三种方式,应该还有别的方式,小伙伴们如果还有其他方式也可以发邮件告诉我。cnryc@126.com。

  第二种方式里的线程,可以写在Global.asax.cs文件的Application_Start()方法的最后。

原文地址:https://www.cnblogs.com/imoonstal/p/4252994.html