OpenStack & Ansible Advent Calendar 2014 12-24
OpenStack & Ansible Advent Calendar 2014 12-24
これは、OpenStack (2枚目) Advent Calendar 2014 と Ansible Advent Calendar 2014 の24日目(クリスマスイヴ!!)の記事です。
OpenStackとAnsibleの、12/24という割と重要な日を同時に担当してしまったので、この2つのキーワードを連携させる内容で書いてみました。
AnsibleからOpenStack上に仮想マシンを作成する
AnsibleではOpenStackを操作するためのモジュール群がいくつか提供されています。 しかしながら、積極的にメンテナンスされているのは、 nova_computeモジュール のみという状態に見えます。 そこで、この記事ではnova_computeモジュールの利用方法を紹介します。
モジュール名 | 機能 |
---|---|
glance_image | 仮想マシンイメージの登録・削除 |
keystone_user | プロジェクト/ユーザー/ロールの作成・削除・紐付け |
nova_compute | 仮想マシンの作成・削除 |
nova_keypair | キーペアの登録・削除 |
quantum_floating_ip | フローティングIPの払い出しと仮想マシンインスタンスへの割り当て |
quantum_floating_ip_associate | 特定フローティングIPの割り当てと割り当て解除 |
quantum_network | 仮想ネットワークの作成・削除 |
quantum_router | 仮想ルータの作成・削除 |
quantum_router_gateway | 仮想ルータと外部ネットワークセグメントの接続・切断 |
quantum_router_interface | 仮想ルータと仮想ネットワークセグメントの接続・切断 |
quantum_subnet | 仮想ネットワーク内のサブネットの作成・削除 |
しかしながら、このモジュールは問題含みで本当に限られた環境でしか安全に動作しません。 利用方法を紹介する前に、標準提供されるOpenStack操作関連のモジュールが抱える問題(結構致命傷)を2つ書いておきます。OpenStackの仮想マシン管理にAnsibleを利用したい場合(あるのか?)は、対応しておくことをお勧めします。
<問題1> quantumモジュールとglanceモジュールはマルチリージョン未対応
neutronを操作する全てのモジュール(quantum_*)と、glanceを操作するモジュール(glance_image)はマルチリージョンに対応してません。 Optionでは、Region_nameを指定できますが、実際には利用されておらず、OpenStackのクライアントオブジェクト生成時に渡されていない....
<問題2> nova_computeモジュールがfloating_ipの割り当て時に使用済みアドレスの除外に失敗しています
nova_computeモジュールで仮想マシン新規作成時にfloating_ipを割り当てる際、以下のような動きをします。
本来の動作
- floating_ip_poolsを指定すると、払い出し済みの全てのfloating_ipの中から未使用のアドレスを1つを選んで仮想マシンに割り当てる
- 未使用のアドレスがなければ、新たに1つfloating_ipを払いだして割り当てる
実際の動作
しかし、実際には、払い出し済みかどうかに関わらず、プール内のすべてのfloating_ipの中から1つを選択して割り当ててしまうのです。これはひどい...
背景
nova_computeモジュールでは、floating_ipが割り当て済みかどうかを、APIから返されるfloating_ipに紐付けられているinstance_idから判断しているのですが、現状のnova apiは、instance_idを空で返してきます。nova_computeモジュールはinstance_idが存在していないため、未使用と判断して、これを仮想マシンへの割り当て候補リストに加えてしまうのです。 ちなみに、HP Public Cloudでは、このnovaの不具合が修正されているので問題ありません。
nova_computeモジュールが持つ致命的な不具合
自前で構築したOpenStack環境だとJuno(2014.2)でもこの不具合を引き当てます。 引き当てるとどうなるかというと、既に他の仮想マシンに割り当てられているfloating_ipが強制的に取り上げられて、新たに作成した仮想マシンに付与してしまいます(novaの仕様)。これは相当やばい。
対策
v1.8系のnova_computeモジュールを使うときは要注意!
対策をちゃんと施したほうが良いです。 Pull Requestしてるんだけど、早くマージしてくれないかなぁ...
実際にnova_computeモジュールを利用してみる
前節の対策はおわすれなく。
必須要件
AnsibleからOpenStackを操作するためには、大きく3つの要件を満たしている必要があります。
- OpenStack APIのURL/アカウント/パスワード/テナント名/リージョン名を持っている
- OpenStackのPythonクライアントライブラリがインストールされている
- nova_computeの不具合に対処済みである
下準備
pythonのvirtualenvを利用して仮想実行環境にAnsibleとOpenStackのクライアントライブラリを閉じ込めます。
1. virtualenv環境構築
$ virtualenv $HOME/advc New python executable in advc/bin/python Installing Setuptools..............................................................................................................................................................................................................................done. Installing Pip.....................................................................................................................................................................................................................................................................................................................................done. $ source advc/bin/activate (advc)$
2. Ansibleのインストール
pipを利用してAnsibleをインストールする
(advc)$ pip install jinja2 passlib pycrypto pyyaml (advc)$ pip install ansible
3. python-novaclientとpython-neutronclientのインストールと環境変数設定
nova_computeモジュールは、python-novaclientが提供するライブラリを利用しているため、利用前にインストールしておく必要があります。
依存関係があるのでpython-keystoneclientもインストールされます。
(advc)$ pip install python-novaclient python-neutronclient (advc)$ vi openrc export OS_AUTH_URL=https://認証用URL:ポート/v2.0/ export OS_REGION_NAME=リージョン名 export OS_TENANT_NAME=テナント名 export OS_USERNAME=ユーザ名 export OS_PASSWORD=パスワード
4. nova_computeモジュールの配置
(advc)$ cd $HOME/advc/lib/python2.7/site-packages/ansible/modules/core/cloud/openstack (advc)$ mv nova_compute.py nova_compute.py.org (advc)$ wget http://goo.gl/8Vr3QT -O nova_compute.py
5. Ansibleの動作確認
(advc)$ cd $HOME (advc)$ echo "localhost ansible_connection=local" > ansible_hosts (advc)$ ansible all -i ansible_hosts -m ping
仮想マシンを作成する
作成に必要な仮想マシンやネットワークの情報は nova コマンドや neutron コマンドで取得しておきましょう!
- create_vm.yml
--- - hosts: localhost tasks: - name: ansible_python_interpreter setup set_fact: ansible_python_interpreter="{{ lookup('pipe', 'which python') }}" - name: create virtual machine instance nova_compute: state: present auth_url: "https://認証URL:ポート/v2.0/" region_name: "リージョン名" login_tenant_name: "テナント名" login_username: "ユーザID" login_password: "パスワード" availability_zone: "アベイラビリティゾーン名" flavor_id: フレーバID floating_ip_pools: - "パブリックネッーワーク名" image_id: "GuestOSイメージID" key_name: "キーペア名" name: "仮想マシンのホスト名" nics: - net-id: "内部ネットワークID" security_groups: "セキュリティグループ名" # # [EOF] #
- 実行
(advc)$ ansible-playbook -i ansible_hosts create_vm.yml PLAY [localhost] ************************************************************** GATHERING FACTS *************************************************************** ok: [localhost] TASK: [ansible_python_interpreter setup] ************************************** ok: [localhost] TASK: [create virtual machine instance] *************************************** changed: [localhost] PLAY RECAP ******************************************************************** localhost : ok=3 changed=1 unreachable=0 failed=0
- 作成されたかを確認してみる
(advc)$ nova show test-vm00 +-----------------------------+----------------------------------------------------------+ | Property | Value | +-----------------------------+----------------------------------------------------------+ | OS-EXT-AZ:availability_zone | アベイラビリティゾーン | | OS-EXT-STS:power_state | 1 | | OS-EXT-STS:task_state | - | | OS-EXT-STS:vm_state | active | | accessIPv4 | | | accessIPv6 | | | config_drive | | | created | 2014-12-24T08:52:24Z | | flavor | フレーバ名(フレーバID) | | hostId | 4bd0942b81bcc260be67911e43a43fc91217d78a18e59d32f2bd275b | | id | 4f0a63bb-f79e-4850-ad5f-3156d677940b | | image | OSイメージ名 (OSイメージID) | | key_name | キーペア名 | | metadata | {} | | name | ホスト名 | | progress | 0 | | security_groups | セキュリティグループ名 | | status | ACTIVE | | tenant_id | テナントID | | updated | 2014-12-24T08:52:54Z | | user_id | ユーザID | | work-net network | 10.0.0.23, 15.126.228.53 | +-----------------------------+----------------------------------------------------------+
よし!できた! これを基本にしてvarsなどをうまく利用すれば、novaコマンドを素で叩くよりは楽に仮想マシンが作れそうです!
それではみなさん素敵なクリスマスを!