AnsibleでOpenLDAP環境構築 -②管理者DNの設定の次は組織(ou)/グループ(cn)の設定。
LDAP構築 まとめの例にならい、
組織(ou)⇒ people,group
グループ(cn) ⇒ ldapmanager
グループID(gidNumber)⇒ 1001
とする。
■組織(ou)/グループ(cn)設定用playbook
以下の内容でplaybookを作成してみた。
[root@ansible_sv ~]# vi /etc/ansible/yml/3_groupadd.yml 1- hosts: ldap_sv 2 remote_user: root 3 4 tasks: 5 - name: add schema 6 shell: > 7 ldapadd -Y EXTERNAL -H ldapi:/// -f /etc/openldap/schema/cosine.ldif; 8 ldapadd -Y EXTERNAL -H ldapi:/// -f /etc/openldap/schema/nis.ldif 9 10 - name: install ldap devel 11 yum: name=gcc,python-devel,openldap-devel state=latest 12 13 - name: install pip 1 14 shell: curl -kL https://bootstrap.pypa.io/get-pip.py | python 15 16 - name: install pip 2 17 pip: 18 name: python-ldap 19 20 - name: baseDN objectClass 21 ldap_entry: 22 dn: dc=abc,dc=def,dc=com 23 state: present 24 server_uri: ldap://localhost/ 25 bind_dn: cn=Manager,dc=abc,dc=def,dc=com 26 bind_pw: manager 27 objectClass: 28 - dcObject 29 - organization 30 attributes: 31 dc: abc 32 o: AbcDef Inc. 33 34 - name: People objectClass 35 ldap_entry: 36 dn: ou=People,dc=abc,dc=def,dc=com 37 state: present 38 server_uri: ldap://localhost/ 39 bind_dn: cn=Manager,dc=abc,dc=def,dc=com 40 bind_pw: manager 41 objectClass: organizationalUnit 42 attributes: 43 ou: People 44 45 - name: Group objectClass 46 ldap_entry: 47 dn: ou=Group,dc=abc,dc=def,dc=com 48 state: present 49 server_uri: ldap://localhost/ 50 bind_dn: cn=Manager,dc=abc,dc=def,dc=com 51 bind_pw: manager 52 objectClass: organizationalUnit 53 attributes: 54 ou: Group 55 56 - name: cn objectClass 57 ldap_entry: 58 dn: cn=ldapmanager,ou=Group,dc=abc,dc=def,dc=com 59 state: present 60 server_uri: ldap://localhost/ 61 bind_dn: cn=Manager,dc=abc,dc=def,dc=com 62 bind_pw: manager 63 objectClass: 64 - top 65 - posixGroup 66 attributes: 67 cn: ldapmanager 68 gidNumber: 1001
以下、各モジュールの説明。
hosts:(1行目)
処理を実行する対象ホストを指定。「ldap_sv」は/etc/ansible/hostsに記述したホスト名となる。
remote_user:(2行目)
hosts:で指定したホストで処理を実行する際に、どのユーザで処理を実行するかを指定。上記の例では先頭の階層に記述しているため、それ以降の全階層において適用される。
tasks:(7行目)
処理の内容を、tasks:以降に記述する。tasks:を記述しないとエラーになるので注意。
name:(5、10、13、16、20、34、45、56行目)
ansible-playbookコマンドを実行した際に、実行結果に出力させる文字列を指定する。
shell:(6、14行目)
linuxコマンドを直接指定できる。類似モジュールで「command:」もあるが、shellは複数行記述できる。
yum:(11行目)
yumコマンドを実行する。その際にモジュール引数というオプションのようなものを指定することができる。
モジュール引数 | 条件 | 説明 |
---|---|---|
name= | – | yumでインストールしたいパッケージ名を指定する。 |
state= | present | パッケージがインストールされていなければインストールを行い、既にインストール済みの場合は何も行わない。 |
latest | パッケージがインストールされていなければ最新版をインストールし、既にインストールされていれば最新版に更新する。 | |
absent | パッケージがインストールされていればアンインストールし、インストールされていなければ何も行わない。 |
pip:(17行目)
pipコマンドでパッケージをインストールする。ldap系モジュールを使用できるようにするため、yumモジュールで開発系パッケージをインストールしたあと、python-ldapのインストールも必要。ansibleがpythonベースに開発されている名残だろうか。(安直な憶測m(__)m)
特殊なモジュールのため、詳細は公式ページを参照。
ldap_entry:(20行目)
ldap関連モジュール。ldap_attrやldap_sert,ldap_searchがある。詳細はansible公式ページのldap関連もしくはGitHubを参照。
モジュール引数 | 条件 | 説明 |
---|---|---|
dn: | 登録するベースDN(本稿ではdc=abc,dc=def,dc=com)を指定する。 | |
state: | present | ベースDN/組織/グループ/ユーザを設定するときに指定する。 |
absent | ベースDN/組織/グループ/ユーザを削除するときに指定する。 | |
server_uri: | OpenLDAPサーバのURLを「ldap://<OpenLDAPサーバのIPアドレス>」という記述で指定する。 | |
bind_dn: | 設定/削除する際にバインド(認証)する管理者DN(本稿では「cn=Manager,dc=abc,dc=def,dc=com」)を指定する。 | |
bind_pw: | 設定/削除する際にバインド(認証)する管理者パスワード(本稿では「manager」)を指定する。 | |
objectClass: | ベースDN/組織/グループ/ユーザに対し、設定/削除するオブジェクトクラスを指定する。オブジェクトクラスの記述の前に「‐」をつけて、複数指定することも可能。その際にオブジェクトクラスや属性の継承関係やスキーマの有無などは事前に確認すべし。 | |
attributes: | ベースDN/組織/グループ/ユーザに対し、設定/削除する属性を指定する。属性は「dc:」「o:」のように、実際にスキーマに登録されているものを指定する。にオブジェクトクラスや属性の継承関係やスキーマの有無などは事前に確認すべし。 |
ldap系モジュールを使用するにあたって
5~13行目を見ると、yumで開発系パッケージをOpenLDAPサーバ側にインストールするように記述している。ldap系モジュールは特殊で、OpenLDAPサーバ側がldap系モジュールの処理があることをちゃんと認識するために、事前にこれらのインストールが必要となる。
※※※注意点※※※
7、8行目にldapaddコマンドでスキーマの登録を行っているが、どうやら順序があるようで、先にcosine.ldifを登録しないとnis.ldifが登録できず、ansibleの実行結果上もエラーが出てくる。以下、失敗したパターンだがエラーの内容を見ると
PLAY [ldap_sv] ************************************************************************************************************ TASK [Gathering Facts] **************************************************************************************************** ok: [192.168.3.6] TASK [add schema] ********************************************************************************************************* fatal: [192.168.3.6]: FAILED! => {"changed": true, "cmd": "ldapadd -Y EXTERNAL -H ldapi:/// -f /etc/openldap/schema/nis.ldif", "delta": "0:00:00.031096", "end": "2018-01-22 19:05:27.590789", "msg": "non-zero return code", "rc": 80, "start": "2018-01-22 19:05:27.559693", "stderr": "SASL/EXTERNAL authentication started\nSASL username: gidNumber=0+uidNumber=0,cn=peercred,cn=external,cn=auth\nSASL SSF: 0\nldap_add: Other (e.g., implementation specific) error (80)\n\tadditional info: olcObjectClasses: AttributeType not found: \"manager\"", "stderr_lines": ["SASL/EXTERNAL authentication started", "SASL username: gidNumber=0+uidNumber=0,cn=peercred,cn=external,cn=auth", "SASL SSF: 0", "ldap_add: Other (e.g., implementation specific) error (80)", "\tadditional info: olcObjectClasses: AttributeType not found: \"manager\""], "stdout": "adding new entry \"cn=nis,cn=schema,cn=config\"", "stdout_lines": ["adding new entry \"cn=nis,cn=schema,cn=config\""]}
赤文字の一部分に「olcObjectClasses: AttributeType not found」というのがある。スキーマ登録時にもオブジェクトクラスと属性の関係をチェックしているようだ。(登録していないオブジェクトクラスに紐づく属性を使おうとするときに出るエラー)
スキーマ登録を行う場合は、この点注意しておくべし。
■ansible-playbookコマンドでplaybookを実行
いよいよansibleの実行。コマンドは
# ansible-playbook <playbook名(フルパス)>
[root@ansible_sv ~]# ansible-playbook /etc/ansible/yml/3_groupadd.yml SSH password: PLAY [ldap_sv] ************************************************************************************************************ TASK [Gathering Facts] **************************************************************************************************** ok: [192.168.3.6] TASK [add schema] ********************************************************************************************************* changed: [192.168.3.6] TASK [install ldap devel] ************************************************************************************************* changed: [192.168.3.6] TASK [install pip 1] ****************************************************************************************************** [WARNING]: Consider using get_url or uri module rather than running curl changed: [192.168.3.6] TASK [install pip 2] ****************************************************************************************************** changed: [192.168.3.6] TASK [baseDN objectClass] ************************************************************************************************* changed: [192.168.3.6] TASK [People objectClass] ************************************************************************************************* changed: [192.168.3.6] TASK [Group objectClass] ************************************************************************************************** changed: [192.168.3.6] TASK [cn objectClass] ***************************************************************************************************** changed: [192.168.3.6] PLAY RECAP **************************************************************************************************************** 192.168.3.6 : ok=9 changed=8 unreachable=0 failed=0 [root@ansible_sv ~]#
install pip 1のタスク部分で、ピンクの文字で「[WARNING]: Consider using get_url or uri module rather than running curl」というのが出てきた。これはエラーではないが、記述しているコマンドより推奨するモジュールがあるよ!というときに出てくる。念のため標準の手順はcurlコマンドのようなので、ここではcurlコマンドにしておく。
ということで、いけました\(^o^)/
実行結果の説明はAnsibleでOpenLDAP環境構築 -①OpenLDAPサーバ関連のパッケージインストールを参照。
■OpenLDAPサーバで事後確認
念のためansible-playbookコマンドで実行したplaybookの内容がOpenLDAPサーバにちゃんと反映されたか確認。
ここで事後確認するポイントは、playbookに沿って以下。
・yumやpipでインストールしたパッケージがちゃんと入っていること。
・組織(ou)/グループ(cn)が登録されていること。(ldapsearchコマンドで確認)
[root@ldapserver ~]# rpm -aq | grep gcc gcc-4.8.5-16.el7_4.1.x86_64 libgcc-4.8.5-16.el7_4.1.x86_64 [root@ldapserver ~]# rpm -aq | grep python-devel python-devel-2.7.5-58.el7.x86_64 [root@ldapserver ~]# rpm -aq | grep openldap-devel openldap-devel-2.4.44-5.el7.x86_64 [root@ldapserver ~]# pip freeze configobj==4.7.2 decorator==3.4.0 iniparse==0.4 perf==0.1 pycurl==7.19.0 pygobject==3.22.0 pygpgme==0.3 pyliblzma==0.5.3 python-ldap==2.5.2 python-linux-procfs==0.4.9 pyudev==0.15 pyxattr==0.5.1 schedutils==0.4 slip==0.4.0 slip.dbus==0.4.0 SSSDConfig==1.15.2 urlgrabber==3.10 yum-metadata-parser==1.1.4 [root@ldapserver ~]#
パッケージ類は大丈夫そう。ちなみに「pip freeze」コマンドは実行したサーバに現状入っているpythonパッケージを表示させるもの。
[root@ldapserver ~]# ldapsearch -LLL -Y EXTERNAL -H ldapi:/// -b 'dc=abc,dc=def,dc=com' '(objectClass=*)' SASL/EXTERNAL authentication started SASL username: gidNumber=0+uidNumber=0,cn=peercred,cn=external,cn=auth SASL SSF: 0 dn: dc=abc,dc=def,dc=com objectClass: dcObject objectClass: organization dc: abc o: AbcDef Inc. dn: ou=People,dc=abc,dc=def,dc=com objectClass: organizationalUnit ou: People dn: ou=Group,dc=abc,dc=def,dc=com objectClass: organizationalUnit ou: Group dn: cn=ldapmanager,ou=Group,dc=abc,dc=def,dc=com objectClass: top objectClass: posixGroup gidNumber: 1001 cn: ldapmanager [root@ldapserver ~]#
ldapsearchコマンドでオブジェクトクラスをワイルドカードで検索してみた。組織(ou)にPeople、Groupがあり、グループ(cn)にldapmanagerができている。
組織/グループのplaybookも成功!