SQL Azure 的 Active Directory B2C onBehalfOf 身份验证

Active Directory B2C onBehalfOf authentication to SQL Azure

我有一个针对 Azure Active Directory 对用户进行身份验证的应用程序。返回的 JWT 令牌然后从应用程序传递到验证令牌的 Web API。

然后我要求 Active Directory 代表用户为 SQL Azure 生成另一个 JWT 令牌。 Web API 现在可以使用 OnBehalfOf 令牌向 SQL Azure 进行身份验证。从这里开始,数据库通过使用 JWT 中的一些独特信息相应地过滤结果来实现 RLS(行级安全性)。

为此,用于请求 onBehalfOf 令牌的 Active Directory 应用程序必须具有 SQL Azure 的 requiredResourceAccess。这是通过编辑 Azure 门户中的应用程序清单来完成的,指定 SQL Azure (022907d3-0f1b-48f7-badc-1ba6abab6d66) 可以访问 Azure SQL 数据库和数据仓库 (c39ef2d1-04ce-46dc- 8b5f-e9a5c60f0fc9).

"requiredResourceAccess": [
    {
      "resourceAppId": "022907d3-0f1b-48f7-badc-1ba6abab6d66",
      "resourceAccess": [
        {
          "id": "c39ef2d1-04ce-46dc-8b5f-e9a5c60f0fc9",
          "type": "Scope"
        }
      ]
    }
  ]

我想支持社交登录,而 Azure B2C 通常更适合我的要求。但是 Azure Active Directory B2C 是否可以支持这种身份验证流程?

const string tenant = "...";
const string clientId = "...";
const string clientSecret = "...";
const string connectionString = "Server=...database.windows.net,1433;Initial Catalog=...;Persist Security Info=False;MultipleActiveResultSets=False;Encrypt=True;TrustServerCertificate=False";

async Task Main()
{
    try
    {
        var authenticationContext = new AuthenticationContext(TenantSettings.Authority);

        var result = await authenticationContext.AcquireTokenAsync(
            "https://database.windows.net/",
            new ClientCredential(clientId, clientSecret),
            new UserAssertion("eyJ...")).ConfigureAwait(false);

        await ConnectToDatabaseAsync(result.AccessToken.Dump());
    }
    catch (Exception ex)
    {
        $"Failed to connect to Azure SQL.\n\tReason: {ex.Message}".Dump();
    }
}

private static async Task ConnectToDatabaseAsync(string accessToken)
{
    using (var connection = new SqlConnection(connectionString))
    {
        connection.AccessToken = accessToken;
        await connection.OpenAsync().ConfigureAwait(false);

        using (var command = new SqlCommand("select USER_NAME()", connection))
        using (var reader = await command.ExecuteReaderAsync())
        {
            await reader.ReadAsync().ConfigureAwait(false);
            reader.GetString(0).Dump("User");
        }
    }
}

private static class TenantSettings
{
    public const string Authority = Instance + Tenant;
    public const string Instance = "https://login.microsoftonline.com/";
    public const string Tenant = tenant;
}

代表 流程当前未在 Azure AD B2C 中实现。请参考Azure Active Directory B2C: Types of applications(Current limitations).

如果您对 Azure 有任何想法或反馈,可以从 here 提交。