【问题标题】:How to log out from AWS Cognito in ASP.NET Core如何在 ASP.NET Core 中从 AWS Cognito 注销
【发布时间】:2021-10-11 22:38:23
【问题描述】:

我正在尝试在 ASP.NET Core 5 Web 应用程序中使用 AWS Cognito 实施身份验证。

我可以通过身份验证,但现在我想实现注销功能。

我可以让注销工作,因为 ASP.NET 认为我没有经过身份验证。

在我的 Startup.cs 我有:

options.SignedOutRedirectUri = Configuration["Authentication:Cognito:SignedOutRedirectUri"];

options.Events = new OpenIdConnectEvents()
{
    OnRedirectToIdentityProviderForSignOut = context =>
    {
        var logoutUri = options.SignedOutRedirectUri;
        context.Response.Redirect(logoutUri);
        context.HandleResponse();

        return Task.CompletedTask;
    }
};

在我的 appsettings.json 中有:

  "SignedOutRedirectUri": "https://mydomain.auth.us-east-2.amazoncognito.com/logout?client_id=<<clientid>>&response_type=code&redirect_uri=https://localhost:44306/Home/LoggedOut"

在我的注销控制器中,我有:

        await HttpContext.SignOutAsync(CookieAuthenticationDefaults.AuthenticationScheme);
        await HttpContext.SignOutAsync(OpenIdConnectDefaults.AuthenticationScheme);

        return Redirect("/Home/LoggedOut");

所以当我点击我的注销链接时,我被重定向到 /Home/LoggedOut 并且我不再经过身份验证(在那个 User.Identity.IsAuthenticated = false 中)。

但是,当我转到任何带有 [Authorize] 的页面时,它会自动将我重新验证给我登录时使用的同一用户 - 它永远不会让我有机会以其他用户身份登录。我希望它带我进入 Cognito 登录对话框并要求我再次进行身份验证。因此,我想在 AWS Cognito 方面,似乎某些地方没有得到清除。

为什么这没有让我返回登录对话框重新进行身份验证?我认为应该使用 GET 到 AWS /logout 端点。

【问题讨论】:

    标签: asp.net-core amazon-cognito


    【解决方案1】:

    我认为问题在于您为 AWS Logout 端点构建的 URL 的参数。 (你还没有设置 logout_uri)

    https://docs.aws.amazon.com/cognito/latest/developerguide/logout-endpoint.html 示例 1 显示了注销和重定向回客户端所需的参数。

    这是我的做法。

    options.Events = new OpenIdConnectEvents()
    {
        OnRedirectToIdentityProviderForSignOut = context =>
        {
            context.ProtocolMessage.IssuerAddress = 
               GetAbsoluteUri(Configuration["Authentication:Cognito:EndSessionEndPoint"], Configuration["Authentication:Cognito:Authority"]);
            context.ProtocolMessage.SetParameter("client_id", Configuration["Authentication:Cognito:ClientId"]);
            context.ProtocolMessage.SetParameter("logout_uri", "https://localhost:5001");
            return Task.CompletedTask;
        }
    };
    

    logout_uri 必须与 AWS 应用程序客户端设置中配置的注销 url 完全匹配。

    辅助方法

     private string GetAbsoluteUri(string signoutUri, string authority)
            {
                var signOutUri = new Uri(signoutUri, UriKind.RelativeOrAbsolute);
                var authorityUri = new Uri(authority, UriKind.Absolute);
    
                var uri = signOutUri.IsAbsoluteUri ? signOutUri : new Uri(authorityUri, signOutUri);
                return uri.AbsoluteUri;
            } 
    

    注销是通过下面的两行来完成的。如您所见,第一行是通过清除本地身份验证 cookie 在本地注销您,第二行通常会调用您的 IDP 上的 end_session 端点以注销您的 IDP,但是由于 cognito 没有并且end_session 端点,当您通过 OnRedirectToIdentityProviderForSignOut 事件配置中间件时,您会覆盖它,指示它改为调用 cognito 确实具有的注销端点,这就是使用此 URL 的地方。由于您没有正确构建它,因此它永远不会退出 cognito。

    public async Task Logout()
            {
                await HttpContext.SignOutAsync(CookieAuthenticationDefaults.AuthenticationScheme);
                await HttpContext.SignOutAsync(OpenIdConnectDefaults.AuthenticationScheme);
            }
    

    和配置值

    ...
    "EndSessionEndPoint": "logout",
    "ClientId": "<your client id>",
    "Authority": "https://<your domain>.auth.<your region>.amazoncognito.com"
    ...
    

    希望对您有所帮助。

    【讨论】:

      猜你喜欢
      • 2017-12-27
      • 2019-04-06
      • 2022-11-10
      • 2019-04-12
      • 2018-10-14
      • 2019-04-24
      • 2017-11-02
      • 2020-03-13
      • 1970-01-01
      相关资源
      最近更新 更多