SignOut 不会重定向到站点主页

Luc*_*cia 1 asp.net-core-mvc openid-connect asp.net-core-3.0

我正在尝试设置一个 ASP.net Core 3 MVC 应用程序,该应用程序使用 OIDC 连接到我公司的 SSO 门户 (OpenAM)。

我使用 Visual Studio 2019 项目生成器创建了一个没有身份验证的基本应用程序,然后按照http://docs.identityserver.io/en/latest/quickstarts/2_interactive_aspnetcore.html#creating-an 中的步骤添加了 OIDC 客户端功能-mvc 客户端。只需对 Startup 类进行最少的更改,登录就可以很好地工作:

    public void ConfigureServices(IServiceCollection services)
    {
        services.AddControllersWithViews();

        // Setup Identity Server client
        JwtSecurityTokenHandler.DefaultMapInboundClaims = false;

        services.AddAuthentication(options =>
            {
                options.DefaultScheme = "Cookies";
                options.DefaultChallengeScheme = "oidc";
            })
            .AddCookie("Cookies")
            .AddOpenIdConnect("oidc", options =>
            {
                options.Authority = "https://mycompany.com/ssoservice/oauth2";
                options.RequireHttpsMetadata = false;

                options.ClientId = "openIdClient";
                options.ClientSecret = "secret";
                options.ResponseType = "code";
                options.ProtocolValidator.RequireNonce = false;

                options.SaveTokens = true;
            });
    }

    // This method gets called by the runtime. Use this method to configure the HTTP request pipeline.
    public void Configure(IApplicationBuilder app, IWebHostEnvironment env)
    {
        if (env.IsDevelopment())
        {
            app.UseDeveloperExceptionPage();
            IdentityModelEventSource.ShowPII = true;
        }
        else
        {
            app.UseExceptionHandler("/Home/Error");
            // The default HSTS value is 30 days. You may want to change this for production scenarios, see https://aka.ms/aspnetcore-hsts.
            app.UseHsts();
        }

        app.UseHttpsRedirection();
        app.UseStaticFiles();

        app.UseRouting();

        app.UseAuthentication();
        app.UseAuthorization();

        app.UseEndpoints(endpoints =>
        {
            // endpoints.MapDefaultControllerRoute();
            endpoints.MapControllerRoute(
                name: "default",
                pattern: "{controller=Home}/{action=Index}/{id?}");
        });
    }
Run Code Online (Sandbox Code Playgroud)

我还设置了一个注销控制器操作:

    [Authorize]
    public IActionResult Logout()
    {
        return SignOut("Cookies", "oidc");
    }
Run Code Online (Sandbox Code Playgroud)

该操作实际上有效,即当激活 cookie 时,将删除 cookie 并且用户从 SSO 门户注销,但是当浏览器重定向到 /signout-callback-oidc 端点时,它会收到一个没有任何内容的 HTTP 200 响应。我希望它自动重定向到站点主页“/”,这是 OpenIdConnectOptions.SignedOutRedirectUri 属性的默认值。

我错过了什么?

Luc*_*cia 7

好的,经过更多时间的摆弄,我发现这是最新社区 OpenAM 版本(以及当前付费 ForgeRock AM 中,但他们正在努力:https://bugster.forgerock)中缺少实施草案的结果.org/jira/browse/OPENAM-13831)。基本上,.net 核心处理程序/signout-callback-oidc依赖于state参数可用以进行重定向,如评论中提到的 Ruard van Elburg:

https://github.com/aspnet/AspNetCore/blob/4fa5a228cfeb52926b30a2741b99112a64454b36/src/Security/Authentication/OpenIdConnect/src/OpenIdConnectHandler.cs#L312-L315

正如state我的日志中所报告的那样,OpenAM 不会发回参数。因此,我们需要自己执行重定向——最直接的方法似乎是使用OnSignedOutCallbackRedirect事件:

启动文件

    services.AddAuthentication(...)
        .AddCookie("Cookies")
        .AddOpenIdConnect("oidc", options =>
        {
            ...
            options.Events.OnSignedOutCallbackRedirect += context =>
            {
                context.Response.Redirect(context.Options.SignedOutRedirectUri);
                context.HandleResponse();

                return Task.CompletedTask;
            };
            ...
        });
Run Code Online (Sandbox Code Playgroud)

感谢所有回复讨论的用户,你们的贡献让我找到了正确解决方案的线索。