LDAP 集成

Neo4j 支持 LDAP,这允许与 Active Directory (AD)、OpenLDAP 或其他与 LDAP 兼容的身份验证服务集成。这意味着您使用 LDAP 服务来管理联合用户,而本机 Neo4j 用户和角色管理将完全关闭。

配置 LDAP 时,以下配置设置很重要。有关 LDAP 配置选项的更详细概述,请参阅 配置设置

LDAP 动态配置设置

以下配置设置可以在数据库运行时更新,请参阅 更新动态设置。更改任何这些设置都会清除身份验证和授权缓存。

参数名称 默认值 描述

dbms.security.ldap.authentication.user_dn_template

uid={0},ou=users,dc=example,dc=com

将用户名转换为 LDAP 特定的完全限定名称,用于登录。

dbms.security.ldap.authorization.user_search_base

ou=users,dc=example,dc=com

设置要搜索用户对象的基对象或命名上下文。

dbms.security.ldap.authorization.user_search_filter

(&(objectClass=*)(uid={0}))

设置用户主体的 LDAP 搜索过滤器。

dbms.security.ldap.authorization.group_membership_attributes

memberOf

列出用户对象的属性名称,其中包含用于映射到角色的组。常见值:memberOfgidNumber

dbms.security.ldap.authorization.nested_groups_enabled

false

此设置确定是否将处理多个 LDAP 搜索结果。必须将其设置为 true 才能解析嵌套组成员资格。

dbms.security.ldap.authorization.group_to_role_mapping

列出从组到预定义内置角色adminarchitectpublishereditorreader,或任何其他自定义定义角色的授权映射。

dbms.security.ldap.authentication.attribute

samaccountname

将属性设置为搜索具有系统帐户的用户。

dbms.security.ldap.authorization.access_permitted_group

设置具有访问权限的用户 LDAP 组。通过身份验证的用户除了 组到角色映射 中分配的任何角色外,还映射到至少 PUBLIC 角色,并可以访问这些角色提供的数据库。如果设置了此属性,则不属于此 LDAP 组的用户将无法通过身份验证,即使他们的凭据正确。

dbms.security.logs.ldap.groups_at_debug_level_enabled

false

设置为true时,它将组查找的结果记录到安全日志中(前提是安全日志级别也设置为DEBUG)。

所有设置都在服务器启动时在默认配置文件neo4j.conf 中定义,或者可以使用 dbms.setConfigValue() 在运行时修改。

设置 Neo4j 以使用 LDAP

首先,您需要将 Neo4j 配置为使用 LDAP 作为身份验证和授权提供程序。

  1. 取消注释设置 dbms.security.auth_enabled=false 并将其值更改为 true 以打开安全功能。

  2. 取消注释设置 dbms.security.authentication_providersdbms.security.authorization_providers 并将其值更改为 ldap。这样,LDAP 连接器将用作身份验证和授权的安全提供程序。

    如果需要,您仍然可以使用 native 提供程序进行混合模式身份验证和授权。这些值以逗号分隔,并按声明顺序查询。

    示例 1. 将 Neo4j 配置为使用 LDAP 和本机身份验证和授权提供程序
    dbms.security.authentication_providers=ldap,native
    dbms.security.authorization_providers=ldap,native

将 LDAP 组映射到 Neo4j 角色

要根据用户的 LDAP 组授予用户权限,您必须将 LDAP 组映射到 Neo4j 内置 和自定义定义的角色。为此,您需要了解 Neo4j 角色具有哪些权限,并根据这些权限创建与 LDAP 服务器中定义的组的映射。该映射必须格式化为以分号分隔的键值对列表,其中键是以逗号分隔的 LDAP 组名称列表,而值是以逗号分隔的相应角色名称列表。例如,group1=role1;group2=role2;group3=role3,role4,role5;group4,group5=role6

示例 2. LDAP 组到 Neo4j 角色映射的示例
dbms.security.ldap.authorization.group_to_role_mapping=\
    "cn=Neo4j Read Only,cn=users,dc=example,dc=com"      = reader;    \ (1)
    "cn=Neo4j Read-Write,cn=users,dc=example,dc=com"     = editor,publisher; \ (2)
    "cn=Neo4j Read-Write,cn=users,dc=example,dc=com","cn=Neo4j Create Data,cn=users,dc=example,dc=com"     = publisher; \ (3)
    "cn=Neo4j Create Data,cn=users,dc=example,dc=com","cn=Neo4j Schema Manager,cn=users,dc=example,dc=com" = architect; \
    "cn=Neo4j Administrator,cn=users,dc=example,dc=com"  = admin; \
    "cn=Neo4j Procedures,cn=users,dc=neo4j,dc=com"       = rolename (4)
1 将 LDAP 组映射到 Neo4j 内置角色。
2 将 LDAP 组映射到两个 Neo4j 内置角色。
3 将两个 LDAP 组映射到 Neo4j 内置角色。
4 将 LDAP 组映射到自定义定义的角色。自定义定义的角色,例如 rolename,必须使用 CREATE ROLE rolename 命令显式创建才能用于授予权限。请参阅 管理角色

将 Neo4j 配置为使用 Active Directory

您可以将 Neo4j 配置为使用 LDAP 安全提供程序来访问和管理您的 Active Directory。根据您的特定用例,有三种替代方法可以做到这一点。

将 Neo4j 配置为支持 LDAP 用户 ID 身份验证

此选项允许用户使用其 LDAP 用户 ID 登录。

neo4j.conf 文件中,取消注释并配置以下设置

  1. 配置 LDAP 以指向 AD 服务器

    dbms.security.ldap.host=ldap://myactivedirectory.example.com
  2. 提供有关 LDAP 目录的用户结构的详细信息

    dbms.security.ldap.authentication.user_dn_template=cn={0},cn=Users,dc=example,dc=com
    dbms.security.ldap.authorization.user_search_base=cn=Users,dc=example,dc=com
    dbms.security.ldap.authorization.user_search_filter=(&(objectClass=*)(cn={0}))
    dbms.security.ldap.authorization.group_membership_attributes=memberOf
  3. 将 LDAP 系统中的组映射到 Neo4j 内置和自定义角色。请参阅 将 LDAP 组映射到 Neo4j 角色

将 Neo4j 配置为支持属性身份验证

这是 Active Directory 的另一种配置,它允许用户通过提供要搜索的属性(默认情况下为 sAMAccountName)来登录。该属性必须是唯一的,才能用作查找。您将创建一个系统帐户,该帐户对您需要的 LDAP 目录部分具有只读访问权限。但是,它不需要对 Neo4j 或任何其他系统具有访问权限。

neo4j.conf 文件中,取消注释并配置以下设置

  1. 配置 LDAP 以指向 AD 服务器

    dbms.security.ldap.host=ldap://myactivedirectory.example.com
  2. 提供有关 LDAP 目录的用户结构的详细信息(将 myattribute 替换为实际的属性名称)

    dbms.security.ldap.authorization.user_search_base=cn=Users,dc=example,dc=com
    dbms.security.ldap.authorization.user_search_filter=(&(objectClass=*)(myattribute={0}))
    dbms.security.ldap.authorization.group_membership_attributes=memberOf
  3. 将 LDAP 系统中的组映射到 Neo4j 内置和自定义角色。请参阅 将 LDAP 组映射到 Neo4j 角色

  4. 将 Neo4j 配置为使用具有对 LDAP 服务器中的所有用户和组的读取访问权限的系统帐户。

    1. dbms.security.ldap.authorization.use_system_account 值设置为 true

    2. dbms.security.ldap.authorization.system_username 值设置为完整区分名称 (DN),因为 dbms.security.ldap.authentication.user_dn_template 不会应用于此用户名。例如,

      dbms.security.ldap.authorization.system_username=cn=search-account,cn=Users,dc=example,dc=com
    3. 配置 LDAP 系统帐户密码。

      dbms.security.ldap.authorization.system_password=mypassword
    4. 配置要搜索的属性,方法是在 neo4j.conf 文件中添加以下行(将 myattribute 替换为实际的属性名称)

      dbms.security.ldap.authentication.search_for_attribute=true
      dbms.security.ldap.authentication.attribute=myattribute
    5. (可选)创建一个 LDAP 组,以将对数据库的身份验证限制在 LDAP 用户的子集

      dbms.security.ldap.authorization.access_permitted_group=cn=Neo4j Access,cn=users,dc=example,dc=com

通过设置 user_dn_template 将 Neo4j 配置为支持 sAMAccountName 身份验证

这是 Active Directory 的另一种配置,它允许来自指定域的所有用户使用 sAMAccountName 登录。使用此选项,您不必创建系统帐户并将系统用户名/密码存储在配置文件中。相反,您将 {0}@example.com 设置为 user_dn_template 的值,以启用从根域开始的身份验证。这样,将检查整个树以查找用户,无论它位于 LDAP 目录树中的哪个位置。

neo4j.conf 文件中,取消注释并配置以下设置

  1. 配置 LDAP 以指向 AD 服务器

    dbms.security.ldap.host=ldap://myactivedirectory.example.com
  2. 提供有关 LDAP 目录的用户结构的详细信息

    dbms.security.ldap.authentication.user_dn_template={0}@example.com
    dbms.security.ldap.authorization.user_search_base=dc=example,dc=com
    dbms.security.ldap.authorization.user_search_filter=(&(objectClass=user)(sAMAccountName={0}))
    dbms.security.ldap.authorization.group_membership_attributes=memberOf
  3. 将 LDAP 系统中的组映射到 Neo4j 内置和自定义角色。有关更多信息,请参阅 将 LDAP 组映射到 Neo4j 角色

设置 dbms.security.ldap.authentication.search_for_attribute 应设置为默认值 false。

将 Neo4j 配置为执行嵌套组查找

当用户是组(例如 engineers)的成员,而该组又是另一个组(例如 employees)的成员时,Active Directory 可以配置为执行嵌套搜索,以便 engineers 组中的用户也将是 employees 组的成员。这反过来意味着可以为 employees 配置 组到角色映射,该映射将传递应用于 engineers

Active Directory 通过可扩展匹配运算符 LDAP_MATCHING_RULE_IN_CHAIN(其对象标识符为 1.2.840.113556.1.4.1941)来促进嵌套搜索。此运算符一直遍历对象祖先链,直到根节点。

要在 neo4j.conf 文件中设置嵌套搜索,请配置以下设置

  1. 启用嵌套组。

    dbms.security.ldap.authorization.nested_groups_enabled=true
  2. 提供有关 LDAP 目录的用户结构的详细信息

    dbms.security.ldap.authentication.user_dn_template=cn={0},cn=users,dc=example,dc=com
    dbms.security.ldap.authorization.user_search_base=dc=example,dc=com
    dbms.security.ldap.authorization.user_search_filter=(&(objectClass=*)(uid={0}))
  3. 提供嵌套组搜索过滤器。
    这是将用于执行用户组的嵌套查找的过滤器。它应包含占位符标记 {0},该标记将被用户区分名称 (DN) 替换(该名称使用 dbms.security.ldap.authorization.user_search_filter 为指定的用户信息找到)。
    此示例使用 Active Directory 的 LDAP_MATCHING_RULE_IN_CHAIN(也称为 1.2.840.113556.1.4.1941)实现

    dbms.security.ldap.authorization.nested_groups_search_filter=(&(objectclass=group)(member:1.2.840.113556.1.4.1941:={0}))
  4. 提供组到角色映射,包括必要的祖先组

    dbms.security.ldap.authorization.group_to_role_mapping=\
    "cn=engineers,cn=users,dc=example,dc=com"=procedures;\
    "cn=employees,cn=users,dc=example,dc=com"=reader
与非嵌套 LDAP 查找相比,嵌套组查找不会对用户对象执行基于属性的查找。相反,dbms.security.ldap.authorization.group_membership_attributes 设置将被忽略,而 dbms.security.ldap.authorization.user_search_filter 仅用于确定用户的区分名称 (DN)。然后将其替换到 dbms.security.ldap.authorization.nested_groups_search_filter 中,以执行用户组的单独嵌套查找。

将 Neo4j 配置为使用 OpenLDAP

您可以将 LDAP 安全提供程序配置为访问和管理您的 OpenLDAP 目录服务。

在 neo4j.conf 文件中,取消注释并配置以下设置

  1. 配置 LDAP 以指向 OpenLDAP 服务器

    dbms.security.ldap.host=myopenldap.example.com
  2. 提供有关 LDAP 目录的用户结构的详细信息

    dbms.security.ldap.authentication.user_dn_template=cn={0},ou=users,dc=example,dc=com
    dbms.security.ldap.authorization.user_search_base=ou=users,dc=example,dc=com
    dbms.security.ldap.authorization.user_search_filter=(&(objectClass=*)(uid={0}))
    dbms.security.ldap.authorization.group_membership_attributes=gidNumber
  3. (可选)创建一个 LDAP 组,以将对数据库的身份验证限制在 LDAP 用户的子集

    dbms.security.ldap.authorization.access_permitted_group=501
  4. 将 LDAP 系统中的组映射到 Neo4j 内置和自定义角色。有关更多信息,请参阅 将 LDAP 组映射到 Neo4j 角色

使用身份验证提供程序在用户级别配置身份验证/授权

用户身份验证提供程序 可用于确定哪些用户可以使用配置的提供程序(包括 LDAP)进行身份验证和授权。

您必须将 dbms.security.require_local_user 配置设置更改为 true 以使用身份验证提供程序。这意味着必须存在具有匹配身份验证提供程序的用户才能进行身份验证和授权。这适用于所有提供程序。

相反,当 dbms.security.require_local_user 设置为 false 时,用户的身份验证提供程序对他们进行身份验证和授权的方式没有任何影响,而是通过数据库配置集中控制身份验证和授权(针对所有用户)。

以下示例展示了如何使用 Cypher 配置具有身份验证提供程序 ldap 的用户。

示例 3. 创建具有身份验证提供程序的用户,该用户可以使用 LDAP 进行身份验证和授权
CREATE USER alice
SET AUTH PROVIDER 'ldap' { SET ID 'cn=alice,ou=engineering,dc=example,dc=com' }

该命令创建用户 alice,该用户可以使用 LDAP 进行身份验证和授权,前提是他们的 LDAP dncn=alice,ou=engineering,dc=example,dc=com

示例 4. 创建具有两个身份验证提供程序的用户,允许用户使用 LDAP 或 mysso 提供程序进行身份验证和授权
CREATE USER alice
SET HOME DATABASE anotherDb
SET AUTH PROVIDER 'ldap' { SET ID 'cn=alice,ou=engineering,dc=example,dc=com' }
SET AUTH 'oidc-mysso' {SET ID 'alicesUniqueMySsoId'}

该命令创建用户 alice,该用户可以使用 ldapmysso 进行身份验证和授权。有关设置 OIDC 提供程序的更多信息,请参阅 使用身份验证提供程序在用户级别配置 SSO。此示例还说明,即使仅使用外部身份验证提供程序,用户也可以设置其主数据库。

示例 5. 更改用户以删除其其中一个身份验证提供程序
ALTER USER alice
REMOVE AUTH 'ldap'

该命令阻止用户 alice 使用 ldap 进行身份验证和授权。

示例 6. 更改用户以允许他们使用用户名和密码进行身份验证和授权
ALTER USER alice
SET AUTH 'native' {SET PASSWORD 'changeme' SET PASSWORD CHANGE REQUIRED}

该命令允许用户 alice 使用指定的用户名和密码进行身份验证和授权(除了他们已配置为使用的内容)。

示例 7. 将数据库配置为允许通过 ldap 进行身份验证,并通过 native 提供程序进行授权
  1. 设置以下数据库配置

    dbms.security.authentication_providers=ldap
    dbms.security.authorization_providers=native
  2. 创建具有 ldap 身份验证提供程序的用户

    CREATE USER alice
    SET AUTH PROVIDER 'ldap' { SET ID 'cn=alice,ou=engineering,dc=example,dc=com' }
  3. 在本地授予用户 READER 角色

    GRANT ROLE READER TO alice

    该命令允许用户 alice 使用 ldap 进行身份验证,并从 native 提供程序接收 READER 角色。

  4. 您还可以通过将 ldap 也设置为授权提供程序,为用户提供 ldap native 角色的并集

    dbms.security.authentication_providers=ldap
    dbms.security.authorization_providers=native,ldap
示例 8. 暂停用户
ALTER USER alice
SET STATUS SUSPENDED

该命令完全阻止用户通过任何方式进行身份验证/授权。

示例 9. 区分不同 LDAP 树中同名用户

假设有两个用户都叫 alice,一个属于 engineering 树 (cn=alice,ou=engineering,dc=example,dc=com),另一个属于 sales 树 (cn=alice,ou=sales,dc=example,dc=com)。

为了区分这两个用户,您可以在数据库中创建两个用户,每个用户都有一个不同的 ID,对应于 LDAP 树中用户的 dn

CREATE USER aliceEngineering
SET AUTH 'ldap' { SET ID 'cn=alice,ou=engineering,dc=example,dc=com' }

CREATE USER aliceSales
SET AUTH 'ldap' { SET ID 'cn=alice,ou=sales,dc=example,dc=com' }

您可以使用 LDAP 命令行工具 ldapsearch 验证您的 LDAP 配置是否正确,以及 LDAP 服务器是否响应。

ldapsearch 命令接受 LDAP 配置设置值作为输入,并验证用户的身份验证(使用 simple 机制)和授权。有关更高级的用法以及如何使用 SASL 身份验证机制,请参阅 ldapsearch 官方文档

  1. 验证用户的身份验证和授权。例如,john

    • 使用 dbms.security.ldap.authorization.use_system_account=false(默认)

      # ldapsearch -v -H ldap://<dbms.security.ldap.host> -x -D <dbms.security.ldap.authentication.user_dn_template : replace {0}> -W -b <dbms.security.ldap.authorization.user_search_base> "<dbms.security.ldap.authorization.user_search_filter : replace {0}>" <dbms.security.ldap.authorization.group_membership_attributes>
      
      ldapsearch -v -H ldap://myactivedirectory.example.com:389 -x -D cn=john,cn=Users,dc=example,dc=com -W -b cn=Users,dc=example,dc=com "(&(objectClass=*)(cn=john))" memberOf
    • 使用 dbms.security.ldap.authorization.use_system_account=true

      # ldapsearch -v -H ldap://<dbms.security.ldap.host> -x -D <dbms.security.ldap.authorization.system_username> -w <dbms.security.ldap.authorization.system_password> -b <dbms.security.ldap.authorization.user_search_base> "<dbms.security.ldap.authorization.user_search_filter>" <dbms.security.ldap.authorization.group_membership_attributes>
      
      ldapsearch -v -H ldap://myactivedirectory.example.com:389 -x -D cn=search-account,cn=Users,dc=example,dc=com -w mypassword -b cn=Users,dc=example,dc=com "(&(objectClass=*)(cn=john))" memberOf
  2. 验证返回的成员资格属性的值是否为映射到 dbms.security.ldap.authorization.group_to_role_mapping 中角色的组。

    # extended LDIF
    #
    # LDAPv3
    # base <cn=Users,dc=example,dc=com> with scope subtree
    # filter: (cn=john)
    # requesting: memberOf
    #
    
    # john, Users, example.com
    dn: CN=john,CN=Users,DC=example,DC=com
    memberOf: CN=Neo4j Read Only,CN=Users,DC=example,DC=com
    
    # search result
    search: 2
    result: 0 Success
    
    # numResponses: 2
    # numEntries: 1

身份验证缓存

身份验证缓存是一种机制,Neo4j 通过该机制缓存通过 LDAP 服务器进行身份验证的结果,以提高性能。它通过参数 dbms.security.ldap.authentication.cache_enableddbms.security.auth_cache_ttl 进行配置。

# Turn on authentication caching to ensure performance.

dbms.security.ldap.authentication.cache_enabled=true
dbms.security.auth_cache_ttl=10m
表 1. 身份验证缓存参数
参数名称 默认值 描述

dbms.security.ldap.authentication.cache_enabled

true

确定是否缓存通过 LDAP 服务器进行身份验证的结果。

是否启用身份验证缓存必须根据您公司的安全准则进行考虑。

dbms.security.auth_cache_ttl

600 秒

是缓存的身份验证和授权信息的生存时间 (TTL)。

将 TTL 设置为 0 将禁用所有身份验证缓存。

较短的 TTL 需要更频繁地重新进行身份验证和重新授权,这会影响性能。

非常长的 TTL 意味着 LDAP 服务器上用户设置的更改可能不会及时反映在 Neo4j 授权行为中。

有效的单位是 mssm;默认单位是 s

管理员可以清除身份验证缓存,以强制重新查询来自联合身份验证提供商系统的身份验证和授权信息。使用 Neo4j 浏览器或 Neo4j Cypher Shell 执行此语句

CALL dbms.security.clearAuthCache()

可用的加密方法

指定 dbms.security.ldap.host 参数配置使用未加密的 LDAP。不指定协议或端口会导致使用默认端口 389 上的 ldap

dbms.security.ldap.host=myactivedirectory.example.com
dbms.security.ldap.host=myactivedirectory.example.com:389
dbms.security.ldap.host=ldap://myactivedirectory.example.com
dbms.security.ldap.host=ldap://myactivedirectory.example.com:389

使用通过 StartTLS 加密的 LDAP

要使用通过 StartTLS 加密的 Active Directory,请设置以下参数

dbms.security.ldap.use_starttls=true
dbms.security.ldap.host=ldap://myactivedirectory.example.com

使用加密的 LDAPS LDAP

要使用加密的 LDAPS 配置 Active Directory,请将 dbms.security.ldap.host 设置为以下之一。如果您没有指定端口,则使用默认端口 636

dbms.security.ldap.host=ldaps://myactivedirectory.example.com
dbms.security.ldap.host=ldaps://myactivedirectory.example.com:636

在测试环境中使用自签名证书 (SSL)

生产环境应始终使用证书颁发机构颁发的 SSL 证书,以安全访问 LDAP 服务器。但是,在某些情况下,例如在测试环境中,您可能希望在 LDAP 服务器上使用 SSL 证书。

要在 LDAP 服务器上配置 SSL 证书,请使用 neo4j.conf 中的 server.jvm.additional 输入证书的详细信息。证书文件 MyCert.jks 的路径是 Neo4j 服务器的绝对路径。

server.jvm.additional=-Djavax.net.ssl.keyStore=/path/to/MyCert.jks
server.jvm.additional=-Djavax.net.ssl.keyStorePassword=mypasword
server.jvm.additional=-Djavax.net.ssl.trustStore=/path/to/MyCert.jks
server.jvm.additional=-Djavax.net.ssl.trustStorePassword=mypasword

组结果的调试日志

在设置 LDAP 集成时,有时需要执行故障排除。在这些情况下,查看来自 LDAP 服务器的组结果可能很有用。要在安全日志中以 DEBUG 级别启用这些声明的日志记录,请将 dbms.security.logs.ldap.groups_at_debug_level_enabled 设置为 true,并将安全日志级别设置为 DEBUG

确保将 dbms.security.logs.ldap.groups_at_debug_level_enabled 设置回 false 以用于生产环境,以避免不必要地记录可能敏感的信息。此外,请记住,LDAP 服务器提供的组结果可能会随着时间的推移而发生变化。