身份提供商
身份提供方
除内置身份验证系统外,Apache Polaris 还支持通过 OpenID Connect (OIDC) 使用外部身份提供方 (IdP) 进行身份验证。此功能可实现与企业 IdP 的灵活身份联合,并支持在 Polaris 的各 realm 之间逐步迁移或采用混合身份验证策略。
身份验证类型
Polaris 支持三种身份验证模式:
internal(默认)- 仅使用 Polaris 内置身份验证。
external- 使用外部 OIDC 提供方进行身份验证(通过 Quarkus OIDC)。
- 禁用内置令牌端点(返回 HTTP 501)。
mixed- 首先尝试内置身份验证;若失败,则回退到 OIDC。
可以通过设置以下属性,在全局或各 realm 粒度上配置身份验证:
# Global default
polaris.authentication.type=internal
# Per-realm override
polaris.authentication.realm1.type=external
polaris.authentication.realm2.type=mixed关键组件
Authenticator
Authenticator 是一个负责解析主体(principal)及其角色,并根据认证过程提供的凭据创建 PolarisPrincipal 的组件。它是一个核心组件,会被所有类型的认证方式调用。
type 属性用于定义 Authenticator 的实现。该属性可以按 realm 覆盖:
polaris.authentication.authenticator.type=default
polaris.authentication.realm1.authenticator.type=custom内部认证配置
令牌代理
TokenBroker 负责对令牌进行签名和验证,以确保令牌可被校验且未被篡改。
polaris.authentication.token-broker.type=rsa-key-pair
polaris.authentication.token-broker.max-token-generation=PT1H提供两种类型:
rsa-key-pair(推荐用于生产环境):使用 RSA 密钥对进行令牌的签名与验证。symmetric-key:两种操作均使用共享密钥;适用于单节点部署或测试。
属性 polaris.authentication.token-broker.max-token-generation 用于指定内部 TokenBroker 签发的令牌的最大有效期。
- 格式:ISO-8601 持续时间(例如,
PT1H表示 1 小时,PT30M表示 30 分钟)。 - 默认值:
PT1H。
令牌服务
令牌服务(Token Service)以及 TokenServiceConfiguration(Quarkus)负责在使用内部认证时,为已认证的主体签发和验证令牌(例如承载令牌)。它与 Authenticator 和 TokenBroker 协同工作。默认实现为 default,在使用内部认证时必须配置此项。
polaris.authentication.token-service.type=default角色映射
使用内部认证时,令牌请求应包含 scope 参数,用于指定要为该主体激活的角色。scope 参数是以空格分隔的角色名称列表。
默认的 ActiveRolesProvider 要求角色名称采用以下格式:PRINCIPAL_ROLE:<角色名称>。
例如,如果该主体拥有 service_admin 和 catalog_admin 两个角色,并且希望同时激活这两个角色,那么 scope 参数应如下所示:
scope=PRINCIPAL_ROLE:service_admin PRINCIPAL_ROLE:catalog_admin以下是一个使用内部认证向 Polaris 令牌端点发送完整请求的示例:
POST /api/catalog/v1/oauth/tokens HTTP/1.1
Host: polaris.example.com:8181
Content-Type: application/x-www-form-urlencoded
grant_type=client_credentials&client_id=root&client_secret=s3cr3t&scope=PRINCIPAL_ROLE%3Aservice_admin%20PRINCIPAL_ROLE%3Acatalog_admin外部身份认证配置
外部身份认证通过 Quarkus OIDC 及 Polaris 专用的 OIDC 扩展进行配置。以下设置用于与身份提供方集成,并从令牌中提取身份信息和角色信息。
OIDC 租户配置
至少必须显式启用一个 OIDC 租户。在 Polaris 中,域(realm)与 OIDC 租户是不同的概念。OIDC 租户代表一个特定的身份提供方配置(例如 quarkus.oidc.idp1)。而域是 Polaris 内部的逻辑分区。
- 多个域可以共享同一个 OIDC 租户。
- 每个域只能关联一个 OIDC 租户。
因此,多域部署可以共享同一个公共身份提供方,同时仍然实施域级别的范围隔离。要配置默认租户:
quarkus.oidc.tenant-enabled=true
quarkus.oidc.auth-server-url=https://auth.example.com/realms/polaris
quarkus.oidc.client-id=polaris或者,也可以使用多个命名租户。此时,每个基于 OIDC 的命名租户都需要使用标准的 Quarkus 配置进行设置:
quarkus.oidc.oidc-tenant1.auth-server-url=http://localhost:8080/realms/polaris
quarkus.oidc.oidc-tenant1.client-id=client1
quarkus.oidc.oidc-tenant1.application-type=service使用多个 OIDC 租户时,正确配置租户解析是你的责任。请参阅 Quarkus OpenID Connect 多租户指南。
主体映射
OIDC 租户解析完全委托给 Quarkus 处理,但 Polaris 需要额外的配置,以便从 Quarkus 生成并校验的凭证中提取 Polaris 主体及其角色。认证流程的这一部分通过 Polaris 特有的属性进行配置,这些属性将 JWT claims 映射到 Polaris 主体字段:
polaris.oidc.principal-mapper.type=default
polaris.oidc.principal-mapper.id-claim-path=polaris/principal_id
polaris.oidc.principal-mapper.name-claim-path=polaris/principal_name这些属性可以按 OIDC 租户进行覆盖:
polaris.oidc.oidc-tenant1.principal-mapper.id-claim-path=polaris/principal_id
polaris.oidc.oidc-tenant1.principal-mapper.name-claim-path=polaris/principal_name❗重要
PrincipalMapper 的默认实现只能处理 JWT 令牌。如果你的 IDP 颁发的是不透明令牌(opaque token),则需要提供自定义实现。
角色映射
类似地,Polaris 需要额外的配置,才能将 Quarkus 提供的角色映射到 Polaris 中定义的角色。该过程分为两个阶段:首先,Quarkus 使用 quarkus.oidc.roles.* 属性将 JWT 声明映射为安全角色;然后,使用 Polaris 特有的属性将 Quarkus 提供的安全角色映射到 Polaris 角色:
quarkus.oidc.roles.role-claim-path=polaris/roles
polaris.oidc.principal-roles-mapper.type=default
polaris.oidc.principal-roles-mapper.filter=^(?!profile$|email$).*
polaris.oidc.principal-roles-mapper.mappings[0].regex=^.*$
polaris.oidc.principal-roles-mapper.mappings[0].replacement=PRINCIPAL_ROLE:$0这些映射可以按 OIDC 租户覆盖,并可跨依赖外部身份提供商的不同 realm 使用。例如:
polaris.oidc.oidc-tenant1.principal-roles-mapper.type=custom
polaris.oidc.oidc-tenant1.principal-roles-mapper.filter=PRINCIPAL_ROLE:.*
polaris.oidc.oidc-tenant1.principal-roles-mapper.mappings[0].regex=PRINCIPAL_ROLE:(.*)
polaris.oidc.oidc-tenant1.principal-roles-mapper.mappings[0].replacement=PRINCIPAL_ROLE:$1默认的 Authenticator 期望安全标识(security identity)以 PRINCIPAL_ROLE:<role name> 格式暴露角色名称。你可以使用 filter 和 mappings 属性来调整 JWT claims 中出现的角色名称。
例如,假设 Quarkus 生成的安全标识暴露了以下角色:role_service_admin 和 role_catalog_admin。Polaris 分别期望 PRINCIPAL_ROLE:service_admin 和 PRINCIPAL_ROLE:catalog_admin。可以使用以下配置来实现所需的映射:
# Exclude role names that don't start with "role_"
polaris.oidc.principal-roles-mapper.filter=role_.*
# Extract the text after "role_"
polaris.oidc.principal-roles-mapper.mappings[0].regex=role_(.*)
# Replace the extracted text with "PRINCIPAL_ROLE:"
polaris.oidc.principal-roles-mapper.mappings[0].replacement=PRINCIPAL_ROLE:$1更多示例如下。
JWT 映射示例
示例 1:自定义声明路径
JWT
{ "polaris": { "roles": ["PRINCIPAL_ROLE:ALL"], "principal_name": "root", "principal_id": 1 } }配置
quarkus.oidc.roles.role-claim-path=polaris/roles polaris.oidc.principal-mapper.id-claim-path=polaris/principal_id polaris.oidc.principal-mapper.name-claim-path=polaris/principal_name
示例 2:通用 OIDC 声明
JWT
{ "sub": "1", "scope": "service_admin catalog_admin profile email", "preferred_username": "root" }配置
quarkus.oidc.roles.role-claim-path=scope polaris.oidc.principal-mapper.id-claim-path=sub polaris.oidc.principal-mapper.name-claim-path=preferred_username polaris.oidc.principal-roles-mapper.filter=^(?!profile$|email$).* polaris.oidc.principal-roles-mapper.mappings[0].regex=^.*$ polaris.oidc.principal-roles-mapper.mappings[0].replacement=PRINCIPAL_ROLE:$0结果
Polaris 角色:
PRINCIPAL_ROLE:service_admin和PRINCIPAL_ROLE:catalog_admin
其他链接
- 有关完整的 Keycloak 集成示例,请参阅:Keycloak 外部身份提供方配置指南
- 参阅开发者说明,其中包含内部实现细节,适合希望了解或扩展 Polaris 身份验证的开发者。
评论
登录后参与评论
KnowForge