Ansibleを使い始めようと思ったのだが、Web上のチュートリアルは、やや古かったり、やたらとたくさんのディレクトリやファイルを作らせたりと、Ansibleの特徴とされているシンプルさが感じられず、うんざりしたのでこの記事をまとめています。触り始めたばかりのため、もし誤りがあればご指摘いただけると幸いです。
1. はじめに
Ansibleとは?
この辺の情報はWebにいくらでもあるので、簡単に。。。
- Python製の構成管理ツールです。(「IT自動化ツール」というように、より汎用性を強調した説明もちらほら見かける)
- 似たようなツールとしては、ChefやPuppet、Itamaeなどがあります。
- スクリプトはyamlで書くので、Pythonの知識は必要ありません。
- シンプルで習得が容易であることがその特徴の一つとされています。(多分ChefやShellと比べて言ってるんだと思う)
用語の解説
まずはこの4つだけ頭に入れておきましょう
①対象ホスト
Ansibleで操作される対象となるマシン
Ansibleがインストールされている必要はありませんが、Python2.5以上がインストールされている必要はあります。
ここではVagrantで対象ホストを構築し、ssh 192.168.33.10
でログインできるものとします。
②実行ホスト
対象ホストをAnsibleで操作するマシン
Ansibleがインストールされている必要があります。
ここではMacで動作確認しています。
③インベントリ
対象ホストの一覧を管理するファイルです。
④Playbook
対象ホストを操作するためのスクリプトです。
ChefやItamaeで言うところのレシピですね。
準備/前提条件
この辺の情報もWeb上にたくさんあるので、具体的な手順は省略させていただきます。
-
Ansibleはインストールされているものとします
-
Ansibleで操作される対象となるマシン(対象ホスト)がVagrantで構築されており、
ssh 192.168.33.10
でログインできること。(IPアドレスは適宜読み替えて下さい) -
作業ディレクトリはVagrantfileが置いてあるディレクトリとします。
$ python --version Python 2.7.10 -- 64-bit $ ansible --version ansible 2.0.2.0 config file = configured module search path = Default w/o overrides $ tree . ├── Vagrantfile ├── inventory.txt # 後から作るファイルです └── playbook.yml # 後から作るファイルです $ cat Vagrantfile Vagrant.configure(2) do |config| config.vm.box = "ubuntu/trusty64" config.vm.network "private_network", ip: "192.168.33.10" config.vm.network :forwarded_port, guest: 80, host: 8080 end
1. ansibleコマンド
まずは、Playbookは使わずに、ansibleコマンドと呼ばれる一行コマンドで動作を見ていきます。
1.1. Hello world!
まずはお馴染みのHello worldで動作確認をしてみます。
# インベントリファイルを作成
$ echo 192.168.33.10 > ./inventory.txt
# ansibleコマンドを実行
$ ansible 192.168.33.10 -i ./inventory.txt -m shell -a "echo Hello world\!"
192.168.33.10 | SUCCESS | rc=0 >>
Hello world!
解説
-iオプション
インベントリファイルを指定します。
-mオプション
実行するモジュールを指定します。モジュールとはAnsibleで実行する処理のことで、ここではshell
を実行しています。文字通り、対象ホストでshell
を実行します。shell
以外にもyum
やservice
、file
などがあります。
こちらに一覧があるので必要に応じて調べてみてください。
-aオプション
実行モジュールの引数です。
1.2. Nginxをインストールする
最初の1行目が実行コマンドで、その後にズラズラっと出ているのが実行結果です。
$ ansible 192.168.33.10 -b -i ./inventory.txt -m apt -a "name=nginx state=latest"
192.168.33.10 | SUCCESS => {
"cache_update_time": 0,
"cache_updated": false,
"changed": true,
"stderr": "",
"stdout": (stdout_linesと同じなので略),
"stdout_lines": [
"Reading package lists...",
"Building dependency tree...",
"Reading state information...",
"The following extra packages will be installed:",
" libxslt1.1 nginx-common nginx-core",
"Suggested packages:",
" fcgiwrap nginx-doc",
"The following NEW packages will be installed:",
" libxslt1.1 nginx nginx-common nginx-core",
"0 upgraded, 4 newly installed, 0 to remove and 3 not upgraded.",
"Need to get 494 kB of archives.",
"After this operation, 1795 kB of additional disk space will be used.",
"Get:1 http://archive.ubuntu.com/ubuntu/ trusty/main libxslt1.1 amd64 1.1.28-2build1 [145 kB]",
"Get:2 http://archive.ubuntu.com/ubuntu/ trusty-updates/main nginx-common all 1.4.6-1ubuntu3.4 [18.3 kB]",
"Get:3 http://archive.ubuntu.com/ubuntu/ trusty-updates/main nginx-core amd64 1.4.6-1ubuntu3.4 [325 kB]",
"Get:4 http://archive.ubuntu.com/ubuntu/ trusty-updates/main nginx all 1.4.6-1ubuntu3.4 [5616 B]",
"Fetched 494 kB in 4s (116 kB/s)",
"Selecting previously unselected package libxslt1.1:amd64.",
"(Reading database ... 65082 files and directories currently installed.)",
"Preparing to unpack .../libxslt1.1_1.1.28-2build1_amd64.deb ...",
"Unpacking libxslt1.1:amd64 (1.1.28-2build1) ...",
"Selecting previously unselected package nginx-common.",
"Preparing to unpack .../nginx-common_1.4.6-1ubuntu3.4_all.deb ...",
"Unpacking nginx-common (1.4.6-1ubuntu3.4) ...",
"Selecting previously unselected package nginx-core.",
"Preparing to unpack .../nginx-core_1.4.6-1ubuntu3.4_amd64.deb ...",
"Unpacking nginx-core (1.4.6-1ubuntu3.4) ...",
"Selecting previously unselected package nginx.",
"Preparing to unpack .../nginx_1.4.6-1ubuntu3.4_all.deb ...",
"Unpacking nginx (1.4.6-1ubuntu3.4) ...",
"Processing triggers for ureadahead (0.100.0-16) ...",
"Processing triggers for ufw (0.34~rc-0ubuntu2) ...",
"Processing triggers for man-db (2.6.7.1-1ubuntu1) ...",
"Setting up libxslt1.1:amd64 (1.1.28-2build1) ...",
"Setting up nginx-common (1.4.6-1ubuntu3.4) ...",
"Processing triggers for ureadahead (0.100.0-16) ...",
"Processing triggers for ufw (0.34~rc-0ubuntu2) ...",
"Setting up nginx-core (1.4.6-1ubuntu3.4) ...",
"Setting up nginx (1.4.6-1ubuntu3.4) ...",
"Processing triggers for libc-bin (2.19-0ubuntu6.7) ..."
]
}
解説
-bオプション
becomeの略で、対象ホストでどのユーザーとして操作をするかを指定します。デフォルトはsudoです。
aptモジュール
対象ホストにてaptコマンドを使ってパッケージをインストールします。
私は対象ホストがUbuntuなのにyumで入れようとしてハマってしまいました。OSに応じて、yum, apt, brewなどが用意されているので、適宜使い分けてください。
2. Playbook
複数のモジュールをまとめて実行するためにPlaybookを使って処理を書いていきましょう。
2.1. Hello world!
まずは動作確認。
$ cat << EOS > ./playbook.yml
- hosts: 192.168.33.10
tasks:
- name: PlaybookでHello world!
shell: echo Hello world! > hello.txt
EOS
$ ansible-playbook -i ./inventory.txt ./playbook.yml
ssh 192.168.33.10
で対象ホストにログインすると、ログイン直後のディレクトリにhello.txt
ができていることを確認できるはずです。
解説
- yaml形式です。ファイル名はなんでも構いません。yamlの書き方についてはこちら。
- tasksの中に、処理を記述していきます。
- nameに記載する文字列は人間向けなのでなんでも構いません。
- shellがモジュールで、その後がモジュール引数ですね。
2.2. Nginxをインストールする
では、複数の処理を書いていきましょう。ここではNginxをインストールした後、起動しています。
$ cat << EOS > ./playbook.yml
- hosts: 192.168.33.10
become: sudo
tasks:
- name: NGINX | Installing NGINX
apt: name=nginx state=present
- name: NGINX | Starting NGINX
service: name=nginx state=started
EOS
$ ansible-playbook -i ./inventory.txt ./playbook.yml
解説
-
become: sudo
はansibleコマンドの説明で出てきた-b
オプションと同じく、対象ホストでの実行ユーザーを指定しています。 -
service
というモジュールでNginx等のサービスを、起動/停止/再起動することができます。
Vagrantファイルで下記のように、ポートフォワードしている場合、実行ホスト側のブラウザで http://192.168.33.10/ を叩くと「Welcome to nginx!」と言ってくれるはずです。
$ cat Vagrantfile
Vagrant.configure(2) do |config|
config.vm.box = "ubuntu/trusty64"
config.vm.network "private_network", ip: "192.168.33.10"
config.vm.network :forwarded_port, guest: 80, host: 8080
end
3. Next Steps
ここまででなんとなくAnsibleの概要はつかめました。この後は、今開発中のサービスに実戦投入しつつ、下記を進めていこうと思います。
- Ansible Galaxyに上がっているRoleを眺めてみる。
- Githubに上がっているPlaybookを眺めてみる。
- Flaskでの開発環境構築処理を記述する。
- Templateとやらの調査。
- ディレクトリ構成やファイル名などに関するお作法(ベストプラクティス)を学ぶ。