システム奮闘記:その90

OpenLDAPの設定入門



Tweet
(2011年1月30日に掲載)
はじめに


 2000年、たった1台のLinuxサーバーからシステム構築が
始まった。それから10年経ち、社内のLinuxサーバーが増えた上
WindowsXPやVISTAパソコンの認証も個々のパソコン上で行なっている。

 OutlookExpressに覚えさせているユーザーIDとパスワードも
個々の端末上にあるため、パソコンが故障して買い替えた場合
設定しなおす必要もある。

 2008年以降は仮想化を導入したため、Linuxサーバー(仮想OSとして)を
より多く増やす事ができるようになった。


 そこでユーザー情報やパスワードなどを一元管理できないかと考え
LDAPに注目する事にした。

 だが費用をかけるわけにはいかないので、活躍するのは
オ−プンソース。そうです!!

 無償のOpenLDAPの登場です!!

 というわけで、OpenLDAPの話を始めます。

注意書き  CentOS5.4を使ってインストールや設定を行なっていますので DebianやSlackware系などには当てはまらない部分もあると思います。  後半では、ディストリビューションに影響されないインストール方法として ソースコンパイルの話も載せています。
LDAPとの出会い  LDAPという名称は最近知ったわけではなく、2002年ぐらいから  「Linux + Samba + OpenLDAP」の話は出ていたので  エルダップ(LDAP)  という名称は耳にしていた。  そしてLDAPは、ユーザー認証に使う話は知っていたのだが どういう仕組みで、どうやって設定するのかは全く知らなかった。  それにLinux関連の本でOpenLDAPの設定の部分を見ると  難しそうなので、手が出せへん (^^;;  だった。  そしてセミナーなどでLDAPの話を聞いても  ホンマに難しくて、わからへん (^^;;  それにLDAPがなくても業務や運用に支障はなかったので 「LDAP」という用語を耳にしてから、長い間、LDAP導入を考えずに そのまま時が流れていったのだった。

ユーザー認証とユーザー情報について

 OpenLDAPの話に入る前に、ユーザー認証の話を書く事にします。  UNIX(Linux)の場合、ユーザー認証を行なう際の、ユーザー情報は /etc/passwdファイルに保管されている。  そしてパスワード情報は/etc/shadowファイルに保管されている。
UNIX(Linux)のユーザー認証とユーザー情報
UNIX(Linux)のユーザー認証とユーザー情報
UNIX(Linux)の場合、ユーザー情報を登録するファイルとして
/etc/passwdがある。
名称は「passwd」だが、パスワード情報は入っていない。
昔は暗号化パスワード情報も入っていたのだが
一般ユーザーから丸見えだったため、セキュリティー上の問題から
パスワード情報は別のファイルに登録するようになった。

パスワード情報は/etc/shadowに登録されている。
このファイルは管理者権限(root)以外は閲覧できない。
そのため「影」(shadow)という名前になっている。

歴史的経緯を知らずにファイル名だけ見ると
わかりづらくなるのだ。

 UNIX(Linux)に登録しているユーザー情報を保管するために
/etc/passwdファイルがあるのだ。


 だが、以下のような誤解もしてしまった。

 Linux上で動くソフトはLinuxに登録しているユーザー

 なので全ての認証は/etc/passwdを使う

 と思い込んでいた。
 

 その思い込みのために、最初に混乱したのが
2004年にSambaでファイルサーバーを設定する時だった。

 Sambaのユーザー認証の概略は以下のようになっている。

Sambaのユーザー認証の概略
Sambaのユーザー認証の概略
/etc/passwdファイルは、あくまでもSambaサーバー上に
そのユーザーが登録されているかどうかの確認に使われるだけだ。

そして実際の認証はSamba独自のデータベースで行なっている。
2種類の独自データベースがあるのだが、ここでは割愛します。

 だが、設定した当時は、上のような図式を知らなかったため
2004年に、Sambaでファイルサーバーを構築し
Linux上にも、Windows側と同じユーザー名とパスワードの
ユーザー登録したのに

 ログインできへん (TT)

 だった。

 この時、本の丸写しでsmbpasswd -a (ユーザー名)コマンドを
使って、ログインできるようになった。

 だが、この時は踏み込んで調べる事はしなかったし
それだけの実力もなかったため、本の丸写しの設定に成功して

 これで、いいのだ!

 とバカボンのパパになっていたのだ (^^)

cyrus-imapの認証

 2007年、Webメールのscalixのインストールをしようとした時だった。  UW-imapの場合、UNIX(Linux)とメールユーザーは一致しているのだが cyrus-imapの場合、以下の事ができるのを知った。  Linux上に存在しないユーザーでも  ユーザー登録ができる!
scalixを含めたcyrus-imapを利用したメールサーバーの場合
独自のユーザー情報ファイルを使う
scalixの場合、独自のユーザー情報ファイルを使う
scalixを含めたcyrus-imapを利用したメールサーバーの場合
Linuxに登録しているユーザーとは独立した形で
ユーザー登録ができるため、独自のユーザー登録ファイルが存在する。
そのため/etc/passwdは使われる事はない。

 Linux上で登録していないユーザーであっても

 メールの利用者としてユーザー登録ができる!!

 衝撃の出来事だった。

 この時、ソフトによって、必ずしもUNIX(Linux)にユーザー登録しなくても
独立した形でユーザー情報の登録が可能なもの知った。


 そして、認証形態が異なる場合、ユーザー情報を保管しているファイルが
/etc/passwdでなくても、他のユーザー情報のファイルの場合がある事が
自然と納得できるようになった。

 まさに・・・

 /etc/passwdの呪縛から解放されたのだ!!

 だった。

 これでLDAPを理解するための素地ができたのだった。

OpenLDAPのインストール

 OpenLDAPとは、LDAPのオ−プンソース版の事なのだ。  2010年11月、LDAPやOpenLDAPがどんな物かを知るため 実験サーバーを使ってインストールしてみようと思った。  ところで・・・  LDAPってどういう意味やねん?  以下の略だという。  Light Directory Access Protocol  直訳すると「軽量住所録に接続するための規約」なのだ。  だが、直訳を見ても  だから何やねん・・・ (--;;  なので、ThinkITの記事([ThinkIT] LDAPとは何をするもの?)や  以下の本を使いながら、LDAPの勉強をする事にした。  「CentOS5で作るネットワークサーバー構築ガイド」  (サーバー構築研究会:秀和システム)

ディレクトリーサービス

 本のLDAPの章の最初の部分にディレクトリーサービスの説明があった。  まずはディレクトリーとは何かを知る事だ。
ディレクトリ(Directory)の意味
英語の「Directory」は「住所録」や「名簿」の意味がある。
LDAPのディレクトリの意味は、単なる「アドレス」だけでなく
ネットワークを利用するユーザー名やホスト名などの様々な情報を
持つ事ができるデータベースになるのだ。

データベースなのでキーとなる語句からの検索が可能であり
ディレクトリーの場合、キーはホスト名やユーザー名になる。

 平たく言えば

 色々な情報を盛りこめる名簿

 なのだ。


 そしてディレクトリーサービスとは

 名簿情報の提供!

 なのだ。


 ディレクトリーサービスといってもピンと来ない。
 でも、意外と身近な所でディレクトリーサービスがあるという。

 DNSサーバーなのらー!

 DNSサーバーが提供しているのは、ドメイン名からIPアドレス
もしくは、その反対の情報を提供しているのだ。

 「名簿情報の提供」という意味合いからDNSサーバーも
一種のディレクトリーサービスというのだ。

 初めて知ったので勉強になった (^^)

LDIFファイル。LDAPに使うデータベース

 テキストファイルを使った階層型データベースだという。  データベースファイルの種類は、LDIFファイルと呼ばれる。  記述方法を見る前に、データ構造を見てみる。  LDAPで情報を扱う基本単位は「エントリー」と呼ばれる。  LDAPのエントリーは、属性の集合で構成されている。
LDAPのデータ構造
LDAPのデータ構造
LDAPのデータベースの基本単位はエントリーと呼ばれる物だ。
そのエントリーは属性の集合で構成されている。
属性は属性タイプと属性値で構成されている。

 これだけだとピンよ来ない。
 でも、前に進む。

 本に書いてあった属性タイプの表を丸写ししてみる。

よく使われる属性タイプ(本の丸写し)
dn 識別子(Distinguished Name)
objectClass オブジェクトクラス
dc ドメイン構成要素(Domain Component)
o 組織名(Organization)
ou 組織単位(Organization Unit)
cn 一般名称(Common Name)

 その他、色々、属性があり、どんな属性があるのかは、RFC2256に規定があります。


 ところでLDAPのデータベースは木構造(ツリー構造)になっている。

LDAPはツリー構造のデータベース
LDAPのデータ構造
階層型データベースで、木構造(ツリー構造)になっているのが特徴だ。

 でも、これだけだったら

 わかった気で終わるのらー!!

 なので、実際に、データベースの中身がどんな記述になるのか
具体例(参考例)を見てみないと「なるほど」と納得する事は難しい。


 LDAPの場合、データベースとしてLDIFファイルに記述する。
 そして記述方法は以下の形を取る。

LDIFファイルの記述法

#コメント dn: <識別子> <属性識別子> : <属性値> <属性識別子> : <属性値> <属性識別子> : <属性値>

#コメント dn: <識別子> <属性識別子> : <属性値> <属性識別子> : <属性値> <属性識別子> : <属性値>

青い枠で囲まれた範囲がLDAPエントリーだ。
「dn: <識別子>」の部分で
識別子の値はキーとなる語句が入る。

残りの属性識別子(付随する情報)と、その値(属性値)が入る。


 具体的に、どんな値が入るのか、実際に入れてみる事にした。

LDIFファイルの記述例

#Ono Mayumi dn: uid=ono,ou=idol,dc=mydomain,dc=jp cn: Ono Mayumi mail: m.ono@example.com description: Very pretty idol

#Rola Chen dn: uid=Rola,ou=idol,dc=mydomain,dc=jp cn: Rola Chen mail: rola.chen@example.com description: Pretty chinese girl

#Tanumura Yumi dn: uid=tanimura,ou=singer,dc=mydomain,dc=jp cn: Tanimura Yumi mail: y.tanimura@example.com description: Very good singer

青い枠で囲まれた範囲がLDAPエントリーだ。

1番目のエントリは私の (o) な小野真弓の情報だ。
赤い部分は識別名と識別子で、「小野真弓」と同定できる値が入る。
複数の属性と属性値で、識別名(dn)の値を構成する事ができる。

2番目は、メチャかわいいローラ・チャンの情報。
ローラは中国人だから「dc=jp」ではなく「dc=cn」にしろという
ツッコミは無しね。日本のアイドルだから (^^)

3番目は歌声が最高の谷村有美の情報なのだ。


何を属性にできるかは、RFC2256で規定がある。

 こんな感じで記述するのだ。
 まさに・・・

 色々な情報を盛りこめる名簿なのらー (^^)

 もし、LDIFファイルでログインするときのユーザー認証の
データベースにする場合、ユーザー名、パスワード(暗号化された物)
シェルの種類などを盛りこめば良いのだ。

OpenLDAPのインストールと設定

 だいたいLDAPが何かを把握したので、実際に設定してみる事にする。  ここはお得意の本の丸写しで、OpenLDAPをインストールに必要なソフトを用意する。
OpenLDAPのインストールに必要なパッケージ
CentOS5系の場合
(1) openldap-2.3.43-3.el5.i386.rpm
(2) openldap-servers-2.3.43-3.el5.i386.rpm
(3) openldap-clients-2.3.43-3.el5.i386.rpm

 というわけでインストール開始する。

openldapのインストール
[root@LDAP]# rpm -ihv openldap-2.3.43-3.el5.i386.rpm 
警告: openldap-2.3.43-3.el5.i386.rpm: ヘッダ V3 DSA signature: NOKEY, key ID e8562897
準備中...                ########################################### [100%]
        パッケージ openldap-2.3.43-3.el5.i386 は既にインストールされています。
[root@LDAP]# 
あとでわかった話、CentOS5系の場合、初期設定で
既にインストールされているのだ。

 そして次のパッケージをインストールする。

openldap-serversのインストール
[root@LDAP]# rpm -ihv openldap-servers-2.3.43-3.el5.i386.rpm 
警告: openldap-servers-2.3.43-3.el5.i386.rpm: ヘッダ V3 DSA signature: NOKEY, key ID e8562897
エラー: 依存性の欠如:
        libltdl.so.3 は openldap-servers-2.3.43-3.el5.i386 に必要とされています
[root@LDAP]# 
[root@LDAP]# rpm -ihv libtool-ltdl-1.5.22-6.1.i386.rpm 
警告: libtool-ltdl-1.5.22-6.1.i386.rpm: ヘッダ V3 DSA signature: NOKEY, key ID e8562897
準備中...                ########################################### [100%]
   1:libtool-ltdl           ########################################### [100%]
[root@LDAP]# 
[root@LDAP]# rpm -ihv openldap-servers-2.3.43-3.el5.i386.rpm 
警告: openldap-servers-2.3.43-3.el5.i386.rpm: ヘッダ V3 DSA signature: NOKEY, key ID e8562897
準備中...                ########################################### [100%]
   1:openldap-servers       ########################################### [100%]
[root@LDAP]# 
依存性の問題で引っかかった。
どうやら「libtool-ltdl」をインストールする必要があるようだ。

ただし、CentOSをインストールする際に、どのパッケージを選ぶかで
「libtool-ltdl」がインストールされる可能性はあると思う。

 最後に、LDAPのクライアントになるためのパッケージをインストール。

openldap-clientsのインストール
[root@LDAP]# rpm -ihv openldap-clients-2.3.43-3.el5.i386.rpm 
警告: openldap-clients-2.3.43-3.el5.i386.rpm: ヘッダ V3 DSA signature: NOKEY, key ID e8562897
準備中...                ########################################### [100%]
   1:openldap-clients       ########################################### [100%]
[root@LDAP]# 

 無事、インストールが終わった。

 再度、必要なパッケージを整理すると以下のようになる。

OpenLDAPのインストールに必要なパッケージ
CentOS5系の場合
(1) openldap-2.3.43-3.el5.i386.rpm

CentOS5の場合、初期設定でインストールされている
(2) openldap-servers-2.3.43-3.el5.i386.rpm
(3) libtool-ltdl-1.5.22-6.1.i386.rpm

(2)をインストールする際に必要な場合もある
(4) openldap-clients-2.3.43-3.el5.i386.rpm

 これでインストールが終わった。

LDAPを使った認証サーバーの設定

 さて、これでLDAPを設定する準備が整った。  そして以下のように、LDAPを使ったLinuxのログイン認証を 行なってみる事にした。
LDAPを使ったLinuxの認証システム
LDAPを使ったLinuxの認証システムの仕組み
従来からある/etc/passwdファイルを使った認証ではなく
LDAPサーバーにあるデータベースから、ユーザー情報を使って
ログイン認証を行う事ができる。

 LDAPを使った場合、クライアント・サーバー方式になるため
クライアントとサーバーの両方に設定が必要だ。

 まずはサーバーの設定から行なう。

LDAPサーバー側の設定

 早速、設定を行なう事にした。  もちろん、本の丸写しなのだ (^^)  OpenLDAPの設定ファイルは /etc/openldap/slapd.conf なのだ。  ファイルを触る前に、まずはOpenLDAPの管理者パスワードを決めて パスワードの暗号化を行なう。
パスワードの暗号化
[root@LDAP]# openssl passwd
Password: 
Verifying - Password: 
Warning: truncating password to 8 characters
GzrpWPZiYFyAA
[root@LDAP]# 
opensslコマンドでパスワードを暗号化する。
暗号化されたパスワードは赤い部分になる。

 管理者パスワードの暗号化を行なった。

 次にLDAPのサーバーの設定を行なう。
 OpenLDAPのsladp.confファイルを触る。

sladp.confファイル (一部抜粋)
変更前
#######################################################################
# ldbm and/or bdb database definitions
#######################################################################
 

database    bdb
suffix        "dc=my-domain,dc=com"
rootdn        "cn=Manager,dc=my-domain,dc=com"
# Cleartext passwords, especially for the rootdn, should
# be avoided.  See slappasswd(8) and slapd.conf(5) for details.
# Use of strong authentication encouraged.
# rootpw        secret
# rootpw        {crypt}ijFYNcSNctBYg
変更後
#######################################################################
# ldbm and/or bdb database definitions
#######################################################################


database    bdb
suffix        "dc=company,dc=jp"
rootdn        "cn=Manager,dc=company,dc=jp"
# Cleartext passwords, especially for the rootdn, should
# be avoided.  See slappasswd(8) and slapd.conf(5) for details.
# Use of strong authentication encouraged.
# rootpw        secret
# rootpw        {crypt}ijFYNcSNctBYg
rootpw            {crypt}GzrpWPZiYFyAA
色をつけたのが変更した箇所だ。

とにかく本の丸写しを行なったため、設定時点では
何を意味するのか理解せずに行なった。

一体、どういう設定なのか、詳しくは後述しています。

 これでOpenLDAPの設定が終わったので、OpenLDAPのデーモンである
slapdデーモンを稼働させる。

slapdデーモンを稼働させる (CentOS5系)
[root@LDAP]# /etc/rc.d/init.d/ldap start
slapd の設定ファイルをチェック中:  config file testing succeeded
                                                           [  OK  ]
slapd を起動中:                                            [  OK  ]
[root@LDAP]# 
CentOSの場合、デーモンを起動させたり停止させるのは簡単にできる。
でも、使い勝手が良い環境になれると、どこのLinuxでも使える
普遍性の高い設定の紹介ができなくなるなぁ・・・。


 次にエントリーの登録を行なう。
 ユーザー認証を行なうために、3種類のエントリの登録が必要だという。

 なぜ3種類のエントリを用意するのかは理解していなかったが

 とりあえず本の丸写しをしよう!

 という事で、本の丸写しの設定を行なう事にした。

初期エントリファイル(init.ldif)
dn: dc=company,dc=jp
objectClass: dcObject
objectClass: organization
o: myorganization
dc: company
 
dn: cn=Manager,dc=company,dc=jp
objectClass: organizationalRole
cn: Manager
 
dn: ou=People,dc=company,dc=jp
objectClass: organizationalUnit
ou: People
 
dn: ou=Group,dc=company,dc=jp
objectClass: organizationalUnit
ou: Group
初期エントリファイル(init.ldif)の意味や、ファイルの内容は
全く理解していなかった。

記述法については後述しています。

 さて、このファイルをLDAPに登録する。

初期エントリファイル(init.ldif)の登録
[suga@LDAP]$ ldapadd -x -D "cn=Manager,dc=company,dc=jp" -W -f ./init.ldif
Enter LDAP Password: 
adding new entry "dc=company,dc=jp"
 
adding new entry "cn=Manager,dc=company,dc=jp"
 
adding new entry "ou=People,dc=company,dc=jp"
 
adding new entry "ou=Group,dc=company,dc=jp"
 
[suga@LDAP]$ 
ldapaddコマンドを使ってエントリを登録する。
赤い部分は管理者パスワードを尋ねられているので
管理者パスワードを入力する。

ところで、このコマンドを使った際、オプションの意味などはは
わからなかった。
実際の使い方については後述しています。


 次に2番めのエントリーとして、グループエントリーの登録を行なう。
 まずは、本の丸写しでグループーアカウントエントリのファイル(group.ldif)を作成する。

グループアカウントエントリのファイル(group.ldif)
dn: cn=member01,ou=group,dc=company,dc=jp
objectClass: posixGroup
objectClass: top
cn: member01
gidNumber: 3001
 
dn: cn=member02,ou=group,dc=company,dc=jp
objectClass: posixGroup
objectClass: top
cn: member02
gidNumber: 3002
 
dn: cn=member03,ou=group,dc=company,dc=jp
objectClass: posixGroup
objectClass: top
cn: member03
gidNumber: 3003
グループアカウントエントリのファイル(group.ldif)の意味は
グループ名、グループIDの登録ぐらいはわかったが
その他の属性や属性値については、全く理解していなかった。

記述法については後述しています。

 さて、このファイルをLDAPに登録する。

グループアカウントエントリのファイル(group.ldif)の登録
[suga@LDAP]$ ldapadd -x -D "cn=Manager,dc=company,dc=jp" -W -f ./group.ldif
Enter LDAP Password:
adding new entry "cn=member01,ou=group,dc=company,dc=jp"
 
adding new entry "cn=member02,ou=group,dc=company,dc=jp"
 
adding new entry "cn=member03,ou=group,dc=company,dc=jp"
 
[suga@LDAP]$ 
初期エントリーファイルと同様に、ldapaddコマンドを使って
グループアカウントエントリのファイル(group.ldif)を登録する。
赤い部分は管理者パスワードを尋ねられているので
管理者パスワードを入力する。


 次に3番めのエントリーとして、ユーザーアカウントエントリの登録を行なう。
 まずは、本の丸写しでユーザーアカウントエントリのファイル(user.ldif)を作成する。

ユーザーアカウントエントリのファイル(user.ldif)
dn: uid=user01,ou=People,dc=company,dc=jp
uid: user01
cn: Test User 01
objectClass: account
objectClass: posixAccount
objectClass: top
userPassword: {CRYPT}oKblFm5ll9Bhs
loginShell: /bin/bash
uidNumber: 5001
gidNumber: 3001
homeDirectory: /home/user01
 
 
dn: uid=user02,ou=People,dc=company,dc=jp
uid: user01
cn: Test User 02
objectClass: account
objectClass: posixAccount
objectClass: top
userPassword: {CRYPT}s.ynvIyRsq7bk
loginShell: /bin/bash
uidNumber: 5002
gidNumber: 3002
homeDirectory: /home/user02
 
 
dn: uid=user03,ou=People,dc=company,dc=jp
uid: user03
cn: Test User 03
objectClass: account
objectClass: posixAccount
objectClass: top
userPassword: {CRYPT}8Bc1wWOkOZ6Yw
loginShell: /bin/bash
uidNumber: 5003
gidNumber: 3003
homeDirectory: /home/user03
ユーザーアカウントエントリのファイル(user.ldif)の意味は
ユーザー名、ユーザー番号、グループ番号、暗号化パスワードの
登録ぐらいはわかったが
その他の属性や属性値については、全く理解していなかった。

記述法については後述しています。

 さて、このファイルをLDAPに登録する。

ユーザーアカウントエントリのファイル(user.ldif)の登録
[suga@LDAP]$ ldapadd -x -D "cn=Manager,dc=company,dc=jp" -W -f ./group.ldif
Enter LDAP Password:
adding new entry "cn=member01,ou=group,dc=company,dc=jp"
 
adding new entry "cn=member02,ou=group,dc=company,dc=jp"
 
adding new entry "cn=member03,ou=group,dc=company,dc=jp"
 
[suga@LDAP]$ 
他のエントリーファイルと同様に、ldapaddコマンドを使って
ユーザーエントリーファイル(user.ldif)を登録する。
赤い部分は管理者パスワードを尋ねられているので
管理者パスワードを入力する。


 これで3種類のエントリーファイルの登録が終わった。
 LDAP側の設定は完了した。

クライアントの設定

 次にLDAPのクライアントの設定を行なう。  クライアントには、nss_ldapをインストールする必要があるが CentOS5系の場合、初期状態でインストールされている。
CentOS5系の場合、既にnss_ldapがインストールされている。
[root@client]# rpm -ihv nss_ldap-253-21.el5.i386.rpm 
警告: nss_ldap-253-21.el5.i386.rpm: ヘッダ V3 DSA signature: NOKEY, key ID e8562897
準備中...                ########################################### [100%]
        パッケージ nss_ldap-253-21.el5.i386 は既にインストールされています。
[root@client]# 
赤い部分に「既にインストールされている」で表示される。

 そしてCentOS5系の場合、/etc/nsswitch.confファイルを触る。

/etc/nsswitch.confファイルを触る
変更前

passwd:     files
shadow:     files
group:      files

変更後

passwd:     files ldap
shadow:     files
group:      files ldap


 ところで・・・

 nsswitch.confって何のファイルやねん?

 調べてみると

 名前解決の順序を指定するファイル

 なのだ。

 だから何やねん!!

 名前解決といえばホスト名からIPアドレス検索するDNSを
連想してしまうが、それは、あくまでも一部だというのだ。
 ユーザー名からユーザー番号、グループ名からグループ番号といった
対になった物を、相互に変換する事を名前検索というのだ。

 名前検索の順序を記述したファイルが nsswitch.confだという。
 もっとわかりやすい例をファイルから抜粋すると以下の部分だ。

/etc/nsswitch.confを一部抜粋
#hosts:     db files nisplus nis dns
hosts:      files dns
ホスト名の名前解決の順序を表している記述だ。
最初はファイルを閲覧する。/etc/hostsの事だ。
それで解決できなかったら、DNS検索というのだ。

つまり名前検索を行なう際、優先順位の高い物から
順番に記述していくのだ。

 さて、nsswitchファイルの書き換えが終わった。


 次に、CentOSの場合、/etc/ldap.confを触る必要がある。

/etc/ldap.confを触る
# Your LDAP server. Must be resolvable without using LDAP.
# Multiple hosts may be specified, each separated by a 
# space. How long nss_ldap takes to failover depends on
# whether your LDAP client library supports configurable
# network or connect timeouts (see bind_timelimit).
host 192.168.X.Y

# The distinguished name of the search base.
base dc=company,dc=jp

赤い部分はLDAPサーバーのIPアドレスを記述する。
青い部分はベースDNを記述する。
ベースDNについては後述しています。

 あとは、クライアント側でログインするユーザーの
ディレクトリを設けておけば良い。

ログインするユーザー用にディレクトリを作成
[root@client]# mkdir /home/user01/
[root@client]#
ユーザー「user01」用のためにディレクトリー作成をした。

 早速、ログインしてみる事にした。

ログインしてみる
[root@client]# telnet localhost
Trying 127.0.0.1...
Connected to localhost.localdomain (127.0.0.1).
Escape character is '^]'.
CentOS release 5.4 (Final)
Kernel 2.6.18-164.el5 on an i686
login: user01
Password: 
-bash-3.2$ 
telnetを使って、自分自身(ローカルホスト)にログインしてみた。

 見事にログインできた!!

 今まで /etc/passwd に登録したLinux(UNIX)でないと
ログインできないと思い込んでいた物が

 完全にぶっとんでしまった!!

 LDAPを使った認証でログインできた。

注意 (2011/4/27追加)
ここではPAMの設定を書いていませんでした。
PAMの設定を行なったのを、すっかり忘れたのかもしれません。

PAMの設定をしなかったため、ドツボにハマった話を
「システム奮闘記:その92」(Samba + OpenLDAP設定入門)で取り上げています。


 でも、今のままではログインの際、シェルの設定ファイルを
読み込んでいないため、シェルが活用できない。
 そこで、bashの設定ファイルを複写してみる。

bashの設定ファイルを複写してみる
[root@client]# cp ~suga/.bashrc /home/user01/
[root@client]# cp ~suga/.bash_profile /home/user01/
[root@client]# cp ~suga/.bash_logout /home/user01/
ユーザー「user01」がログインして、シェルが使えるよう
bashのファイルをいれておいた。

 早速、ログインしてみる事にした。
 今度はログイン画面からログインしてみる事にした。

ログイン画面(CentOS 5系)
ログイン画面
ユーザーIDを入力
ユーザーIDを入力
ユーザーIDを入力(拡大画面)
ユーザーIDを入力(拡大画面)
パスワードを入力
パスワードを入力画面
ログイン成功!
ログイン成功画面
普通に使える状態でログインできる。

 他のマシンからtelnetでログインを行なってみる。

LDAPのクライアントのマシンにログインしてみる
[root@linux]# telnet 192.168.X.Y
Trying 192.168.X.Y...
Connected to ldap.xxxx.yyyy.jp (192.168.X.Y).
Escape character is '^]'.
CentOS release 5.4 (Final)
Kernel 2.6.18-164.el5 on an i686
login: user01
Password: 
Last login: Thu Dec  9 18:15:14 from linux
[user01@client]$ 
普通に使える状態でログインできる。

 改めて・・・

 おー! すげー!!

 と思った。


 そしてLDAPでユーザー認証を行なう場合でも
/etc/passwdに登録しているユーザーも今まで通り使えるため

 LDAP認証と/etc/passwd認証は共存できる!

 を知った。

 そしてクライアント・サーバー公式なので、複数のクライアントが
ぶらさがる事も可能だ。

LDAPサーバーでLinuxユーザーアカウントを一元管理
LDAPサーバーでLinuxのユーザーアカウントを一元管理
複数のLinuxマシンのユーザーアカウントを個々の端末で管理するより
LDAPサーバーで一元管理した方が便利になるし、整合性も取りやすい。
紆余曲折しながらも、ここまで到達したのだ。

Windowsのユーザーアカウントの一元化について

 LinuxのユーザーアカウントをLDAPを使って一元管理できるのがわかった。  同じようにWindowsのユーザーアカウントもLDAPで管理できないかと 思ったりする。
Windowsのユーザーアカウントを
OpenLDAPサーバーで一元管理はできないのか?
LDAPサーバーでWindowsのユーザーアカウントを一元管理できないのか?
個々のWindows端末にユーザーアカウント情報を登録するのではなく
上図のように、LDAPサーバーに保管する方式ができないかと思ってみた。

 結論から書きますと、上図のような事は不可能です。
 以下のような方法が必要になります。

Windowsのユーザーアカウントを
OpenLDAPサーバーで一元管理するためには
LDAPサーバーでWindowsのユーザーアカウントを一元管理する方法
OepnLDAPを使ってWindowsのユーザーアカウントの一元管理を行なうには
途中で、Sambaサーバーを中継する必要があります。
Sambaを使い、NTドメインとPDCコントローラーの構築が必要になる。

他にも有償ソフトを使えば、LDAPでWindowsのユーザーアカウントの
一元管理ができるらしいが、私は知らないので何とも言えない・・・。

 SambaとOpenLDAPの連携ですが、別の機会で取り上げたいと思います。


OpenLDAP設定ファイルについて

 さてさて本の丸写しで設定を行なってきたのだが そこで終わってしまうと、トラブルが起こった際は・・・  対処できず、ドツボにハマる!  という経験則がある。  というわけでドツボにハマらないように、概略でも良いから OpenLDAPの設定ファイルや、LDIFファイルを見ていく事にした。  より詳しく調べられるように次の本も用意した。  「入門LDAP/OpenLDAP」(デージーネット秀和システム)  これで心強い味方ができたのだ (^^)

slapd.confファイルについて

 OpenLDAPの設定ファイルのslapd.confファイルについて 見ていく事にする。
sladp.confファイル (一部抜粋)
#######################################################################
# ldbm and/or bdb database definitions
#######################################################################
 

database    bdb
suffix        "dc=company,dc=jp"
rootdn        "cn=Manager,dc=company,dc=jp"
# Cleartext passwords, especially for the rootdn, should
# be avoided.  See slappasswd(8) and slapd.conf(5) for details.
# Use of strong authentication encouraged.
# rootpw        secret
# rootpw        {crypt}ijFYNcSNctBYg
rootpw            {crypt}GzrpWPZiYFyAA
赤色の部分がベースDN。青色が特権DN。
桃色が管理者パスワードなのだ。

 ベースDNとはなんだろうか。特権DNとは何だろうか?


 そこで、LDAPでのログイン認証のために作ったエントリーを
階層構造の図として見てみる事にする。

LDAP認証のために作ったエントリーの階層構造
LDAP認証のために作ったエントリーの階層構造
LDAP認証のため、図のような階層構造のデータベースを作成した。

 ベースDNとは何か?
 本などでは・・・

 検索開始位置

 なのだが、いまいち、よくわからん。
 でも、図にするとわかりやすい。

ベースDNとは
ベースDNとは何か
DNとは「Distinguished Name」の略で、唯一の名前という意味だ。
ベースは「Base」なので、同定するための基本となる名前になる。

図では茶色に塗った部分がベースDNなる。
どのデータも共通して持っている部分なので、目的のデータを
検索するのに必要な、基本という意味でベースDNと呼ぶし
階層構造のデータベースのため、検索開始の位置になる。

 次に特権DNなのだが、図にすると、わかりやすい。

特権DNとは
特権DNとは何か?
桃色の部分が特権DNなのだ。
特権という言い回しよりも、管理者DNの方がわかりやすいと思う。

OpenLDAPの運用管理者のデータを保管する位置(階層)を示す。

 次に管理者パスワードを見てみる。

管理者パスワードの設定
rootpw            {crypt}GzrpWPZiYFyAA
記述方法は暗号化パスワードの前に「{crypt}」を付ける事で
暗号化の方式を示している。

もし、暗号化の方法がMD5方式なら「{MD5}」になる。

 パスワードだが、平文で登録する事も可能だ。
 以下のように、パスワードの頭に何もつけなければ良いのだ。

平文で管理者パスワードの設定
rootpw            onomayumi
平文の場合は、そのままパスワードを記述すれば良いのだ。
上の設定だとパスワードは「onomayumi」になる。

ただし、セキュリティー上、好ましくないため、平文では記述せず
暗号化した物を記述する必要がある。


 そこで、もう1度、設定ファイルのslapd.confファイルを見てみる。

sladp.confファイル (一部抜粋)
#######################################################################
# ldbm and/or bdb database definitions
#######################################################################
 

database    bdb
suffix        "dc=company,dc=jp"
rootdn        "cn=Manager,dc=company,dc=jp"
# Cleartext passwords, especially for the rootdn, should
# be avoided.  See slappasswd(8) and slapd.conf(5) for details.
# Use of strong authentication encouraged.
# rootpw        secret
# rootpw        {crypt}ijFYNcSNctBYg
rootpw            {crypt}GzrpWPZiYFyAA
赤色の部分がベースDN。青色が特権DN。
桃色が管理者パスワードなのだ。

ここでの設定は、LDAPの運用に必要な基本となる情報を
設定する部分になる。

 これでOpenLDAPのサーバーの設定は完了だ。

LDIFファイルの設定

 次にデータベースのデータ形式と代入方法の話をします。  データ形式の設定と代入を行なうにはLDIFファイルを使います。 まず最初に、各ユーザー、各グループ、管理者情報を入れるための エントリを登録します。
最初に登録する必要があるエントリ
最初に登録が必要なエントリ
エントリとは「LDAPで扱う情報の基本単位」なのだが
「箱」と置き換えても、わかりやすい。

そして、LDAPは階層型データベースだが、マトリョーシカのように
入れ子の形で見た方が、すっきりする。

最初に、全ての情報を管理する基本エントリ(大もとの箱)の登録を行なう。

そして、大もとの箱の中に入る3つの箱の登録だ。

(1)管理者情報を管理する箱(管理者エントリ)の登録。
(2)ユーザー情報を管理する箱(ユーザーエントリ)の登録。
(3)グループ情報を管理する箱(グループエントリ)の登録だ。

平たく言えば、箱を用意して、各箱に名前をつける作業なのだ。

 エントリ(箱)を用意するだけではない。
 何のエントリ(箱)かを認識するために、エントリ(箱)に名前を付ける必要がある。

各エントリに名前をつける
各エントリに名前をつける
各エントリ(箱)に名前を付ける。

この場合は、エントリ(箱)の名前だけ付けるが、場合によっては
エントリ(箱)に関する付帯情報(所在地、連絡先など)も代入する事がある。

 LDIFファイルを、平たく言えば

 箱を用意して、各箱に名前や付帯情報を入れる作業

 を行なうために必要なファイルなのだ。



 概略ばかり書いてもピンと来ない。
 なので

 実践あるのみ!

 なのだ。


 まずはLDAP認証のためのデータベースとして、init.ldifファイルを
作成しました。そのファイルを見てみる事にします。

初期エントリーファイル: init.ldif

dn: dc=company,dc=jp objectClass: dcObject objectClass: organization o: myorganization dc: company

dn: cn=Manager,dc=company,dc=jp objectClass: organizationalRole cn: Manager

dn: ou=People,dc=company,dc=jp objectClass: organizationalUnit ou: People

dn: ou=Group,dc=company,dc=jp objectClass: organizationalUnit ou: Group

このLDIFファイルは4つのエントリーと、エントリー内の
属性の記述と、属性値の代入をしています。
エントリーは、見やすいように枠で囲んでいます。

基本となるエントリーは青く囲んだ部分です。

 青く囲んだ基本となるエントリーを抜き出して見てみる事にした。

初期エントリーファイル: init.ldif の
基本となるエントリーを見てみる
dn: dc=company,dc=jp
objectClass: dcObject
objectClass: organization
o: myorganization
dc: company
赤い部分はベースDNになる。
階層構造データベースで、検索開始の位置を表すため
開始位置を同定できる物として「dc=company,dc=jp」となる。

 ところで

 objectClassって何やねん?

 どんな事か、調べてみると本に書いてあった。

属性「objectClass」について
オブジェクトクラス「objectClass」とは、エントリに登録されるべき
属性に関する取り決めで、各エントリに登録できる属性を規定する物。

 つまり

 属性のパッケージ

 なのだ。

 PHP言語のオブジェクトクラスやC言語の構造体を連想すれば
わかりやすいと思う。

 オブジェクトの規定はCentOS5系の場合、/etc/openldap/schemaの
ディレクトリ内のschemaファイルで規定されている。

/etc/openldap/schemaのディレクトリ
[suga@LDAP]$ ls
README        cosine.schema         misc.schema      ppolicy.schema
corba.schema  dyngroup.schema       nis.schema       redhat
core.ldif     inetorgperson.schema  openldap.ldif
core.schema   java.schema           openldap.schema
[suga@LDAP]$ 
拡張子が「schema」のファイルが、オブジェクトの規定と
属性の規定をしているファイルなのだ。

 core.schemaファイルに「dcObject」と「organization」

core.scemaファイルの中身
オブジェクト「dcObject」を見てみる
# RFC 2247
objectclass ( 1.3.6.1.4.1.1466.344 NAME 'dcObject'
	DESC 'RFC2247: domain component object'
	SUP top AUXILIARY MUST dc )
赤い「MUST」は絶対に必要な属性なのだ。
そのため「dc」属性は必須で、その値を代入する必要があるのだ。
オブジェクト「organization」を見てみる
objectclass ( 2.5.6.4 NAME 'organization'
	DESC 'RFC2256: an organization'
	SUP top STRUCTURAL
	MUST o
	MAY ( userPassword $ searchGuide $ seeAlso $ businessCategory $
		x121Address $ registeredAddress $ destinationIndicator $
		preferredDeliveryMethod $ telexNumber $ teletexTerminalIdentifier $
		telephoneNumber $ internationaliSDNNumber $ 
		facsimileTelephoneNumber $ street $ postOfficeBox $ postalCode $
		postalAddress $ physicalDeliveryOfficeName $ st $ l $ description ) )
赤い部分の「MUST」の項目は絶対に必要な属性で
属性値の代入は必要不可欠になる。
そのためオブジェクト「organization」を入れたエントリは
組織名の属性を「o」を絶対に入れる必要がある。

そして青い部分の「MAY」は、あっても良いという属性で
無理にエントリに入れる必要はない。

 さて、初期エントリのファイル(init.ldif)で
基本となるエントリの部分を、もう1度見てみる。

初期エントリーファイル: init.ldif の
基本となるエントリを見てみる
dn: dc=company,dc=jp
objectClass: dcObject
objectClass: organization
o: myorganization
dc: company
青い部分でオブジェクトで「dcObject」と「organization」が
指定されているため、属性「o」(所属名)と属性「dn」の値を
必ず代入する必要がある。

 さて、もう1度、init.ldifファイルの全体を眺めてみる。

初期エントリーファイル: init.ldif
dn: dc=company,dc=jp
objectClass: dcObject
objectClass: organization
o: myorganization
dc: company

dn: cn=Manager,dc=company,dc=jp objectClass: organizationalRole cn: Manager

dn: ou=People,dc=company,dc=jp objectClass: organizationalUnit ou: People

dn: ou=Group,dc=company,dc=jp objectClass: organizationalUnit ou: Group

管理者エントリ(青い枠)を見てみる。
オブジェクトが「organizationalRole」になっている。
直訳すると「組織での役割」になる
一般名称の「cn」属性が必須で、属性値の代入が必要になるため
「Manager」という値を代入している。


ユーザーエントリ(赤い部分)を見てみる。
オブジェクトが「organizationalUnit」になっている。
直訳すると「組織単位」だ。
組織単位の「ou」属性が必須で、属性値の代入が必要になるため
「people」の値を代入している。


グループエントリ(緑の枠)を見てみる。
ユーザーエントリと同じオブジェクトだ。
組織単位の「ou」属性が必須になり、属性値「group」を代入している。


ちなみに、オブジェクトの「organizationalRole」と
「organizationalUnit」は、core.schemaファイルで
定義されています。

 基本となるエントリの登録と、各エントリに必要な値を行なう。
 登録の際のコマンドを説明します。

初期エントリーファイル(init.ldif)の登録
[suga@LDAP]$ ldapadd -x -D "cn=Manager,dc=company,dc=jp" -W -f ./init.ldif
Enter LDAP Password:
adding new entry "dc=company,dc=jp"
 
adding new entry "cn=Manager,dc=company,dc=jp"
 
adding new entry "ou=People,dc=company,dc=jp"
 
adding new entry "ou=Group,dc=company,dc=jp"
 
[suga@LDAP]$ 
ldapaddコマンドを使ってエントリーを登録する。
コマンドのオプションだが、以下の通りの使い方になる。

ldapaddコマンドのオプション
-x 簡易認証のオプション。
これがない場合は、SASL認証になる。
SASL認証は私は設定した事がないので、わかりません (^^;;
-D この後ろに、どのユーザーのDNかが来る。
ここでは管理者権限で登録するため、管理者DNにあたる
cn=Manager,dc=company,dc=jp」が入る。
-W パスワード認証の際、プロンプト上から入力を指定
-f LDIFファイルを読み込むためオプション。

 ldapaddコマンドの使い方だが、普通に使う分には
上の4つのオプションぐらいなので、難しくはないのだ。


 さて、これでユーザーアカウント、グループアカウントを登録するのに
必要な土台を作る事ができた。

 次に、グループアカウントのエントリを登録していく。
 
グループアカウントのエントリの登録
グループアカウントのエントリの登録
既に、赤く囲んだグループエントリの登録は完了した。

その下にぶら下がる個々のグループアカウントのエントリの登録を行なう。
グループアカウントのエントリ内には、そのグループの情報が格納されている。

 さて、グループアカウントを登録するためのLDIFファイルを用意する。

グループアカウントを登録するための
LDIFファイル(group.ldif)

dn: cn=member01,ou=group,dc=company,dc=jp objectClass: posixGroup objectClass: top cn: member01 gidNumber: 3001

dn: cn=member02,ou=group,dc=company,dc=jp objectClass: posixGroup objectClass: top cn: member02 gidNumber: 3002

dn: cn=member03,ou=group,dc=company,dc=jp objectClass: posixGroup objectClass: top cn: member03 gidNumber: 3003

1つのエントリに、1つのグループの情報が格納されている。
ここでは3グループの登録が行なわれる。

 さて、グループアカウントのLDIFファイルの形式を見ていく。

グループアカウントのLDIFファイルの書式
dn: cn=member01,ou=group,dc=company,dc=jp
objectClass: posixGroup
objectClass: top
cn: member01
gidNumber: 3001
桃色の部分は、そのグループ名である事を同定するためのDNなのだ。
青い部分はオブジェクトの指定で「posixGroup」になる。
グループアカウントのエントリに使われる属性が定義されている。

赤い部分の「top」オブジェクトは、全てのオブジェクトの基底になる。

 グループアカウントエントリが、どんな形式で、どんな属性を
持っているのか知るため、オブジェクト(posixGroup)を見てみる。

オブジェクト(posixGroup)を見てみる
(nis.schema)
objectclass ( 1.3.6.1.1.1.2.2 NAME 'posixGroup'
        DESC 'Abstraction of a group of accounts'
        SUP top STRUCTURAL
        MUST ( cn $ gidNumber )
        MAY ( userPassword $ memberUid $ description ) )
桃色部分は、このオブジェクトが「top」を基底にしている事を宣言している。
青い部分は必須の属性だ。名称の「cn」とグループID値の「gidNumber」だ。
赤い部分は、あっても、なくても良いという属性だ。

 踏み込んで「top」オブジェクトを見てみる。

「top」オブジェクトを見てみる (core.schema)
# system schema
#objectclass ( 2.5.6.0 NAME 'top'
#       DESC 'RFC2256: top of the superclass chain'
#       ABSTRACT
#       MUST objectClass )
「#」で無効化している。
どこで「top」オブジェクトを定義しているのか、わからない。

ただ、これを見る限り、必須属性は「objectClass」だ。
もっと他の属性があると思ったが、意外だった。

 さて、グループアカウントエントリのファイルを再度見てみる。

グループアカウントを登録するための
LDIFファイル(group.ldif)

dn: cn=member01,ou=group,dc=company,dc=jp objectClass: posixGroup objectClass: top cn: member01 gidNumber: 3001

dn: cn=member02,ou=group,dc=company,dc=jp objectClass: posixGroup objectClass: top cn: member02 gidNumber: 3002

dn: cn=member03,ou=group,dc=company,dc=jp objectClass: posixGroup objectClass: top cn: member03 gidNumber: 3003

必須属性は名称の「cn」と、グループ番号の「gidNumber」だ。
ここでのエントリは、必須属性のみ使っている。
そして、2つの必須属性に、属性値の代入を行なっているのだ。

 さて、このファイルをLDAPに登録する。

グループエントリーファイル(group.ldif)の登録
[suga@LDAP]$ ldapadd -x -D "cn=Manager,dc=company,dc=jp" -W -f ./group.ldif
Enter LDAP Password:
adding new entry "cn=member01,ou=group,dc=company,dc=jp"
 
adding new entry "cn=member02,ou=group,dc=company,dc=jp"
 
adding new entry "cn=member03,ou=group,dc=company,dc=jp"
 
[suga@LDAP]$ 
ldapaddコマンドは、先ほど、説明しましたので省略します。
エントリが登録されていくのがわかる。

 これでグループアカウントのエントリ登録が終わった。


 最後に、ユーザーアカウントのエントリ登録だ。

ユーザーアカウントのエントリの登録
ユーザーアカウントのエントリの登録
既に、赤く囲んだユーザーエントリの登録は完了した。

その下にぶら下がる個々のユーザーアカウントのエントリの登録を行なう。
ユーザーアカウントのエントリ内には、そのユーザーの情報が格納されている。

 ユーザーアカウントエントリのファイル(user.ldif)を見てみる。

ユーザーアカウントエントリのファイル(user.ldif)

dn: uid=user01,ou=People,dc=company,dc=jp uid: user01 cn: Test User 01 objectClass: account objectClass: posixAccount objectClass: top userPassword: {CRYPT}oKblFm5ll9Bhs loginShell: /bin/bash uidNumber: 5001 gidNumber: 3001 homeDirectory: /home/user01

dn: uid=user02,ou=People,dc=company,dc=jp uid: user01 cn: Test User 02 objectClass: account objectClass: posixAccount objectClass: top userPassword: {CRYPT}s.ynvIyRsq7bk loginShell: /bin/bash uidNumber: 5002 gidNumber: 3002 homeDirectory: /home/user02

dn: uid=user03,ou=People,dc=company,dc=jp uid: user03 cn: Test User 03 objectClass: account objectClass: posixAccount objectClass: top userPassword: {CRYPT}8Bc1wWOkOZ6Yw loginShell: /bin/bash uidNumber: 5003 gidNumber: 3003 homeDirectory: /home/user03

1つのユーザーアカウントエントリには、1つのユーザーの情報が格納される。
ここでは3つのユーザー(3つのユーザーアカウントエントリ)がある。

 さて、ユーザーアカウントエントリを見ていく事にする。

ユーザーアカウントエントリのファイル(user.ldif)
dn: uid=user01,ou=People,dc=company,dc=jp
uid: user01
cn: Test User 01
objectClass: account
objectClass: posixAccount
objectClass: top
userPassword: {CRYPT}oKblFm5ll9Bhs
loginShell: /bin/bash
uidNumber: 5001
gidNumber: 3001
homeDirectory: /home/user01
赤い部分と青い部分を見ると、2種類のオブジェクトクラスで
構成されているエントリだというのがわかる。
ユーザーアカウントエントリの場合、どういう属性が
必須なのか見てみる事にした。

 まずは「account」オブジェクトを見てみる。

「account」オブジェクトを見てみる (cosine.schema)
objectclass ( 0.9.2342.19200300.100.4.5 NAME 'account'
        SUP top STRUCTURAL
        MUST userid
        MAY ( description $ seeAlso $ localityName $
                organizationName $ organizationalUnitName $ host )
        )
赤い部分の必須の属性はユーザーIDだ。
そして青い部分の、任意で使える属性は、所属組織名(organizationName)
ホスト名(host)などがある。

 次に「posixAccount」オブジェクトを見てみる。

「posixAccount」オブジェクトを見てみる(nis.schema)
objectclass ( 1.3.6.1.1.1.2.0 NAME 'posixAccount'
        DESC 'Abstraction of an account with POSIX attributes'
        SUP top AUXILIARY
        MUST ( cn $ uid $ uidNumber $ gidNumber $ homeDirectory )
        MAY ( userPassword $ loginShell $ gecos $ description ) )
赤い部分の名称(cn)、ユーザーID(uid)、ユーザー番号(uidNumber)
グループ番号(groupNumber)、ホームディレクトリ(homedirectory)は必須だ。

青い部分は任意の属性だ。ユーザーパスワード(userPassword)や
ログインした時のシェル(loginShell)がある。

 もう一度、エントリを見てみる事にする。

ユーザーアカウントエントリのファイル(user.ldif)
dn: uid=user01,ou=People,dc=company,dc=jp
uid: user01
cn: Test User 01
objectClass: account
objectClass: posixAccount
objectClass: top
userPassword: {CRYPT}oKblFm5ll9Bhs
loginShell: /bin/bash
uidNumber: 5001
gidNumber: 3001
homeDirectory: /home/user01
赤い部分は必須属性で、青い部分は任意で使える属性だ。
この構成でユーザーアカウント管理を行なっているのだ。

 さて、このファイルをLDAPに登録する。

ユーザーエントリーファイル(user.ldif)の登録
[suga@LDAP]$ ldapadd -x -D "cn=Manager,dc=company,dc=jp" -W -f ./group.ldif
Enter LDAP Password:
adding new entry "cn=member01,ou=group,dc=company,dc=jp"
 
adding new entry "cn=member02,ou=group,dc=company,dc=jp"
 
adding new entry "cn=member03,ou=group,dc=company,dc=jp"
 
[suga@LDAP]$ 
他のエントリーファイルと同様に、ldapaddコマンドを使って
ユーザーエントリーファイル(user.ldif)を登録する。
赤い部分は管理者パスワードを尋ねられているので
管理者パスワードを入力する。

 これで3種類のエントリーファイルの登録が終わった。
 OpenLDAPを使ったLinuxの認証サーバーの設定は完了なのだ。

 OpenLDAPでは、RFCで規定されたスキーマ(データベースの形式)と
各種ソフトが用意する独自スキーマがあり、応用範囲の広い使い方ができるのだ。

OpenLDAPの使い方入門

 OpenLDAPをインストールしてエントリ登録ができただけでは なんだか寂しいので、少し使い方を紹介します。

エントリの検索方法

 OpenLDAPの説明の際、以下のエントリを登録した。  それを検索してみる事にした。
登録したエントリの検索
[suga@ldap]$ ldapsearch -x -LLL -D "cn=manager,dc=company,dc=jp" -W -b "ou=people,dc=company,dc=jp"
Enter LDAP Password: 
dn: ou=People,dc=company,dc=jp
objectClass: organizationalUnit
ou: People

dn: uid=user01,ou=People,dc=company,dc=jp
uid: user01
cn: Test User 01
objectClass: account
objectClass: posixAccount
objectClass: top
userPassword:: e0NSWVBUfW9LYmxGbTVsbDlCaHM=
loginShell: /bin/bash
uidNumber: 5001
gidNumber: 3001
homeDirectory: /home/user01

dn: uid=user02,ou=People,dc=company,dc=jp
uid: user02
cn: Test User 02
objectClass: account
objectClass: posixAccount
objectClass: top
userPassword:: e0NSWVBUfXMueW52SXlSc3E3Yms=
loginShell: /bin/bash
uidNumber: 5002
gidNumber: 3002
homeDirectory: /home/user02

dn: uid=user03,ou=People,dc=company,dc=jp
uid: user03
cn: Test User 03
objectClass: account
objectClass: posixAccount
objectClass: top
userPassword:: e0NSWVBUfThCYzF3V09rT1o2WXc=
loginShell: /bin/bash
uidNumber: 5003
gidNumber: 3003
homeDirectory: /home/user03

[suga@ldap]$ 
登録したエントリの検索・出力を行なう際は、ldapsearchコマンドを使う。
そして認証が行なわれ、認証に問題なければ、結果が出力される。

 ldapsearchコマンドの使い方だが、以下の通りだ。

ldapsearchコマンドの使い方
[suga@ldap]$ ldapsearch -x -LLL -D "cn=manager,dc=company,dc=jp" -W -b "ou=people,dc=company,dc=jp"
Enter LDAP Password: 
dn: ou=People,dc=company,dc=jp
objectClass: organizationalUnit
ou: People

dn: uid=user01,ou=People,dc=company,dc=jp
uid: user01
cn: Test User 01
objectClass: account
objectClass: posixAccount
objectClass: top
userPassword:: e0NSWVBUfW9LYmxGbTVsbDlCaHM=
loginShell: /bin/bash
uidNumber: 5001
gidNumber: 3001
homeDirectory: /home/user01


(以下、省略)
オプションの説明
-x 簡易認証のオプション。
これがない場合は、SASL認証になる。
SASL認証は私は設定した事がないので、わかりません (^^;;
-LLL 検索結果の際、コメントやLDAPのバージョンを表示しない。
-D この後ろに、どのユーザーのDNかが来る。
ここでは管理者権限で検索するため、管理者DNにあたる
cn=Manager,dc=company,dc=jp」が入る。
-W パスワード認証の際、プロンプト上から入力を指定
-b 検索を開始するベースDNの指定を行なう。
ここではユーザーアカウントの中のエントリの検索なので
ユーザーアカウントのDNの"ou=people,dc=company,dc=jp"を指定する


エントリ内容の変更

 登録したエントリの変更・修正を行なう際は、ldapmodifyコマンドを使う。  説明する前に注意点を書きます。
エントリの「変更・修正」の意味合い
(1) エントリ内の属性を増やしたり削除する場合
(2) エントリ内の属性の、属性値の変更

 追加・削除と属性値の変更が入り交じっているので混乱しそうなのだが
追加・変更といっても、エントリそのものを追加・削除するのではないため
エントリ内の変更の範疇に入る。



 まずは(1)のエントリ内の属性の追加を行なってみる。
 ldapmodifyコマンドを使う前に、変更を記述したファイルを用意する必要がある。

modify1.ldif
dn: uid=user01,ou=People,dc=company,dc=jp
changetype: modify
add: description
description: Test user01


dn: uid=user02,ou=People,dc=company,dc=jp
changetype: modify
add: description
description: Test user02


dn: uid=user03,ou=People,dc=company,dc=jp
changetype: modify
add: description
description: Test user03
記述方法
(1) 変更するエントリのDNを記述します。
(2) 赤い部分の、おまじないをつける。
ここは丸写しなのだ。
(3) 追加・削除・変更する属性を記述(青い部分)
ここでは「description」属性を追加するという意味になる。
(4) 属性値の指定(桃色)
ここでは追加する「description」属性の属性値の代入を行なう。

 ファイルが用意できたので、ldapmodifyコマンドを使ってみる。

ldapmodifyコマンドの使い方
[suga@ldap]$ ldapmodify -x -D "cn=Manager,dc=company,dc=jp" -W -f ./modify1.ldif 
Enter LDAP Password: 
modifying entry "uid=user01,ou=People,dc=company,dc=jp"

modifying entry "uid=user02,ou=People,dc=company,dc=jp"

modifying entry "uid=user03,ou=People,dc=company,dc=jp"

[suga@ldap]$ 
オプションの説明
-x 簡易認証のオプション。
これがない場合は、SASL認証になる。
SASL認証は私は設定した事がないので、わかりません (^^;;
-D この後ろに、どのユーザーのDNかが来る。
ここでは管理者権限で検索するため、管理者DNにあたる
cn=Manager,dc=company,dc=jp」が入る。
-W パスワード認証の際、プロンプト上から入力を指定
-f LDIFファイルを読み込むためオプション。

 これで実際にエントリ内の属性が追加されたかどうか確認してみる。

エントリ内の属性が追加された様子
変更前のエントリ
[suga@ldap]$ ldapsearch -x -LLL -D "cn=manager,dc=company,dc=jp" -W -b "ou=people,dc=company,dc=jp"
Enter LDAP Password: 
dn: ou=People,dc=company,dc=jp
objectClass: organizationalUnit
ou: People

dn: uid=user01,ou=People,dc=company,dc=jp
uid: user01
cn: Test User 01
objectClass: account
objectClass: posixAccount
objectClass: top
userPassword:: e0NSWVBUfW9LYmxGbTVsbDlCaHM=
loginShell: /bin/bash
uidNumber: 5001
gidNumber: 3001
homeDirectory: /home/user01


(以下、省略)
変更後のエントリ
[suga@ldap]$ ldapsearch -x -LLL -D "cn=manager,dc=company,dc=jp" -W -b "ou=people,dc=company,dc=jp"
Enter LDAP Password: 
dn: ou=People,dc=company,dc=jp
objectClass: organizationalUnit
ou: People

dn: uid=user01,ou=People,dc=company,dc=jp
uid: user01
cn: Test User 01
objectClass: account
objectClass: posixAccount
objectClass: top
userPassword:: e0NSWVBUfW9LYmxGbTVsbDlCaHM=
loginShell: /bin/bash
uidNumber: 5001
gidNumber: 3001
homeDirectory: /home/user01
description: Test user01

(以下、省略)
変更後、青い部分の「description」属性が追加されている。

 次に(2)の属性値の変更の場合だ。
 変更ファイルは以下の記述になる。

modify2.ldif
dn: uid=user01,ou=People,dc=company,dc=jp
changetype: modify
replace: description
description: Sample user01


dn: uid=user02,ou=People,dc=company,dc=jp
changetype: modify
replace: description
description: Sample user02


dn: uid=user03,ou=People,dc=company,dc=jp
changetype: modify
replace: description
description: Sample user03
記述方法
(1) 変更するエントリのDNを記述します。
(2) 赤い部分の、おまじないをつける。
ここは丸写しなのだ。
(3) 追加・削除・変更する属性を記述(青い部分)
ここでは「description」属性の値を変更するという意味になる。
(4) 属性値の指定(桃色)
ここでは新しい「description」属性の属性値の代入を行なう。

 早速、試してみる。

ldapmodifyコマンドで属性値の変更を行なう
[suga@ldap]$ ldapmodify -x -D "cn=Manager,dc=company,dc=jp" -W -f ./modify2.ldif
Enter LDAP Password: 
modifying entry "uid=user01,ou=People,dc=company,dc=jp"

modifying entry "uid=user02,ou=People,dc=company,dc=jp"

modifying entry "uid=user03,ou=People,dc=company,dc=jp"

[suga@ldap]$ 

 そして変更した値が反映されているかどうか確認してみる。

エントリ内の属性値が変更された様子
変更前のエントリ
[suga@ldap]$ ldapsearch -x -LLL -D "cn=manager,dc=company,dc=jp" -W -b "ou=people,dc=company,dc=jp"
Enter LDAP Password: 
dn: ou=People,dc=company,dc=jp
objectClass: organizationalUnit
ou: People

dn: uid=user01,ou=People,dc=company,dc=jp
uid: user01
cn: Test User 01
objectClass: account
objectClass: posixAccount
objectClass: top
userPassword:: e0NSWVBUfW9LYmxGbTVsbDlCaHM=
loginShell: /bin/bash
uidNumber: 5001
gidNumber: 3001
homeDirectory: /home/user01
description: Test user01


(以下、省略)
変更後のエントリ
[suga@ldap]$ ldapsearch -x -LLL -D "cn=manager,dc=company,dc=jp" -W -b "ou=people,dc=company,dc=jp"
Enter LDAP Password: 
dn: ou=People,dc=company,dc=jp
objectClass: organizationalUnit
ou: People

dn: uid=user01,ou=People,dc=company,dc=jp
uid: user01
cn: Test User 01
objectClass: account
objectClass: posixAccount
objectClass: top
userPassword:: e0NSWVBUfW9LYmxGbTVsbDlCaHM=
loginShell: /bin/bash
uidNumber: 5001
gidNumber: 3001
homeDirectory: /home/user01
description: Sample user01

(以下、省略)
変更前の赤い部分と、変更後の青い部分を見比べると
属性値が変更されたのがわかる。

エントリの削除

 登録されたエントリが不要になった場合の削除方法です。  ldapdeleteコマンドを使う。  まず登録されているエントリを見てみます。
登録したエントリの検索
[suga@ldap]$ ldapsearch -x -LLL -D "cn=manager,dc=company,dc=jp" -W -b "ou=people,dc=company,dc=jp"
Enter LDAP Password: 
dn: ou=People,dc=company,dc=jp
objectClass: organizationalUnit
ou: People

dn: uid=user01,ou=People,dc=company,dc=jp
uid: user01
cn: Test User 01
objectClass: account
objectClass: posixAccount
objectClass: top
userPassword:: e0NSWVBUfW9LYmxGbTVsbDlCaHM=
loginShell: /bin/bash
uidNumber: 5001
gidNumber: 3001
homeDirectory: /home/user01

dn: uid=user02,ou=People,dc=company,dc=jp uid: user02 cn: Test User 02 objectClass: account objectClass: posixAccount objectClass: top userPassword:: e0NSWVBUfXMueW52SXlSc3E3Yms= loginShell: /bin/bash uidNumber: 5002 gidNumber: 3002 homeDirectory: /home/user02

dn: uid=user03,ou=People,dc=company,dc=jp uid: user03 cn: Test User 03 objectClass: account objectClass: posixAccount objectClass: top userPassword:: e0NSWVBUfThCYzF3V09rT1o2WXc= loginShell: /bin/bash uidNumber: 5003 gidNumber: 3003 homeDirectory: /home/user03 [suga@ldap]$
青く囲んだエントリが不要になったので削除してみる事にした。

 さて、エントリ削除の場合、ldapdeleteコマンドが使われる。
 早速、使ってみる事にした。

ldapdeleteコマンドを使ってエントリを削除する
[suga@ldap]$ ldapdelete -x -D "cn=Manager,dc=company,dc=jp" -W "uid=user02,ou=people,dc=company,dc=jp"
Enter LDAP Password: 
[suga@ldap]$ 
記述方法
-x 簡易認証のオプション。
これがない場合は、SASL認証になる。
SASL認証は私は設定した事がないので、わかりません (^^;;
-D この後ろに、どのユーザーのDNかが来る。
ここでは管理者権限で検索するため、管理者DNにあたる
cn=Manager,dc=company,dc=jp」が入る。
-W パスワード認証の際、プロンプト上から入力を指定
赤い部分 消去したいエントリのDN。

 さて、消去コマンドを使った後、エントリがどうなっているのか
見てみる事にした。

エントリの検索結果
[suga@ldap]$ ldapsearch -x -LLL -D "cn=manager,dc=company,dc=jp" -W -b "ou=people,dc=company,dc=jp"
Enter LDAP Password: 
dn: ou=People,dc=company,dc=jp
objectClass: organizationalUnit
ou: People

dn: uid=user01,ou=People,dc=company,dc=jp
uid: user01
cn: Test User 01
objectClass: account
objectClass: posixAccount
objectClass: top
userPassword:: e0NSWVBUfW9LYmxGbTVsbDlCaHM=
loginShell: /bin/bash
uidNumber: 5001
gidNumber: 3001
homeDirectory: /home/user01

dn: uid=user03,ou=People,dc=company,dc=jp
uid: user03
cn: Test User 03
objectClass: account
objectClass: posixAccount
objectClass: top
userPassword:: e0NSWVBUfThCYzF3V09rT1o2WXc=
loginShell: /bin/bash
uidNumber: 5003
gidNumber: 3003
homeDirectory: /home/user03

[suga@ldap]$ 
消去する前は3つあったエントリだが、不要なエントリを消去した事で
出力されるエントリは2つになった。消去成功なのだ。

 ldapadd、ldapmodify、ldapdelete、ldapsearchの基本4つの
コマンドを説明しました。
 他にもコマンドがありますが、ここでは割愛します。

LDAPの応用。メールアドレス帳

 LDAPは、各種情報を盛りこんだ名簿を提供する機能なのだ。  OutlookExpressのアドレス帳を一元管理する事もできる。  そこでアドレス帳になるエントリファイルを用意する。
mailaddress.ldif
dn: uid=user04,ou=People,dc=company,dc=jp
uid: user04
cn: Test User 04
objectClass: inetOrgPerson
objectClass: top
sn: test04
mail: user04@example.com


dn: uid=user05,ou=People,dc=company,dc=jp
uid: user05
cn: Test User 05
objectClass: inetOrgPerson
objectClass: top
sn: test05
mail: user05@example.com

dn: uid=user06,ou=People,dc=company,dc=jp
uid: user06
cn: Test User 06
objectClass: inetOrgPerson
objectClass: top
sn: test06
mail: user06@example.com
オブジェクトクラスが「inetOrgPerson」になっている。
inetorgperson.schemaで定義されています。

特に必須属性はないのだが、メールアドレスの登録ため
「uid」(ユーザーID)、「cn」(名称)、「sn」(姓)と
「mail」(アドレス)に属性値を代入しておく。

 既に、このエントリの受け皿になるユーザーエントリは登録しているので
このエントリも登録する事にした。

エントリの登録
[suga@ldap]$ ldapadd -x -D "cn=Manager,dc=company,dc=jp" -W -f ./mailaddress.ldif
Enter LDAP Password: 
adding new entry "uid=user04,ou=People,dc=company,dc=jp"

adding new entry "uid=user05,ou=People,dc=company,dc=jp"

adding new entry "uid=user06,ou=People,dc=company,dc=jp"

[suga@ldap]$ 

 早速、登録したエントリがアドレス帳になるかどうか
確認してみる事にした。

OutlookExpressを開く
OutlookExpressの画面

 次の操作を行なう。

LDAPサーバーに接続してアドレスを呼び出す設定(1)
LDAPサーバーに接続してアドレスを呼び出す設定(1)
「ツール」の「アカウント」を選択する。

 すると次の画面が出てくる。

LDAPサーバーに接続してアドレスを呼び出す設定(2)
LDAPサーバーに接続してアドレスを呼び出す設定(2)
赤く囲んだ「追加(A)」を選択する。

 すると選択肢が出てくる。

LDAPサーバーに接続してアドレスを呼び出す設定(3)
LDAPサーバーに接続してアドレスを呼び出す設定(3)
ここで「ディレクトリサービス(D)」を選択する。

 するとインターネット接続ウィザード画面が出てくる。
 ここからLDAPサーバーへの接続設定になる。

LDAPサーバーに接続してアドレスを呼び出す設定(4)
LDAPサーバーに接続してアドレスを呼び出す設定(4)
赤く囲んだ部分に、LDAPサーバーのIPアドレスを入力する。

 次に進む。

LDAPサーバーに接続してアドレスを呼び出す設定(5)
LDAPサーバーに接続してアドレスを呼び出す設定(5)
ここは「いいえ」に印をつけて「次へ(N)」を選ぶ。

 これで設定完了だ。

設定完了の画面
設定完了の画面

 でも、ここで設定完了ではないのだ。
 まだ続きがあるのだ。

LDAPサーバーに接続してアドレスを呼び出す設定(6)
LDAPサーバーに接続してアドレスを呼び出す設定(6)
インターネットアカウントの画面で、作成したディレクトリサービスを選択し
赤く囲んだ「プロパティ」を押します。

 するとプロパティ画面が出てきます。

LDAPサーバーに接続してアドレスを呼び出す設定(7)
LDAPサーバーに接続してアドレスを呼び出す設定(6)
ここは何も触らず「詳細設定」を選択する

 すると以下の画面が出てきます。

LDAPサーバーに接続してアドレスを呼び出す設定(8)
LDAPサーバーに接続してアドレスを呼び出す設定(7)
赤く囲んだ検索ベースの部分にユーザーアカウントを検索するための
DNを入力します。ここでは「ou=people,dc=compnay,dc=jp」なのだ。

 これで設定完了だ。


 さて、実際にLDAPサーバーに登録されているアドレスが
閲覧できるかどうか確かめるため、アドレス帳を開いてみる。

LDAPサーバーに接続してアドレスを呼び出す(3)
LDAPサーバーに接続してアドレスを呼び出す(3)
赤く囲んだ「人の検索」を選択する。

 そして検索方法を選択する画面が出てくる。

LDAPサーバーに接続してアドレスを呼び出す(4)
LDAPサーバーに接続してアドレスを呼び出す(4)
今回は、以下のような検索方法を使いました。
赤い囲んだ部分では「電子メールが」を選び
青く囲んだ部分では「次の文字列を含む」を選んだ。

 そして「文字列」を入力します。

LDAPサーバーに接続してアドレスを呼び出す(5)
LDAPサーバーに接続してアドレスを呼び出す(5)
メールアドレスに含まれる文字列をいれます。
今回は「example」を入力します。
そして「追加」のボタンを押して、検索方法の1つにします。

 検索方法が決まった所で、検索を始めます。

LDAPサーバーに接続してアドレスを呼び出す(6)
LDAPサーバーに接続してアドレスを呼び出す(6)
赤く囲んだ「検索開始」を選びます。

 すると検索結果が出力された。

アドレスが出力された様子アドレスが出力された様子
アドレスが出力された様子
見事にLDAPサーバーに登録したメールアドレスが出てきた。
メーラーのメールアドレス帳としてLDAPサーバーが使える事がわかる。


 LDAPを活用したメールアドレス帳。
 オ−プンソースWebメールのスケーリックス(Scalix)でも採用されている、
 scalixについては「システム奮闘記:その87」(scalix入門 導入と設定)
をご覧ください。


OpenLDAPのソースコンパイル

 最近、CentOSを触っているため、RPM形式のファイルを使って ソフトのインストールを行なうようになった。  だが、普遍性を高めるには  ソースコンパイルでのインストールは重要なのらー!!  RPMばかりに頼ると、ライブラリ依存の話も忘れたりする。  そこでソースコンパイルでのインストールも行なってみる事にした。

ソースコンパイルでLDAPサーバー構築

 早速、OpenLDAPのサイトからダウンロードする。  最新版は2.4.23(2011/1/25現在)だった。なんと・・・  私の誕生日に出ているのだ!!  2010年7月19日リリースなのだ。妙な縁を感じてしまいそうだ。  早速、展開してみる。
展開している様子
[root@ldap]# tar xvfz openldap-stable-20100719.tgz 
openldap-2.4.23/
openldap-2.4.23/doc/
openldap-2.4.23/ANNOUNCEMENT
openldap-2.4.23/CHANGES
openldap-2.4.23/COPYRIGHT
openldap-2.4.23/INSTALL


(途中、省略)


openldap-2.4.23/doc/man/man1/ldapmodrdn.1
openldap-2.4.23/doc/man/man1/ldappasswd.1
openldap-2.4.23/doc/man/man1/ldapsearch.1
openldap-2.4.23/doc/man/man1/ldapurl.1
openldap-2.4.23/doc/man/man1/ldapwhoami.1
[root@ldap]# 

 そしてコンパイルのため、該当のディレクトリに入る。

展開した先のディレクトリに入る
[root@ldap]# cd openldap-2.4.23/
[root@ldap]# ls
ANNOUNCEMENT  INSTALL      README      clients       contrib  libraries
CHANGES       LICENSE      aclocal.m4  configure     doc      servers
COPYRIGHT     Makefile.in  build       configure.in  include  tests
[root@ldap]# 
configureファイルがあるので、インストールは簡単そうに思えた。

 早速、configureファイルを動かして、コンパイルを行なうための
Makefileを生成する。

configureを動かしてみる
[root@ldap]# ./configure --enable-crypt --with-tls --enable-wrappers
Configuring OpenLDAP 2.4.23-Release ...
checking build system type... i686-pc-linux-gnu
checking host system type... i686-pc-linux-gnu
checking target system type... i686-pc-linux-gnu


(途中、省略)


checking db.h usability... yes
checking db.h presence... yes
checking for db.h... yes
checking for Berkeley DB major version in db.h... 4
checking for Berkeley DB minor version in db.h... 3
checking if Berkeley DB version supported by BDB/HDB backends... no
configure: error: BerkeleyDB version incompatible with BDB/HDB backends
[root@ldap]# 
青い部分は発生したエラー内容だ。そして処理は中断となった。

 なんでコケるねん!!

 ちょっと調べてみると、同じエラーの対処方法を書いた
サイトを発見した。
 あるシステム管理者の日常


 どうやらコンパイルに必要なBerkeleyDBのバージョンと
Linux上に入っているDBのバージョンが異なるのだ。

 OpenLDAP-2.4.23に必要なBekeleyDBのバージョンは
READMEにも書いていた。

READMEの中身を一部抜粋
 SLAPD:
     BDB and HDB backends require Oracle Berkeley DB 4.4, 4.5,
     4.6, 4.7, or 4.8.  It is highly recommended to apply the
     patches from Oracle for a given release.
バージョンが4.4から4.8までのを使う必要があるというのだ。

 コンパイルした環境(CentOS5.4)に入っているBerkeleyDBの
バージョンを確認してみた。

CentOS5.4にインストールされているBerkeleyDBのバージョン
[root@ldap]# rpm -iq db4
Name        : db4                          Relocations: (not relocatable)
Version     : 4.3.29                            Vendor: CentOS
Release     : 10.el5                        Build Date: 2009年09月20日 11時06分43秒
Install Date: 2011年01月18日 10時11分12秒      Build Host: builder16.centos.org
Group       : System Environment/Libraries   Source RPM: db4-4.3.29-10.el5.src.rpm
Size        : 2125026                          License: GPL
Signature   : DSA/SHA1, 2009年09月20日 12時53分28秒, Key ID a8a447dce8562897
URL         : http://www.sleepycat.com/
Summary     : C 用の Berkeley DB データベースライブラリ (バージョン 4)
Description :
Berkeley Database (Berkeley DB) は、プログラム可能なツールキットで、
従来のアプリケーションとクライアント/サーバーアプリケーションの両方に対し、
組込みデータベースを提供します。  Berkeley DB には、B+tree、
拡張線形ハッシュ、固定長、および可変長レコードのアクセスメソッドと
トランザクションが収録されており、ロック、ログ作成、共有メモリのキャッシング、
データベースの復旧を行います。 Berkeley DB は、C、C++、Java、Perl API を
サポートしています。  このデータベースは、Python や Perl などの多数の
アプリケーションで使用されているため、すべてのシステムにインストールする
必要があります。
[root@ldap]# 
CentOS5.4には、BekeleyDBのバージョン4.3.29が入っている。

 バージョンが合わへんやん!!

 CentOS5.4にはBerkeleyDBは4.3系で、OpenLDAP-2.4.23に必要なのは
4.4以上なのだ。

 BerkeleyDBもインストールせんとアカンの・・・

 ここでberkeleyDBの4.8系をダウンロードする事にした。
  Oracle Berkeley DB ダウンロード

 そしてソースの展開を行なう。

BerkeleyDBの展開
[root@ldap]# tar xvfz db-4.8.30.tar.gz 
db-4.8.30/
db-4.8.30/btree/
db-4.8.30/btree/bt_compress.c
db-4.8.30/btree/bt_compact.c
db-4.8.30/btree/bt_compare.c
db-4.8.30/btree/btree_autop.c


(途中、省略)


db-4.8.30/txn/txn_rec.c
db-4.8.30/txn/txn_region.c
db-4.8.30/txn/txn_stat.c
db-4.8.30/txn/txn_util.c
[root@ldap]# 

 そして展開した先のディレクトリを見てみる。

db-4.8.30を展開した先
[root@ldap]# cd db-4.8.30
[root@ldap]# ls
LICENSE        db185          dbinc_auto       hsearch       perl
README         db_archive     dbm              java          php_db4
btree          db_checkpoint  dbreg            libdb_csharp  qam
build_brew     db_deadlock    dist             libdb_java    rep
build_s60      db_dump        docs             lock          repmgr
build_unix     db_dump185     docs_src         log           sequence
build_vxworks  db_hotbackup   env              mod_db4       stl
build_wince    db_load        examples_c       mp            tcl
build_windows  db_printlog    examples_csharp  mutex         test
clib           db_recover     examples_cxx     os            test_micro
common         db_sql         examples_java    os_brew       test_stl
crypto         db_stat        examples_stl     os_qnx        txn
csharp         db_upgrade     fileops          os_s60
cxx            db_verify      hash             os_vxworks
db             dbinc          hmac             os_windows
[root@ldapx]# 

 configureファイルがあらへんやん!!

 それだけでない。Makefileファイルがないのだ。
 これでは、コンパイルができないではないか。

 でも、READMEにヒントが隠されていた。

READMEの内容
Berkeley DB 4.8.30: (April  9, 2010)

This is version 4.8.30 of Berkeley DB from Oracle.  To view release and
installation documentation, load the distribution file docs/index.html
into your web browser.
赤く色づけしたファイル名にコンパイルの仕方が書いてあった。

 docs/index.htmlファイルをブラウザで見ながら
その通りにやってみる事にした。

 まずは、docsディレクトリの中でconfigureを使うというのだ。

docsディレクトリからconfigureを行なう
[root@ldap docs]# ../dist/configure --prefix=/usr
checking build system type... i686-pc-linux-gnu
checking host system type... i686-pc-linux-gnu
checking if building in the top-level or dist directories... no
checking if --disable-cryptography option specified... no


(途中、省略)


config.status: creating clib_port.h
config.status: creating include.tcl
config.status: creating db.h
config.status: creating db_config.h
config.status: executing libtool commands
[root@ldap docs]# 
赤い部分は動かすconfigureの相対パスを指定。
青い部分はオプションだ。既存のBerkeleyDBを上書きするため
インストール先のディレクトリを /usrに指定した。

 もし、これをconfigureがあるdistディレクトリで行なうと
エラーが出る。

もし、configureがあるdistディレクトリで行なう
[root@ldap dist]# ./configure --prefix=/usr
checking build system type... i686-pc-linux-gnu
checking host system type... i686-pc-linux-gnu
checking if building in the top-level or dist directories... yes
configure: error: Berkeley DB should not be built in the top-level or "dist" directories. Change directory to the build_unix directory and run ../dist/configure from there.
[root@ldap dist]# 
赤い部分はエラーの内容だ。

 次にコンパイル作業だ。これもdocsディレクトリ上で行なう。

コンパイルとインストールを同時に行なう
(make installを行なう)
[root@ldap docs]# make install
./libtool --mode=compile cc -c -I. -I../dist/..  -D_GNU_SOURCE -D_REENTRANT -O3  ../dist/../mutex/mut_tas.c
libtool: compile:  cc -c -I. -I../dist/.. -D_GNU_SOURCE -D_REENTRANT -O3 ../dist/../mutex/mut_tas.c  -fPIC -DPIC -o .libs/mut_tas.o
libtool: compile:  cc -c -I. -I../dist/.. -D_GNU_SOURCE -D_REENTRANT -O3 ../dist/../mutex/mut_tas.c -o mut_tas.o >/dev/null 2>&1


(途中、省略)


libtool: install: cp -p .libs/db_verify /usr/local/BerkeleyDB.4.8/bin/db_verify
Installing documentation: /usr/local/BerkeleyDB.4.8/docs ...
[root@ldap docs]# 
コンパイルとインストールに成功した。

 さて、BerkeleyDBが上書きされたかどうか確認してみる。

BerkeleyDBのバージョン確認
(/usr/libディレクトリ)
コンパイル前
[suga@ldap]$ ls -l | grep libdb
-rw-r--r--   1 root root  1354212  9月 20  2009 libdb-4.3.a
-rw-r--r--   1 root root      800  9月 20  2009 libdb-4.3.la
lrwxrwxrwx   1 root root       22 12月 15 15:33 libdb-4.3.so -> ../../lib/libdb-4.3.so
lrwxrwxrwx   1 root root       22 12月 15 15:36 libdb.so -> ../../lib/libdb-4.3.so
-rw-r--r--   1 root root  1487126  9月 20  2009 libdb_cxx-4.3.a
-rw-r--r--   1 root root      828  9月 20  2009 libdb_cxx-4.3.la
-rwxr-xr-x   1 root root  1109436  9月 20  2009 libdb_cxx-4.3.so
lrwxrwxrwx   1 root root       16 12月 15 15:36 libdb_cxx.so -> libdb_cxx-4.3.so
lrwxrwxrwx   1 root root       23 12月 15 15:40 libdbus-glib-1.so.2 -> libdbus-glib-1.so.2.1.0
-rwxr-xr-x   1 root root   120028  1月 21  2009 libdbus-glib-1.so.2.1.0
[suga@ldap]$ 
コンパイル後
[suga@ldap]$ ls -l | grep libdb
-rw-r--r--   1 root root  1354212  9月 20  2009 libdb-4.3.a
-rw-r--r--   1 root root      800  9月 20  2009 libdb-4.3.la
lrwxrwxrwx   1 root root       22  1月 18 10:11 libdb-4.3.so -> ../../lib/libdb-4.3.so
-rw-r--r--   1 root root  1881032  1月 25 17:20 libdb-4.8.a
-rw-r--r--   1 root root      927  1月 25 17:20 libdb-4.8.la
-rwxr-xr-x   1 root root  1541092  1月 25 17:20 libdb-4.8.so
lrwxrwxrwx   1 root root       12  1月 25 17:20 libdb-4.so -> libdb-4.8.so
-rw-r--r--   1 root root  1881032  1月 25 17:20 libdb.a
lrwxrwxrwx   1 root root       12  1月 25 17:20 libdb.so -> libdb-4.8.so
-rw-r--r--   1 root root  1487126  9月 20  2009 libdb_cxx-4.3.a
-rw-r--r--   1 root root      828  9月 20  2009 libdb_cxx-4.3.la
-rwxr-xr-x   1 root root  1109436  9月 20  2009 libdb_cxx-4.3.so
lrwxrwxrwx   1 root root       23  1月 18 10:18 libdbus-glib-1.so.2 -> libdbus-glib-1.so.2.1.0
-rwxr-xr-x   1 root root   120028  1月 21  2009 libdbus-glib-1.so.2.1.0
[suga@ldap]$ 
青い部分は静的ライブラリ。すっかり上書きされた。
赤い部分は共有ライブラリで、リンクが張り直された状態だ。

 すっかり上書きされた。
 でも、原型が残っているため、不具合が起こった場合でも
元に戻すのは簡単だ。

BerkeleyDBの更新について
BerkeleyDBのバージョンをあげたが、この共有ライブラリに依存している
ソフトはあるため、場合によっては不具合が生じる可能性もあります。

不具合が生じても私は一切、責任は負えないので、自己責任でお願いします。


 さて、BerkeleyDB-4.8のインストールが成功したので
OpenLDAPのインストールを再開する。

OpenLDAPのインストール手順

 まずは、configureを行なう。
configureを行なう
[root@ldap]# ./configure --enable-crypt --with-tls --enable-wrappers
Configuring OpenLDAP 2.4.23-Release ...
checking build system type... i686-pc-linux-gnu
checking host system type... i686-pc-linux-gnu
checking target system type... i686-pc-linux-gnu
checking for a BSD-compatible install... /usr/bin/install -c
checking whether build environment is sane... yes


(途中、省略)


    Add bdb ...
    Add hdb ...
    Add relay ...
Making servers/slapd/overlays/statover.c
    Add syncprov ...
Please run "make depend" to build dependencies
[root@ldap]# 
青い部分が、configureのオプションだ。
「--enable-crypt」はパスワードの暗号化を有効にする。
「--with-tls」はTLS/SSLによる暗号化通信を有効にする
「--enable-wrappers」は、TCP-Wrapperを有効にする。

1番目以外は、使いそうもないが、本に書いてあった
ソースコンパイルの方法にはあったので
おまじないとして付けてみた (^^)

 次に「make depend」を行なう。
 Makefileファイルにおいて、依存関係を生成するというのだ。
 わかった風な書き方をしたのだが、知ったかぶりをしても
ボロが出るのは確実なので、ここは正直に・・・

 イマイチ、わかりませーん (^^)

 なのだ。
 でも、ここで足踏みしている余裕はないので、忍法「先送りの術」で
調べる事は先送りして、前に進む。

make dependを行なう
[root@ldap]# make depend
Making depend in /usr/local/src/openldap-2.4.23
  Entering subdirectory include
make[1]: ディレクトリ `/usr/local/src/openldap-2.4.23/include' に入ります
Making ldap_config.h
make[1]: ディレクトリ `/usr/local/src/openldap-2.4.23/include' から出ます
 
  Entering subdirectory libraries


(途中、省略)


make[3]: `depend' に対して行うべき事はありません.
make[3]: ディレクトリ `/usr/local/src/openldap-2.4.23/doc/man/man8' から出ます
 
make[2]: ディレクトリ `/usr/local/src/openldap-2.4.23/doc/man' から出ます
 
make[1]: ディレクトリ `/usr/local/src/openldap-2.4.23/doc' から出ます
 
[root@ldap]# 
これでコンパイルを行なうためのファイル(Makefile)が生成できた。

 いよいよコンパイルだ。

makeを行なう
[root@ldap]# make
Making all in /usr/local/src/openldap-2.4.23
  Entering subdirectory include
make[1]: ディレクトリ `/usr/local/src/openldap-2.4.23/include' に入ります
make[1]: `all' に対して行うべき事はありません.


(途中、省略)


make[3]: ディレクトリ `/usr/local/src/openldap-2.4.23/doc/man/man8' から出ます
 
make[2]: ディレクトリ `/usr/local/src/openldap-2.4.23/doc/man' から出ます
 
make[1]: ディレクトリ `/usr/local/src/openldap-2.4.23/doc' から出ます
 
[root@ldap2 openldap-2.4.23]# 
無事、コンパイルが終了した。

 さて、コンパイルした物をインストールだ。
 「make install」を行なう。

make install を行なう
[root@ldap]# make install
Making all in /usr/local/src/openldap-2.4.23
  Entering subdirectory include
make[1]: ディレクトリ `/usr/local/src/openldap-2.4.23/include' に入ります
make[1]: `all' に対して行うべき事はありません.
make[1]: ディレクトリ `/usr/local/src/openldap-2.4.23/include' から出ます


(途中、省略)


make[3]: ディレクトリ `/usr/local/src/openldap-2.4.23/doc/man/man8' から出ます
 
make[2]: ディレクトリ `/usr/local/src/openldap-2.4.23/doc/man' から出ます
 
make[1]: ディレクトリ `/usr/local/src/openldap-2.4.23/doc' から出ます
 
[root@ldap]# 

 これでOpenLDAP-2.4.23のインストールが完了した。

実際に稼働させてみる

 インストールした物が、問題なく動くかどうかの確認を行なってみる。  設定ファイル、コマンド、ライブラリなどのディレクトリは CentOS系で、RPMでインストールした場合とは異なるので注意が必要だ。  まずは設定ファイルの slapd.confファイルを触る。  ディレクトリは /usr/local/etc だ。
/usr/local/lib/exec/sldapd を触る
#######################################################################
# BDB database definitions
#######################################################################

database        bdb
suffix          "dc=my-domain,dc=com"
rootdn          "cn=Manager,dc=my-domain,dc=com"
# Cleartext passwords, especially for the rootdn, should
# be avoid.  See slappasswd(8) and slapd.conf(5) for details.
# Use of strong authentication encouraged.
rootpw          secret
# The database directory MUST exist prior to running slapd AND 
# should only be accessible by the slapd and slap tools.
# Mode 700 recommended.
directory       /usr/local/var/openldap-data
# Indices to maintain
index   objectClass     eq
今回は、実験のため、初期設定のまま使う事にした。
なので、どこも触らない事にした (^^)

 これで準備は完了したので、LDAPのデーモンを起動させる。

LDAPデーモンを起動させる
[root@ldap]# /usr/local/libexec/slapd start
[root@ldap]# 
[root@ldap]# ps aux | grep slapd
root     12901  0.0  0.8  16416  4140 ?        Ssl  17:36   0:00 /usr/local/libexec/slapd start
root     12904  0.0  0.1   4984   756 pts/2    R+   17:36   0:00 grep slapd
[root@ldap]# 
赤い部分はデーモンの起動。

青い部分はデーモンが稼働しているかどうかを確かめるため
稼働中のプロセスを見るコマンドを実行。

桃色はLDAPデーモンが稼働しているという表示だ。

 LDAPデーモンが稼働しているのが確認できたので、
実際にエントリの登録を行なってみる。

 そこでエントリ登録のためのLDIFファイルを用意する。

エントリ登録ファイル (init.ldif)
dn: dc=my-domain,dc=com
objectClass: dcObject
objectClass: organization
o: myorganization
dc: my-domain

dn: cn=Manager,dc=my-domain,dc=com
objectClass: organizationalRole
cn: Manager

dn: ou=People,dc=my-domain,dc=com
objectClass: organizationalUnit
ou: People

dn: ou=Group,dc=my-domain,dc=com
objectClass: organizationalUnit
ou: Group

 早速、登録してみる。

エントリファイルの登録
[root@ldap]# /usr/local/bin/ldapadd -x -D "cn=Manager,dc=my-domain,dc=com" -W -f ./init.ldif
Enter LDAP Password: 
adding new entry "dc=my-domain,dc=com"

adding new entry "cn=Manager,dc=my-domain,dc=com"

adding new entry "ou=People,dc=my-domain,dc=com"

adding new entry "ou=Group,dc=my-domain,dc=com"

[root@ldap]# 
問題なく登録できた。

 そして登録したエントリを検索コマンドを使って、出力してみる。

登録したエントリを検索コマンドを使って、出力してみる
[suga@ldap]$ /usr/local/bin/ldapsearch -x -LLL -b "dc=my-domain,dc=com" "(objectClass=*)"
dn: dc=my-domain,dc=com
objectClass: dcObject
objectClass: organization
o: myorganization
dc: my-domain

dn: cn=Manager,dc=my-domain,dc=com
objectClass: organizationalRole
cn: Manager

dn: ou=People,dc=my-domain,dc=com
objectClass: organizationalUnit
ou: People

dn: ou=Group,dc=my-domain,dc=com
objectClass: organizationalUnit
ou: Group

[suga@ldap]$ 
出力が問題なくできた。

 どうやらソースコンパイルは成功したのだ。


 だが、LDAPサーバーとして稼働させるのが最終目的なので
クライアントからLDAPサーバーが使えるかどうかの確認も必要だ。

 そこで以下の実験を行なってみる。

LDAPサーバーの稼働実験の概略
クライアントからコマンド操作
クライアント(Linux)からLDAPサーバーへコマンドを送ってみて
出力結果が返ってくるかどうか、確認してみる事にした。

 早速、実験してみる事にした。

LDAPサーバーの動作確認実験
[suga@client]$ ldapsearch -h 192.168.X.Y -x -LLL -b "dc=my-domain,dc=com" "(objectClass=*)"
dn: dc=my-domain,dc=com
objectClass: dcObject
objectClass: organization
o: myorganization
dc: my-domain

dn: cn=Manager,dc=my-domain,dc=com
objectClass: organizationalRole
cn: Manager

dn: ou=People,dc=my-domain,dc=com
objectClass: organizationalUnit
ou: People

dn: ou=Group,dc=my-domain,dc=com
objectClass: organizationalUnit
ou: Group

[suga@client]$ 
見事にLDAPサーバーにあるエントリ情報を出力できた。

 これでバッチリだ!! (^^)

 ソースコンパイルも問題なく動いたので、仮にCentOS以外の環境で
OpenLDAPの設定を行なう機会があっても、あまり動じなくなった。
 でも、ソースコンパイルの際に、コケると、どうしようもないが (^^;;


 あとは、BerkeleyDBのライブラリの上書きをした場合の
ライブラリの依存性の問題も出てくる。

 安易にソースコンパイルができたからといって、手放しで喜べないのだ。

まとめ  今回はLDAPでユーザー管理の一元化ができないかと考え OpenLDAPを触ってみました。  OpenLDAPインストール入門と、ちょっとした操作方法の紹介なので 物足らないと感じる方もおられると思います。  実際に社内での活用例がないためです。  良い活用方法は、今後、見つけていきたいと思います。  あと、OpenLDAPの話には続きがあります。  今回の話は「Samba + OpenLDAP」の話につなげるための第一段階という 位置付けの意味合いもあります。  そこで、第2段階のSambaでNTドメイン構築の話を 「システム奮闘記:その91」で取り上げています。

次章:「SambaでPDC構築入門」を読む
前章:「xenserverの運用・管理」を読む
目次:システム奮闘記に戻る

Tweet