[英]Identity Server 4 - Log User Out when Idle
Hej Community, Hej社区,
I got stuck and I need some advice or pointer to a solution.我被卡住了,我需要一些建议或指向解决方案的指针。 I have a fairly simple Identity Server 4 Setup:
我有一个相当简单的 Identity Server 4 设置:
I would like to automatically log out the user after 10 minutes of inactivity.我想在 10 分钟不活动后自动注销用户。 In the sample below I used 10 s to make testing somewhat quicker.
在下面的示例中,我使用了 10 秒来加快测试速度。 The authentication, redirect and user enforced logout work as expected and like a charm using the code below.
身份验证、重定向和用户强制注销按预期工作,就像使用下面的代码一样。 However, when the user idles for longer than the set 10 s, the user is still signed in and is not redirected to the login page at the IDS host.
但是,当用户空闲时间超过设定的 10 s 时,用户仍处于登录状态,不会重定向到 IDS 主机上的登录页面。
The MVC client is setup using Hybrid Grant as: MVC 客户端使用 Hybrid Grant 设置为:
Client Definition客户定义
var mvcClient = new Client
{
ClientId = "account-mvc",
ClientName = "Account MVC",
ClientUri = "https://localhost:5002",
AllowedGrantTypes = GrantTypes.Hybrid,
ClientSecrets = { new Secret("secret".Sha256()) },
EnableLocalLogin = true,
RequireConsent = false,
AllowOfflineAccess = false,
AccessTokenLifetime = 10, // 10 s by intention
IdentityTokenLifetime = 10, // 10 s by intention
RedirectUris = "https://localhost:5002/signin-oidc",
PostLogoutRedirectUris = "https://localhost:5002/signout-callback-oidc",
FrontChannelLogoutUri = "https://localhost:5002/signout-oidc",
AllowedScopes =
{
IdentityServerConstants.StandardScopes.OpenId,
IdentityServerConstants.StandardScopes.Profile,
IdentityServerConstants.StandardScopes.Email,
},
};
Identity Server Options身份服务器选项
services.AddIdentityServer(options =>
{
options.Authentication.CheckSessionCookieName = "auth-cookie";
options.Authentication.CookieLifetime = new System.TimeSpan(0, 0, 10);
options.Authentication.CookieSlidingExpiration = false;
options.Csp.Level = IdentityServer4.Models.CspLevel.Two;
options.Events.RaiseErrorEvents = true;
options.Events.RaiseInformationEvents = true;
options.Events.RaiseFailureEvents = true;
options.Events.RaiseSuccessEvents = true;
})
.Add... // Left out for brevity
In the Startup of the MVC client I add:在 MVC 客户端的启动中,我添加:
MVC Client Startup MVC 客户端启动
services.AddAuthentication(options =>
{
options.DefaultScheme = "Cookies";
options.DefaultChallengeScheme = "oidc";
})
.AddCookie("Cookies", options =>
{
options.ExpireTimeSpan = TimeSpan.FromSeconds(10);
options.SlidingExpiration = false;
options.Cookie.Name = "mvc-cookie";
})
.AddOpenIdConnect("oidc", options =>
{
options.SignInScheme = "Cookies";
options.Authority = "https://localhost:5001/";
options.ClientId = "account-mvc";
options.ClientSecret = "secret";
options.ResponseType = "code id_token";
options.SaveTokens = true;
options.GetClaimsFromUserInfoEndpoint = true;
options.Scope.Add("openid");
options.Scope.Add("profile");
options.Scope.Add("email");
});
and added app.UseAuthentication()
in the Configure
method.并在
Configure
方法中添加了app.UseAuthentication()
。
Question题
How can I make sure that the user is signed out at the Identity Server once the session timed out?一旦会话超时,如何确保用户在 Identity Server 上注销? Any hint and help appreciated!
任何提示和帮助表示赞赏!
After more debugging I found that the cookie lifetime of the MVC client worked as intended with a sliding expiration.经过更多调试后,我发现 MVC 客户端的 cookie 生存期按预期工作,并具有滑动到期时间。 However, once the cookie expired, the Idenity Server (IDS) was contacted and the cookie was refreshed as the session was still alive / active at the IDS.
但是,一旦 cookie 过期,就会联系身份服务器 (IDS) 并刷新 cookie,因为会话在 IDS 上仍然处于活动状态/活动状态。
I figured two solutions from which I decided to use Solution 1 for now and see if it is the most suitable in the long-run.我想出了两个解决方案,我决定暂时使用解决方案 1 ,看看它是否最适合长期使用。
If anyone has a comment or recommendation towards security and best practice please comment or post another solution.
如果有人对安全性和最佳实践有意见或建议,请发表评论或发布其他解决方案。
The Client property UserSsoLifetime
(available in Identity Server 4 from v2.3
) can be used to set the maximum time until a user must re-authenticate to use the client.客户端属性
UserSsoLifetime
(在v2.3
Identity Server 4 中可用)可用于设置用户必须重新进行身份验证才能使用客户端的最长时间。 So for the sample of the question the only required addition is in the Client Definition by adding UserSsoLifetime = 10
, such as,因此,对于问题的示例,唯一需要的添加是通过添加
UserSsoLifetime = 10
在客户端定义中,例如,
Client Definition客户定义
var mvcClient = new Client
{
ClientId = "account-mvc",
ClientName = "Account MVC",
ClientUri = "https://localhost:5002",
AllowedGrantTypes = GrantTypes.Hybrid,
ClientSecrets = { new Secret("secret".Sha256()) },
EnableLocalLogin = true,
RequireConsent = false,
AllowOfflineAccess = false,
UserSsoLifetime = 10, // <- HERE
AccessTokenLifetime = 10, // 10 s by intention
IdentityTokenLifetime = 10, // 10 s by intention
RedirectUris = "https://localhost:5002/signin-oidc",
PostLogoutRedirectUris = "https://localhost:5002/signout-callback-oidc",
FrontChannelLogoutUri = "https://localhost:5002/signout-oidc",
AllowedScopes =
{
IdentityServerConstants.StandardScopes.OpenId,
IdentityServerConstants.StandardScopes.Profile,
IdentityServerConstants.StandardScopes.Email,
},
};
This will force the user to re-authenticate after 10 s of inactivity.这将强制用户在 10 秒不活动后重新进行身份验证。
This SO question solves the issue with an OIDC property which can be used to force the user to re-authenticate via the login prompt once the session expired - see @Scotty Brady's answer .这个SO 问题解决了 OIDC 属性的问题,该属性可用于在会话过期后强制用户通过登录提示重新进行身份验证 - 请参阅@Scotty Brady 的回答。
So for the example denoted in the question should look like the following.因此,问题中表示的示例应如下所示。 Note that only the MVC client needs changes, namely the Cookie lifetime was removed and OIDC options were added forcing the re-authentication and to use the token lifetime from IDS (each line marked with a
// <- HERE
).请注意,只有 MVC 客户端需要更改,即删除了 Cookie 生存期,并添加了 OIDC 选项以强制重新身份验证并使用来自 IDS 的令牌生存期(每行标有
// <- HERE
)。 This way, the cookie settings from IDS are used (sliding lifetime of 10s).这样,就使用了来自 IDS 的 cookie 设置(滑动寿命为 10 秒)。
MVC Client Startup MVC 客户端启动
services.AddAuthentication(options =>
{
options.DefaultScheme = "Cookies";
options.DefaultChallengeScheme = "oidc";
})
.AddCookie("Cookies") // <- HERE
.AddOpenIdConnect("oidc", options =>
{
options.SignInScheme = "Cookies";
options.Authority = "https://localhost:5001/";
options.ClientId = "account-mvc";
options.ClientSecret = "secret";
options.ResponseType = "code id_token";
options.UseTokenLifetime = true; // <- HERE
options.SaveTokens = true;
options.GetClaimsFromUserInfoEndpoint = true;
options.Events.OnRedirectToIdentityProvider = context => // <- HERE
{ // <- HERE
context.ProtocolMessage.Prompt = "login"; // <- HERE
return Task.CompletedTask; // <- HERE
}; // <- HERE
options.Scope.Add("openid");
options.Scope.Add("profile");
options.Scope.Add("email");
});
You can utilize End Session Endpoint of the IdentityServer.您可以使用 IdentityServer 的End Session Endpoint 。
The end session endpoint can be used to trigger single sign-out ( see spec ).
结束会话端点可用于触发单点注销( 请参阅规范)。
To use the end session endpoint a client application will redirect the user's browser to the end session URL.
要使用结束会话端点,客户端应用程序会将用户的浏览器重定向到结束会话 URL。 All applications that the user has logged into via the browser during the user's session can participate in the sign-out.
用户在会话期间通过浏览器登录的所有应用程序都可以参与注销。
You can utilize this endpoint to redirect end user back to login page using post_logout_redirect_uri paramter.您可以利用此端点使用post_logout_redirect_uri参数将最终用户重定向回登录页面。
声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.