数据 API 生成器通过自定义身份验证提供程序支持第三方标识提供者。 当你的组织使用 Okta、Auth0 或其他符合 OAuth 2.0/OpenID Connect 的标识提供者时,请使用此方法。
身份验证流
使用自定义标识提供者时,客户端应用将处理用户身份验证,然后将访问令牌发送到数据 API 生成器:
| 阶段 | 发生的情况 |
|---|---|
| 用户身份验证 | 用户通过标识提供者登录(Okta、Auth0 等) |
| 令牌获取 | 客户端应用从 IdP 接收访问令牌 |
| API 调用 | 客户端在 Authorization 标头中将令牌发送到 DAB。 |
| 验证 | DAB 验证 JWT(颁发者、受众、签名) |
| 授权 | DAB 提取角色并评估权限 |
先决条件
- 您在身份提供商(如 Okta、Auth0 等)处的账户
- 在标识提供者中注册的应用程序
- 已安装的数据 API 生成器 CLI (安装指南)
- 具有至少一个实体的现有
dab-config.json实体
快速参考
| 设置 | 价值 |
|---|---|
| Provider | Custom |
| 验证所必需的 |
iss、 aud、 exp有效签名 |
| 授权所必需的 |
roles 包含所选角色的声明 |
| 令牌标头 | Authorization: Bearer <token> |
| 角色声明类型 |
roles (已修复,不可配置) |
| 角色选择标头 | X-MS-API-ROLE |
步骤 1:配置标识提供者
确切的步骤取决于你的提供商。 以下是所需的键值:
要收集的值
| 价值 | 在哪里找到 | 用于 |
|---|---|---|
| 颁发者 URL | 提供程序文档或 OAuth 元数据终结点 | DAB jwt.issuer (用作 JWT 授权机构) |
| 观众 | 应用程序的客户端 ID 或自定义 API 标识符 | DAB jwt.audience |
注释
DAB 使用配置的 jwt.issuer 作为 JWT 授权。 签名密钥通过标准的 OpenID Connect 元数据(通常为 <issuer>/.well-known/openid-configuration)自动发现。
Okta 示例
- 登录到 Okta 管理控制台。
- 导航到 应用程序>应用程序。
- 创建或选择应用程序。
- 记下 客户端 ID (用作目标受众)。
- 颁发者通常是
https://<your-domain>.okta.com。
Auth0 示例
- 登录到 Auth0 仪表板。
- 导航到 应用程序>API。
- 创建或选择 API。
- 记下 标识符(用作目标受众)。
- 你的颁发者是
https://<your-tenant>.auth0.com/。
重要
数据 API 生成器对基于角色的 roles 授权使用固定声明类型。 无法配置此值。 如果标识提供者在不同的声明(例如 groups 或 permissions)中生成角色,则必须将提供程序配置为也生成 roles 声明,或使用登录后操作将值复制到 roles 声明中。
步骤 2:配置数据 API 生成器
将身份验证提供程序设置为 Custom 并配置 JWT 设置:
CLI
# Set the authentication provider
dab configure \
--runtime.host.authentication.provider Custom
# Set the expected audience
dab configure \
--runtime.host.authentication.jwt.audience "<your-api-identifier>"
# Set the expected issuer
dab configure \
--runtime.host.authentication.jwt.issuer "https://<your-issuer>/"
生成的配置
{
"runtime": {
"host": {
"authentication": {
"provider": "Custom",
"jwt": {
"audience": "<your-api-identifier>",
"issuer": "https://<your-issuer>/"
}
}
}
}
}
步骤 3:配置实体权限
定义标识提供者分配的角色的权限:
CLI
# Allow authenticated users to read
dab update Book \
--permissions "authenticated:read"
# Allow users with 'admin' role full access
dab update Book \
--permissions "admin:*"
生成的配置
{
"entities": {
"Book": {
"source": "dbo.Books",
"permissions": [
{
"role": "authenticated",
"actions": ["read"]
},
{
"role": "admin",
"actions": ["*"]
}
]
}
}
}
步骤 4:在标识提供者中配置角色
DAB 期望声明中 roles 的角色。 配置您的身份提供者以包含此声明。
Okta:将群组添加为角色
- 在 Okta 管理控制台中,转到 安全>API。
- 选择授权服务器。
- 转到“ 声明 ”选项卡。
- 添加声明:
-
名称:
roles - 包含在令牌类型中:访问令牌
- 值类型:组
- 筛选器:选择要包含的组
-
名称:
Auth0:添加角色与动作
- 在 Auth0 仪表板中,转到 操作>库。
- 创建一个新的操作(登录后触发)。
- 添加代码以包括角色:
exports.onExecutePostLogin = async (event, api) => {
const roles = event.authorization?.roles || [];
if (roles.length > 0) {
api.accessToken.setCustomClaim('roles', roles);
}
};
- 部署操作并且将其添加到登录流。
小窍门
有关使用 Okta 配置 JWT 声明的详细指南,请参阅 使用 Okta 的 SDK 实现高级 JWT 声明。
步骤 5:测试配置
启动数据 API 生成器:
dab start从标识提供者获取令牌。 使用提供商的 SDK 或 Postman 等工具。
检查 jwt.io 处的令牌以验证:
- 声明
aud与已配置的受众匹配 - 声明
iss与配置的颁发者匹配 -
roles声明包含预期值
- 声明
调用 API:
curl -X GET "http://localhost:5000/api/Book" \ -H "Authorization: Bearer <your-token>"若要使用自定义角色,请包括
X-MS-API-ROLE标头:curl -X GET "http://localhost:5000/api/Book" \ -H "Authorization: Bearer <your-token>" \ -H "X-MS-API-ROLE: admin"
JWT 验证详细信息
数据 API 生成器验证 JWT 的以下方面:
| 检查 | Description |
|---|---|
| 签名 | 使用通过配置的 jwt.issuer 颁发机构发现的签名密钥(OpenID Connect 元数据/JWKS)进行验证 |
| 颁发者 | 必须完全匹配 jwt.issuer 配置 |
| 观众 | 必须完全匹配 jwt.audience 配置 |
| 过期日期 | 令牌不得过期(exp 声明) |
| 不早于 | 令牌必须有效(nbf 声明(如果存在) |
Troubleshooting
| 症状 | 可能的原因 | 解决方案 |
|---|---|---|
401 Unauthorized |
颁发者不匹配 | 请检查iss声明是否完全匹配(包括结尾的斜杠) |
401 Unauthorized |
受众不匹配 | 检查aud声明是否与配置的值匹配 |
401 Unauthorized |
令牌已过期 | 获取新令牌 |
401 Unauthorized |
元数据不可用 | 确保 DAB 能够到达 <issuer>/.well-known/openid-configuration |
403 Forbidden |
角色不在令牌中 | 将角色添加到 IdP 配置 |
403 Forbidden |
缺少角色声明 | 将 IdP 配置为包含 roles 声明 |
403 Forbidden |
错误的声明名称 | DAB 使用声明类型 roles (固定,不可配置) |
重要
DAB 当前使用声明类型 roles 来进行所有角色检查。 此值是硬编码的,不能更改为groupspermissions其他声明名称。 将标识提供者配置为在名为 roles 的声明中发送角色。
常见发行者格式
| Provider | 颁发者格式 |
|---|---|
| Okta |
https://<domain>.okta.com 或 https://<domain>.okta.com/oauth2/default |
| Auth0 |
https://<tenant>.auth0.com/ (请注意尾部斜杠) |
| Azure AD B2C | https://<tenant>.b2clogin.com/<tenant-id>/v2.0/ |
| Keycloak | https://<host>/realms/<realm> |
完整配置示例
Okta 配置
{
"$schema": "https://github.com/Azure/data-api-builder/releases/latest/download/dab.draft.schema.json",
"data-source": {
"database-type": "mssql",
"connection-string": "@env('SQL_CONNECTION_STRING')"
},
"runtime": {
"host": {
"authentication": {
"provider": "Custom",
"jwt": {
"audience": "0oa1234567890abcdef",
"issuer": "https://dev-12345.okta.com"
}
}
}
},
"entities": {
"Book": {
"source": "dbo.Books",
"permissions": [
{
"role": "authenticated",
"actions": ["read"]
},
{
"role": "editor",
"actions": ["create", "read", "update"]
}
]
}
}
}
Auth0 配置
{
"$schema": "https://github.com/Azure/data-api-builder/releases/latest/download/dab.draft.schema.json",
"data-source": {
"database-type": "mssql",
"connection-string": "@env('SQL_CONNECTION_STRING')"
},
"runtime": {
"host": {
"authentication": {
"provider": "Custom",
"jwt": {
"audience": "https://my-api.example.com",
"issuer": "https://my-tenant.auth0.com/"
}
}
}
},
"entities": {
"Book": {
"source": "dbo.Books",
"permissions": [
{
"role": "authenticated",
"actions": ["read"]
},
{
"role": "admin",
"actions": ["*"]
}
]
}
}
}