更新时间:2023-12-05 11:28:28
如果您尝试添加新角色已经登录的用户,您需要注册用户了。然后创建与新身份新角色和标志用户新的身份。这是更新的cookie的唯一途径。
If you are trying to add new role to already logged-in user, you need to sign user out. Then create new identity with new role and sign user in with the new identity. That's the only way to update the cookie.
要检查是否已经改变了用户属性是你已经在使用回调***的地方: CookieAuthenticationProvider.OnValidateIdentity
。事情是这样的。
Best place to check if user properties have changed are in callback you already use: CookieAuthenticationProvider.OnValidateIdentity
. Something like this.
app.UseCookieAuthentication(new CookieAuthenticationOptions
{
// other stuff
Provider = new CookieAuthenticationProvider
{
// this function is executed every http request and executed very early in the pipeline
// and here you have access to cookie properties and other low-level stuff.
// makes sense to have the invalidation here
OnValidateIdentity = async context =>
{
// invalidate user cookie if user's security stamp have changed
var invalidateBySecirityStamp = SecurityStampValidator.OnValidateIdentity<ApplicationUserManager, ApplicationUser>(
validateInterval: TimeSpan.FromMinutes(30),
regenerateIdentity: (manager, user) => user.GenerateUserIdentityAsync(manager));
await invalidateBySecirityStamp.Invoke(context);
if (context.Identity == null || !context.Identity.IsAuthenticated)
{
return;
}
if(/*Need to update cookie*/)
{
// get user manager. It must be registered with OWIN
var userManager = context.OwinContext.GetUserManager<UserManager>();
var username = context.Identity.Name;
// get new user identity with updated properties
var updatedUser = await userManager.FindByNameAsync(username);
// updated identity from the new data in the user object
var newIdentity = updatedUser.GenerateUserIdentityAsync(manager);
// kill old cookie
context.OwinContext.Authentication.SignOut(context.Options.AuthenticationType);
// sign in again
var authenticationProperties = new AuthenticationProperties() { IsPersistent = context.Properties.IsPersistent };
context.OwinContext.Authentication.SignIn(authenticationProperties, newIdentity);
}
}
}
});
免责声明 - 从未测试过,甚至没有试图编译
Disclaimer - never tested it, not even tried to compile it.
也可以看到我的其他答案参考 - pretty多同一块code的,但不同的目标。
Also can see my other answer for reference - pretty much the same piece of code, but different goal.
UPD:
关于这个问题的另一部分 - 如何检测一个角色的变化:结果
我能想到的办法 - 对用户记录另一个GUID。类似 SecurityStamp
,但不使用框架。说它 MySecurityStamp
。在登录添加 MySecurityStamp
的值到cookie作为索赔。在每次请求中的cookie来在数据库中的值进行比较 MySecurityStamp
的价值。如果值不同 - 时间以再生的身份。而在每一个新的角色添加/删除修改 MySecurityStamp
在数据库中的用户。这将覆盖所有的浏览器的所有会话。
UPD:
Regarding another part of the question - how to detect a role change:
I can think of a way - have another GUID on a user record. Similar to SecurityStamp
, but not used by the framework. Call it MySecurityStamp
. On sign-in add value of MySecurityStamp
to the cookie as a claim. On every request compare value of MySecurityStamp
in the cookie to the value in the database. If values are different - time to regenerate the identity. And on every new role added/removed modify MySecurityStamp
for the user in the database. This will cover all the sessions in all the browsers.