【问题标题】:Enabling SSL in ASP.NET MVC 5 app results in OpenIdConnectProtocolValidator issue在 ASP.NET MVC 5 应用程序中启用 SSL 会导致 OpenIdConnectProtocolValidator 问题
【发布时间】:2015-06-12 17:03:47
【问题描述】:

我有一个针对 Azure Active Directory 进行身份验证的 ASP.NET MVC 5 应用程序。我想在整个应用程序上启用 SSL。因此利用全局过滤器如下:

public class FilterConfig
{
    /// <summary>
    /// Registers the global filters.
    /// </summary>
    /// <param name="filters">The filters.</param>
    public static void RegisterGlobalFilters(GlobalFilterCollection filters)
    {
        filters.Add(new RequireHttpsAttribute());
    }
}

在此之后,我还将项目属性中的“启用 SSL”设置为 true。这给了我以下 SSL URL -> https://localhost:34567。我更新了项目,使其位于“项目 URL”中服务器下的“Web 选项卡”下的 IIS Express 路径中。但是在运行该站点时,我遇到了以下错误:

IDX10311:RequireNonce 为“真”(默认),但 validationContext.Nonce 为空。无法验证随机数。如果不需要检查 nonce,请将 OpenIdConnectProtocolValidator.RequireNonce 设置为 'false'。

我有授权。在网站上启用。我使用 Azure Active Directory。

安全码如下:

app.UseOpenIdConnectAuthentication(
            new OpenIdConnectAuthenticationOptions
            {
                ClientId = clientId,
                Authority = authority,
                PostLogoutRedirectUri = postLogoutRedirectUri                    
            });

        app.UseWindowsAzureActiveDirectoryBearerAuthentication(
            new WindowsAzureActiveDirectoryBearerAuthenticationOptions
            {
                Audience = audience,
                Tenant = tenant,      
            });

授权。正在从 web.config 读取值,如下所示:

<add key="ida:ClientId" value="<some_guid>" />
<add key="ida:Audience" value="https://localhost:34567/" />
<add key="ida:AADInstance" value="https://login.windows.net/{0}" />
<add key="ida:Tenant" value="microsoft.onmicrosoft.com" />
<add key="ida:PostLogoutRedirectUri" value="https://localhost:34567/" />

我尝试按照错误消息中的指示将 RequireNonce 设置为 false,如下所示:

ProtocolValidator = new OpenIdConnectProtocolValidator
                {
                    RequireNonce = false
                }

但这只是导致了一个无效的请求错误。

有人可以帮我理解这里的问题吗?在启用 SSL 之前一切正常。

【问题讨论】:

  • 我想我明白了。该应用程序。 Azure AD 中的详细信息硬连线以依赖于原始 HTTP 终结点。一旦我验证了我的理论,就会更新这个。
  • 我也收到了...
  • 拜托,你修复了这个错误吗?我也有同样的情况。
  • 在这个线程中检查我的答案:stackoverflow.com/questions/39412570/…

标签: asp.net-mvc ssl openid-connect nonce asp.net-mvc-filters


【解决方案1】:

如果错误消息以 OICE_20004 开头或包含 IDX10311,您可以忽略异常。注意:风险自负。

Notifications = new OpenIdConnectAuthenticationNotifications()
{
    RedirectToIdentityProvider = (context) =>
    {
        // Ensure the URI is picked up dynamically from the request;
        string appBaseUrl = context.Request.Scheme + "://" + context.Request.Host + context.Request.PathBase + context.Request.Uri.PathAndQuery;
        context.ProtocolMessage.RedirectUri = context.Request.Scheme + "://" + context.Request.Host + context.Request.PathBase + context.Request.Uri.PathAndQuery;
        context.ProtocolMessage.PostLogoutRedirectUri = appBaseUrl;
        return Task.FromResult(0);
    },
    AuthenticationFailed = (context) =>
    {
        if (context.Exception.Message.StartsWith("OICE_20004") || context.Exception.Message.Contains("IDX10311"))
        {
            context.SkipToNextMiddleware();
            return Task.FromResult(0);
        }
        return Task.FromResult(0);
    },
}

【讨论】:

  • 能否为您提供的解决方案添加更多描述?
  • 在场景中为我工作:用户使用浏览器后退按钮导航到 SSO 身份验证页面。
  • 你能添加一些描述吗?
  • 我认为最好在跳到下一个中​​间件之前检查 context.OwinContext.Authentication.User.Identity.IsAuthenticated。
【解决方案2】:

在 Azure 管理门户中,检查相应活动目录下的应用程序是否具有相同的登录 URL回复 URL

如果它们不一样,你会得到这个错误。

当您启用 SSL 时会发生这种情况,因为它仅将登录 URL 更改为 HTTPS URL,而回复 URL 保持相同的 HTTP URL。

编辑: 如果您想知道为什么会发生这种情况,请继续阅读,

当您尝试使用 https URL 访问您的应用程序时,它会在您的浏览器中设置一个具有唯一编号 (nonce) 的 cookie,并点击 Azure AD 进行身份验证。身份验证后,浏览器必须授予对该 cookie 的访问权限。但由于登录 URL 和回复 URL 不同,浏览器无法识别您的应用程序,也无法访问该 cookie,因此应用程序会抛出此错误。

