構成管理ツール Ansibleを試す (FFmpegのPlaybookを作る)

ansiblelogo
今や構成管理ツールは百花繚乱、何を使ったらいいのかよくわからないのが正直なところなのですが、以前から気になっていたAnsibleをちょっと触ってみました。まだ入門レベルのことしか試していませんが感想などを書きたいと思います。

Ansible is a radically simple IT orchestration engine that makes your applications and systems easier to deploy. Avoid writing scripts or custom code to deploy and update your applications— automate in a language that approaches plain English, using SSH, with no agents to install on remote systems.

選んだ理由としては、ミドルウェアが増えない、サーバ/クライアントに特別なエージェント(デーモン)が不要という2点です。

ソフトウェアのインストールなどサーバ構築の手順は Playbook と呼ばれるYAMLファイルに記述します。スクリプト言語(DSL含む)と比較すると表現力は劣りますが、手軽に書けるところは魅力です。より複雑な処理が必要な場合はモジュール化してYAMLから呼び出してねっていうスタンスみたいです。

作業にあたって、公式リファレンス以外では以下のページを参考にさせていただきました。日本語で良くまとまっているので理解が進みました。

目次

  • Ansibleのインストール
  • FFmpegをインストールするPlaybook
  • サポートされているCPU命令に応じて処理を変える
  • ゲートウェイサーバを経由させる
  • 感想など

環境

  • CentOS 6.4 (x86_64/Intel Xeon E5-2690 2.90GHz 仮想32コア/96GB RAM)
  • Ansible 1.4
  • GCC 4.4.7
  • Python 2.7.5
  • リモートサーバ CentOS 6.4 (x86_64) 50台 (東日本DCに10台、西日本DCに40台)

リモートサーバ環境は、OSが同じでCPUなどのハードウェア構成はそれぞれ異なっているサーバ群を対象に検証しました。

Ansibleのインストール

Ansible本体は yum ではなく pip でインストールしました。依存モジュールとして paramiko/PyYAML/Jinja2 もいっしょにインストールされます。Ansible本体を動作させるにはPython 2.6以降が必要ですが、CentOS 6.x系であればシステムのPythonでその条件を満たしています。

FFmpegをインストールするPlaybook

映像配信サービス向けのエンコードサーバクラスタを構築するという想定で、FFmpegをサーバにインストールするPlaybookを作ってみます。FFmpegは任意のメディアコーデック/コンテナライブラリを組み込んでビルドする大きなソフトウェアです。今回は以下の構成でFFmpegをビルド/インストールします。rpm/debパッケージで配布されているものはコーデック/コンテナ不足 & 最適化不足のため実務では使えないかと思います。

  1. Gitのインストール
  2. CMakeのインストール
  3. Yasm (x86アセンブラ)のソースコードのダウンロード
  4. Yasm をコンパイル
  5. Yasm のインストール
  6. x264 (H.264/AVCビデオコーデック)のソースコードのダウンロード
  7. x264 のコンパイル
  8. x264 のインストール
  9. libfdk-aac (AACオーディオコーデック)のソースコードのダウンロード
  10. libfdk-aac のコンパイル
  11. libfdk-aac のインストール
  12. libmp3lame (MP3オーディオコーデック)のソースコードのダウンロード
  13. libmp3lame のコンパイル
  14. libmp3lame のインストール
  15. libogg (ビットストリームライブラリ)のソースコードのダウンロード
  16. libogg のコンパイル
  17. libogg のインストール
  18. libopus (Opusオーディオコーデック)のソースコードのダウンロード
  19. libopus のコンパイル
  20. libopus のインストール
  21. libvorbis (Vorbisオーディオコーデック)のソースコードのダウンロード
  22. libvorbis のコンパイル
  23. libvorbis のインストール
  24. libvpx (VP8/VP9ビデオコーデック)のソースコードのダウンロード
  25. libvpx のコンパイル
  26. libvpx のインストール
  27. FFmpeg のソースコードのダウンロード
  28. FFmpeg のコンパイル
  29. FFmpeg のインストール

