【问题标题】:Unable to limit authentication issuers in a multi-tenant application (Blazor Server App / OpenIDConnect / Azure App Services)无法在多租户应用程序(Blazor 服务器应用程序/OpenIDConnect/Azure 应用程序服务)中限制身份验证颁发者
【发布时间】:2021-06-12 03:19:48
【问题描述】:

我正在尝试向部署在 Azure 应用服务中的 Blazor 服务器应用添加多租户身份验证和授权。场景非常基础:

  1. 允许多租户身份验证(运行良好)
  2. 将身份验证限制为指定的租户/颁发者(此代码在 startup.cs 中)
  3. 授权经过身份验证的用户

第 2 步失败了。当我在 Azure 中部署我的应用程序时,我仍然可以使用来自未经验证的颁发者的帐户打开应用程序。这是我的代码(startup.cs):

public IConfiguration Configuration { get; }
public void ConfigureServices(IServiceCollection services)
        {
            services.AddAuthentication(OpenIdConnectDefaults.AuthenticationScheme)
                    .AddMicrosoftIdentityWebApp(options =>
                    {
                        Configuration.Bind("AzureAd", options);
                        // Restrict users to specific belonging to specific tenants
                        options.TokenValidationParameters = new TokenValidationParameters 
                        {   ValidateIssuer = true,
                            // Tried first this, but with no effect:
                            // ValidIssuers = new List<string> {
                            //    "https://sts.windows.net/<tenant1>/",
                            //    "https://sts.windows.net/<tenant2>/"
                            //},
                            //So instead tried to use IssuerValidator, but this did not restrict access either:
                            IssuerValidator = ValidateSpecificIssuers
                        };
                    });

            services.AddControllersWithViews()
                .AddMicrosoftIdentityUI();
//...

private string[] GetAcceptedTenantIds()
        {
            return new[]
            {
            "<tenant1>",
            "<tenant2>",
            };
        }

        public string ValidateSpecificIssuers(string issuer, SecurityToken securityToken, TokenValidationParameters validationParameters)
        {
            var validIssuers = GetAcceptedTenantIds().Select(tid => "https://login.microsoftonline.com/{tid}");
            if (validIssuers.Contains(issuer))
            {
                return issuer;
            }
            else
            {
                throw new SecurityTokenInvalidIssuerException("The sign-in user's account does not belong to one of the tenants that this Web App accepts users from.");
            }
        }

我正在使用具有多组织身份验证的 Visual Studio Blazor Server App 项目模板。相关代码部分没有其他更改(appsettings.json 中的 "TenantId": "organizations" 除外)。 我发现了这个post,它说 ValidIssuer(s) 的行为不像人们预期的那样。这就是我尝试使用 IssuerValidator 的原因。不幸的是,结果相同。

我错过了什么?接下来我应该尝试什么?

【问题讨论】:

  • 你试过这个样本吗? github.com/Azure-Samples/…
  • 能否请您通过jwt.ms 解析您的令牌以检查其发行者?
  • @StanleyGong 我使用了同一个教程中的 1-WebApp-OIDC/link 1-2-AnyOrg/。我选择了那个,因为入职工作正常,我不需要按租户对任何数据进行分区,而且我对 AadIssuerValidator 有点迷失(它来自哪里?)。话虽如此,但我想知道 options.Events.OnTokenValidated 是否是检查发行者(与 TokenValidationParameters 相比)的更好策略?
  • @JimXu 恐怕我一开始就无法弄清楚如何获得该 jwt。是否可以在 Chrome 开发工具中找到它?
  • @SannaW 你可以使用 fiddler 来捕获请求然后你可以得到 jwt。

标签: authentication azure-web-app-service openid-connect multi-tenant blazor-server-side


【解决方案1】:

我终于想通了(感谢@JimXu,他说我应该使用提琴手).. 问题出在我的 Azure App ServiceApp Registration 设置中:

  1. 我有应用服务身份验证“开启”。所以身份验证过程使用的是(https://login.microsoftonline.com/kmsi 重定向到https://myapp.azurewebsites.net/.auth/login/aad/callback)而不是我的应用程序代码(重定向到https://myapp.azurewebsites.net/singin-oidc)--> “关闭”
  2. .auth/login/aad/callback 有效,因为我还在我的应用注册重定向 URI 中添加了 https://myapp.azurewebsites.net/.auth/login/aad/callback --> 已删除

ValidIssuers 不足以限制用户,所以我必须在那里拥有那个 IssuerValidator。现在的代码如下所示:

...
public void ConfigureServices(IServiceCollection services)
    {
        services.AddAuthentication(OpenIdConnectDefaults.AuthenticationScheme)
                .AddMicrosoftIdentityWebApp(options =>
                {
                    Configuration.Bind("AzureAd", options);
                    options.TokenValidationParameters = new TokenValidationParameters 
                    {   ValidateIssuer = true,
                        IssuerValidator = ValidateSpecificIssuers
                    };
                });

...

private string[] GetAcceptedIssuers()
    {
        return new[]
        {
        "https://login.microsoftonline.com/<tenant1>/v2.0",
        "https://login.microsoftonline.com/<tenant2>/v2.0",
        };
    }

public string ValidateSpecificIssuers(string issuer, SecurityToken securityToken, TokenValidationParameters validationParameters)
    {
        var validIssuers = GetAcceptedIssuers();
        if (validIssuers.Contains(issuer))
        {
            return issuer;
        }
        else
        {
            throw new SecurityTokenInvalidIssuerException("The sign-in user's account does not belong to one of the tenants that this Web App accepts users from.");
        }
    }

【讨论】:

    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 2022-01-27
    • 1970-01-01
    • 2021-01-04
    • 2019-01-29
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多