【讨论】:

    【解决方案3】:

    即使在成功登录后,我也可以通过在我的 Web 应用程序上按几次后退按钮来重现此错误。 你能试试这两件事吗: 在下面的代码中:

    app.UseOpenIdConnectAuthentication(
                    new OpenIdConnectAuthenticationOptions
                    {
                        ClientId = mViewWebSite.ClientId,
                        Authority = mViewWebSite.Authority,
                        PostLogoutRedirectUri = mViewWebSite.PostLogoutRedirectUri
                    });
    

    添加协议验证器作为身份验证选项之一,如错误提示:

    ProtocolValidator = new Microsoft.IdentityModel.Protocols.OpenIdConnectProtocolValidator(){
                                RequireNonce = false
                            }
    

    或添加通知,通过此您可以捕获此错误并将其重定向到某个错误页面。我这样做是为了让它优雅。直到 Katana 人修复它。

    Notifications = new OpenIdConnectAuthenticationNotifications
                            {
                                AuthenticationFailed = context =>
                                {
                                    context.HandleResponse();
                                    context.Response.Redirect("/Error.aspx?message=" + context.Exception.Message);
                                    return Task.FromResult(0);
                                }
                            },
    

    【讨论】:

    【解决方案4】:

    我设法在 Global.asax 文件中使用以下方法解决此问题。至少这不会向客户端显示异常。我使用 ELMAH 来捕获异常。

    protected void Application_Error(object sender, EventArgs args)
        {
            var ex = Server.GetLastError();
            if (ex.Message.Contains("IDX10311:"))
            {
                Server.ClearError();
                Response.Redirect("https://www.yoursitename.com");                 
            }
    

    【讨论】:

      【解决方案5】:

      好吧,最好看一下武士刀源代码,从中我发现异常类型是 OpenIdConnectProtocolInvalidNonceException 所以我这样处理它。

              if (n.Exception is OpenIdConnectProtocolInvalidNonceException &&
                  n.OwinContext.Authentication.User.Identity.IsAuthenticated)
              {
                  n.SkipToNextMiddleware();
                  return;
              }
      

      我在缓存页面和登录后单击后退按钮的用户的浏览器上弹出此异常。

      【讨论】:

      • 在哪些情况下可以在 AuthenticationFailed 通知上对用户进行身份验证(user.Identity.IsAuthenticated = true)?
      • @TempoClick 登录后,点击返回按钮尝试返回上一页,某些登录参数不存在重新登录。
      【解决方案6】:

      这里的问题很简单……我花了好几个小时才弄明白。 由于我在本地测试没有 https 并且在最初在 Azure AD 中创建我的应用程序时告诉你真相,因为我在测试期间不希望它是 https 我将其设为纯 http(replyUrl 的主页网址,注销所有爵士乐)

      然后在这样做之后我遇到了无限循环问题,很多人都遇到了。所以然后我决定在我的本地模拟证书,是的,它摆脱了无限重定向,但随后又带来了另一个“IDX10311:RequireNonce is 'true'”

      长话短说……让您的 AzureAD 应用程序在其所有端点中都使用 https。还有哇!

      【讨论】:

      • 或者您可以在 github.com/IdentityServer/IdentityServer3/issues/542 中尝试“missxlian 于 2016 年 2 月 25 日发表评论”(在这篇文章中也有建议)
      【解决方案7】:

      @zb3b answer + @jonmeyer answer:

      app.UseOpenIdConnectAuthentication(new OpenIdConnectAuthenticationOptions
      {
          ...
          Notifications = new OpenIdConnectAuthenticationNotifications()
          {
              ...
              AuthenticationFailed = (context) =>
              {
                  if ((context.Exception is OpenIdConnectProtocolInvalidNonceException) &&
                      (context.OwinContext.Authentication.User.Identity.IsAuthenticated))
                  {
                      context.SkipToNextMiddleware();
                      return Task.FromResult(0);
                  }
      
                  return Task.FromResult(0);
              },
              ...
          }
      });
      

      【讨论】:

        【解决方案8】:

        添加我刚刚遇到的另一个案例:您连接的网络可能正在修改 HTML 内容。

        一位客户致电提出问题:他无法解决此错误。那是一台他以前没有登录过的新笔记本电脑。在尝试了几种可能的解决方案大约一小时后,我决定检查他连接的网络。

        事实证明,他连接到机场的网络,开放且不安全,并且没有使用 VPN 服务(那里缺少一些 SETA)。我不确切知道谁在运营该网络或他们在做什么,但 Azure AD 服务一定检测到了某种类型的随机数篡改。

        用户连接到可信网络的那一刻,问题就解决了。

        【讨论】:

          猜你喜欢
          • 2021-12-04
          • 1970-01-01
          • 1970-01-01
          • 1970-01-01
          • 1970-01-01
          • 2021-09-13
          • 2016-01-29
          • 1970-01-01
          • 1970-01-01
          相关资源
          最近更新 更多