Asp.Net Core 中IdentityServer4 授权原理及刷新Token的应用
一、前言
上面分享了IdentityServer4
两篇系列文章,核心主题主要是密码授权模式
及自定义授权模式
,但是仅仅是分享了这两种模式的使用,这篇文章进一步来分享IdentityServer4
的授权流程及refreshtoken
。
系列文章目录(没看过的先看这几篇文章再来阅读本文章):
- Asp.Net Core IdentityServer4 中的基本概念
- Asp.Net Core 中IdentityServer4 授权中心之应用实战
- Asp.Net Core 中IdentityServer4 授权中心之自定义授权模式
为了继续保持IdentityServer4
系列博客分享上下文一致,我这里再把上回授权中心
拆分后的图贴出来,如图:
图中的授权中心
就是通过IdentityServer4
实现的授权服务中心,我下面就直接用授权中心
代替IdentityServer4
的授权服务来继续述说,也感谢大家对我的支持,一直阅读我的文章。
二、授权流程
2.1 客户端验证流程图
流程图中,客户端仅仅会到授权中心
请求一次,并拿到验证公钥返回给Api资源
拥有端,后面客户端再次尝试请求Api资源
时候就不会再到授权中心
去获取验证公钥,会直接用之前获取到的公钥
进行验证,验证通过则授权通过。
2.2 授权及刷新refresh_token 流程图
然而通过授权中心
获取到的access_token
是有有效时间的,如果失效则需要通过refresh_token
重新到授权中心
去刷新获取最新的access_token
,整体的流程图如下:
客户端携带上一次获取到的access_token
请求受保护的Api资源
时,通过公钥
进行验证时发现access_token
已经过期,则客户端再携带refresh_token
向授权中心
再次发起请求,刷新access_token
以获得最新的access_token
和refresh_token
,用最新的access_token
去获取受保护的Api资源
,这样可以减少客户端多次跳转登录授权页面,提高用户体验。
三、应用实战
说到例子,我这里不从零开始撸代码, 还是在之前的代码基础上继续改造代码,在原有的定义客户端的代码中新增刷新access_token
的相关配置,代码如下:
public static IEnumerable<Client> GetClients()
{
return new List<Client>
{
new Client()
{
ClientId =OAuthConfig.UserApi.ClientId,
AllowedGrantTypes = new List<string>()
{
GrantTypes.ResourceOwnerPassword.FirstOrDefault(),//Resource Owner Password模式
GrantTypeConstants.ResourceWeixinOpen,
},
ClientSecrets = {new Secret(OAuthConfig.UserApi.Secret.Sha256()) },
AllowOfflineAccess = true,//如果要获取refresh_tokens ,必须把AllowOfflineAccess设置为true
AllowedScopes= {
OAuthConfig.UserApi.ApiName,
StandardScopes.OfflineAccess,
},
AccessTokenLifetime = OAuthConfig.ExpireIn,
},
};
}
如果你需要刷新access_token
,则需要把AllowOfflineAccess
设置true
,同时添加StandardScopes.OfflineAccess
这个Scopes
,主要代码如下:
AllowOfflineAccess = true,//如果要获取refresh_tokens ,必须把AllowOfflineAccess设置为true
AllowedScopes= {
OAuthConfig.UserApi.ApiName,
StandardScopes.OfflineAccess,//如果要获取refresh_tokens ,必须在scopes中加上OfflineAccess
},
授权中心
,完整代码如下:
OAuthMemoryData
代码如下:
/// <summary>
///
/// </summary>
public class OAuthMemoryData
{
/// <summary>
/// 资源
/// </summary>
/// <returns></returns>
public static IEnumerable<ApiResource> GetApiResources()
{
return new List<ApiResource>
{
new ApiResource(OAuthConfig.UserApi.ApiName,OAuthConfig.UserApi.ApiName),
};
}
public static IEnumerable<Client> GetClients()
{
return new List<Client>
{
new Client()
{
ClientId =OAuthConfig.UserApi.ClientId,
AllowedGrantTypes = new List<string>()
{
GrantTypes.ResourceOwnerPassword.FirstOrDefault(),//Resource Owner Password模式
GrantTypeConstants.ResourceWeixinOpen,
},
ClientSecrets = {new Secret(OAuthConfig.UserApi.Secret.Sha256()) },
AllowOfflineAccess = true,//如果要获取refresh_tokens ,必须把AllowOfflineAccess设置为true
AllowedScopes= {
OAuthConfig.UserApi.ApiName,
StandardScopes.OfflineAccess,
},
AccessTokenLifetime = OAuthConfig.ExpireIn,
},
};
}
/// <summary>
/// 测试的账号和密码
/// </summary>
/// <returns></returns>
public static List<TestUser> GetTestUsers()
{
return new List<TestUser>
{
new TestUser()
{
SubjectId = "1",
Username = "test",
Password = "123456"
},
};
}
/// <summary>
/// 微信openId 的测试用户
/// </summary>
/// <returns></returns>
public static List<TestUser> GetWeiXinOpenIdTestUsers()
{
return new List<TestUser>
{
new TestUser(){
SubjectId="owerhwroogs3902openId",
}
};
}
}
Startup
完整代码如下:
public class Startup
{
public Startup(IConfiguration configuration)
{
Configuration = configuration;
}
public IConfiguration Configuration { get; }
// This method gets called by the runtime. Use this method to add services to the container.
public void ConfigureServices(IServiceCollection services)
{
services.AddControllers();
services.Configure<CookiePolicyOptions>(options =>
{
// This lambda determines whether user consent for non-essential cookies is needed for a given request.
options.CheckConsentNeeded = context => true;
options.MinimumSameSitePolicy = SameSiteMode.None;
});
#region 内存方式
//services.AddIdentityServer()
// .AddDeveloperSigningCredential()
// .AddInMemoryApiResources(OAuthMemoryData.GetApiResources())
// .AddInMemoryClients(OAuthMemoryData.GetClients())
// .AddTestUsers(OAuthMemoryData.GetTestUsers());
#endregion
#region 数据库存储方式
services.AddIdentityServer()
.AddDeveloperSigningCredential()
.AddInMemoryApiResources(OAuthMemoryData.GetApiResources())
//.AddInMemoryClients(OAuthMemoryData.GetClients())
.AddClientStore<ClientStore>()
.AddResourceOwnerValidator<ResourceOwnerPasswordValidator>()
.AddExtensionGrantValidator<WeiXinOpenGrantValidator>();//添加微信端自定义方式的验证
#endregion
}
// This method gets called by the runtime. Use this method to configure the HTTP request pipeline.
public void Configure(IApplicationBuilder app, IWebHostEnvironment env)
{
if (env.IsDevelopment())
{
app.UseDeveloperExceptionPage();
}
app.UseIdentityServer();
app.UseRouting();
app.UseAuthorization();
app.UseEndpoints(endpoints =>
{
endpoints.MapControllers();
});
}
}
授权中心
代码基本上已经改造完成,我们用postman 访问授权中心
试一试,如下图:
访问结果中已经包含了refresh_token
和access_token
等相关信息。
我们再来通过access_token
访问Api资源
(上两篇有相关代码,未阅读上两篇先去查阅)这里我就直接携带access_token
去访问,如图:
访问成功!!
我们再来刷新下refresh_token
,访问如图:
刷新refresh_token
成功。
我们到这里再来做一个小小的测试,测试上面的授权流程中的,第4,5 步,上面说到第4步主要是客户端第一次请求Api资源
时会向ids4
服务网关去请求获取验证公钥,
获取成功返回给Api资源
并存储在内存中,后续不再会到ids4
服务去获取验证公钥
我们把上面的授权中心
(ids4服务网关)停止运行,再来用之前的access_token
请求Api资源
,如下图:
现在已经确定授权中心
(ids4服务网关)确实停止了,不能访问了,那我们再来通过之前未过期的access_token
来请求Api资源
网关,结果如下图:
完美,请求还是成功,这完全证明:客户端请求Api资源网关(受保护的资源)时,第一次收到请求会到授权中心(ids4服务网关)获取验证公钥,并保持到内存中,后面的请求不会再到授权中心去获得验证公钥,而是Api资源网关(受保护的资源)中直接通过保存下来的验证公钥进行验证,从而通过授权。
Asp.Net Core 中IdentityServer4 授权原理及刷新Token的应用的更多相关文章
- Asp.Net Core 中IdentityServer4 授权中心之自定义授权模式
一.前言 上一篇我分享了一篇关于 Asp.Net Core 中IdentityServer4 授权中心之应用实战 的文章,其中有不少博友给我提了问题,其中有一个博友问我的一个场景,我给他解答的还不够完 ...
- Asp.Net Core 中IdentityServer4 授权中心之应用实战
一.前言 查阅了大多数相关资料,查阅到的IdentityServer4 的相关文章大多是比较简单并且多是翻译官网的文档编写的,我这里在 Asp.Net Core 中IdentityServer4 的应 ...
- Asp.Net Core 中IdentityServer4 实战之角色授权详解
一.前言 前几篇文章分享了IdentityServer4密码模式的基本授权及自定义授权等方式,最近由于改造一个网关服务,用到了IdentityServer4的授权,改造过程中发现比较适合基于Role角 ...
- Asp.Net Core 中IdentityServer4 实战之 Claim详解
一.前言 由于疫情原因,让我开始了以博客的方式来学习和分享技术(持续分享的过程也是自己学习成长的过程),同时也让更多的初学者学习到相关知识,如果我的文章中有分析不到位的地方,还请大家多多指教:以后我会 ...
- ASP.NET Core 中jwt授权认证的流程原理
目录 1,快速实现授权验证 1.1 添加 JWT 服务配置 1.2 颁发 Token 1.3 添加 API访问 2,探究授权认证中间件 2.1 实现 Token 解析 2.2 实现校验认证 1,快速实 ...
- 从零搭建一个IdentityServer——聊聊Asp.net core中的身份验证与授权
OpenIDConnect是一个身份验证服务,而Oauth2.0是一个授权框架,在前面几篇文章里通过IdentityServer4实现了基于Oauth2.0的客户端证书(Client_Credenti ...
- 聊聊 asp.net core 认证和授权
使用asp.net core 开发应用系统过程中,基本上都会涉及到用户身份的认证,及授权访问控制,因此了解认证和授权流程也相当重要,下面通过分析asp.net core 框架中的认证和授权的源码来分析 ...
- ASP.NET Core 认证与授权[5]:初识授权
经过前面几章的姗姗学步,我们了解了在 ASP.NET Core 中是如何认证的,终于来到了授权阶段.在认证阶段我们通过用户令牌获取到用户的Claims,而授权便是对这些的Claims的验证,如:是否拥 ...
- ASP.NET Core 认证与授权[6]:授权策略是怎么执行的?
在上一章中,详细介绍了 ASP.NET Core 中的授权策略,在需要授权时,只需要在对应的Controler或者Action上面打上[Authorize]特性,并指定要执行的策略名称即可,但是,授权 ...
随机推荐
- linux openjdk安装
sudo apt-get install openjdk-8-jdk 默认提示是 sudo apt-get install openjdk-8-jre, 这个只有jre https://openjdk ...
- java中Redis5大基本类型的用法
存储格式 基本用法 通过Jedis(封装了redis的Java客户端)对redis进行操作. Jedis工具类 public class JedisPoolUtil { private static ...
- Java开发面试常见问题合集
次面试事故 面试官:你看过哪些源码?我:都挺熟悉的面试官:对hashMap了解程度怎么样?面试官:那你能讲讲 HashMap的实现原理吗?面试官:HashMap什么时候会进行 rehash?面试官:结 ...
- Java IO: Reader And Writer
原文链接 作者: Jakob Jenkov 译者: 李璟(jlee381344197@gmail.com) Java IO的Reader和Writer除了基于字符之外,其他方面都与InputStre ...
- 关于前端使用JavaScript获取base64图片大小的方法
base64原理 Base64编码要求把3个8位字节(38=24)转化为4个6位的字节(46=24),之后在6位的前面补两个0,形成8位一个字节的形式. 如果剩下的字符不足3个字节,则用0填充,输出字 ...
- 云服务器——之Linux下安装tomcat
在上一篇文章中已经准备好了tomcat安装的基本环境jdk的安装,那么我们现在来记录tomcat的安装. 第一步:下载tomcat安装包 http://tomcat.apache.org/ 第二步:通 ...
- MyEclipse提示Errors occurred during the build
最近在使用Extjs 在springsource Tool Suite运行时老是出现: Errors occurred during the build. Errors running builder ...
- 用shell脚本新建文件并自动生成头说明信息
目标: 新建文件后,直接给文件写入下图信息 代码实现: [root@localhost test]# vi AutoHead.sh #!/bin/bash #此程序的功能是新建shell文件并自动生成 ...
- paxos算法学习总结
核心思想 分布式系统架构下如何让整体尽快达成一致观点,也就是多个不同观点收敛到一个观点的过程. 难点 可能会发生少数节点故障,但绝不是大面积故障,不然系统也没法正常工作. 由于存在单点故障,因此不可能 ...
- Job Shop
flow shop: 如果每个作业需要在每个处理机上加工,而且每个作业的工序也相同,即在处理机上加工的顺序相同,则这种多类机的环境称为同顺序作业或流水作业. job shop: 如果每个作业需要在每个 ...