使用 OIDC 配置 SSO
本指南介绍如何使用 OpenID Connect(OIDC)协议为 API7 控制台配置单点登录(SSO)。OIDC SSO 允许用户使用现有企业凭证进行认证,无需单独维护控制台账户。
工作原理
- 用户在控制台登录页选择 OIDC 登录选项。
- 浏览器会重定向到 IdP 授权端点。
- 认证完成后,IdP 会携带授权码重定向回控制台。
- 控制台使用授权码换取令牌,获取用户信息,并创建或更新用户账户。
- 如果配置了角色和权限边界映射,这些映射会在每次登录时应用。
前置条件
开始前,请确保你已具备:
- 正在运行且可访问控制台的 API7 网关部署。
- 符合 OIDC 标准的身份提供商,例如 Keycloak、Microsoft Entra ID、Auth0 或 Okta。
- 来自 IdP 的以下信息:
- Issuer URL:OIDC 发现端点,不包含
/.well-known/openid-configuration。 - Client ID:在 IdP 中注册的应用标识符。
- Client Secret:应用密钥。
- Issuer URL:OIDC 发现端点,不包含
第 1 步:在 IdP 中注册 API7 控制台
在你的身份提供商中将 API7 控制台注册为 OIDC 客户端应用程序:
-
创建一个新的应用程序,授权类型选择 Authorization Code(也称为 "standard flow" 或 "confidential client")。
-
将重定向 URI 设置为:
https://<DASHBOARD_URL>/api/oidc/<LOGIN_OPTION_ID>/callback。备注LOGIN_OPTION_ID会在 API7 中创建登录选项后生成(第 2 步)。完成第 2 步后,你可能需要回到 IdP 更新重定向 URI。 -
记录 Client ID、Client Secret 和 Issuer URL,供下一步使用。
关于特定 IdP 的详细说明,请参阅下方提供商专用配置部分。
第 2 步:创建 OIDC 登录选项
- 在 API7 控制台中,进入 Organization > Settings。
- 点击 Add Login Option。
- 填写配置:
| 字段 | 描述 | 示例 |
|---|---|---|
| Name | 登录页显示的名称,格式为 "Login with {Name}" | Corporate SSO |
| Provider | 选择 OIDC | — |
| Issuer | OIDC 提供商的 Issuer URL,不包含 /.well-known/openid-configuration | https://idp.example.com/realms/my-realm |
| Client ID | 来自 IdP 的应用标识符 | api7-dashboard |
| Client Secret | 来自 IdP 的应用密钥 | ******** |
| Request Scope | 空格分隔的作用域列表。openid 是必需项。 | openid profile email |
| Root URL | 用户访问控制台的 URL。必须匹配协议、主机和端口。 | https://dashboard.example.com |
| SSL Verify | 是否验证 IdP 的 TLS 证书 | true |
| Logout URL | IdP 的 end_session_endpoint URL,可选携带 post_logout_redirect_uri | https://idp.example.com/.../logout?post_logout_redirect_uri=https://dashboard.example.com |
| Attributes Mapping | 将 IdP 声明映射到 API7 用户字段:username、email、name | preferred_username、email、name |
- 点击 Add。
创建后,登录选项会显示其 Callback URL。复制该 URL,并将其作为重定向 URI 注册到你的 IdP 中(如果第 1 步尚未完成)。
第 3 步:验证 SSO 登录
- 退出 API7 控制台。
- 在登录页,你应看到一个新选项:Login with {Name}。
- 点击该选项,通过 IdP 完成认证。
- 认证成功后,你会被重定向回控制台。
SSO 用户会出现在 Organization > Users 下。默认情况下,该用户未分配任何角色,无法管理资源,直到你配置角色映射或手动分配角色。
在控制台中删除用户会移除其角色和权限边界,但该用户仍可再次作为新用户登录。若要完全撤销访问权限,请从 IdP 中移除该用户。
配置角色映射
角色映射会根据身份提供商中的属性自动为 SSO 用户分配 API7 角色。这样可以免去手动分配角色,并保持权限同步。
自动角色映射优先于手动角色分配。启用映射后,用户下次登录时会覆盖任何手动更改。
第 1 步:在 IdP 中暴露角色属性
配置 IdP,使其在用户信息或令牌声明中包含角色相关属性。具体方式因 IdP 而异:
- 用户属性:直接在用户资料中添加属性,例如
position: admin。 - 组成员关系:将用户加入某个组,例如
api7-admins,并将组成员关系作为声明提供。
详细说明请参阅提供商专用配置部分。
第 2 步:在 API7 中启用角色映射
- 在 API7 控制台中,进入 Organization > Settings。
- 选择你的 OIDC 登录选项。
- 启用 Role Mapping。
- 配置映射规则:
| 字段 | 描述 | 示例 |
|---|---|---|
| Internal Role | 要分配的 API7 角色 | Super Admin |
| Role Attribute | 指向 IdP 属性的 JSONPath | $.position 或 $.groups[*] |
| Operation | 比较方式:Exact Match、Contains String、Exact Match in Array 或 Contains String in Array | Exact Match |
| Role Value | 期望的属性值 | admin |
- 点击 Enable。
具有匹配属性的用户会在下次登录时自动分配指定角色。
权限边界映射
权限边界映射的工作方式与角色映射相同,但它将权限策略作为边界分配,而不是附加角色。有关策略和边界的定义,请参阅权限策略和权限边界。请在登录选项设置中启用 Permission Boundary Mapping,并使用相同的属性匹配方式配置映射规则。
提供商专用配置
Keycloak
IdP 设置
- 创建一个 realm,例如
my-realm。 - 创建一个 client,例如
api7-dashboard:- 启用 client authentication(confidential access type)。
- 启用 standard flow(authorization code grant)。
- 将重定向 URI 设置为
https://<DASHBOARD_URL>/api/oidc/<LOGIN_OPTION_ID>/callback。
- 在 client 的 Credentials 标签页中,复制 Client Secret。
- 根据需要创建带密码的 users。
- 在 Realm Settings 中找到 OpenID Connect Discovery 链接并记录:
issuerURL,例如https://keycloak.example.com/realms/my-realm。- 用作 Logout URL 的
end_session_endpointURL。
属性映射配置
| 属性映射 | IdP 声明 | API7 字段 |
|---|---|---|
| username | preferred_username | username |
email | email | |
| name | name | name |
通过用户属性映射角色
- 在 Realm Settings 中启用 Unmanaged Attributes。
- 进入用户的 Attributes 标签页,并添加键值对,例如
position: admin。 - 在 Client Scopes 中,选择 Request Scope 中包含的作用域,例如
profile。 - 添加 User Attribute mapper:
- User Attribute:
position - Token Claim Name:
position
- User Attribute:
- 在 API7 中使用映射规则:属性
$.position,操作Exact Match,值admin。
通过组成员关系映射角色
- 创建一个 group,例如
admin,并将用户加入该组。 - 在 Client Scopes 中添加 Group Membership mapper:
- Token Claim Name:
groups
- Token Claim Name:
- 在 API7 中使用映射规则:属性
$.groups[*],操作Contains String,值admin。
Microsoft Entra ID (Azure AD)
IdP 设置
- 在 Azure portal 中,进入 Microsoft Entra ID > App registrations 并注册一个新应用。
- 在 Certificates & secrets 下创建新的客户端密钥并保存。
- 在 Endpoints 下找到 OpenID Connect metadata document URL。提取颁发者 URL,例如
https://login.microsoftonline.com/{tenant-id}/v2.0。 - 在 Authentication 下添加重定向 URI:
https://<DASHBOARD_URL>/api/oidc/<LOGIN_OPTION_ID>/callback。
属性映射配置
| 属性映射 | IdP 声明 | API7 字段 |
|---|---|---|
| username | preferred_username | username |
email | email | |
| name | name | name |
Issuer URL 不应包含 /.well-known/openid-configuration。
角色映射
- 在 App roles 下创建角色,例如
SuperAdmin。 - 在 Enterprise applications 下将角色分配给用户。
- 在 API7 中使用映射规则:属性
$.roles,操作Exact Match in Array,值SuperAdmin。
Auth0
IdP 设置
- 在 Applications 下创建一个 Regular Web Application。
- 记录 Client ID、Client Secret 和 Domain(issuer)。
- Issuer URL 为
https://<DOMAIN>/(包含末尾斜杠)。 - 在应用的 Settings 标签页下:
- 将回调 URL 添加到 Allowed Callback URLs。
- 将控制台 URL 添加到 Allowed Logout URLs 和 Allowed Web Origins。
- 查看
https://<DOMAIN>/.well-known/openid-configuration中的发现文档,找到end_session_endpoint。
属性映射配置
| 属性映射 | IdP 声明 | API7 字段 |
|---|---|---|
| username | name | username |
email | email | |
| name | name | name |
角色映射
Auth0 需要通过登录后操作(post-login Action)将角色写入令牌声明:
- 在 User Management > Roles 下创建角色,例如
admin,并分配用户。 - 在 Actions > Triggers 下创建一个
post-login操作:
exports.onExecutePostLogin = async (event, api) => {
const roles = (event.authorization && event.authorization.roles) || [];
const claimName = "https://dashboard.example.com/roles";
api.idToken.setCustomClaim(claimName, roles);
api.accessToken.setCustomClaim(claimName, roles);
};
- 将该操作绑定到 Post Login 触发器。
- 在 API7 中使用映射规则:属性
$['https://dashboard.example.com/roles'],操作Exact Match in Array,值admin。
删除登录选项
删除登录选项会移除与该选项关联的所有控制台用户。
- 进入 Organization > Users,确认哪些用户与该登录选项关联。
- 进入 Organization > Settings。
- 在登录选项上点击 Delete。
始终必须保留至少一个已启用的登录选项。你无法删除或禁用最后一个已启用的登录选项。