libvpx にはVP9コーデックが含まれているのでぜひ加えておきましょう。libtheora (Theoraコーデック) はこれまで組み込んでも実際は使う機会がほとんどなかったので外しました。あとは、ネットラジオのアーカイブとか作るような人なら libopus も入れておきましょう。Opusは今後普及が期待されるオーディオコーデックです。WebRTCのMTIコーデック(対応必須ですよという意味、ちなみにビデオコーデックはまだ決まっていない)にもなっているので、HTML5を勉強している人も知っておく必要があるかと思います。

また、上記の構成でビルドされたバイナリは libfdk-aac のライセンスがGPL非互換のため再配布不可なので注意してください。別のAACコーデックである libfaac を組み込んだ場合も同様です。ソフトウェアライセンス関連はまだ単純でいいのですが、ビジネスだとパテント絡みで利権やくざが怖いです。

参考:
2003年の記事ですけどこれはひどいですね。資本主義とはいったい。。
MPEG-4 backers protest Microsoft license
(要約:MPEG LAがMicrosoftに対して 「Windows Mediaのライセンスは安すぎる!不正競争だ!」)

話が逸れました。
まず、デプロイ対象ホストを Inventory host file(インベントリファイル) と呼ばれるINIファイルに書いておきます。

* servers.ini

インベントリファイルはYAMLではないんですね。なぜでしょう。

まずは疎通確認してみます。

FFmpegの Playbook は以下のように作りました。さすがに150行を超えていると分割したくなりますけど、FFmpegの場合はコーデック/コンテナライブラリ毎に分割するとファイル数が増えて管理が面倒になる気がします。どれくらいの粒度で分割すれば良いかは調整していく必要がありそうです。

Playbookでは以下の標準モジュールを利用しています (モジュール一覧: Ansible Modules)

* command
* get_url
* git
* shell
* yum

* ffmpeg.yml

* 実行

実際に50台のサーバを対象に実行してみると普通に何度か失敗しました。ネットワークや筐体障害というのは日常的にあることですので、リモートホストが生きていれば時間を置いて再度実行することになります。ただし今回の例では全てのソフトウェアをバージョン指定でインストールしているわけではないので、べき等性(何度実行しても状態は変わらない)は保証されません。

映像配信サービス用にエンコードサーバクラスタを構築することを考えた時に、全ホストのOSは統一はできてもCPUなどのハードウェア環境はそうもいかないことが多いと思います。よって、各環境に最適化されたバイナリをデプロイするには現地でコンパイルする必要があります。

サポートされているCPU命令に応じて処理を変える

リモートサーバのCPU/コア数、サポートされている命令を判別してコンパイル時に適切な CFLAGS を設定できるようにしたいのですけど、なにかスマートな方法はないものでしょうか。

リモートサーバのシステム情報(Ansibleの文脈では FACTS と呼ばれる)について確認するには setup モジュールを利用します。

ansible_processor はプロセッサ名の文字列が仮想コアの数だけ詰まってるリストになっています。上記例では物理CPU (ansible_processor_count)が2つ、物理CPU内のコア(ansible_processor_cores)が8つ、各コアがHTの2スレッドで仮想32コアの環境になります。コンパイル時のcc1の並列実行数には ansible_processor_count * ansible_processor_cores の値を指定するのが効率良さそうです。スラッシングを避けるためにも並列数はあまり増やさない方がいいと思います。

次に、サポートされているCPU命令に応じて処理を分ける場合です。こちらはAnsibleの setup モジュールだと flags の値は取れないようですので、setup モジュールを修正するか新しいモジュールを作る他なさそうです。一応 ohai モジュールを使えばできそうなんですが、Ruby処理系はともかく mixlib-* などたくさんの追加依存モジュールによって環境が汚れるのはツライところです。

setup モジュールには Hardware クラスというのがあって、LinuxHardware や SunOSHardware などOS毎にサブクラスが定義されています。Linux OSを対象とする場合は LinuxHardware クラスの get_cpu_facts メソッドをいじります。/proc/cpuinfo の内容をバラしてるだけの処理ですので修正は簡単です。

