微信开发-ACCESS TOKEN 过期失效解决方案
微信开发-ACCESS TOKEN 过期失效解决方案
起因:因为access_token的重要性,开发过微信的都知道,但是他有自己的生命周期,官方解释为:"有效期为7200秒",一天调用2000次。流量一高,就over了,没办法,龙哥不帮我们解决问题,我们就要自己解决,不能等死。
解决思路很简单:建立公共access token数据,有效期内不重新创建access_token。
解决方案:
1、微信类库:有效期内直接读取access token数据文件中的json数据,过期失效,重新获取并创建新的access token数据文件
2、数据文件:存放有效的access token数据,具体有:access_token.json和jsapi_ticket.json
核心代码如下:
Index: wxjsSDK.cs
===================================================================
--- wxjsSDK.cs (revision 0)
+++ wxjsSDK.cs (revision 1)
@@ -0,0 +1,209 @@
+using System;
+using System.Collections.Generic;
+using System.Web;
+using System.IO;
+using System.Security.Cryptography;
+using System.Runtime.Serialization.Json;
+using System.Runtime.Serialization;
+using System.Net;
+using System.Runtime.Serialization.Formatters.Binary;
+using System.Text;
+
+namespace JR.Common
+{
+ public class wxjsSDK
+ {
+ private string appId;
+ private string appSecret;
+
+
+ public wxjsSDK(string appId, string appSecret)
+ {
+ this.appId = appId;
+ this.appSecret = appSecret;
+ }
+
+
+
+ //得到数据包,返回使用页面
+ public System.Collections.Hashtable getSignPackage()
+ {
+ string jsapiTicket = getJsApiTicket();
+ string url = HttpContext.Current.Request.Url.ToString(); //"http://$_SERVER[HTTP_HOST]$_SERVER[REQUEST_URI]";
+ string timestamp = Convert.ToString(ConvertDateTimeInt(DateTime.Now));
+ string nonceStr = createNonceStr();
+ // 这里参数的顺序要按照 key 值 ASCII 码升序排序
+ string rawstring = "jsapi_ticket=" + jsapiTicket + "&noncestr=" + nonceStr + "×tamp=" + timestamp + "&url=" + url + "";
+ string signature = SHA1_Hash(rawstring);
+ var signPackage = new System.Collections.Hashtable();
+ signPackage.Add("appId", appId);
+ signPackage.Add("nonceStr", nonceStr);
+ signPackage.Add("timestamp", timestamp);
+ signPackage.Add("url", url);
+ signPackage.Add("signature", signature);
+ signPackage.Add("rawString", rawstring);
+ return signPackage;
+ }
+
+
+ //创建随机字符串
+ private string createNonceStr()
+ {
+ int length = 16;
+ string chars = "abcdefghijklmnopqrstuvwxyzABCDEFGHIJKLMNOPQRSTUVWXYZ0123456789";
+ string str = "";
+ var rad = new Random();
+ for (int i = 0; i < length; i++)
+ {
+ str += chars.Substring(rad.Next(0, chars.Length - 1), 1);
+ }
+ return str;
+ }
+
+
+ //得到ticket 如果文件里时间 超时则重新获取
+ private string getJsApiTicket()
+ {
+ string ticket = "";
+ // jsapi_ticket 应该全局存储与更新,以下代码以写入到文件中做示例
+ string path = HttpContext.Current.Server.MapPath(@"/log/jssdk/jsapi_ticket.json");
+ if (!File.Exists(path))
+ {
+ File.Create(path).Close();
+ }
+ StreamReader sr = new StreamReader(path, System.Text.Encoding.Default);
+ string filecontent = sr.ReadToEnd();
+ CommonJsonModel jsonModel = null;
+ if (!string.IsNullOrEmpty(filecontent))
+ {
+ jsonModel = new CommonJsonModel(filecontent);
+ }
+ sr.Close();
+ sr.Dispose();
+ if (jsonModel == null || int.Parse(jsonModel.GetValue("expires_in")) < ConvertDateTimeInt(DateTime.Now))
+ {
+ string accessToken = getAccessToken();
+ string url = "https://api.weixin.qq.com/cgi-bin/ticket/getticket?type=jsapi&access_token=" + accessToken;
+ jsonModel = new CommonJsonModel(httpGet(url));
+ ticket = jsonModel.GetValue("ticket");
+ if (ticket != "")
+ {
+ string json = "{\"ticket\":\"" + ticket + "\",\"expires_in\":" + (ConvertDateTimeInt(DateTime.Now) + 7000) + "}";
+ StreamWriterMetod(json, path);
+ }
+ }
+ else
+ {
+ ticket = jsonModel.GetValue("ticket");
+ }
+ return ticket;
+ }
+
+
+ //得到accesstoken 如果文件里时间 超时则重新获取
+ private string getAccessToken()
+ {
+ // access_token 应该全局存储与更新,以下代码以写入到文件中做示例
+ string access_token = "";
+ string path = HttpContext.Current.Server.MapPath(@"/log/jssdk/access_token.json");
+ if (!File.Exists(path))
+ {
+ File.Create(path).Close();
+ }
+ StreamReader sr = new StreamReader(path, System.Text.Encoding.Default);
+ string filecontent = sr.ReadToEnd();
+ CommonJsonModel jsonModel = null;
+ if (!string.IsNullOrEmpty(filecontent))
+ {
+ jsonModel = new CommonJsonModel(filecontent);
+ }
+ sr.Close();
+ sr.Dispose();
+ if (jsonModel == null || int.Parse(jsonModel.GetValue("expires_in")) < ConvertDateTimeInt(DateTime.Now))
+ {
+ string url = "https://api.weixin.qq.com/cgi-bin/token?grant_type=client_credential&appid=" + appId +
+ "&secret=" + appSecret + "";
+ jsonModel = new CommonJsonModel(httpGet(url));
+ access_token = jsonModel.GetValue("access_token");
+ if (access_token != "")
+ {
+ string json = "{\"access_token\":\"" + access_token + "\",\"expires_in\":" + (ConvertDateTimeInt(DateTime.Now) + 7000) + "}";
+ StreamWriterMetod(json, path);
+ }
+ }
+ else
+ {
+ access_token = jsonModel.GetValue("access_token");
+ }
+ return access_token;
+ }
+
+
+ //发起一个http请球,返回值
+ private string httpGet(string url)
+ {
+ try
+ {
+ var MyWebClient = new WebClient();
+ MyWebClient.Credentials = CredentialCache.DefaultCredentials; //获取或设置用于向Internet资源的请求进行身份验证的网络凭据
+ Byte[] pageData = MyWebClient.DownloadData(url); //从指定网站下载数据
+ string pageHtml = System.Text.Encoding.Default.GetString(pageData);//如果获取网站页面采用的是GB2312,则使用这句
+ //string pageHtml = Encoding.UTF8.GetString(pageData); //如果获取网站页面采用的是UTF-8,则使用这句
+ return pageHtml;
+ }
+ catch (WebException webEx)
+ {
+ Console.WriteLine(webEx.Message.ToString());
+ return null;
+ }
+ }
+
+
+ //SHA1哈希加密算法
+ private string SHA1_Hash(string str_sha1_in)
+ {
+ SHA1 sha1 = new SHA1CryptoServiceProvider();
+ byte[] bytes_sha1_in = System.Text.UTF8Encoding.Default.GetBytes(str_sha1_in);
+ byte[] bytes_sha1_out = sha1.ComputeHash(bytes_sha1_in);
+ string str_sha1_out = BitConverter.ToString(bytes_sha1_out);
+ str_sha1_out = str_sha1_out.Replace("-", "").ToLower();
+ return str_sha1_out;
+ }
+
+
+ /// <summary>
+ /// StreamWriter写入文件方法
+ /// </summary>
+ private void StreamWriterMetod(string str, string patch)
+ {
+ FileStream stream = new FileStream(patch, FileMode.OpenOrCreate, FileAccess.Write, FileShare.Delete | FileShare.ReadWrite);
+ StreamWriter writer = new StreamWriter(stream);
+ writer.WriteLine(str);
+ stream.Flush();
+ writer.Close();
+ stream.Close();
+ stream.Dispose();
+ writer.Dispose();
+ }
+
+
+
+
+ /// <summary>
+ /// 将c# DateTime时间格式转换为Unix时间戳格式
+ /// </summary>
+ /// <param name="time">时间</param>
+ /// <returns>double</returns>
+ private int ConvertDateTimeInt(System.DateTime time)
+ {
+ int intResult = 0;
+ System.DateTime startTime = TimeZone.CurrentTimeZone.ToLocalTime(new System.DateTime(1970, 1, 1));
+ intResult = Convert.ToInt32((time - startTime).TotalSeconds);
+ return intResult;
+ }
+
+
+ }
+
+
+}
access_token.json
{"access_token":"4H14BVCUrAxxxxxxxxxxxxWeLu-zKETaBYqsoKFjsHZDc3xOwc-m43WDw2HjzxEkng2nC7iJuHydNt5PqRDY7HCoAU4lmuaPoYsIQHdW9kA","expire_time":1428599121}
access_token.json
{"jsapi_ticket":"bxLdikRXVbTPdHSM05e5u1wgoccccccccccccccccccccccccccccc11FFzYsiqbXZN0SDGN6Dnksnt2Q","expire_time":1428599122}
微信开发-ACCESS TOKEN 过期失效解决方案的更多相关文章
- 微信公众平台开发 ACCESS TOKEN
获取access token 返回 access_token是公众号的全局唯一票据,公众号调用各接口时都需使用access_token.正常情况下access_token有效期为7200秒,重复获取将 ...
- nodejs微信开发获取token,ticket-1
/* jshint -W079 */ /* jshint -W020 */ "use strict"; var _ = require("lodash"); v ...
- 微信access token过期
两台服务器使用同一个微信账号(同一个app id) 时,当其中一台服务器向微信请求access token时,会造成另一台服务器的access token过期
- atitit. access token是什么??微信平台公众号开发access_token and Web session保持状态机制
atitit. access token是什么??微信平台公众号开发access_token and Web session保持状态机制 1. token机制and session保持状态机制 1 ...
- 微信公众平台开发(26) ACCESS TOKEN
本文介绍微信公众平台下Access Token的概念及获取方法. 一.Access Token access_token是公众号的全局唯一票据,公众号调用各接口时都需使用access_token.正常 ...
- Force.com微信开发系列(四)申请Access Token及自定义菜单之创建菜单
在微信接口开发中,许多服务的使用都离不开Access Token,Access Token相当于打开这些服务的钥匙,正常情况下会在7200秒内失效,重复获取将导致上次获取的Token失效,本文将首先介 ...
- 微信公众平台开发(112) 自动更新微信access token
关键字:Memcache access_token 更新 存储 7200 本文介绍如何存储及更新 access token的方法. 一.Access Token access_token是公众号的全局 ...
- .NET微信开发通过Access Token和OpenID获取用户信息
本文介绍如何获得微信公众平台关注用户的基本信息,包括昵称.头像.性别.国家.省份.城市.语言. 本文的方法将囊括订阅号和服务号以及自定义菜单各种场景,无论是否有高级接口权限,都有办法来获得用户基本信息 ...
- 微信公众平台开发视频教程-03-获取Access Token和获取微信服务器IP,添加微信菜单
1 获取access token 此token是以后每次调用微信接口都会带上的票据,token是公众号全局唯一票据,在调用其他接口之前都需要先得到token,taoken长度至少512个字符,通常用s ...
随机推荐
- 操作各个版本的excel的链接写法
有很有意思的网站:https://connectionstrings.com/ace-oledb-12-0/ 很详细得介绍了各种写法 这里主要提两个: string strCon = @" ...
- 探索软件工程道路上的我II (Θ∀Θ#)
------作业要求------ 第一版本程序Prog1:+ 给定一个数组,实现数组元素求和:具体要求:实现对一维数组(a[100])的所有元素相加运算.+ 数据准备:a)数组长度:100:b)数组数 ...
- Caused by: java.lang.NoClassDefFoundError:
tomcat启动不了 报错信息头如下: Caused by: java.lang.NoClassDefFoundError: at java.lang.Class.getDeclaredMethods ...
- 第三个Sprint总结
工作进展:项目基本已经完成 工作状况:
- 如何用github快速搭建个人博客
当当当当-来看下新鲜出炉的Github博客 http://wli12.github.io/ 喜欢写markdown,但cnblogs对md文件的渲染简直丑爆了... 好奇怎么用github+Jekyl ...
- VIM-Sed常用的一些记录。。。逐渐学习。。
:[range]co[py] {address} :t :[range]m[ove] {address] 例如 :1,3t10 1-3行复制到10行后.用m就是移动了. :sort / / // ...
- myeclipse打war包时,报错security alert integrity check error
今天在用myeclipse打包项目时,出现如下图的提示: 在网上查找了一下原因,主要是由于Jar包不符合所导致的.解决办法如下: 将com.genuitec.eclipse.export.wizard ...
- PullToRefreshGridView刷新加载
<com.handmark.pulltorefresh.library.PullToRefreshGridView xmlns:ptr="http://schemas.a ...
- cache manifest 格式
下面说明书写 cache manifest 文件需要遵循的格式.1 首行必须是 CACHE MANIFEST.2 其后,每一行列出一个需要缓存的资源文件名.3 可根据需要列出在线访问的白名单.白名单中 ...
- JavaScript高级程序设计-第六章面向对象的程序设计
创建对象主要的两种形式,创建Object实例和创建对象字面量 对象包含属性和方法 数据 .属性有四个特性,特性是为了描述属性行为的,他们是: Configurable(可配置的)是否能删除或是否能修改 ...