如何设置asp.net身份验证的cookie过期时间

38

我使用Asp.Net Identity来控制我的应用程序的授权。现在,我需要做到这一点:如果用户在30分钟内没有操作,则跳转到登录页面,当他登录时不选中“isPersistent”复选框。 而且,如果他选中了“isPersistent”复选框,则将cookie的过期日期设置为14天。 我尝试通过更改Startup.Auth.cs文件来实现这一点:

public void ConfigureAuth(IAppBuilder app)
{
    app.UseCookieAuthentication(new CookieAuthenticationOptions
    {
        AuthenticationType = DefaultAuthenticationTypes.ApplicationCookie,
        LoginPath = new PathString("/Account/Login"),
        SlidingExpiration = true,
        CookieName = WebHelpers.ConstStrings.AUTHCOOKIESNAME
    });
}

并且 SignIn 代码看起来像这样:

private async Task SignInAsync(User user, bool isPersistent)
{
    AuthenticationManager.SignOut(DefaultAuthenticationTypes.ExternalCookie);
    var identity = await UserManager.CreateIdentityAsync(user, DefaultAuthenticationTypes.ApplicationCookie);
    if (isPersistent)
    {
        AuthenticationManager.SignIn(new AuthenticationProperties() { IsPersistent = isPersistent }, identity);
    }
    else
    {
        AuthenticationManager.SignIn(new AuthenticationProperties() { ExpiresUtc = new DateTimeOffset(DateTime.UtcNow.AddMinutes(30)) }, identity);
    }
}

但是我发现当用户不选择isPersistent复选框时,cookie的过期日期已经是“Session”,而不是当前时间加30分钟。

输入图像描述

使用以下代码后,cookie状态为如下,因此“记住我”复选框无法工作。:(

        app.UseCookieAuthentication(new CookieAuthenticationOptions
        {
            AuthenticationType = DefaultAuthenticationTypes.ApplicationCookie,
            LoginPath = new PathString("/Account/Login"),
            ExpireTimeSpan = TimeSpan.FromMinutes(30),
            SlidingExpiration = true,
            CookieName = WebHelpers.ConstStrings.AUTHCOOKIESNAME
        });

输入图像描述

4个回答

59
如果AuthenticationPropertiesIsPersistent属性设置为false,则cookie过期时间将设置为会话(长名称为“Session Cookie”,在关闭浏览器后删除)。
如果选中“记住我”复选框,则AuthenticationManager.SignIn(new AuthenticationProperties{ IsPersistent = true }, userIdentity);将创建一个cookie,其过期时间等于您在Startup.cs中设置的ExpireTimeSpan(默认为14天)。
如果未选中“记住我”复选框,则必须使用AuthenticationManager.SignIn(new AuthenticationProperties{ IsPersistent = true, ExpiresUtc = DateTimeOffset.UtcNow.AddMinutes(30)}, userIdentity);。同样,IsPersistent设置为true,但现在我们为ExpiresUtc赋值,因此它不使用CookieAuthenticationOptionsStartup.cs
public override async Task SignInAsync(ApplicationUser user, bool isPersistent, bool rememberBrowser)
{
    var userIdentity = await CreateUserIdentityAsync(user).WithCurrentCulture();
    // Clear any partial cookies from external or two factor partial sign ins
    AuthenticationManager.SignOut(DefaultAuthenticationTypes.ExternalCookie, DefaultAuthenticationTypes.TwoFactorCookie);
    if (rememberBrowser)
    {
        var rememberBrowserIdentity = AuthenticationManager.CreateTwoFactorRememberBrowserIdentity(ConvertIdToString(user.Id));
        AuthenticationManager.SignIn(new AuthenticationProperties { IsPersistent = isPersistent }, userIdentity, rememberBrowserIdentity);
    }
    else
    {
        //AuthenticationManager.SignIn(new AuthenticationProperties { IsPersistent = isPersistent }, userIdentity);
        if (isPersistent)
        {
            AuthenticationManager.SignIn(new AuthenticationProperties { IsPersistent = true }, userIdentity);
        }
        else
        {
            AuthenticationManager.SignIn(new AuthenticationProperties { IsPersistent = true, ExpiresUtc = DateTimeOffset.UtcNow.AddMinutes(30) }, userIdentity);
        }        
    }
}

完美,我使用了你的代码并实现了上述功能,谢谢。另外,我将Owin从2.1.0版本升级到了3.0.1。 - Ivan.Yu
3
这是针对哪个版本的ASP.NET身份验证?我正在使用默认的ASP.NET MVC 5模板上的2.2.2版本,并且为了登录,我有以下代码行 var result = await SignInManager.PasswordSignInAsync(model.Email, model.Password, isPersistent: false, shouldLockout: false);,没有 ExpiresUtc 或其他任何可设置的方式。 - empz
还想知道如何在较新版本的ASP.NET Identity中实现这一点.... - phxism
@phxism:请看下面我的回答。 - Dejan

10
请提供需要翻译的内容。
public void ConfigureAuth(IAppBuilder app)
{
  app.UseCookieAuthentication(new CookieAuthenticationOptions
  {
      ExpireTimeSpan = TimeSpan.FromHours(1),
  });            
}

谢谢,但我发现如果我设置了这个属性,'记住我'功能将无法工作。 - Ivan.Yu
这对我不起作用。它仍然默认为14天。 - Garth
@NabeelZafar 谢谢你的帮助,但我在下面发布了对我有用的答案。 - Garth

9
为了在ASP.NET Core 3.1中实现您所描述的功能,我按以下方式在 Startup 中配置身份验证:
        services.ConfigureApplicationCookie(o =>
        {
            ...
            o.ExpireTimeSpan = TimeSpan.FromMinutes(30);
            o.SlidingExpiration = true;
            ...
            o.Events.OnSigningIn = ctx =>
            {
                if (ctx.Properties.IsPersistent)
                {
                    var issued = ctx.Properties.IssuedUtc ?? DateTimeOffset.UtcNow;
                    ctx.Properties.ExpiresUtc = issued.AddDays(14);
                }
                return Task.FromResult(0);
            };
        });

使用 OnSigningIn 回调,如果勾选了“isPersistent”复选框,则将过期日期显式设置为现在 + 14 天。

完美地工作了!使用身份验证事件比覆盖身份验证登录操作要容易得多。 - Ibraheem Ahmed

0

我曾经遇到过同样的问题,这段代码对我很有用(在Startup.cs文件中)。

services.Configure<IdentityOptions>(options =>
{
    options.Cookies.ApplicationCookie.ExpireTimeSpan = TimeSpan.FromDays(3650);
});

这将使持久性cookie的过期时间增加约10年

NB:如果您想要更短的过期时间,可以使用TimeSpan.FromMinutes(1);表示1分钟或TimeSpan.FromSeconds(30);表示30秒等。


如果您将Cookie的过期时间设置在2038之后,一些浏览器可能会比预期提前过期。 - Brian

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接