一、应用场景
以调用微信公众号的Api为例, 经常会用到access_token,官方文档这样描述:“是公众号的全局唯一接口调用凭据,有效期目前为2个小时,需定时刷新,重复获取将导致上次获取的access_token失效,建议公众号开发者使用中控服务器统一获取和刷新Access_token,其他业务逻辑服务器所使用的access_token均来自于该中控服务器,不应该各自去刷新,否则容易造成冲突,导致access_token覆盖而影响业务。”
在这个场景中我们可以创建一个后台运行的服务,按照access_token的有效期定时执行去请求获取新的access_token并存储,其他所有需要用到这个access_token的都到这个共有的access_token。
二、实现方式(一)
ASP.NET Core 在2.0的时候就提供了一个名为IHostedService的接口,我们要做的只有两件事:
1. 实现它。
2. 将这个接口实现注册到依赖注入服务中。
A. 实现IHostedService的接口
首先看一下这个IHostedService:
public interface IHostedService { Task StartAsync(CancellationToken cancellationToken); Task StopAsync(CancellationToken cancellationToken); }
通过名字就可以看出来,一个是这个服务启动的时候做的操作,另一个则是停止的时候。
新建一个类 TokenRefreshService 实现 IHostedService ,如下面代码所示:
1. 1 internal class TokenRefreshService : IHostedService, IDisposable 2 { 3 private readonly ILogger _logger; 4 private Timer _timer; 5 6 public TokenRefreshService(ILogger<TokenRefreshService> logger) 7 { 8 _logger = logger; 9 } 10 11 public Task StartAsync(CancellationToken cancellationToken) 12 { 13 _logger.LogInformation("Service starting"); 14 _timer = new Timer(Refresh, null, TimeSpan.Zero,TimeSpan.FromSeconds(5)); 15 return Task.CompletedTask; 16 } 17 18 private void Refresh(object state) 19 { 20 _logger.LogInformation(DateTime.Now.ToLongTimeString() + ": Refresh Token!"); //在此写需要执行的任务 21 22 } 23 24 public Task StopAsync(CancellationToken cancellationToken) 25 { 26 _logger.LogInformation("Service stopping"); 27 _timer?.Change(Timeout.Infinite, 0); 28 return Task.CompletedTask; 29 } 30 31 public void Dispose() 32 { 33 _timer?.Dispose(); 34 } 35 }
既然是定时刷新任务,那么就用了一个timer, 当服务启动的时候启动它,由它定时执行Refresh方法来获取新的Token。
这里为了方便测试写了5秒执行一次, 实际应用还是读取配置文件比较好, 结果如下:
BackService.TokenRefreshService:Information: 17:23:30: Refresh Token! BackService.TokenRefreshService:Information: 17:23:35: Refresh Token! BackService.TokenRefreshService:Information: 17:23:40: Refresh Token! BackService.TokenRefreshService:Information: 17:23:45: Refresh Token! BackService.TokenRefreshService:Information: 17:23:50: Refresh Token!
B. 在依赖注入中注册这个服务。
在Startup的ConfigureServices中注册这个服务,如下代码所示:
services.AddSingleton<IHostedService, TokenRefreshService>();