配置 Neo4j 单点登录 (SSO)企业版
Neo4j 支持通过实现 OpenID Connect (OIDC) 标准的身份提供商进行 SSO 身份验证和授权。本页面详细介绍了如何为多个身份提供商配置单点登录 (SSO)。它还提供了常见问题解答以及在配置 SSO 时遇到常见问题的解决方案。
|
以下配置是为服务于 https://:7474/ 的 Neo4j Browser 而设计的(在 因此,在身份提供商中重现这些配置时,必须修改重定向 URI,以包含为 Neo4j Browser 应用程序提供服务的 URI。例如: https://:7474/browser/?idp_id={provider}&auth_flow_step=redirect_uri
|
SSO 的工作方式如下:
-
服务器 (Neo4j DBMS) 联系身份提供商 (Okta、Entra ID、Google 等) 并从提供商处获取 JSON Web 密钥 (JWKs)。
-
客户端 (例如 Bloom、Neo4j Browser 等) 要求用户提供凭据并联系身份提供商。
-
身份提供商会以 JSON Web Token (JWT) 进行响应,这是一个包含与用户相关的字段(声明,claims,如电子邮件、受众、组等)的 JSON 文件。
-
客户端向服务器提供 JWT,服务器使用 JWKs 验证其签名。
-
您可以选择通过在 neo4j.conf 文件中将
dbms.security.require_local_user设置为true,并使用 Cypher 为用户设置 身份验证提供商,从而在用户层面控制身份验证和授权。此设置强制要求关联了相关身份验证提供商的用户必须先存在于数据库中,才能通过该提供商进行身份验证和授权。有关如何在此模式下修改或创建用户的信息,请参阅 管理用户。
此模式允许您使用 Cypher 执行以下操作:-
挂起 SSO 用户。
-
为 SSO 用户设置主数据库。
-
为 SSO 用户设置用户友好的名称(而不是依赖外部标识符)。
-
为 SSO 用户设置密码。
-
为 SSO 用户设置密码更改要求。
-
有关更多信息和示例,请参阅 使用身份验证提供商在用户层面配置 SSO。
|
即使在使用不同的声明作为 |
Okta
以下示例展示了如何配置 Okta,以便使用访问令牌 (Access Tokens) 和 ID 令牌 (ID Tokens) 进行身份验证和授权。此示例假设您正在使用 Okta Developer Edition 服务。有关如何自定义从 Okta 返回的带有组 (groups) 声明的令牌的完整指南,请参阅 Okta 官方文档。
配置客户端
-
在 Okta 仪表板的左侧,导航至 Applications 并点击 Create App Integration。
-
对于登录方法,选择 OIDC - OpenID Connect;对于应用程序类型,选择 Single-Page Application。
-
点击 Next。
-
使用适当的重定向 URI 配置客户端。
-
为应用程序集成添加名称。
-
添加 Sign-in redirect URIs,例如 https://:7474/browser/?idp_id=okta&auth_flow_step=redirect_uri。此 URI 将在身份验证成功后接受返回的令牌响应。
-
-
添加 Sign-out redirect URIs,例如 https://:7474/。
-
在 Assignments 部分,暂时选择 Skip group assignment。
-
点击 Save。
-
记录 Client ID。稍后在 neo4j.conf 文件中配置 Okta 参数和 Well-known OpenID Connect 端点时需要用到它。
将 Okta 组分配给应用程序
-
在 Okta 仪表板左侧,导航至 Dashboard → Directory → Groups,然后点击 Add Group。
-
为组添加名称(例如
engineers),然后点击 Save。 -
点击您刚刚创建的组,然后点击 Assign people。
-
将用户添加到组中。用户可以在创建用户时或通过编辑组来添加到组中。
-
将组分配给应用程序。
-
点击 Applications,然后点击 Assign Applications。
-
选择您之前创建的应用程序,然后点击 Assign。
-
访问令牌 (Access Token)
本示例展示了如何配置 Okta 以使用访问令牌进行身份验证和授权,以及如何配置 Neo4j 以使用它们。
向访问令牌添加组声明
-
在 Okta 仪表板左侧,导航至 Security → API。
-
点击默认授权服务器(显示
api://default作为受众的那个),以返回访问令牌中的groups声明。-
在 Claims 选项卡上,点击 Add Claim。
-
添加名称为
groups的声明。 -
从 Value type 下拉菜单中,选择 Groups。
-
从 Filter 下拉菜单中,选择 Matches regex 并将值设置为
.*。 -
点击 Create。
-
配置 Neo4j
-
通过在 neo4j.conf 文件中配置以下设置,将 Neo4j 配置为使用 Okta 身份验证。
dbms.security.authentication_providers=oidc-okta dbms.security.authorization_providers=oidc-okta dbms.security.oidc.okta.display_name=Okta dbms.security.oidc.okta.auth_flow=pkce dbms.security.oidc.okta.well_known_discovery_uri=https://dev-54101110.okta.com/oauth2/default/.well-known/oauth-authorization-server dbms.security.oidc.okta.audience=api://default dbms.security.oidc.okta.claims.username=sub dbms.security.oidc.okta.claims.groups=groups dbms.security.oidc.okta.params=client_id=0oao2rybx5hIERt5W5d7;response_type=code;scope=openid profile email dbms.security.oidc.okta.authorization.group_to_role_mapping= "engineers" = admin; \ "collaborators" = readertoken_type_principal和token_type_authentication被省略,这意味着将使用访问令牌。 -
使用
engineer角色用户的电子邮件登录您的 Okta SSO 凭据,该用户在数据库中对应admin角色。
图 1. Okta OIDC 登录成功
ID 令牌 (ID Token)
本示例展示了如何配置 Okta 以使用 ID 令牌进行身份验证和授权,以及如何配置 Neo4j 以使用它们。
向 ID 令牌添加组声明
您可以向 ID 令牌添加组声明,以使用 ID 令牌配置身份验证和授权。
-
在 Okta 仪表板左侧,导航至 Security → API。
-
点击默认授权服务器(显示
api://default作为受众的那个),以返回访问令牌中的groups声明。-
在 Claims 选项卡上,点击 Add Claim。
-
添加名称为
groups的声明。 -
从 Include in token type 下拉菜单中,选择 ID Token。
-
从 Value type 下拉菜单中,选择 Groups。
-
从 Filter 下拉菜单中,选择 Matches regex 并将值设置为
.*。 -
点击 Create。
-
-
添加名称为
userid、值类型为User ID的声明。userid声明不像访问令牌的默认sub声明那样默认包含在 ID 令牌中,因此需要手动添加。您为声明提供的名称也需要在 neo4j.conf 文件的配置dbms.security.oidc.okta.claims.username=userid中指定。-
点击 Add Claim。
-
添加名称为
userid的声明。 -
从 Include in token type 下拉菜单中,选择 ID Token。
-
从 Value type 下拉菜单中,选择 Expression。
-
在 Value 字段中,输入
(appuser !=null) ? appuser.userName : app.clientId。 -
点击 Create。
-
配置 Neo4j
-
通过在 neo4j.conf 文件中配置以下设置,将 Neo4j 配置为使用 Okta 身份验证。
dbms.security.authentication_providers=oidc-okta, native dbms.security.authorization_providers=oidc-okta dbms.security.oidc.okta.display_name=Okta dbms.security.oidc.okta.auth_flow=pkce dbms.security.oidc.okta.well_known_discovery_uri=https://dev-54101110.okta.com/oauth2/default/.well-known/oauth-authorization-server dbms.security.oidc.okta.audience=0oao2rybx5hIERt5W5d7 dbms.security.oidc.okta.claims.username=userid dbms.security.oidc.okta.claims.groups=groups dbms.security.oidc.okta.params=client_id=0oao2rybx5hIERt5W5d7;response_type=code;scope=openid profile email dbms.security.oidc.okta.authorization.group_to_role_mapping="admin_group" = admin; dbms.security.oidc.okta.config=token_type_principal=id_token;token_type_authentication=id_token您可以在 Sign On 选项卡上找到您应用程序的 OpenID Connect ID Token 下的受众参数。
-
(可选) 如果您想在用户层面控制身份验证和授权,请在 neo4j.conf 文件中将
dbms.security.require_local_user配置为true。此设置强制要求关联了相关身份验证提供商的用户必须先存在于数据库中,才能通过该提供商进行身份验证和授权。有关如何在此模式下创建用户的信息,请参阅 创建用户。例如,要创建用户
jake,使其可以使用native或okta进行身份验证,并使用 Okta 进行授权(如步骤 3 所配置),您可以使用以下 Cypher 查询:CREATE USER jake SET HOME DATABASE 'jakesHomeDb' SET AUTH 'oidc-okta' {SET ID 'jakesUniqueOktaUserId'} // `jakesUniqueOktaUserId` must match the value of the claim that you configured via dbms.security.oidc.okta.claims.username SET AUTH 'native' {SET PASSWORD 'changeme' SET PASSWORD CHANGE REQUIRED}有关更多示例,请参阅 使用身份验证提供商在用户层面配置 SSO。
Microsoft Entra ID (前身为 Azure Active Directory)
以下示例展示了如何配置 Microsoft Entra ID,以便使用访问令牌和 ID 令牌进行身份验证和授权。
注册应用程序
-
登录 Azure 门户。
-
点击 Microsoft Entra ID 并导航至 Manage → App registrations。
-
点击 New registration。
-
为您的应用程序输入名称,例如
Neo4j SSO。 -
在 Select the supported account types 下,选择
Accounts in this organizational directory only (Default Directory only - Single tenant)。 -
在 Redirect URI 下,选择
Single-page application (SPA)并输入重定向 URI:https://:7474/browser/?idp_id=azure&auth_flow_step=redirect_uri。该重定向 URI 将在身份验证成功后接受返回的令牌响应。 -
点击 Register。
访问令牌
本示例展示了如何配置 Neo4j 以使用 Entra ID 访问令牌进行身份验证和授权。
配置 Entra ID
-
在 App registrations 页面上,选择您刚刚创建的应用程序。
-
从左侧菜单中,导航至 Manage → Token configuration。
-
点击 Add groups claim。
-
选择 Groups assigned to the application (recommended for large enterprise companies to avoid exceeding the limit on the number of groups a token can emit) 以将其包含在访问令牌中。
-
保存更改。
-
-
导航至 Expose an API 并点击 Add a Scope。
第一次点击 Add a Scope 按钮时,您会看到一个新面板,提示您需要在继续之前添加一个 Application ID URI。您可以在应用程序的 Overview 页面上找到它。它是一个 GUID,看起来像这样:
api://<GUID>。该 GUID 是您应用程序的唯一标识符。 -
设置好 Application ID URI 后,点击 Save and continue。
-
填写 Add a scope 面板中的所有必填字段。
-
输入新的 Scope name (例如
access-token)、Admin consent display name 和 Admin consent description。 -
确保已选择 Enabled 范围状态。
-
再次点击 Add scope 按钮以创建新范围。您可以添加 API 支持的所有范围。记下它们以备后用。
-
配置 Neo4j
通过在 neo4j.conf 文件中配置以下设置,您可以将 Neo4j 配置为使用 Entra ID 进行身份验证。
# Configure the access_token
dbms.security.oidc.azure.config=principal=unique_name;code_challenge_method=S256;token_type_principal=access_token;token_type_authentication=access_token
# Configure the OIDC token endpoint with the Directory (tenant) ID
dbms.security.oidc.azure.token_endpoint=https://login.microsoftonline.com/54e85725-ed2a-49a4-a19e-11c8d29f9a0f/oauth2/v2.0/token
# Configure the iss claim in the id token with the Directory (tenant) ID
# Make sure you add the trailing slash (`/`) at the end of the URL or this operation might fail.
dbms.security.oidc.azure.issuer=https://sts.windows.net/54e85725-ed2a-49a4-a19e-11c8d29f9a0f/
# Provide the Entra ID parameters, such as client_id, response_type, scope, etc.
dbms.security.oidc.azure.params=client_id=4376dc8b-b5af-424f-9ada-c1c1b2d416b9;response_type=code;scope=openid profile email api://4376dc8b-b5af-424f-9ada-c1c1b2d416b9/access-token
ID 令牌
本示例展示了如何配置 Neo4j 以使用 Entra ID ID 令牌进行身份验证和授权。
配置 Neo4j
-
在 App registrations 页面上,选择您在 注册应用程序 中创建的应用程序。
-
在应用程序的 Overview 页面上,复制 Application (client) ID 值,并将其用于在 neo4j.conf 文件中配置以下属性。
dbms.security.oidc.azure.audience=4376dc8b-b5af-424f-9ada-c1c1b2d416b9 dbms.security.oidc.azure.params=client_id=4376dc8b-b5af-424f-9ada-c1c1b2d416b9;response_type=code;scope=openid profile email -
在应用程序的 Overview 页面上,点击 Endpoints 选项卡,并复制 OpenID Connect metadata document URI:将其用于在 neo4j.conf 文件中配置
well_known_discovery_uri。dbms.security.oidc.azure.well_known_discovery_uri=https://login.microsoftonline.com/54e85725-ed2a-49a4-a19e-11c8d29f9a0f/v2.0/.well-known/openid-configuration -
在 neo4j.conf 文件中将 Neo4j 配置为使用 Entra ID 身份验证。
dbms.security.authentication_providers=oidc-azure dbms.security.authorization_providers=oidc-azure dbms.security.oidc.azure.display_name=Azure dbms.security.oidc.azure.auth_flow=pkce dbms.security.oidc.azure.config=token_type_principal=id_token;token_type_authentication=id_token -
配置应该将哪个 JWT 声明用作用户名。可能的值为
sub、email或preferred_username。sub是唯一保证唯一且稳定的声明。有关详细信息,请参阅 Microsoft 文档 以及 OpenID 规范。dbms.security.oidc.azure.claims.username=sub
将 Entra 组映射到 Neo4j 角色
决定是要直接使用 Entra 组还是使用 Entra 应用程序角色 (App Roles)。
如果您已经有用户被分配到这些组,并且希望在 neo4j.conf 文件中执行“组到角色”映射,那么直接使用 Entra 组可能很方便。
Entra 应用程序角色在 Neo4j 角色和组之间提供了一层分离。使用应用程序角色时,只有与 Neo4j 相关的角色会被发送到 JWT 令牌中。这防止了应用程序之间的权限泄露。JWT 令牌还限制每个用户每个令牌最多 200 个角色,通过仅发送相关的应用程序角色可以避免此限制。
有关 Entra ID 应用程序角色的详细信息,请参阅 Microsoft 文档。
直接使用 Entra 组
-
在 App registrations 页面上,选择您的应用程序。
-
从左侧菜单中,导航至 Manage → Manifest。
-
验证服务器是否配置为在 JWT 身份令牌中返回组对象 ID。
"groupMembershipClaims": "SecurityGroup, ApplicationGroup", -
从左侧菜单中,导航至 Manage → Groups。
-
创建组并将用户分配给它们。记录 Object Id 列。
-
配置从 Entra 组对象 ID 到 Neo4j 角色的映射。有关详细信息,请参阅 将身份提供商组映射到 Neo4j 角色。
dbms.security.oidc.azure.authorization.group_to_role_mapping= "e8b6ddfa-688d-4ace-987d-6cc5516af188" = admin; \ "9e2a31e1-bdd1-47fe-844d-767502bd138d" = reader -
配置 Neo4j 以使用 JWT 令牌中的
groups字段。dbms.security.oidc.azure.claims.groups=groups
使用 Entra ID 应用程序角色
-
从左侧菜单中,导航至 App roles 并将 Neo4j 角色添加到 Microsoft Entra ID 中。
-
点击 Create app role。
-
填写字段:
-
Display name:
admin -
Allowed member types:
Users/Groups -
Value:
admin。
Value 列必须对应于 Neo4j 角色,或者在 neo4j.conf 文件中进行映射。 -
Description:
Neo4j admin role
-
-
点击 Apply。
-
-
对要添加的其他角色重复上述步骤。
-
在 neo4j.conf 文件中配置从 Entra 应用程序角色到 Neo4j 角色的映射。有关详细信息,请参阅 将身份提供商组映射到 Neo4j 角色。
dbms.security.oidc.azure.authorization.group_to_role_mapping= "managers" = admin; \ "engineers" = reader -
配置 Neo4j 以使用 JWT 令牌中的
roles字段。dbms.security.oidc.azure.claims.groups=roles -
(可选) 如果您想在用户层面控制身份验证和授权,请在 neo4j.conf 文件中将
dbms.security.require_local_user配置为true。此设置强制要求关联了相关身份验证提供商的用户必须先存在于数据库中,才能通过该提供商进行身份验证和授权。有关如何在此模式下创建用户的信息,请参阅 创建用户。例如,要创建用户
jake,使其可以使用 Azure 进行身份验证和授权,您可以使用以下 Cypher 查询:CREATE USER jake SET HOME DATABASE 'jakesHomeDb' SET AUTH 'oidc-azure' {SET ID 'jakesUniqueAzureUserId'} // `jakesUniqueAzureUserId` must match the value of the claim that you configured via dbms.security.oidc.azure.claims.username有关更多示例,请参阅 使用身份验证提供商在用户层面配置 SSO。
ID 令牌
本示例展示了如何结合原生授权,使用 Google OpenID Connect 进行 ID 令牌身份验证。
-
配置客户端和重定向 URI
图 2. Google OIDC 客户端创建
图 3. Google OIDC 客户端配置SSO 授权不适用于 Google,因为 Google 返回的 JWT 不包含用户所属组的信息,且无法进行相关配置。因此,建议通过在 Neo4j 中创建该用户的原生版本来使用原生(或其它风格)授权。
-
通过在 neo4j.conf 文件中设置以下配置,将 Neo4j 配置为使用 Google 身份验证:
dbms.security.authentication_providers=oidc-google dbms.security.authorization_providers=native dbms.security.oidc.google.display_name=Google dbms.security.oidc.google.auth_flow=pkce dbms.security.oidc.google.well_known_discovery_uri=https://#/.well-known/openid-configuration dbms.security.oidc.google.audience=345461137297-v9brpjmgbvbm3d5s9fq65tktevosd3rn.apps.googleusercontent.com dbms.security.oidc.google.claims.username=email dbms.security.oidc.google.params=client_id=345461137297-v9brpjmgbvbm3d5s9fq65tktevosd3rn.apps.googleusercontent.com;response_type=code;scope=openid profile email dbms.security.oidc.google.token_params=client_secret=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 dbms.security.oidc.google.config=token_type_principal=id_token;token_type_authentication=id_token -
使用以下选项之一,在数据库中创建一个可以原生进行身份验证和授权的用户,以便能够向用户授予来自原生授权的角色。
此方法依赖于存在一个可以原生进行身份验证的管理员用户,然后通过 身份验证提供商 创建权限较低的用户。这些用户只能使用
oidc-google进行身份验证,但将获得使用native授权授予他们的角色。数据库 首次启动 时,默认会创建一个名为
neo4j的管理员用户。-
在 neo4j.conf 文件中,仅为
admin用户临时启用原生身份验证,并启用对身份验证和授权的用户级控制:dbms.security.authentication_providers=oidc-google, native dbms.security.require_local_user=true这将切换到 用户身份验证提供商 模式,在该模式下,用户只有在数据库中拥有相应的身份验证提供商时,才能进行身份验证和授权。
-
创建一个只能使用
oidc-google进行身份验证和授权的用户:CREATE USER jake SET HOME DATABASE 'jakesHomeDb' SET AUTH 'oidc-google' {SET ID 'jakesUniqueGoogleUserId'} (1)1 jakesUniqueGoogleUserId必须与您通过dbms.security.oidc.google.claims.username配置的声明的值相匹配。 -
向用户
jake授予角色,例如reader:GRANT ROLE reader TO jake该用户隐式接收
native授权,因为native在授权提供商列表中,并且您已显式向该用户授予了角色。 -
以这种方式设置用户后,您可以完全禁用数据库的原生身份验证。这将阻止所有用户(包括管理员)使用用户名和密码登录:
dbms.security.authentication_providers=oidc-google
或者,如果您不使用身份验证提供商,则可以临时启用
native身份验证来创建一个 SSO 身份验证的管理员用户alice,然后由她来创建其他只能使用 SSO 身份验证的用户。-
临时启用
native身份验证:dbms.security.authentication_providers=oidc-google, native -
创建一个 SSO 身份验证的
admin用户(在本例中,必须在 Google SSO 提供商中设置一个等同于alice@neo4j-test.com的用户,且其凭据必须已知):CREATE USER `alice@neo4j-test.com` SET PASSWORD 'secretpassword'; GRANT ROLE admin to `alice@neo4j-test.com`; -
为数据库禁用原生身份验证,以防止用户使用用户名和密码登录:
dbms.security.authentication_providers=oidc-google -
以
alice@neo4j-test.com(管理员用户)身份通过 Google SSO 登录。 -
创建其他只能使用
oidc-google进行身份验证的用户,他们将获得使用native授权授予他们的角色。CREATE USER jakesUniqueGoogleUserId (1) SET HOME DATABASE 'jakesHomeDb' SET PASSWORD 'secretpassword' SET PASSWORD CHANGE NOT REQUIRED1 jakesUniqueGoogleUserId必须与您通过dbms.security.oidc.google.claims.username配置的声明的值相匹配。 -
使用原生授权授予用户角色:
GRANT ROLE reader TO jakesUniqueGoogleUserId
-
常见问题解答 (FAQ)
何时应使用 pkce 作为授权流程?
假设可以通过公共互联网访问客户端(Neo4j Browser 或 Bloom),请始终使用 pkce 授权流程而不是 implicit,因为后者要求将客户端的密钥对公共客户端公开。通常,如果两种流程都可用,建议选择 pkce,因为它比 implicit 更安全。
如果配置中列出了客户端密钥,Google 身份验证安全吗?
是的。Google 使用 pkce 流程,但身份提供商有时也会使用客户端密钥来确保请求令牌的客户端正是使用它的客户端(pkce 无法保证这一点)。客户端密钥不会增加任何额外的安全性,因为它本质上是公开的,但 pkce 流程提供了足够的安全性。
无法解析类型为 "access_token" 的 JWT
当在 Browser 上收到 Failed to get credentials: Could not parse JWT of type "access_token" 消息时,这可能意味着提供商只接受 ID 令牌。
在您的 neo4j.conf 中更改为 ID 令牌:
dbms.security.oidc.{{provider}}.config=token_type_principal=id_token;token_type_authentication=id_token
何时应使用 ID 令牌与访问令牌?
由于访问令牌寿命较短,因此在可能的情况下使用访问令牌通常更安全。如果身份提供商上的授权权限发生更改,Neo4j 将会授权失败。Neo4j Browser 将尝试重新连接,并比使用 ID 令牌更快地反映更改后的权限。
JWT 声明的调试日志记录
设置 OIDC 集成时,有时需要进行故障排除。在这些情况下,查看身份提供商提供的 JWT 中包含的声明可能会很有用。
要在安全日志中以 DEBUG 级别启用这些声明的日志记录,请将 dbms.security.logs.oidc.jwt_claims_at_debug_level_enabled 设置为 true,并将安全日志级别设置为 DEBUG。您可以在 <NEO4J_HOME>/conf/server-logs.xml 中执行此操作。
如果您需要有关如何设置和管理安全日志的更多信息,请参阅 配置安全日志。
|
请务必在生产环境中将 dbms.security.logs.oidc.jwt_claims_at_debug_level_enabled 设置回 |