I am using asp.net identity (WebApi 2, MVC 5, not .net core) to add claims to my user's identity when she logs in from our singe page application. This looks like this (I have stripped out the checks for invalid names, locked accounts, etc)
public override async Task GrantResourceOwnerCredentials(OAuthGrantResourceOwnerCredentialsContext context)
{
var userManager = context.OwinContext.GetUserManager<CompWalkUserManager>();
var user = await userManager.FindByNameAsync(context.UserName);
var check = await userManager.CheckPasswordAsync(user, context.Password);
if (!check)
{
await userManager.AccessFailedAsync(user.Id);
context.SetError("invalid_grant", invalidUser);
return;
}
ClaimsIdentity oAuthIdentity = await user.GenerateUserIdentityAsync(userManager,
OAuthDefaults.AuthenticationType);
ClaimsIdentity cookiesIdentity = await user.GenerateUserIdentityAsync(userManager,
CookieAuthenticationDefaults.AuthenticationType);
//These claims are key/value pairs stored in the local database
var claims = GetClaimsForUser(user);
cookiesIdentity.AddClaims(claims);
oAuthIdentity.AddClaims(claims);
AuthenticationProperties properties = CreateProperties(user.UserName);
AuthenticationTicket ticket = new AuthenticationTicket(oAuthIdentity, properties);
context.Validated(ticket);
context.Request.Context.Authentication.SignIn(cookiesIdentity);
}
At this point, everything is working as expected. I can check the user's claims via an AuthorizationFilterAttribute
as methods on my api are called.
However, it is possible that an administrator might change the values of the claims while the user is logged in (our tokens are good for 14 days). As an example we have a claim named Locations
with a value of EditAndDelete
. The admin might change this value to NoAccess
in the database, but the authentication will not know about about this.
I can see that at run-time I can add or remove claims from my identity
, but these changes do not persist past the current request. Is there a way to update the auth ticket in the cookies on the fly? I would like to be able to update my Identity
with the new value without having the user have to log out.
If you want to go the Identity way of doing that, you need to hit the db on every login. You set the
SecurityStamp
validation interval to 0:When the permissions are changed for a user, you update their securitystamp: