LDAP Linux HOWTO

Luiz Ernesto Pinheiro Mal�re

v1.10, 2007-03-18

修订历史
修订 1.102007/03/18
指向更新后的文档的指针
修订 1.092004/03/05
OpenLDAP 2.2 和一般更正。
修订 1.082003/04/02
使用 DIGEST-MD5 认证的 SASL。
修订 1.072002/09/16
拼写错误更正。
修订 1.062002/07/17
迁移到 DocBook XML 标准,角色文档的修订。引入 OpenLDAP 2.1。
修订 1.052001/06/22修订者:lepm
更正导致 PDF 版本文档不一致的长行。
修订 1.042001/02/28修订者:lepm
更正了更多拼写错误,并更新了以下部分:漫游访问、使用 LDAP 认证。
修订 1.032000/09/28修订者:lepm
介绍 OpenLDAP 2.0,它包含 LDAPv3,如 RFC2251 中所定义。
修订 1.022000/09/13修订者:lepm
更正拼写错误并添加了“发布历史”部分。
修订 1.012000/02/15修订者:lepm
添加了以下部分:LDAP 迁移工具、使用 LDAP 认证、图形化 LDAP 工具、RFC。
修订 1.001999/06/20修订者:lepm
初始版本。

本文档介绍了在 Linux 机器上安装、配置、运行和维护 LDAP(轻型目录访问协议)服务器的信息。该文档还详细介绍了如何创建 LDAP 数据库、如何添加、更新和删除目录中的信息。本文主要基于密歇根大学 LDAP 信息页面和 OpenLDAP 管理员指南。


目录
1. 简介
1.1. 什么是 LDAP?
1.2. LDAP 如何工作?
1.3. LDAP 后端、对象和属性
1.4. 此文档的新版本
1.5. 意见和建议
1.6. 致谢
1.7. 版权和免责声明
2. 安装 LDAP 服务器
2.1. 先决条件
2.2. 下载软件包
2.3. 解压软件
2.4. 配置软件
2.5. 构建服务器
3. 配置 LDAP 服务器
3.1. 配置文件格式
3.2. 全局指令
3.3. 通用后端指令
3.4. 通用数据库指令
3.5. BDB 数据库指令
3.6. LDBM 数据库指令
3.7. 访问控制示例
3.8. 配置文件示例
4. 运行 LDAP 服务器
4.1. 命令行选项
4.2. 启动 LDAP 服务器
4.3. 杀死 LDAP 服务器
5. 数据库创建和维护
5.1. 在线创建数据库
5.2. 离线创建数据库
5.3. 关于 LDIF 格式的更多信息
5.4. ldapsearch、ldapdelete 和 ldapmodify 实用程序
6. 附加信息和功能
6.1. LDAP 迁移工具
6.2. 使用 LDAP 进行身份验证
6.3. SASL 配置:Digest-MD5
6.4. 图形化 LDAP 工具
6.5. 日志
7. 参考
7.1. 网址
7.2. 书籍
7.3. RFC
表清单
3-1. 调试级别
3-2. 数据库后端
4-1. 调试级别

第 1 章:简介

本文档不再更新,请参考最新文档:OpenLDAP 管理员指南

本文档的主要目的是在您的 Linux 机器上设置和使用 LDAP 目录服务器。您将学习如何安装、配置、运行和维护 LDAP 服务器。之后,您还将学习如何使用 LDAP 客户端和实用程序在目录中存储、检索和更新信息。LDAP 目录服务器的守护进程称为 slapd,它在许多不同的 UNIX 平台上运行。

还有另一个守护进程负责 LDAP 服务器之间的复制。 它被称为 slurpd,目前您不必担心它。 在本文档中,您将运行一个 slapd,它仅为您的本地域提供目录服务,无需复制,因此也无需 slurpd。 有关复制的完整信息,请访问:OpenLDAP 管理员指南

本地域设置是配置服务器的一个简单选择,非常适合入门,如果您愿意,以后也可以轻松升级到另一种配置。 本文档中提供的信息代表了使用 LDAP 服务器的良好初始化。 阅读本文档后,您可能会受到鼓舞,扩展服务器的功能,甚至使用现有的 C、C++ 和 Java 开发工具包编写自己的客户端。


1.1. 什么是 LDAP?

LDAP 代表轻型目录访问协议。 顾名思义,它是一种轻量级的客户端-服务器协议,用于访问目录服务,特别是基于 X.500 的目录服务。 LDAP 通过 TCP/IP 或其他面向连接的传输服务运行。 LDAP 在 RFC2251 “轻型目录访问协议 (v3) 中定义。

目录类似于数据库,但往往包含更多描述性的、基于属性的信息。 目录中的信息通常读取的频率远高于写入的频率。 目录经过调整,可以对大容量的查找或搜索操作提供快速响应。 它们可能具有广泛复制信息的能力,以提高可用性和可靠性,同时缩短响应时间。 当目录信息被复制时,副本之间的暂时不一致是可以接受的,只要它们最终同步即可。

提供目录服务有很多不同的方法。 不同的方法允许在目录中存储不同种类的信息,对如何引用、查询和更新信息,如何保护信息免受未经授权的访问等方面提出不同的要求。 一些目录服务是本地的,为受限制的上下文(例如,单台机器上的 finger 服务)提供服务。 其他服务是全局的,为更广泛的上下文提供服务。


1.2. LDAP 如何工作?

LDAP 目录服务基于客户端-服务器模型。 一个或多个 LDAP 服务器包含构成 LDAP 目录树或 LDAP 后端数据库的数据。 LDAP 客户端连接到 LDAP 服务器并提出问题。 服务器会响应答案,或者响应一个指向客户端可以获取更多信息的位置的指针(通常是另一个 LDAP 服务器)。 无论客户端连接到哪个 LDAP 服务器,它看到的目录视图都是相同的; 提供给一个 LDAP 服务器的名称引用的条目与在另一个 LDAP 服务器中引用的条目相同。 这是像 LDAP 这样的全局目录服务的一个重要特征。


1.3. LDAP 后端、对象和属性

LDAP 服务器守护进程称为 SlapdSlapd 支持各种不同的 数据库后端,您可以使用它们。

它们包括 首选 BDB,一种高性能的事务数据库后端; LDBM,一个轻量级的基于 DBM 的后端; SHELL,一个到任意 shell 脚本的后端接口,以及 PASSWD,一个到 passwd(5) 文件的简单后端接口。

BDB 使用 Sleepycat Berkeley DB 4。LDBM 使用 Berkeley DBGDBM

BDB 事务后端适用于多用户读/写数据库访问,可以混合使用任何读写操作。 BDB 用于需要以下功能的应用程序

  • 事务,包括以原子方式对数据库进行多次更改,以及在必要时回滚未提交的更改。

  • 能够从系统崩溃和硬件故障中恢复,而不会丢失任何已提交的事务。

在本文档中,我假设您选择 BDB 数据库。

为了在基于 LDAP 的目录服务器之间导入和导出目录信息,或者描述将要应用于目录的一组更改,通常使用称为 LDIF(LDAP 数据交换格式)的文件格式。 LDIF 文件以面向对象的条目层次结构存储信息。 您将要获取的 LDAP 软件包附带一个将 LDIF 文件转换为 BDB 格式的实用程序

一个常见的 LDIF 文件如下所示

dn: o=TUDelft, c=NL
o: TUDelft
objectclass: organization
dn: cn=Luiz Malere, o=TUDelft, c=NL
cn: Luiz Malere
sn: Malere
mail: malere@yahoo.com
objectclass: person

如您所见,每个条目都由一个可区分的名称 (DN) 唯一标识。 DN 由条目的名称加上一条将该条目追溯到目录层次结构顶部的名称路径(就像一棵树)组成。

在 LDAP 中,对象类定义了可用于定义条目的 属性的集合。 LDAP 标准提供了以下基本类型的对象类

  • 目录中的组,包括单个对象或对象组的无序列表。

  • 位置,例如国家/地区名称和描述。

  • 目录中的组织。

  • 目录中的人员。

一个条目可以属于多个对象类。 例如,一个人的条目由 person 对象类定义,但也可能由 inetOrgPerson、groupOfNames 和 organization 对象类中的属性定义。 服务器的对象类结构(它的模式)决定了特定条目的所需和允许属性的总列表。

目录数据表示为属性-值对。 任何特定的信息片段都与描述性属性相关联。

例如,commonName 或 cn 属性用于存储一个人的姓名。 名为 Jonas Salk 的人可以在目录中表示为

cn: Jonas Salk

目录中输入的每个人都由 person 对象类中的属性集合定义。 用于定义此条目的其他属性可能包括

givenname: Jonas
surname: Salk
mail: jonass@airius.com

必需属性包括使用该对象类的条目中必须存在的属性。 所有条目都需要 objectClass 属性,该属性列出了条目所属的对象类。

允许的属性包括使用该对象类的条目中可能存在的属性。 例如,在 person 对象类中,cn 和 sn 属性是必需的。 允许使用 description、telephoneNumber、seeAlso 和 userpassword 属性,但不是必需的。