setup モジュールに以下のパッチを当てると、サポートされているCPU命令のリストとL2キャッシュサイズ(KB)がFACTSに追加されます。

コンパイラがGCCの場合、-march=native がサポートされていないプラットフォーム上でソフトウェアをコンパイルする際は上記情報を使って CFLAGS を組み立てます。

setup モジュールを修正するのではなく新規にモジュールを作る場合、出力結果のJSONに ansible_facts というキーを追加して、そこに任意の情報を入れておけばAnsibleがFACTSに追加してくれるようです。サポートされているCPU命令のリストやL2キャッシュサイズ、コンパイラのバージョン(gccなら -dumpversion の値)を集めて、最終的に Autotools や CMake に渡す CFLAGS (あるいはCXXFLAGS)を組み立てるロジックを埋め込んでおくと便利そうです。

ここではマルチメディア処理や機械学習処理など、CPUバウンドな科学技術計算を扱うソフトウェアをインストールする場合に考えなければならない問題を取り上げてみました。

ゲートウェイサーバを経由させる

Ansible Advent Calender 2013に良いエントリーがありました。MSP屋さんの視点は貴重ですね。

ネットワークセグメントが異なる自社DC間の通信において、ゲートウェイサーバ(踏み台)経由でないとSSHセッションが貼れないケースが考えられます(コンプライアンスの対象範囲を狭めたり、セキュリティ上の理由から)。ゲートウェイサーバではソフトウェアの新規インストールが許可されておらず、なおかつ実行可能なコマンドも厳しく制限されていることが多いため、これを解決できないとAnsibleの導入は難しくなります。

そこでAnsibleではSSHに渡すオプションを ANSIBLE_SSH_ARGS 環境変数で指定できるようなのでこれを利用します。ここから先はAnsible自体とは関係ない話なので詳細は上記エントリー等を参照ください。ssh_configProxyCommand を使ってゲートウェイサーバを経由させるだけです。

ただし、ゲートウェイサーバのOpenSSHがv5.4未満かつ nc コマンドが入っていなくて新規インストールもできない環境だとお手上げですかね? あと、最近流行ってるワンタイムキーによる二段階認証が必要な場合も厳しいかなぁと思います。

感想など

Ansibleは導入コストの低さも魅力ですが、ミドルウェアが増えない点が特に良いです。

Playbook内でいっぱい変数を使ったりRole分割しすぎると訳が分からなくなってくるので、上手くバランスを取って整備する必要があると感じました。今回作成したFFmpegインストール用のPlaybookの場合は、コーデック/コンテナライブラリ毎に分割すると細かくなりすぎて整備が煩雑になる気がするので、例えば映像関連と音声関連とで分けるくらいの粒度なら整備しやすいかもしれません。

ところで、Slashdotで他のツールとの比較記事がありました。

言われてみればWeb UIについては考えていませんでした。確かにWebブラウザから構成管理情報が閲覧できるとシステム運用者は嬉しいと思います。

以前は映像配信サービスの開発/運用に携わっていましたが、配信系だけでも数百台規模でしたし、エンコーダやストレージサーバクラスタも全て構成管理するのはちょっと面倒でした。ソフトウェアも商用ライセンスでたくさん買ってたので、インストールされているサーバ台数は正確に計上しなければなりません。そういった面でノード情報をINIファイルで管理するAnsibleでは正直心配なので、結局は構成管理用サーバを別に立ち上げてデータベースにノード情報と併せて管理することになるかもしれません。それやったらChefでいいやろって話になりますけども。

使い始めてまだ2週間弱ですけど、覚えることが少なくて使いやすいなと思いました。でもきっと年明けにはぜんぶ忘れていることでしょう。

おまけ

システム運用自動化の記事に対する他業種/職種の方々の反応を見るのは面白いです。

運用を機械に任せることに不安を抱いているのではなく、資本であるところの人を減らしているという事自体が不安なんだと思います。外からは体のいい人件費削減と読み取られても仕方ないかと。こういうのって株主の方々はどう見てるんでしょうか。

あわせて読む:

コメントを残す

メールアドレスが公開されることはありません。 が付いている欄は必須項目です