I'm unable to log off the user in an MVC 5 app using ASP.NET Identity with Owin (latest versions). Login works great...but I can't log the user off without opening the browser settings to delete the cookie.
When the LogOff action runs, the browser redirects to the designated page which has the [Authorize] attribute. It should be rejected at that point and redirected to the Login page.
Note that if I manually delete the cookies, it will redirect correctly when attempting to open the [Authorize] page, so the redirect action for unauthenticated users is working correctly.
I see a lot of similar questions and have tried the solutions, but nothing is working so far.
I changed:
AuthenticationManager.SignOut();
To:
AuthenticationManager.SignOut(DefaultAuthenticationTypes.ApplicationCookie);
as suggested in previous answers, but it didn't change the behavior.
Login works fine. I notice after attempting to LogOff, there are two cookies with the same name instead of just one. One cookie is empty, and one is not.
Here's my LogOff method:
[HttpPost]
[AllowAnonymous]
public ActionResult LogOff()
{
AuthenticationManager.SignOut(DefaultAuthenticationTypes.ApplicationCookie);
//Clear the principal to ensure the user does not retain any authentication
HttpContext.User = new GenericPrincipal(new GenericIdentity(string.Empty), null);
// Redirect to a controller/action that requires authentication to ensure a redirect takes place
// this clears the Request.IsAuthenticated flag since this triggers a new request
return RedirectToLocal(String.Empty);
}
And my OwinStartup class:
public class OwinStartup
{
public void Configuration(IAppBuilder app)
{
ConfigureAuth(app);
}
// For more information on configuring authentication, please visit http://go.microsoft.com/fwlink/?LinkId=301864
public void ConfigureAuth(IAppBuilder app)
{
// UserManagerFactory = () => new UserManager<IdentityUser>(new UserStore<IdentityUser>(new TenantDbContext()));
// Configure the db context, user manager and signin manager to use a single instance per request
app.CreatePerOwinContext(TenantDbContext.Create);
app.CreatePerOwinContext<ApplicationUserManager>(ApplicationUserManager.Create);
app.CreatePerOwinContext<ApplicationSignInManager>(ApplicationSignInManager.Create);
// Enable the application to use a cookie to store information for the signed in user
// and to use a cookie to temporarily store information about a user logging in with a third party login provider
// Configure the sign in cookie
app.UseCookieAuthentication(new CookieAuthenticationOptions
{
AuthenticationType = DefaultAuthenticationTypes.ApplicationCookie,
LoginPath = new PathString("/Account/Login"),
CookieSecure = CookieSecureOption.Always,
Provider = new CookieAuthProvider
{
// Enables the application to validate the security stamp when the user logs in.
// This is a security feature which is used when you change a password or add an external login to your account.
OnValidateIdentity = SecurityStampValidator.OnValidateIdentity<ApplicationUserManager, ApplicationUser>(
validateInterval: TimeSpan.FromMinutes(30),
regenerateIdentity: (manager, user) => user.GenerateUserIdentityAsync(manager))
}
});
AntiForgeryConfig.UniqueClaimTypeIdentifier = ClaimTypes.NameIdentifier;
}
public class CookieAuthProvider : CookieAuthenticationProvider
{
public override void ResponseSignIn(CookieResponseSignInContext context)
{
context.CookieOptions.Domain = context.Request.Uri.Host;
base.ResponseSignIn(context);
}
}
}
And here's my AuthenticationManager:
private IAuthenticationManager AuthenticationManager
{
get
{
return HttpContext.GetOwinContext().Authentication;
}
}