asp.net 核心中的关联失败

Correlation failed in asp.net core

我的 Web 应用程序无法使用 OpenIdConnect 进行身份验证。目前我在 OnRemoteFailure.

上看到 "Correlation failed" 错误

上下文:

启动:

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

        services.AddMvc();

        (...)

        services.AddAuthorization();
        services.AddAuthentication(sharedOptions =>
        {
            sharedOptions.DefaultScheme = CookieAuthenticationDefaults.AuthenticationScheme;
            sharedOptions.DefaultChallengeScheme = OpenIdConnectDefaults.AuthenticationScheme;
            sharedOptions.DefaultSignInScheme = CookieAuthenticationDefaults.AuthenticationScheme;
            sharedOptions.DefaultAuthenticateScheme = CookieAuthenticationDefaults.AuthenticationScheme;
        })
        .AddCookie()
        .AddOpenIdConnect(o =>
        {
            o.ClientId = clientId;
            o.Authority = $"https://login.microsoftonline.com/{tenantId}/{signinPolicy}/v2.0";
            o.SignInScheme = CookieAuthenticationDefaults.AuthenticationScheme;
            o.SaveTokens = true;
            o.Events = new OpenIdConnectEvents
            {
                OnTokenValidated = async context =>
                {
                    (...)
                },
                OnRedirectToIdentityProvider = async context =>
                {
                    if (context.Request.Headers.TryGetValue("X-Forwarded-Prefix", out var prefix) && prefix.Count > 0 &&
                    context.Request.Headers.TryGetValue("X-Forwarded-Host", out var hostValues) && hostValues.Count > 0 &&
                    context.Request.Headers.TryGetValue("X-Forwarded-Proto", out var protoValues) && protoValues.Count > 0)
                    {
                        // Use external URL and path
                        string redirectUri = $"{protoValues.First()}://{hostValues.First()}{prefix.First()}{context.Options.CallbackPath}";
                        context.ProtocolMessage.RedirectUri = redirectUri;
                    }
                },
                OnTokenResponseReceived = async context =>
                {
                },
                OnAuthenticationFailed = async context =>
                {
                },
                OnRemoteFailure = async context =>
                {
                }
            };
            o.ConfigurationManager = new PolicyConfigurationManager($"https://login.microsoftonline.com/{tenantId}/{signinPolicy}/v2.0",
                                      new[] { signinPolicy });
        });

        (...)
    }

    public void Configure(IApplicationBuilder app, IHostingEnvironment env, ILoggerFactory loggerFactory)
    {
        app.UseStaticFiles();

        app.UseAuthentication();

        app.Use(async (context, next) =>
        {
            if (context.Request.Headers.TryGetValue("X-Forwarded-Prefix", out var prefix) && prefix.Count() > 0)
            {
                context.Request.PathBase = prefix.First();
            }
            await next.Invoke();
        });

        app.UseMvc(routes =>
        {
            routes.MapRoute(
                name: "default",
                template: "{controller=Home}/{action=Index}/{id?}");
        });
    }

控制器:

public class AccountController : Controller
{
    [HttpGet]
    public IActionResult SignIn()
    {
        if (Request.Headers.TryGetValue("X-Forwarded-Prefix", out var prefix) && prefix.Count() > 0)
        {
            return Challenge(new AuthenticationProperties { RedirectUri = prefix.First() }, OpenIdConnectDefaults.AuthenticationScheme);
        }
        else
        {
            (...)
        }
    }
    (...)
}

事件 OnTokenValidated 从未触发。

关于反向代理,基本映射https://internal_url:port/internal_path to https://external_url/external_path.

我检查了请求,这是访问的 GET:

https://login.microsoftonline.com/{tenantId}/oauth2/v2.0/authorize?p={signinPolicy}&client_id={clientId}&redirect_uri=https%3A%2F%2F{external_host}%2F{external_path}%2Fsignin-oidc&response_type=id_token&scope=openid%20profile&response_mode=form_post&nonce=(...)&x-client-SKU=ID_NET&x-client-ver=2.1.4.0

成功后POST请求失败:

https://{external_url}/{external_path}/signin-oidc

此 POST 包含表单数据 id_tokenstate

在 B2C 中配置的重定向 URL 是 https://{external_url}/{external_path}/signin-oidc。我也试过 https://{external_url}/{external_path},但效果不佳。

我尝试使用转发 Headers,但没有帮助。

任何人都可以指出缺少的内容吗?

提前致谢!

我发现了问题。问题出在中间件的顺序上。身份验证中间件必须在 PathBase 更改之后进行。 我的情况不需要转发 headers。

遵循固定的 Configure 方法。

public void Configure(IApplicationBuilder app, IHostingEnvironment env, ILoggerFactory loggerFactory)
{
    app.Use(async (context, next) =>
    {
        if (context.Request.Headers.TryGetValue("X-Forwarded-Prefix", out var prefix) && prefix.Count() > 0)
        {
            context.Request.PathBase = prefix.First();
        }
        await next.Invoke();
    });

    app.UseStaticFiles();

    app.UseAuthentication();

    app.UseMvc(routes =>
    {
        routes.MapRoute(
            name: "default",
            template: "{controller=Home}/{action=Index}/{id?}");
    });
}