.NET Core 2 CookieAuthentication 忽略过期时间跨度
.NET Core 2 CookieAuthentication ignores expiration time span
我正在使用 CookieAuthentication
开发 .NET Core 2.1 Web 应用程序。出于某种原因,在 CookieAuthenticationOptions
对象上设置 ExpireTimeSpan
和 Cookie.Expiration
不会影响 Cookie 的生命周期。 Chrome 始终显示与 1969-12-31T23:59:59.000Z
相同的到期日期。所以关闭浏览器后 window cookie 就消失了。
Startup.cs
public void ConfigureServices(IServiceCollection services)
{
services.AddDistributedMemoryCache();
services.AddAuthentication(CookieAuthenticationDefaults.AuthenticationScheme)
.AddCookie(options =>
{
options.LoginPath = new PathString("/Account/Login/");
options.AccessDeniedPath = new PathString("/Account/Login/");
options.Cookie.SecurePolicy = CookieSecurePolicy.SameAsRequest;
options.Cookie.Expiration = TimeSpan.FromDays(14);
options.ExpireTimeSpan = TimeSpan.FromDays(14);
});
services.AddMvc(options =>
{
options.Filters.Add(new AutoValidateAntiforgeryTokenAttribute());
});
services.AddAntiforgery(options => options.HeaderName = "X-CSRF-TOKEN");
}
public void Configure(IApplicationBuilder app, IHostingEnvironment env)
{
if (env.IsDevelopment())
{
app.UseBrowserLink();
app.UseDeveloperExceptionPage();
}
else
{
app.UseExceptionHandler("/Error");
}
var provider = new FileExtensionContentTypeProvider();
provider.Mappings[".tag"] = "riot/tag";
app.UseStaticFiles(new StaticFileOptions()
{
ContentTypeProvider = provider
});
app.UseAuthentication();
app.UseMvc(routes =>
{
routes.MapRoute(
name: "default",
template: "{controller=Home}/{action=Index}/{id?}");
});
}
登录时我正在使用此代码
ClaimsPrincipal user = new ClaimsPrincipal(new ClaimsIdentity(new[] { new Claim(ClaimTypes.Name, userId.Value.ToString()) }, CookieAuthenticationDefaults.AuthenticationScheme));
await HttpContext.SignInAsync(CookieAuthenticationDefaults.AuthenticationScheme, user);
我试过将 services.AddMvc
放在 services.AddAuthentication
之前,但没有任何区别。我也在 services.AddAuthentication
之后尝试 services.ConfigureApplicationCookie
就像这个答案 Cookie expiry in ASP.NET Core 2.0 with Identity
我错过了什么?
来自 Use cookie authentication without ASP.NET Core Identity,粗体表示强调。
The TimeSpan after which the authentication ticket stored inside the
cookie expires. ExpireTimeSpan is added to the current time to create
the expiration time for the ticket. The ExpiredTimeSpan value always
goes into the encrypted AuthTicket verified by the server. It may also
go into the Set-Cookie header, but only if IsPersistent is set. To set
IsPersistent to true, configure the AuthenticationProperties passed to
SignInAsync. The default value of ExpireTimeSpan is 14 days.
使用IsPersistent = true
例子
var claims = new List<Claim>
{
new Claim(ClaimTypes.NameIdentifier, client.Id),
new Claim(ClaimTypes.Role, client.Role)
};
var identity = new ClaimsIdentity(claims, CookieAuthenticationDefaults.AuthenticationScheme);
await HttpContext.SignInAsync(CookieAuthenticationDefaults.AuthenticationScheme,
new ClaimsPrincipal(identity),
new AuthenticationProperties
{
ExpiresUtc = DateTime.UtcNow.AddYears(1),
IsPersistent = true
});
Chrome 中的到期日期表示浏览器中 cookie 的生命周期,而不是令牌的超时时间。当使用带有 ASP.NET Identity 的 Identity Server 4 时,Identity Server 的 cookie 超时在这里起作用。客户端令牌过期后,用户将根据 Identity Server 重新进行身份验证,并且由于该令牌尚未过期,因此会更新客户端令牌。要在 Identity Server 上设置过期时间,您必须在 Identity Server Startup.cs 中添加 ConfigureApplicationCookie 中间件,如下所示:
services.AddAuthentication();
services.ConfigureApplicationCookie(options =>
{
options.Cookie.Expiration = TimeSpan.FromDays(14);
options.ExpireTimeSpan = TimeSpan.FromDays(14);
options.SlidingExpiration = false;
});
services.AddMvc().SetCompatibilityVersion(Microsoft.AspNetCore.Mvc.CompatibilityVersion.Version_2_1);
.net core 3.1 更新(cooke.expiration 不再需要作为单独的选项):
services.AddAuthentication();
services.ConfigureApplicationCookie(options =>
{
options.ExpireTimeSpan = TimeSpan.FromDays(14);
options.SlidingExpiration = false;
});
services.AddMvc();
Identity 有专门的 cookie 配置选项 CookieAuthenticationOptions 和 cookie Expiration 值已决定被忽略,一些说明可以在这里找到:
Github issue
Test reference
我正在使用 CookieAuthentication
开发 .NET Core 2.1 Web 应用程序。出于某种原因,在 CookieAuthenticationOptions
对象上设置 ExpireTimeSpan
和 Cookie.Expiration
不会影响 Cookie 的生命周期。 Chrome 始终显示与 1969-12-31T23:59:59.000Z
相同的到期日期。所以关闭浏览器后 window cookie 就消失了。
Startup.cs
public void ConfigureServices(IServiceCollection services)
{
services.AddDistributedMemoryCache();
services.AddAuthentication(CookieAuthenticationDefaults.AuthenticationScheme)
.AddCookie(options =>
{
options.LoginPath = new PathString("/Account/Login/");
options.AccessDeniedPath = new PathString("/Account/Login/");
options.Cookie.SecurePolicy = CookieSecurePolicy.SameAsRequest;
options.Cookie.Expiration = TimeSpan.FromDays(14);
options.ExpireTimeSpan = TimeSpan.FromDays(14);
});
services.AddMvc(options =>
{
options.Filters.Add(new AutoValidateAntiforgeryTokenAttribute());
});
services.AddAntiforgery(options => options.HeaderName = "X-CSRF-TOKEN");
}
public void Configure(IApplicationBuilder app, IHostingEnvironment env)
{
if (env.IsDevelopment())
{
app.UseBrowserLink();
app.UseDeveloperExceptionPage();
}
else
{
app.UseExceptionHandler("/Error");
}
var provider = new FileExtensionContentTypeProvider();
provider.Mappings[".tag"] = "riot/tag";
app.UseStaticFiles(new StaticFileOptions()
{
ContentTypeProvider = provider
});
app.UseAuthentication();
app.UseMvc(routes =>
{
routes.MapRoute(
name: "default",
template: "{controller=Home}/{action=Index}/{id?}");
});
}
登录时我正在使用此代码
ClaimsPrincipal user = new ClaimsPrincipal(new ClaimsIdentity(new[] { new Claim(ClaimTypes.Name, userId.Value.ToString()) }, CookieAuthenticationDefaults.AuthenticationScheme));
await HttpContext.SignInAsync(CookieAuthenticationDefaults.AuthenticationScheme, user);
我试过将 services.AddMvc
放在 services.AddAuthentication
之前,但没有任何区别。我也在 services.AddAuthentication
之后尝试 services.ConfigureApplicationCookie
就像这个答案 Cookie expiry in ASP.NET Core 2.0 with Identity
我错过了什么?
来自 Use cookie authentication without ASP.NET Core Identity,粗体表示强调。
The TimeSpan after which the authentication ticket stored inside the cookie expires. ExpireTimeSpan is added to the current time to create the expiration time for the ticket. The ExpiredTimeSpan value always goes into the encrypted AuthTicket verified by the server. It may also go into the Set-Cookie header, but only if IsPersistent is set. To set IsPersistent to true, configure the AuthenticationProperties passed to SignInAsync. The default value of ExpireTimeSpan is 14 days.
使用IsPersistent = true
例子
var claims = new List<Claim>
{
new Claim(ClaimTypes.NameIdentifier, client.Id),
new Claim(ClaimTypes.Role, client.Role)
};
var identity = new ClaimsIdentity(claims, CookieAuthenticationDefaults.AuthenticationScheme);
await HttpContext.SignInAsync(CookieAuthenticationDefaults.AuthenticationScheme,
new ClaimsPrincipal(identity),
new AuthenticationProperties
{
ExpiresUtc = DateTime.UtcNow.AddYears(1),
IsPersistent = true
});
Chrome 中的到期日期表示浏览器中 cookie 的生命周期,而不是令牌的超时时间。当使用带有 ASP.NET Identity 的 Identity Server 4 时,Identity Server 的 cookie 超时在这里起作用。客户端令牌过期后,用户将根据 Identity Server 重新进行身份验证,并且由于该令牌尚未过期,因此会更新客户端令牌。要在 Identity Server 上设置过期时间,您必须在 Identity Server Startup.cs 中添加 ConfigureApplicationCookie 中间件,如下所示:
services.AddAuthentication();
services.ConfigureApplicationCookie(options =>
{
options.Cookie.Expiration = TimeSpan.FromDays(14);
options.ExpireTimeSpan = TimeSpan.FromDays(14);
options.SlidingExpiration = false;
});
services.AddMvc().SetCompatibilityVersion(Microsoft.AspNetCore.Mvc.CompatibilityVersion.Version_2_1);
.net core 3.1 更新(cooke.expiration 不再需要作为单独的选项):
services.AddAuthentication();
services.ConfigureApplicationCookie(options =>
{
options.ExpireTimeSpan = TimeSpan.FromDays(14);
options.SlidingExpiration = false;
});
services.AddMvc();
Identity 有专门的 cookie 配置选项 CookieAuthenticationOptions 和 cookie Expiration 值已决定被忽略,一些说明可以在这里找到: Github issue Test reference