我们目前使用Identityserver4 2.0构建了一个身份服务器。我们正在为API添加一些政策指南。我一直在阅读一些教程,主要是这篇Policy-Based Authorization in ASP.NET Core
public void ConfigureServices(IServiceCollection services)
{
services.AddMvc();
services.AddAuthorization(options =>
{
options.AddPolicy("RequireElevatedRights", policy => policy.RequireRole("SuperAdministrator", "ChannelAdministrator"));
});
}
[Authorize(Policy = "RequireElevatedRights")]
public class ChannelAdministrationController: Controller
{
}
我认为我们对如何做到这一点有一些想法。据我了解,我们的API将检查当前用户授权并围绕该授权构建策略。基本上我们正在检查用户在标题中发送的令牌是否正确?
我的问题是,如果用户在创建令牌后更改了权限。鉴于访问令牌有效期为1小时,刷新令牌不会过期。这是否意味着拥有有效令牌的用户仍然可以访问一小时的内容?
我们如何确保当前经过身份验证的用户实际上仍有权执行声明中的操作?
答案 0 :(得分:2)
(jwt)令牌的主要观点是,您不必在每次请求时点击数据库。
身份令牌(长期令牌)和访问令牌(短期,<= 60分钟)不应包含授权相关数据。
身份令牌应仅包含很少更改并与用户身份相关联的声明(用户名,第一个+姓氏,生日,电子邮件,email_verified等)。
不要把角色放在&#34;管理员&#34;如果你希望它经常变化。
授权(允许用户A创建它,或者读取/查看资源)应该在一个单独的(每个服务)数据库中完成,然后从那里获取它(如果需要,还可以缓存)。
您的替代方案,如果您确实已经提供了这样的权限&#34;在令牌内部或有必要立即生效的情况(受损帐户,或解雇工人),然后您可以撤销令牌。
但请记住,吊销端点仅适用于刷新和引用(也称为不透明)令牌。
您无法开箱即用撤销JWT。当然,当生成它时,可以在令牌中放入一个唯一的(随机的)id,并将其放入内存缓存(redis,本地缓存)中,并具有令牌的到期时间。
在每个请求中,您检查该ID是否仍在缓存中。如果其位置和令牌有效,则允许访问。否则否认它。
当您执行一些敏感更改时,将消息发送到您的消息总线(rabbitmq,azure queues,redis),触发一个处理程序,从缓存中删除该ID,并在下次请求时找不到该值在缓存中并将拒绝访问
答案 1 :(得分:0)
虽然我的答案可能没有Tseng的评论和之前的答案那么深刻,但我对此进行了一些实验,并采用了略微不同的方法。
我被要求将角色转储到已颁发的令牌中,是的,你100%正确,除非令牌更新(我的情况是1小时),如果api服务器没有,他们可以访问1小时或更长时间被任何电话击中。
我的解决方法有两点:
它可能不是pretties解决方案,但它意味着超级管理员改变你的角色的那一刻,如果有的话,它会从db存储库中擦除用户令牌。 前端将在60秒后(或者在他们拨打电话之前)点击api服务器,强制用户再次被重定向到登录页面以获取新令牌。
这意味着在最坏的情况下,用户可以在擦除令牌后60秒内访问。
不是最干净的解决方案,而是为实验做了诀窍。