每个属性都有一个对应的语法定义。语法定义描述了属性提供的信息类型,例如:

  • bin binary(二进制)。

  • ces case exact string(区分大小写的字符串,比较时大小写必须匹配)。

  • cis case ignore string(忽略大小写的字符串,比较时忽略大小写)。

  • tel telephone number string(电话号码字符串,类似于 cis,但在比较时忽略空格和破折号 `- ')。

  • dn distinguished name(专有名称)。

注意:通常,objectclass 和 attribute 定义位于 schema 文件中,该文件位于 OpenLDAP 安装主目录下的 schema 子目录中。


1.4. 本文档的新版本

本文档可能会根据读者的反馈进行更正和更新。 您应该查看:

http://www.tldp.org/HOWTO/LDAP-HOWTO.html

以获取本 HOWTO 的新版本。


1.5. 意见和建议

如果您对本文档中提供的某些信息有任何疑问,请通过以下电子邮件地址与我联系:malere@yahoo.com

如果您有评论和/或建议,也请告诉我!


1.6. 致谢

本 Howto 是我在荷兰代尔夫特理工大学实习的成果。我要感谢那些鼓励我撰写本文档的人:Rene van LeukenWim Tiwon。非常感谢你们。他们也像我一样是 Linux 爱好者。

我还要感谢德国 Ldap-Howto 的作者 Thomas Bendler,他对我的文档做出了贡献,以及 LDP 项目的伟大志愿者 Joshua Go。

Karl Lattimer 值得嘉奖,因为他对 SASL 相关问题做出了巨大贡献。

感谢我的主!


1.7. 版权和免责声明

版权 (c) 1999 Luiz Ernesto Pinheiro Mal�re。根据 GNU 自由文档许可证 1.1 版或自由软件基金会发布的任何后续版本条款,允许复制、分发和/或修改本文档;没有不变部分,没有封面文本,也没有封底文本。许可证的副本包含在题为“GNU 自由文档许可证”的部分中。

如果您有任何疑问,请访问以下网址:https://gnu.ac.cn/licenses/fdl.txt 并联系 Linux HOWTO 协调员:guylhem@metalab.unc.edu


第 2 章. 安装 LDAP 服务器

安装服务器需要五个步骤:


2.1. 预先要求

为了完全符合 LDAPv3 标准,OpenLDAP 客户端和服务器需要安装一些额外的软件包。在编写本文档时,我使用了一台安装了 2.4.20 内核的 Mandrake 9.0 机器,并手动安装了 Berkeley BDB 软件包和 SASL 库。

OpenSSL TLS 库

OpenSSL TLS 库通常是基本系统的一部分,或者组成一个可选的软件组件。OpenSSL 的官方网址是:http://www.openssl.org

Kerberos 身份验证服务

OpenLDAP 客户端和服务器支持基于 Kerberos 的身份验证服务。特别是,OpenLDAP 支持使用 Heimdal 或 MIT Kerberos V 软件包的 SASL/GSSAPI 身份验证机制。如果您希望使用基于 Kerberos 的 SASL/GSSAPI 身份验证,则应安装 Heimdal 或 MIT Kerberos V。Heimdal Kerberos 可从 http://www.pdc.kth.se/heimdal 获得,MIT Kerberos 可从 http://web.mit.edu/kerberos/www 获得。

强烈建议使用强大的身份验证服务,例如 Kerberos 提供的那些。

Cyrus 的简单身份验证和安全层库

Cyrus 的 SASL 库通常是基本系统的一部分,或者组成一个可选的软件组件。Cyrus SASL 可从 http://asg.web.cmu.edu/sasl/sasl-library.html 获得。如果预先安装了 OpenSSL 和 Kerberos/GSSAPI 库,Cyrus SASL 将会使用它们。在编写本文档时,我使用了 Cyrus SASL 2.1.17。

数据库软件

Slapd 的主要数据库后端 BDB 需要 Sleepycat Software Berkeley DB,版本 4。如果在配置时不可用,您将无法使用主要数据库后端构建 slapd。

您的操作系统可能在基本系统中或作为可选软件组件提供 Berkeley DB,版本 4。如果没有,则可以从 Sleepycat 获得多个版本。在编写本文档时,建议使用最新版本 4.2.52。 OpenLDAP 的 slapd LDBM 后端支持多种数据库管理器,例如 Berkeley DB(版本 3)和 GDBM。 GDBM 可从 FSF 的 下载站点 ftp://ftp.gnu.org/pub/gnu/gdbm/ 获得。

线程

几乎可以保证线程支持是您的基本 Linux 系统的一部分。 OpenLDAP 旨在利用线程。 OpenLDAP 支持 POSIX pthreads、Mach CThreads 和许多其他变体。如果 configure 脚本找不到合适的线程子系统,它将会报错。如果发生这种情况,请查阅 OpenLDAP FAQ 的软件 - 安装 - 平台提示部分:http://www.openldap.org/faq/

TCP 包装器

如果预先安装了 Slapd,它将支持 TCP 包装器(IP 级别的访问控制过滤器)。对于包含非公共信息的服务器,建议使用 TCP 包装器或其他 IP 级别的访问过滤器(例如 IP 级别的防火墙提供的那些)。


2.2. 下载软件包

有两种免费分发的 LDAP 服务器:密歇根大学 LDAP 服务器和 OpenLDAP 服务器。还有 Netscape 目录服务器,它仅在某些条件下免费(例如,教育机构可以免费获得)。 OpenLDAP 服务器基于最新版本的密歇根大学服务器,并且有邮件列表和额外的文档可供使用。本文档假定您正在使用 OpenLDAP 服务器。

它最新的 tar gzip 压缩版本可在以下地址获得:

http://www.openldap.org

如果您想获取最新版本的密歇根大学服务器,请访问此地址:

ftp://terminator.rs.itd.umich.edu/ldap

为了编写本文档,我使用了 OpenLDAP 软件包的 2.2.5 版本。我的操作系统是内核为 2.4.20 的 Mandrake Linux 9.0。

在 OpenLDAP 站点上,您始终可以找到 OpenLDAP 服务器的最新开发版本和稳定版本。在更新本文档时,最新的稳定版本是 openldap-stable-20031217.tgz(版本 2.1.25)。最新的开发版本也是 openldap-2.2.5.tgz。


2.3. 解压软件

现在您已经在本地机器上拥有了 tar gzip 压缩软件包,您可以解压它。

首先,将软件包复制到所需的目录,例如 /usr/local。接下来使用以下命令:

tar xvzf openldap-2.2.5.tgz 

您也可以使用此命令:

gunzip openldap-2.2.5.tgz | tar xvf -

2.4. 配置软件

OpenLDAP 服务器源代码随附了一个配置脚本,用于设置安装目录、编译器和链接器标志等选项。在解压软件的目录下键入以下命令:

./configure --help

这将打印出所有您可以在构建软件之前使用 configure 脚本自定义的选项。一些有用的选项是 --prefix=pref 、--exec-prefix=eprefix 和 --bindir=dir,用于设置安装目录。通常,如果您在没有选项的情况下运行 configure,它将自动检测合适的设置并准备在默认的通用位置构建内容。所以只需键入:

./configure

并观察输出,看看一切是否顺利。

提示:有时您需要将特定选项传递给您的 configure 脚本,例如 --with-tls(用于启用 slapd 以使用安全通道:LDAPS://)。在这种情况下,您的 SSL/TLS 库可能位于系统的非标准目录中。您可以使用 env 命令更改环境,使 configure 脚本了解库的位置。示例:假设您已将 openssl 软件包安装在 /usr/local/openssl 下。以下命令将构建具有 SSL/TLS 支持的 slapd:

env CPPFLAGS=-I/usr/local/openssl/include \
      LDFLAGS=-L/usr/local/openssl/lib \
      configure --with-tls ...

您可以在 configure 脚本之前使用 env 命令指定以下环境变量:

  • CC:指定备用 C 编译器。

  • CFLAGS:指定其他编译器标志。

  • CPPFLAGS:指定 C 预处理器标志。

  • LDFLAGS:指定链接器标志。

  • LIBS:指定其他库。


2.5. 构建服务器

配置完软件后,您可以开始构建它。首先使用以下命令构建依赖项:

make depend

然后使用以下命令构建服务器:

make

如果一切顺利,服务器将按照配置进行构建。如果没有,请返回上一步以查看配置设置。您应该阅读位于解压软件的目录中的 INSTALL 和 README 文件。此外,检查 configure 脚本的特定提示,它们位于解压软件的目录下的 doc/install/configure 路径中。

为了确保正确构建,您应该运行测试套件(只需要几分钟):

make test

适用于您的配置的测试将会运行,并且它们应该通过。某些测试,例如复制测试,可能会被跳过。

现在安装二进制文件和 man 手册。您可能需要成为超级用户才能执行此操作(取决于您安装的位置):

su root -c 'make install'

就这样,现在您有了服务器的二进制文件和几个其他实用程序的二进制文件。转到 第 3 章 部分,了解如何配置 LDAP 服务器的操作。


第 3 章. 配置 LDAP 服务器

安装并构建软件后,您就可以配置它以在您的站点上使用。所有 slapd 运行时配置都是通过 slapd.conf 文件完成的,该文件安装在您在配置脚本中指定的 prefix 目录中,或者默认情况下安装在 /usr/local/etc/openldap 中。

本节详细介绍了 slapd.conf 中常用的配置指令。 有关完整列表,请参阅 slapd.conf(5) 手册页。 配置文件的指令分为 全局后端特定数据库特定。 在这里您将找到指令的描述,以及它们的默认值(如果有)和使用示例。


3.1. 配置文件格式

slapd.conf 文件由三种类型的配置信息组成:全局、后端特定和数据库特定。 首先指定全局信息,然后是与特定后端类型关联的信息,然后是与特定数据库实例关联的信息。

全局指令可以在后端和/或数据库指令中被覆盖,后端指令可以被数据库指令覆盖。

空白行和以“#”字符开头的注释行将被忽略。如果某行以空白字符开头,则会被认为是前一行的延续(即使前一行是注释)。slapd.conf 的通用格式如下:

# global configuration directives
<global config directives>

# backend definition
backend <typeA>
<backend-specific directives>

# first database definition & config directives
database <typeA>
<database-specific directives>

# second database definition & config directives
database <typeB>
<database-specific directives>

# second "typeA" database definition & config directives
database <typeA>
<database-specific directives>

# subsequent backend & database definitions & config directives
... 

一个配置指令可能会带参数。如果带参数,它们之间用空格分隔。如果一个参数包含空格,则该参数应该用双引号括起来,例如“like this”。如果一个参数包含双引号或反斜杠字符 `\',则该字符应该用反斜杠字符 `\' 转义。

该发行版包含一个示例配置文件,该文件将被安装在 /usr/local/etc/openldap 目录中。许多包含模式定义(属性类型和对象类)的文件也位于 /usr/local/etc/openldap/schema 目录中。


3.2. 全局指令

本节中描述的指令适用于所有后端和数据库,除非在后端或数据库定义中专门覆盖。应该用实际文本替换的参数用尖括号 <> 括起来。

access to <what> [ by <who> <accesslevel> <control> ]+

此指令授予访问权限(由 <accesslevel> 指定)给一组条目和/或属性(由 <what> 指定),由一个或多个请求者(由 <who> 指定)。 有关更多详细信息,请参阅 第 3.7 节 中的示例。

重要提示: 如果未指定任何访问指令,则默认访问控制策略(访问 * by * read)允许所有经过身份验证和匿名用户进行读取访问。

attributetype <RFC2252 Attribute Type Description>

此指令定义一个属性类型。 有关更多详细信息,请查看以下 URL:Schema Specification

idletimeout <integer>

指定在强制关闭空闲客户端连接之前等待的秒数。 默认值 0 的 idletimeout 将禁用此功能。

include <filename>

此指令指定 slapd 应该从给定文件中读取额外的配置信息,然后再继续执行当前文件的下一行。 包含的文件应遵循正常的 slapd 配置文件格式。 该文件通常用于包含包含模式规范的文件。

注意:使用此指令时应小心 - 嵌套的 include 指令的数量没有限制,并且不进行循环检测。

loglevel <integer>

此指令指定调试语句和操作统计信息应被 syslog 的级别(目前已记录到 syslogd(8) LOCAL4 工具)。 你必须配置 OpenLDAP --enable-debug(默认)才能使其工作(除了两个始终启用的统计级别)。 日志级别是累加的。 要显示哪些数字对应于哪种调试,请使用 -? 调用 slapd 或查阅下表。 <integer> 的可能值为

表 3-1。 调试级别

级别描述
-1启用所有调试
0无调试
1跟踪函数调用
2调试数据包处理
4繁重的跟踪调试
8连接管理
16打印出发送和接收的数据包
32搜索过滤器处理
64配置文件处理
128访问控制列表处理
256统计信息记录连接/操作/结果
512统计信息记录发送的条目
1024打印与 shell 后端的通信
2048打印条目解析调试

示例

loglevel 255 或 loglevel -1

这将导致大量的调试信息被 syslog。

默认

loglevel 256

objectclass <RFC2252 Object Class Description>

此指令定义一个对象类。 有关更多详细信息,请查看以下 URL:Schema Specification

referral <URI>

此指令指定当 slapd 找不到本地数据库来处理请求时要传递的回调。

示例

referral ldap://root.openldap.org

这会将非本地查询转发到 OpenLDAP 项目的全局根 LDAP 服务器。 智能 LDAP 客户端可以在该服务器上重新提出查询,但请注意,这些客户端中的大多数只会知道如何处理包含主机部分和可选的可分辨名称部分的简单 LDAP URL。

sizelimit <integer>

此指令指定从搜索操作返回的最大条目数。

默认

sizelimit 500

timelimit <integer>

此指令指定 slapd 花费在应答搜索请求中的最长时间(以实际时间为单位)。 如果未在此时间内完成请求,则将返回指示超过 timelimit 的结果。

默认

timelimit 3600


3.3. 通用后端指令

本节中的指令仅适用于定义它们的后端。 每种类型的后端都支持它们。 后端指令适用于相同类型的所有数据库实例,并且根据指令的不同,可能会被数据库指令覆盖。

backend <type>

此指令标记后端定义的开始。 <type> 应该是 bdb 或以下列出的其他受支持的后端类型之一

表 3-2。 数据库后端

类型描述
bdbBerkeley DB 事务后端
dnssrvDNS SRV 后端
ldbm轻量级 DBM 后端
ldap轻量级目录访问协议(代理)后端
meta元目录后端
monitor监视器后端
passwd提供对 passwd(5) 的只读访问
perlPerl 可编程后端
shellShell(外部程序)后端
sqlSQL 可编程后端

示例

backend bdb

这标志着新的 BDB 后端定义的开始


3.4. 通用数据库指令

本节中的指令仅适用于定义它们的数据库。 每种类型的数据库都支持它们。

database <type>

此指令标记新数据库实例定义的开始。 <type> 应该是前一项中列出的后端类型之一。

示例

database bdb

这标志着新的 BDB 后端数据库实例定义的开始。

readonly { on | off }

此指令将数据库置于“只读”模式。 任何修改数据库的尝试都将返回“unwilling to perform”错误。

默认

readonly off

replica uri=ldap[s]://<hostname>[:<port>] | host=<hostname>[:<port>]
                [bindmethod={simple|kerberos|sasl}]
                ["binddn=<DN>"]
                [saslmech=<mech>]
                [authcid=<identity>]
                [authzid=<identity>]
                [credentials=<password>]
                [srvtab=<filename>]

此指令指定此数据库的复制站点。 uri= 参数指定一个 scheme、一个主机以及可选的端口,可以在其中找到从属 slapd 实例。 可以对 <hostname> 使用域名或 IP 地址。 如果未给出 <port>,则使用标准 LDAP 端口号(389 或 636)。

注意:host 赞成使用 uri 参数。

uri 允许将副本 LDAP 服务器指定为 LDAP URI,例如 ldap://slave.example.com:389 或 ldaps://slave.example.com:636

binddn= 参数给出了绑定为用于更新从属 slapd 的 DN。 它应该是一个对从属 slapd 的数据库具有读/写访问权限的 DN。 它还必须与从属 slapd 的配置文件中的 updatedn 指令匹配。 通常,此 DN *不应*与主数据库的 rootdn 相同。 由于 DN 可能包含嵌入的空格,因此整个 "binddn=<DN>" 字符串应括在双引号中。

bindmethod 是 simple 或 kerberos 或 sasl,具体取决于连接到从属 slapd 时是使用基于简单密码的身份验证、Kerberos 身份验证还是 SASL 身份验证。

除非存在足够的完整性和隐私保护(例如 TLS 或 IPSEC),否则不应使用简单身份验证。 简单身份验证需要指定 binddn 和 credentials 参数。

不推荐使用 Kerberos 身份验证,而推荐使用 SASL 身份验证机制,尤其是 KERBEROS_V4 和 GSSAPI 机制。 Kerberos 身份验证需要 binddn 和 srvtab 参数。

通常建议使用 SASL 身份验证。 SASL 身份验证需要使用 saslmech 参数指定一种机制。 根据机制,可以使用 authcid 和 credentials 分别指定身份验证身份和/或凭据。 authzid 参数可用于指定授权身份。

有关更多详细信息,请查看此 URL:Replication with Slurpd

replogfile <filename>

此指令指定 slapd 将更改记录到的复制日志文件的名称。 复制日志通常由 slapd 写入,由 slurpd 读取。 通常,仅当使用 slurpd 复制数据库时才使用此指令。 但是,如果 slurpd 未运行,您也可以使用它来生成事务日志。 在这种情况下,您需要定期截断该文件,否则该文件将无限增长。

有关更多详细信息,请查看此 URL:Replication with Slurpd

rootdn <dn>

此指令指定对于此数据库上的操作不受访问控制或管理限制约束的 DN。 DN 不需要引用目录中的条目。 DN 可以引用 SASL 身份。

基于条目的示例

rootdn "cn=Manager, dc=example, dc=com"

基于 SASL 的示例

rootdn "uid=root,cn=example.com,cn=digest-md5,cn=auth"

rootpw <password>

此指令可用于为 rootdn 指定密码(当 rootdn 设置为数据库中的 DN 时)。

示例

rootpw secret

也可以提供 RFC 2307 格式的密码哈希。 slappasswd 可用于生成密码哈希。

示例

rootpw {SSHA}ZKKuqbEKJfKSXhUbHG3fG8MDn9j1v4QN

哈希是使用命令 slappasswd -s secret 生成的。

suffix <dn suffix>

此指令指定将传递到此后端数据库的查询的 DN 后缀。 可以给出多个后缀行,并且每个数据库定义都需要至少一个后缀行。

示例

suffix "dc=example, dc=com"

DN 以“dc=example, dc=com”结尾的查询将被传递到此后端。

注意: 当选择将查询传递到的后端时,slapd 会按照它们在文件中出现的顺序查看每个数据库定义中的后缀行。 因此,如果一个数据库后缀是另一个数据库后缀的前缀,则它必须出现在配置文件中的后缀之后。

syncrepl

此指令用于保持复制的数据库与主数据库同步,以便复制的数据库内容与主数据库内容保持最新。

本文档未详细介绍此指令,因为我们正在配置单个 LDAP 服务器。 有关此指令的更多信息,请访问:LDAP Sync Replication

updatedn <dn>

此指令仅适用于从属 slapd。 它指定允许更改副本的 DN。 这可能是 slurpd 在更改副本时绑定的 DN,也可能是与 SASL 身份关联的 DN。

基于条目的示例

updatedn "cn=Update Daemon, dc=example, dc=com"

基于 SASL 的示例

updatedn "uid=slurpd,cn=example.com,cn=digest-md5,cn=auth"

有关更多详细信息,请查看此 URL:Replication with Slurpd

updateref <URL>

此指令仅适用于从属 slapd。 它指定返回给向副本提交更新请求的客户端的 URL。 如果指定多次,则提供每个 URL。

示例

updateref ldap://master.example.net


3.5. BDB 数据库指令

此类别中的指令仅适用于 BDB 数据库。 也就是说,它们必须遵循“database bdb”行,并且在任何后续“backend”或“database”行之前。 有关 BDB 配置指令的完整参考,请参阅 slapd-bdb 手册页 (man slapd-bdb)。

directory <directory>

此指令指定包含数据库和关联索引的 BDB 文件所在的目录。

默认

directory /usr/local/var/openldap-data

sessionlog <sid> <limit>

此指令在 syncrepl 复制提供程序服务器中指定一个会话日志存储,其中包含有关已从由 <sid> 标识的复制内容中排除的条目的信息。 第一个在 cookie 中具有相同 <sid> 值的 syncrepl 搜索请求将在提供程序服务器中建立会话日志存储。 会话日志存储中的条目数量受 <limit> 限制。 过多的条目将按 FIFO 顺序从存储中删除。 <sid> 和 <limit> 都是非负整数。 <sid> 不超过三位十进制数字。

对于已存在的会话中的 LDAP 内容同步操作,可以使用会话日志存储来减少同步流量。如果副本不是太旧,可以通过会话存储中的信息进行更新,则提供者 slapd 会将 scoped-out 条目的身份以及添加到或修改的复制内容中的 in-scope 条目发送给消费者 slapd。如果副本状态过于陈旧,超出历史存储的覆盖范围,则提供者 slapd 会将未更改的 in-scope 条目的身份以及已更改的 in-scope 条目发送给消费者 slapd。然后,消费者 slapd 将删除副本中未被标识为存在于提供者内容中的那些条目。

有关 syncrepl 的更多信息,请访问:LDAP 同步复制


3.6. LDBM 数据库指令

此类别中的指令仅适用于 LDBM 后端数据库。也就是说,它们必须遵循 "database ldbm" 行,并且出现在任何其他 "database" 或 "backend" 行之前。有关 LDBM 配置指令的完整参考,请参见 slapd-ldbm 手册页 (man slapd-ldbm)。

cachesize <integer>

此指令指定 LDBM 后端数据库实例维护的内存缓存的大小(以条目数计)。

默认

cachesize 1000

dbcachesize <integer>

此指令指定与每个打开的索引文件关联的内存缓存的大小(以字节计)。如果底层数据库方法不支持,则此指令将被忽略,且不会发出任何提示。增加此数字会使用更多内存,但可以显著提高性能,尤其是在修改或构建索引期间。

默认

dbcachesize 100000

dbnolocking

如果存在此选项,则禁用数据库锁定。启用此选项可能会以数据安全为代价来提高性能。

dbnosync

此选项导致磁盘上的数据库内容在更改后不会立即与内存中的更改同步。启用此选项可能会以数据安全为代价来提高性能。

directory <directory>

此指令指定包含数据库和关联索引的 LDBM 文件所在的目录。

默认

directory /usr/local/var/openldap-data

index {<attrlist> | default} [pres,eq,approx,sub,none]

此指令指定要为给定属性维护的索引。如果仅给出 <attrlist>,则维护默认索引。

示例

index default pres,eq
index uid
index cn,sn pres,eq,sub
index objectClass eq

第一行将要维护的默认索引集设置为 present 和 equality。第二行导致为 uid 属性类型维护默认 (pres,eq) 索引集。第三行导致为 cn 和 sn 属性类型维护 present、equality 和 substring 索引。第四行导致为 objectClass 属性类型维护 equality 索引。

默认情况下,不维护任何索引。通常建议至少维护一个 objectClass 上的 equality 索引。

index objectClass eq

mode <integer>

此指令指定新创建的数据库索引文件应具有的文件保护模式。

默认

mode 0600


3.7. 访问控制示例

access 指令提供的访问控制功能非常强大。本节展示了它的一些使用示例。首先,一些简单的例子

access to * by * read 

此访问指令授予每个人读取权限。

以下示例显示了使用正则表达式在两个访问指令中按 DN 选择条目,其中排序很重要。

access to dn=".*, o=U of M, c=US" 
by * search 
access to dn=".*, c=US" 
by * read 

授予 c=US 子树下的条目读取权限,但 "o=U of M, c=US" 子树下的条目除外,后者被授予搜索权限。未授予 c=US 任何权限,因为两个访问指令均未匹配此 DN。如果这些访问指令的顺序颠倒,则永远不会匹配 U-M 特定的指令,因为所有 U-M 条目也都是 c=US 条目。

实现相同访问控制的另一种方法是

access to dn.children="dc=example,dc=com"
	by * search
	access to dn.children="dc=com"
	by * read

授予 dc=com 子树下的条目读取权限,但 dc=example,dc=com 子树下的条目除外,后者被授予搜索权限。未授予 dc=com 任何权限,因为两个访问指令均未匹配此 DN。如果这些访问指令的顺序颠倒,则永远不会到达尾随指令,因为 dc=example,dc=com 下的所有条目也都在 dc=com 条目下。

注意: 另请注意,如果没有匹配的 access to 指令或 "by <who>" 子句,则访问被拒绝。也就是说,每个 *access to* 指令都以隐式的 *by * none* 子句结尾,并且每个访问列表都以隐式的 *access to * by * none* 指令结尾。

下一个示例再次显示了访问指令和 "by <who>" 子句的排序的重要性。它还显示了使用属性选择器来授予对特定属性的访问权限以及各种 <who> 选择器。

access to dn.subtree="dc=example,dc=com" attr=homePhone
	by self write
	by dn.children=dc=example,dc=com" search
	by peername=IP:10\..+ read
access to dn.subtree="dc=example,dc=com"
	by self write
	by dn.children="dc=example,dc=com" search
	by anonymous auth

此示例适用于 "dc=example,dc=com" 子树中的条目。对于除 homePhone 之外的所有属性,条目可以写入自身,example.com 下的条目可以通过它们进行搜索,其他任何人都没有访问权限(隐式 by * none),除了身份验证/授权(始终以匿名方式完成)。homePhone 属性可由条目写入,可由 example.com 下的条目搜索,可由从网络 10 连接的客户端读取,否则不可读(隐式 by * none)。所有其他访问都因隐式的 access to * by * none 而被拒绝。

有时,允许特定 DN 从属性中添加或删除自身是有用的。例如,如果您想创建一个组并允许人们仅从 member 属性中添加和删除他们自己的 DN,则可以使用如下访问指令来实现:

access to attr=member,entry 
	by dnattr=member selfwrite 

dnattr <who> 选择器表示该访问适用于 member 属性中列出的条目。selfwrite 访问选择器表示此类成员只能从属性中添加或删除他们自己的 DN,而不是其他值。需要添加 entry 属性,因为访问条目的任何属性都需要访问该条目。

OpenLDAP 管理员指南中提供了大量有关访问控制的信息。请查看:访问控制 以获取有关此主题的更多信息。


3.8. 配置文件示例

以下是一个配置文件示例,其中穿插着说明性文字。它定义了两个数据库来处理 X.500 树的不同部分;两者都是 BDB 数据库实例。显示的行号仅供参考,不包含在实际文件中。首先,全局配置部分

1.    # example config file - global configuration section
2.    include /usr/local/etc/schema/core.schema
3.    referral ldap://root.openldap.org
4.    access to * by * read

第 1 行是注释。第 2 行包含另一个配置文件,其中包含核心模式定义。第 3 行上的 referral 指令表示,不属于下面定义的任何数据库本地的查询将被转发到在主机 root.openldap.org 的标准端口 (389) 上运行的 LDAP 服务器。

第 4 行是全局访问控制。它适用于所有条目(在任何适用的数据库特定访问控制之后)。

配置文件的下一部分定义了一个 BDB 后端,该后端将处理树的 "dc=example,dc=com" 部分中的事物的查询。该数据库将复制到两个 slave slapd,一个在 truelies 上,另一个在 judgmentday 上。将为多个属性维护索引,并且 userPassword 属性将受到保护,免受未经授权的访问。

5.     # BDB definition for the example.com
6.     database bdb
7.     suffix "dc=example,dc=com"
8.     directory /usr/local/var/openldap-data
9.     rootdn "cn=Manager,dc=example,dc=com"
10.    rootpw secret
11.    # replication directives
12.    replogfile /usr/local/var/openldap/slapd.replog
13.	   replica uri=ldap://slave1.example.com:389
14.            binddn="cn=Replicator,dc=example,dc=com"
15.            bindmethod=simple credentials=secret
16.    replica uri=ldaps://slave2.example.com:636
17.            binddn="cn=Replicator,dc=example,dc=com"
18.            bindmethod=simple credentials=secret
19.    # indexed attribute definitions
20.    index uid pres,eq
21.    index cn,sn,uid pres,eq,sub
22.    index objectClass eq
23.    # database access control definitions
24.    access to attr=userPassword
25.            by self write
26.            by anonymous auth
27.            by dn.base="cn=Admin,dc=example,dc=com" write
28.            by * none
29.    access to *
30.            by self write
31.            by dn.base="cn=Admin,dc=example,dc=com" write
32.            by * read

第 5 行是注释。数据库定义的开始由第 6 行上的 database 关键字标记。第 7 行指定将查询传递到此数据库的 DN 后缀。第 8 行指定数据库文件所在的目录。

第 9 行和第 10 行标识数据库“超级用户”条目和关联密码。此条目不受访问控制或大小或时间限制的限制。请记住使用 slappasswd 加密 rootpw。

示例:rootpw {SSHA}Jq4xhhkGa7weT/0xKmaecT4HEXsdqiYA

第 11 到 18 行用于复制。有关这些指令的更多信息,请参见 复制 链接。

第 20 到 22 行指示要为各种属性维护的索引。

第 24 到 32 行指定此数据库中条目的访问控制。由于这是第一个数据库,因此控制也适用于任何数据库中未保存的条目(例如 Root DSE)。对于所有适用的条目,userPassword 属性可由条目本身和“admin”条目写入。它可以用于身份验证/授权目的,但不能以其他方式读取。所有其他属性都可以由条目和“admin”条目写入,但可以由所有用户(经过身份验证或未经身份验证)读取。

示例配置文件的下一部分定义了另一个 BDB 数据库。这一个处理涉及 dc=example,dc=net 子树的查询,但由与第一个数据库相同的实体管理。请注意,如果没有第 39 行,由于第 4 行的全局访问规则,将允许读取访问。

33.    # BDB definition for example.net
34.    database bdb
35.    suffix "dc=example,dc=net"
36.    directory /usr/local/var/openldap-data-net
37.    rootdn "cn=Manager,dc=example,dc=com"
38.    index objectClass eq
39.    access to * by users read

第 4 章。运行 LDAP 服务器

LDAP 守护程序 slapd 旨在作为独立服务器运行。这允许服务器利用缓存,管理底层数据库的并发问题,并节省系统资源。从 inetd(8) 运行不是一种选择。


4.1. 命令行选项

Slapd 支持许多命令行选项,如手册页中所述。本节详细介绍了一些常用选项

-f <filename>

此选项指定 slapd 的备用配置文件。默认值通常为 /usr/local/etc/openldap/slapd.conf。

-h <URLs>

此选项指定备用侦听器配置。默认值为 ldap:///,这意味着通过 TCP 在默认 LDAP 端口 389 上的所有接口上进行 LDAP。您可以指定特定的主机端口对或其他协议方案(例如 ldaps:// 或 ldapi://)。例如,-h "ldaps:// ldap://127.0.0.1:667" 将创建两个侦听器:一个用于在默认 LDAP/SSL 端口 636 上的所有接口上通过 SSL 进行 LDAP,另一个用于在端口 667 上的 localhost(环回)接口上通过 TCP 进行 LDAP。可以使用 IPv4 点分十进制形式或使用主机名来指定主机。端口值必须是数字。

-n <service-name>

此选项指定用于日志记录和其他目的的服务名称。默认服务名称为 slapd。

-l <syslog-local-user>

此选项指定 syslog(8) 设施的本地用户。值可以是 LOCAL0、LOCAL1、LOCAL2、... 和 LOCAL7。默认值为 LOCAL4。并非所有系统都支持此选项。有关更多详细信息,请参见 第 6.5 节

-u user -g group

这些选项分别指定要将 slapd 作为其运行的用户和组。user 可以是用户名或 uid。group 可以是组名或 gid。

-r directory

此选项指定运行时目录。slapd 将在打开侦听器之后但在读取任何配置文件或初始化任何后端之前 chroot(2) 到此目录。

-d <level> | ?

此选项将 slapd 的调试级别设置为 <level>。 当 level 为 `?' 字符时,会打印各种调试级别,并且 slapd 退出,无论您给出任何其他选项。 当前调试级别为

表 4-1. 调试级别

级别描述
-1启用所有调试
0无调试
1跟踪函数调用
2调试数据包处理
4繁重的跟踪调试
8连接管理
16打印出发送和接收的数据包
32搜索过滤器处理
64配置文件处理
128访问控制列表处理
256统计信息记录连接/操作/结果
512统计信息记录发送的条目
1024打印与 shell 后端的通信
2048打印条目解析调试

您可以通过为每个所需的级别指定一次 debug 选项来启用多个级别。 或者,由于调试级别是可累加的,您可以自己进行计算。 也就是说,如果您想跟踪函数调用并观察正在处理的配置文件,您可以将 level 设置为这两个级别的总和(在本例中为 -d 65)。 或者,您可以让 slapd 进行计算(例如 -d 1 -d 64)。 详情请参考 <ldap.h>。

注意: slapd 必须使用 -DLDAP_DEBUG 定义编译,以便提供超出两个统计级别的任何调试信息。


4.2. 启动 LDAP 服务器

一般来说,slapd 像这样运行

/usr/local/etc/libexec/slapd [<option>]*

其中 /usr/local/etc/libexec 由 configure 确定,<option> 是上述(或 slapd(8) 中)描述的选项之一。 除非您指定了调试级别(包括级别 0),否则 slapd 将自动 fork 并从其控制终端分离并在后台运行。


4.3. 终止 LDAP 服务器

要安全地终止 slapd,您应该给出如下命令

kill -INT `cat $(ETCDIR)/slapd.pid`

以更极端的方式终止 slapd 可能会导致其数据库损坏,因为它可能需要在退出前刷新各种缓冲区。 请注意,slapd 会将其 pid 写入 slapd.conf 文件中配置的目录中的一个名为 slapd.pid 的文件中,例如:/usr/local/var/slapd.pid

Slapd 还会将其参数写入 slapd.conf 文件中配置的目录中的一个名为 slapd.args 的文件中,例如 /usr/local/var/slapd.args


第 5 章. 数据库创建和维护

本节介绍如何从头开始创建 slapd 数据库。 有两种创建数据库的方法。 首先,您可以使用 LDAP 在线创建数据库。 使用此方法,您只需启动 slapd 并使用您选择的 LDAP 客户端添加条目。 这种方法适用于相对较小的数据库(几百或几千个条目,具体取决于您的要求)。 这种方法适用于支持更新的数据库类型。

第二种数据库创建方法是使用 slapd 提供的特殊实用程序离线创建。 如果您有数千个条目要创建,使用 LDAP 方法会花费很长时间,或者如果您想确保在创建数据库时无法访问它,则最好使用此方法。 请注意,并非所有数据库类型都支持这些实用程序。


5.1. 在线创建数据库

OpenLDAP 软件包附带一个名为 ldapadd 的实用程序,用于在 LDAP 服务器运行时添加条目。 如果您选择在线创建数据库,您可以使用 ldapadd 工具来添加条目(您也可以使用 OpenLDAP 软件包之外提供的其他客户端来添加条目,例如 Ldap Browser)。 添加第一个条目后,您仍然可以使用 ldapadd 添加更多条目。 在启动 slapd 之前,您应该确保在 sladp.conf 文件中设置以下配置选项

suffix <dn> 

3.4 节中所述,此选项说明此数据库将保存哪些条目。 您应该将其设置为您尝试创建的子树的根的 DN。 例如

suffix "o=TUDelft, c=NL" 

您应该确保指定一个应该创建索引文件的目录

directory /usr/local/tudelft 

您需要使用适当的权限创建此目录,以便 slapd 可以写入它。

您需要配置 slapd,以便您可以作为具有添加条目权限的目录用户连接到它。 您可以将目录配置为支持专门用于此目的的特殊超级用户或 root 用户。 这是通过数据库定义中的以下两个选项完成的

rootdn <dn> 
rootpw <passwd>   /* Remember to use a SHA password here !!! */ 

这些选项指定可用于作为数据库的“超级用户”条目(即允许执行任何操作的条目)进行身份验证的 DN 和密码。 此处指定的 DN 和密码始终有效,无论命名的条目是否实际存在或是否具有给定的密码。 这解决了如何在任何条目存在之前进行身份验证和添加条目的“先有鸡还是先有蛋”的问题。

Slapd 原生理解您是否在 rootpw 指令上使用 SHA-1 加密密码。 我使用一个生成 SHA-1 密码的 Java 类,但可以使用命令 slappasswd 来生成密码

slappasswd -h {SHA}
rootpw    "{SHA}5en6G6MezRroT3XKqkdPOmY/BfQ="

例如

        rootdn "cn=Manager,dc=example,dc=com"
        rootpw "{SHA}5en6G6MezRroT3XKqkdPOmY/BfQ="

slappasswd 的默认输出是生成安全哈希密码 {SSHA},在这种情况下,您不需要传递 -h 参数,只需直接调用 slappasswd 即可。

如果您使用 SASL 作为针对 LDAP 进行身份验证的机制,则可以丢弃 rootpw 行。 有关更多详细信息,请参见 3.4 节6.2 节

最后,您应该确保数据库定义包含您想要的索引定义

index {<attrlist> | default} [pres,eq,sub,none] 

例如,要索引 cn、sn、uid 和 objectclass 属性,可以使用以下索引配置行。

index cn,sn,uid pres,eq,sub
index objectClass pres,eq

注意: 请注意,并非所有索引类型都适用于所有属性类型。 有关示例,请参见 3.6 节

一旦您将所有内容配置好后,启动 slapd,使用您的 LDAP 客户端连接,然后开始添加条目。 例如,要使用 ldapadd 工具添加 TUDelft 条目,然后添加 Postmaster 条目,您可以创建一个名为 /tmp/newentry 的文件,其内容为

o=TUDelft, c=NL 
objectClass=organization 
description=Technical University of Delft Netherlands 

cn=Postmaster, o=TUDelft, c=NL 
objectClass=organizationalRole 
cn=Postmaster 
description= TUDelft postmaster - postmaster@tudelft.nl 

然后使用如下命令实际创建条目

ldapadd -f /tmp/newentry -x -D "cn=Manager, o=TUDelft, c=NL" -w secret 

上面的命令假设您已将 rootdn 设置为 "cn=Manager, o=TUDelft, c=NL",并将 rootpw 设置为 "secret"(可能在 slapd.conf 中进行 SHA-1 加密)。 如果您不想在命令行中键入密码,请使用 ldapadd 命令的 -W 选项而不是 -w "password"。 系统将提示您输入密码

ldapadd -f /tmp/newentry -x -D "cn=Manager, o=TUDelft, c=NL" -W 
Enter LDAP Password: 

5.2. 离线创建数据库

第二种数据库创建方法是使用下面描述的 slapd 数据库工具离线创建数据库。 如果您有数千个条目要创建,使用上面描述的 LDAP 方法会花费很长时间,则最好使用此方法。 这些工具读取 slapd 配置文件和一个包含要添加的条目的文本表示的输入 LDIF 文件。 对于支持这些工具的数据库类型,它们直接生成数据库文件(否则您必须使用上面的在线方法)。 您需要确保首先在配置文件数据库定义中设置几个重要的配置选项

suffix <dn> 

如前一节所述,此选项说明此数据库将保存哪些条目。 您应该将其设置为您尝试创建的子树的根的 DN。 例如

suffix "o=TUDelft, c=NL" 

您应该确保指定一个应该创建索引文件的目录

directory /usr/local/tudelft 

最后,您需要指定要构建哪些索引。 这是通过一个或多个 index 选项完成的。

index {<attrlist> | default } [pres,eq,approx,sub,none]

例如

index cn,sn,uid pres,eq,sub
index objectClass eq

这将为 cn、sn 和 uid 属性创建 presence、equality 和 substring 索引,并为 objectClass 属性创建一个 equality 索引。 有关此选项的更多信息,请参见配置文件部分。

一旦您将所有内容配置好后,您可以通过运行 slapadd(8) 程序来创建主数据库和关联的索引

slapadd -l <inputfile> -f <slapdconfigfile> [-d <debuglevel>]
 [-n <integer>|-b <suffix>]

这些参数具有以下含义

-l <inputfile>

指定包含要以文本形式添加的条目的 LDIF 输入文件(请查看下一节)。

-f <slapdconfigfile>

指定 slapd 配置文件,该文件告知在何处创建索引、创建哪些索引等。

-d <debuglevel>

打开调试,如 <debuglevel> 指定的那样。 调试级别与 slapd 的相同。 有关更多详细信息,请参见 4.1 节

-n <databasenumber>

一个可选参数,指定要修改哪个数据库。 配置文件中列出的第一个数据库是 1,第二个数据库是 2,依此类推。 默认情况下,使用配置文件中的第一个数据库。 不应与 -b 结合使用。

-b <suffix>

一个可选参数,指定要修改哪个数据库。 提供的 suffix 与数据库 suffix 指令匹配以确定数据库编号。 不应与 -n 结合使用。

有时可能需要重新生成索引(例如在修改 slapd.conf(5) 之后)。 可以使用 slapindex(8) 程序完成此操作。 slapindex 的调用方式如下

slapindex -f <slapdconfigfile> [-d <debuglevel>] [-n <databasenumber>|-b <suffix>]

其中 -f、-d、-n 和 -b 选项与 slapadd(1) 程序的相同。 slapindex 基于当前数据库内容重建所有索引。

slapcat 程序用于将数据库转储到 LDIF 文件。 当您想要对数据库进行人类可读的备份或想要离线编辑数据库时,这可能很有用。 程序的调用方式如下

slapcat -l <filename> -f <slapdconfigfile> [-d <debuglevel>] [-n <databasenumber>|-b <suffix>]

其中 -n 或 -b 用于选择使用 -f 指定的 slapd.conf(5) 中的数据库。 相应的 LDIF 输出将写入标准输出或使用 -l 选项指定的文件。


5.3. 更多关于 LDIF 格式的信息

LDAP 数据交换格式 (LDIF) 用于以简单的文本格式表示 LDAP 条目。 条目的基本形式是

#comment 
dn: <distinguished name> 
<attrdesc>: <attrvalue> 
<attrdesc>: <attrvalue>
...

以 '#' 字符开头的行是注释。 属性描述 (attrdesc) 可以是简单的属性类型,例如 cn 或 objectClass 或 1.2.3(与属性类型关联的 OID),或者可以包含选项,例如 cn;lang_en_US 或 userCertificate;binary。

可以通过以单个空格或制表符字符开始下一行来继续一行。 例如

dn: cn=Barbara J Jensen, dc=example, dc=
 com
cn: Barbara J
    Jensen

等效于

dn: cn=Barbara J Jensen, dc=example, dc=com
cn: Barbara J Jensen

多个属性值在单独的行上指定。 例如,

cn: Barbara J Jensen
cn: Babs Jensen

如果 <attrvalue> 包含非打印字符或以空格、双冒号 (':') 或小于号 ('<') 开头,则 <attrdesc> 后跟双冒号和值的 base64 编码。 例如,值“ 以空格开头”将像这样编码

cn:: IGJlZ2lucyB3aXRoIGEgc3BhY2U=

您还可以指定包含属性值的 URL。 例如,以下指定应从文件 /path/to/file.jpeg 获取 jpegPhoto 值。

cn:< file://path/to/file.jpeg

同一 LDIF 文件中的多个条目用空行分隔。 这是一个包含三个条目的 LDIF 文件示例。

# Barbara's Entry
dn: cn=Barbara J Jensen, dc=example, dc=com
cn: Barbara J Jensen
cn: Babs Jensen
objectClass: person
sn: Jensen

# Bjorn's Entry
dn: cn=Bjorn J Jensen, dc=example, dc=com
cn: Bjorn J Jensen
cn: Bjorn Jensen
objectClass: person
sn: Jensen
# Base64 encoded JPEG photo
jpegPhoto:: /9j/4AAQSkZJRgABAAAAAQABAAD/2wBDABALD
A4MChAODQ4SERATGCgaGBYWGDEjJR0oOjM9PDkzODdASFxOQ
ERXRTc4UG1RV19iZ2hnPk1xeXBkeFxlZ2P/2wBDARESEhgVG

# Jennifer's Entry
dn: cn=Jennifer J Jensen, dc=example, dc=com
cn: Jennifer J Jensen
cn: Jennifer Jensen
objectClass: person
sn: Jensen
# JPEG photo from file
jpegPhoto:< file://path/to/file.jpeg

请注意,Bjorn 条目中的 jpegPhoto 是 base 64 编码的,而 Jennifer 条目中的 jpegPhoto 是从 URL 指示的位置获得的。

尾随空格不会从 LDIF 文件中的值中删除。 多个内部空格也不会被压缩。 如果您不希望它们出现在您的数据中,请不要将它们放在那里。


5.4. ldapsearch, ldapdelete 和 ldapmodify 实用程序

ldapsearch - ldapsearch 是对 ldap_search(3) 库调用的 shell 可访问接口。 使用此实用程序在您的 LDAP 数据库后端上搜索条目。

调用 ldapsearch 的概要如下(请查看 ldapsearch 手册页以查看每个选项的含义)

ldapsearch  [-n]  [-u]  [-v]  [-k]  
[-K]  [-t]  [-A] [-B] [-L] 
[-R] [-d debuglevel] [-F sep] [-f file] 
[-x] [-D binddn]  [-W]  [-w bindpasswd]  
[-h ldaphost]  [-p ldapport]   [-b searchbase]   
[-s base|one|sub] 
[-a never|always|search|find] [-l timelimit] 
[-z sizelimit] filter [attrs...] 

ldapsearch 打开与 LDAP 服务器的连接,绑定并使用过滤器 filter 执行搜索。 过滤器应符合 RFC 1558 中定义的 LDAP 过滤器的字符串表示形式。 如果 ldapsearch 找到一个或多个条目,则检索由 attrs 指定的属性,并将条目和值打印到标准输出。 如果未列出任何 attrs,则返回所有属性。

ldapsearch -x -b 'o=TUDelft,c=NL' 'objectclass=*' 

ldapsearch -b 'o=TUDelft,c=NL' 'cn=Rene van Leuken' 

ldasearch -u -b 'o=TUDelft,c=NL' 'cn=Luiz Malere' sn mail

-b 选项代表 searchbase(初始搜索点),-u 选项代表用户友好输出信息,-x 选项用于指定简单身份验证。

ldapdelete - ldapdelete 是对 ldap_delete(3) 库调用的 shell 可访问接口。 使用此实用程序删除 LDAP 数据库后端上的条目。

调用 ldapdelete 的概要如下(请查阅 ldapdelete 的 man 手册,了解每个选项的含义):

ldapdelete   [-n]   [-v]  [-k]  [-K]  
[-c]  [-d debuglevel]  [-f file]  [-D binddn]  
[-W]  [-w passwd] [-h ldaphost] [-p ldapport] 
[dn]... 

ldapdelete 打开与 LDAP 服务器的连接,进行绑定,并删除一个或多个条目。如果提供了一个或多个 dn 参数,则会删除具有这些 Distinguished Names(可分辨名称)的条目。每个 dn 应该是一个字符串表示的 DN,如 RFC 1779 中所定义。如果没有提供 dn 参数,则会从标准输入(或者如果使用了 -f 标志,则从文件)读取 DN 列表。

以下是 ldapdelete 的一些使用示例:

ldapdelete 'cn=Luiz Malere,o=TUDelft,c=NL' 

ldapdelete -v 'cn=Rene van Leuken,o=TUDelft,c=NL' -D 'cn=Luiz Malere,o=TUDelft,c=NL' -W 

-v 选项代表 verbose(详细)模式,-D 选项代表 Binddn(用于身份验证的 DN),-W 选项代表 password prompt(密码提示)。

ldapmodify - ldapmodify 是一个可以通过 shell 访问的接口,它调用 ldap_modify(3) 和 ldap_add(3) 库函数。使用此实用程序修改 LDAP 数据库后端上的条目。

调用 ldapmodify 的概要如下(请查阅 ldapmodify 的 man 手册,了解每个选项的含义):

ldapmodify   [-a]  [-b]  [-c]  [-r]  
[-n]  [-v]  [-k]  [-d debuglevel]  
[-D binddn]  [-W]  [-w passwd] 
[-h ldaphost] [-p ldapport] [-f file] 

ldapadd [-b] [-c] [-r] [-n] 
[-v]  [-k]  [-K]  [-d debuglevel]  
[-D binddn]  [-w passwd]  [-h ldaphost] 
[-p ldapport] [-f file] 

ldapadd 被实现为指向 ldapmodify 工具的一个硬链接。当作为 ldapadd 调用时,ldapmodify 的 -a(添加新条目)标志会自动开启。ldapmodify 打开与 LDAP 服务器的连接,进行绑定,并修改或添加条目。条目信息从标准输入读取,或者通过 -f 选项从文件读取。

以下是 ldapmodify 的一些使用示例:

假设文件 /tmp/entrymods 存在且包含以下内容:

dn: cn=Modify Me, o=University of Michigan, c=US 
changetype: modify 
replace: mail 
mail: modme@terminator.rs.itd.umich.edu 
- 
add: title 
title: Grand Poobah 
- 
add: jpegPhoto 
jpegPhoto: /tmp/modme.jpeg 
- 
delete: description 
- 

命令

ldapmodify -b -r -f /tmp/entrymods 

将会把 "Modify Me" 条目的 mail 属性的内容替换为值 "modme@terminator.rs.itd.umich.edu",添加一个 "Grand Poobah" 的 title 属性,并添加文件 /tmp/modme.jpeg 的内容作为 jpegPhoto 属性,并完全删除 description 属性。

可以使用旧的 ldapmodify 输入格式执行与上述相同的修改:

cn=Modify Me, o=University of Michigan, c=US 
mail=modme@terminator.rs.itd.umich.edu 
+title=Grand Poobah 
+jpegPhoto=/tmp/modme.jpeg 
-description 

以及下面的命令:

ldapmodify -b -r -f /tmp/entrymods 

假设文件 /tmp/newentry 存在且包含以下内容:

dn: cn=Barbara Jensen, o=University of Michigan, c=US 
objectClass: person 
cn: Barbara Jensen 
cn: Babs Jensen 
sn: Jensen 
title: the world's most famous manager 
mail: bjensen@terminator.rs.itd.umich.edu 
uid: bjensen 

命令

ldapadd -f /tmp/entrymods 

如果 cn=Barbara Jensen, o=University of Michigan, c=US 条目尚不存在,则将添加该条目。如果具有此 dn 的条目已经存在,该命令将指出错误并且不会覆盖该条目。

假设文件 /tmp/newentry 存在且包含以下内容:

dn: cn=Barbara Jensen, o=University of Michigan, c=US 
changetype: delete 

命令

ldapmodify -f /tmp/entrymods 

将删除 Babs Jensen 的条目。

-f 选项代表 file(从文件而不是标准输入读取修改信息),-b 选项代表 binary(输入文件中任何以 '/' 开头的值都被解释为二进制文件),-r 选项代表 replace(默认替换现有值)。


第 6 章. 附加信息和功能

在本节中,您将找到有关身份验证、日志和 LDAP 客户端等主题的附加信息和有用的参考资料。在本节的末尾,还有一些非常不错的关于 LDAP 主题的通用 URL 和书籍推荐。


6.1. LDAP 迁移工具

LDAP 迁移工具是 PADL Software Ltd. 提供的一系列 Perl 脚本。它们用于将配置文件转换为 LDIF 格式。我建议在使用它们之前阅读许可条款,即使是免费的。如果您计划使用您的 LDAP 服务器来验证用户身份,这些工具可能非常有用。使用迁移工具将您的 NIS 或密码档案转换为 LDIF 格式,使这些文件与您的 LDAP 服务器兼容。也可以应用这些 Perl 脚本将用户、组、别名、主机、网络组、网络、协议、RPC 和服务从现有的命名服务(NIS、平面文件和 NetInfo)迁移到 LDIF 格式。

要下载 LDAP 迁移工具并获取更多信息,请访问以下地址:http://www.padl.com/tools.html

该软件包附带一个 README 文件,并且脚本文件的名称也很直观。首先查看 README 文件,然后开始应用这些脚本。

另一个推荐的包含迁移工具的 URL 是

http://dataconv.org/apps_ldap.html


6.2. 使用 LDAP 进行身份验证

要访问 LDAP 服务,LDAP 客户端必须首先向该服务进行身份验证。也就是说,它必须告诉 LDAP 服务器谁将要访问数据,以便服务器可以决定允许客户端查看和执行哪些操作。如果客户端成功通过 LDAP 服务器的身份验证,那么当服务器随后收到来自客户端的请求时,它将检查是否允许客户端执行该请求。此过程称为访问控制。

在 LDAP 中,身份验证在“bind”操作中提供。Ldapv3 支持三种类型的身份验证:匿名、简单和 SASL 身份验证。未执行“bind”操作而发送 LDAP 请求的客户端被视为匿名客户端。简单身份验证包括向 LDAP 服务器发送客户端(用户)的完全限定 DN 和客户端的明文密码。此机制存在安全问题,因为密码可以从网络读取。为了避免以这种方式暴露密码,您可以在加密通道(例如 SSL)中使用简单身份验证机制,前提是 LDAP 服务器支持此功能。

最后,SASL 是简单身份验证和安全层 (RFC 2222)。它指定了一个质询-响应协议,其中客户端和服务器之间交换数据,用于身份验证和在上面进行后续通信的安全层的建立。通过使用 SASL,LDAP 可以支持 LDAP 客户端和服务器之间达成的任何类型的身份验证。Cyrus-SASL 软件包可从以下 URL 获取:http://asg.web.cmu.edu/sasl/sasl-library.html

除了验证用户以访问您目录树中的信息外,您的 LDAP 服务器还可以验证来自其他服务的用户(Sendmail、Login、Ftp 等)。这是通过将特定的用户信息迁移到您的 LDAP 服务器并使用一种称为 PAM(可插入身份验证模块)的机制来实现的。LDAP 的身份验证模块可以从以下地址以 tar ball 形式获取:http://www.padl.com/OSS/pam_ldap.html


6.3. SASL 配置:Digest-MD5

我使用 DIGEST-MD5 机制运行了 LDAP-SASL 身份验证。为了完成这项工作,我严格按照下面列出的步骤操作。

  • 手动编译和构建,下载 SleepyCat 4.2.52。下载后,我只按照我在解压缩 .tar.gz 捆绑包的目录下的文件 docs/index.html 中列出的说明进行操作。

    解压后,您可以运行建议的

    root@rdnt03:/usr/local/BerkeleyDB.4.2/build_unix#../dist/configure
    root@rdnt03:/usr/local/BerkeleyDB.4.2/build_unix#make
    root@rdnt03:/usr/local/BerkeleyDB.4.2/build_unix#make install
    
  • 下载 Cyrus SASL 2.1.17,解压并按照我在解压缩 .tar.gz 文件的目录下的文档 doc/install.html 中列出的说明进行操作。这里需要注意一点,您需要使用一些 env 参数来运行 configure 脚本

    root@rdnt03:/usr/local/cyrus-sasl-2.1.17#env CPPFLAGS="-I/usr/local/BerkeleyDB.4.2/include"
    LDFLAGS="-L/usr/local/BerkeleyDB.4.2/lib" ./configure

    CPPFLAGS 和 LDFLAGS 环境变量参数应指向安装 Berkeley BDB 的相应 include 和 lib 目录。

    之后,您可以运行建议的

    root@rdnt03:/usr/local/cyrus-sasl-2.1.17#make
    root@rdnt03:/usr/local/cyrus-sasl-2.1.17#make install
    root@rdnt03:/usr/local/cyrus-sasl-2.1.17#ln -s /usr/local/lib/sasl2 /usr/lib/sasl2
  • 最后,我使用与本文档中列出的相同方向安装了 OpenLDAP 2.2.5,只是以与 SASL 的 configure 相同的方式运行 configure 脚本

    root@rdnt03:/usr/local/openldap-2.2.5#env CPPFLAGS="-I/usr/local/BerkeleyDB.4.2/include"
    LDFLAGS="-L/usr/local/BerkeleyDB.4.2/lib" ./configure

    之后,我运行了建议的

    root@rdnt03:/usr/local/openldap-2.2.5#make depend
    root@rdnt03:/usr/local/openldap-2.2.5#make
    root@rdnt03:/usr/local/openldap-2.2.5#make install
  • 接下来,我创建了 sasl 用户数据库

    root@rdnt03:~# saslpasswd2 -c admin

    系统会提示您输入密码。请记住,用户名不应是 DN(可分辨名称)。另请记住使用与目录树上的管理员条目相同的密码。

  • 现在,您应该在启动 slapd 守护进程并测试身份验证之前,在 slapd.conf 文件中设置 sasl-regexp 指令。我的 slapd.conf 文件位于 /usr/local/etc/openldap。

    sasl-regexp uid=(.*),cn=rdnt03,cn=DIGEST-MD5,cn=auth uid=$1,ou=People,o=Ever

    此参数的格式为

    uid=<username>,cn=<realm>,cn=<mech>,cn=auth

    用户名从 sasl 获取,并插入到 ldap 搜索字符串中代替 $1。您的 realm 应该就是您的 FQDN(完全限定域名),但在某些情况下并非如此,例如我的情况。要找出您的 realm 是什么,请执行

    root@rdnt03:~# sasldblistusers2
    admin@rdnt03: userPassword
    admin@rdnt03: cmusaslsecretOTP

    在我的例子中,rdnt03 被指示为 realm。如果它是您的 FQDN,您应该没有任何问题。我使用以下 LDIF 文件

    dn: o=Ever
    o: Ever
    description: Organization Root
    objectClass: top
    objectClass: organization
    
    dn: ou=Staff, o=Ever
    ou: Staff
    description: These are privileged users that can interact with Organization products
    objectClass: top
    objectClass: organizationalUnit
    
    dn: ou=People, o=Ever
    ou: People
    objectClass: top
    objectClass: organizationalUnit
    
    dn: uid=admin, ou=Staff, o=Ever
    uid: admin
    cn: LDAP Adminstrator
    sn: admin
    userPassword: {SHA}5en6G6MezRroT3XKqkdPOmY/BfQ=
    objectClass: Top
    objectClass: Person
    objectClass: Organizationalperson
    objectClass: Inetorgperson
    
    dn: uid=admin,ou=People,o=Ever
    objectClass: top
    objectClass: person
    objectClass: organizationalPerson
    objectClass: inetOrgPerson
    userPassword: {SHA}5en6G6MezRroT3XKqkdPOmY/BfQ=
    displayName: admin
    mail: admin@eversystems.com.br
    uid: admin
    cn: Administrator
    sn: admin
    

    使用以下命令将条目添加到您的 LDAP 目录:

    slapadd -c -l Ever.ldif -f slapd.conf -v -d 256
  • 现在,启动 slapd 守护进程并使用 ldapsearch 命令运行查询

    root@rdnt03:~# ldapsearch -U admin@rdnt03 -b 'o=Ever' '(objectclass=*)'
    SASL/DIGEST-MD5 authentication started
    Please enter your password:
    SASL username: admin@rdnt03
    SASL SSF: 128
    SASL installing layers
    ...
    Entries
    ...

就这样!如果您更喜欢将 SASL 与 Kerberos V 或 GSSAPI 一起使用,则在 http://www.openldap.org/doc/admin22/sasl.html 有一个有用的链接。此链接假定您已经成功安装并配置了 SASL 库。邮件列表将帮助您开始处理此事:http://asg.web.cmu.edu/sasl/index.html#mailinglists


6.4. 图形化 LDAP 工具

Kldap 是为 KDE 编写的图形化 LDAP 客户端。Kldap 具有友好的界面,能够显示存储在您的目录中的所有信息树。您可以在以下网址查看该应用程序的一些屏幕截图并下载它:http://www.mountpoint.ch/oliver/kldap/

KDirAdm 是一个为 KDE 桌面环境 2 或更高版本编写的 LDAP 目录管理工具。它的目标是提供大多数商业目录管理工具的所有功能:http://www.carillonis.com/kdiradm/

Directory Administrator 是最广泛使用的 GNOME 应用程序,用于管理 LDAP 目录服务器上的 UNIX 用户和组。Directory administrator 允许您创建和删除用户和组,以及管理与您的用户相关的地址簿信息、每个服务器的访问控制和 Sendmail 邮件路由:http://diradmin.open-it.org/index.php

GQ 是另一个具有更简单界面的图形化 LDAP 客户端。它是为 GNOME 编写的。它也可以在 KDE 下运行,就像 Kldap 在 GNOME 下运行一样。下载和获取更多信息的地址是:http://biot.com/gq/

LDAP Browser/Editor: 这个工具非常棒,它具有完整的管理和浏览功能。请查看:Ldap Browser


6.5. 日志

Slapd 使用 syslog(8) 工具生成日志。syslog(8) 工具的默认用户是 LOCAL4,但也允许使用 LOCAL0、LOCAL1 到 LOCAL7 的值。

为了启用日志的生成,您必须编辑您的 syslog.conf 文件,该文件通常位于 /etc 目录中。

创建类似这样的行

local4.*     /usr/adm/ldaplog 

这将使用默认用户 LOCAL4 作为 syslog 工具。如果您不熟悉此行的语法,请查看 syslog、syslog.conf 和 syslogd 的 man 手册。如果您想指定生成的日志级别或更改默认用户,您可以在启动 slapd 时使用以下选项

-s syslog-level 

此选项告诉 slapd 应将调试语句记录到 syslog(8) 工具的哪个级别。该级别描述了消息的严重性,并且是以下有序列表中的一个关键字(从高到低):emerg, alert, crit, err, warning, notice, info 和 debug。示例:slapd -f myslapd.conf -s debug

-l syslog-local-user 

选择 syslog(8) 工具的本地用户。值可以是 LOCAL0、LOCAL1 等,直到 LOCAL7。默认值为 LOCAL4。但是,此选项仅在支持带有 syslog(8) 工具的本地用户的系统上允许。

现在来看看生成的日志(例如,示例中的 /usr/adm/ldaplog)。它们可以极大地帮助您解决查询、更新、绑定等问题。


第 7 章. 参考资料

在本节中,您将找到关于 LDAP 的其他文档:有用的 URL、精彩的书籍和定义 RFC。


7.1. URL

以下 URL 包含关于 LDAP 的非常有用的信息。 本 HOWTO 就是根据这些 URL 制作的,因此如果在阅读本文档后您需要更具体的信息,您可能会在这里找到它。


7.2. 书籍

这些是最流行和有用的关于 LDAP 的书籍。

  • Implementing LDAP by Mark Wilcox (Mark Wilcox 著的《实现 LDAP》)

  • LDAP: Programming Directory-Enabled Applications with Lightweight Directory Access Protocol by Howes and Smith (Howes 和 Smith 著的《LDAP:使用轻型目录访问协议进行目录启用应用程序编程》)

  • Understanding and Deploying LDAP Directory Servers by Howes, Smith, and Good (Howes、Smith 和 Good 著的《理解和部署 LDAP 目录服务器》)


7.3. RFC

支持 LDAP 开发工作的 RFC

  • RFC 1558: A String Representation of LDAP Search Filters (RFC 1558:LDAP 搜索过滤器的字符串表示形式)

  • RFC 1777: Lightweight Directory Access Protocol (RFC 1777:轻型目录访问协议)

  • RFC 1778: The String Representation of Standard Attribute Syntaxes (RFC 1778:标准属性语法的字符串表示形式)

  • RFC 1779: A String Representation of Distinguished Names (RFC 1779:专有名称的字符串表示形式)

  • RFC 1781: Using the OSI Directory to Achieve User Friendly Naming (RFC 1781:使用 OSI 目录实现用户友好的命名)

  • RFC 1798: Connectionless LDAP (RFC 1798:无连接 LDAP)

  • RFC 1823: The LDAP Application Programming Interface (RFC 1823:LDAP 应用程序编程接口)

  • RFC 1959: An LDAP URL Format (RFC 1959:LDAP URL 格式)

  • RFC 1960: A String Representation of LDAP Search Filters (RFC 1960:LDAP 搜索过滤器的字符串表示形式)

  • RFC 2251: Lightweight Directory Access Protocol (v3) (RFC 2251:轻型目录访问协议 (v3))

  • RFC 2307: LDAP as a Network Information Service (RFC 2307:LDAP 作为网络信息服务)