この記事は最終更新から1年以上経過しています。 気をつけてね。
アプリケーションプラットフォームの構築運用を少人数で行うためのツールとして、だいぶ浸透してきた感のあるOpscodeのChef。
chef-clientのクロスプラットフォーム性を支えるのが同じくOpscodeが保守するOhaiだ。
Ohaiに聞くとプラットフォームの情報が取れる
Ohaiはインベントリ収集ツール。
レシピ(リソース/プロバイダ)を複数のプラットフォームに対応させるため、Chef-Clientが今から作用する対象を判断する情報をリストアップする。
Ohaiの利点は全てのプラットフォームで同じ問い合わせが出来ることだ、折角なので他のプログラムからも使えるように動作をチェックしてみる。
ohaiコマンド
gemでohai
をインストールした後なら、コマンドラインからohaiを叩ける。
これはstdout
にJSONを出すだけだが、Chefがnode
のインベントリとして表示する情報がそのまま出ているのがわかる。
$ ohai | head
{
"languages": {
"ruby": {
"platform": "x86_64-darwin12.2.0",
"version": "1.9.3",
"release_date": "2012-04-20",
"target": "x86_64-apple-darwin12.2.0",
"target_cpu": "x86_64",
"target_vendor": "apple",
"target_os": "darwin12.2.0",
結構これでも十分だ。
Ohai::Systemオブジェクト
OhaiをPryからインタラクティブに実行して、Ohaiプラグインを使ってインベントリを収集していく。
各アトリビュートはOhai::System
から作成したインスタンスの@data
に溜まっていく。
> require 'ohai'
=> true
> ohai = Ohai::System.new
=> #<Ohai::System:0x007fc7ec050440
@data={},
@hints={},
@plugin_path="",
@providers={},
@seen_plugins={}>
プラグインパスが空に見えるが、デフォルトでOhai同梱のものへパスが通っており使用出来る。
> Ohai::Config[:plugin_path]
=> ["/Users/sawanoboriyu/.rvm/gems/ruby-1.9.3-p194@chef-labs/gems/ohai-6.14.0/lib/ohai/plugins"]
require_pluginで基本のOSプラグインを実行
プラグインの実行にはrequire_plugin
メソッドを使う、まずOS情報を取らないと他のプラグインは満足に動かないので初めに実行。
> ohai.require_plugin "os"
=> true
> ohai.data
=> {"languages"=>
{"ruby"=>
{"platform"=>"x86_64-darwin12.2.0",
"version"=>"1.9.3",
"release_date"=>"2012-04-20",
"target"=>"x86_64-apple-darwin12.2.0",
"target_cpu"=>"x86_64",
"target_vendor"=>"apple",
"target_os"=>"darwin12.2.0",
"host"=>"x86_64-apple-darwin12.2.0",
"host_cpu"=>"x86_64",
"host_os"=>"darwin12.2.0",
"host_vendor"=>"apple",
"bin_dir"=>"/Users/sawanoboriyu/.rvm/rubies/ruby-1.9.3-p194/bin",
"ruby_bin"=>"/Users/sawanoboriyu/.rvm/rubies/ruby-1.9.3-p194/bin/ruby",
"gems_dir"=>"/Users/sawanoboriyu/.rvm/gems/ruby-1.9.3-p194@chef-labs",
"gem_bin"=>"/Users/sawanoboriyu/.rvm/rubies/ruby-1.9.3-p194/bin/gem"}},
"kernel"=>
{"name"=>"Darwin",
"release"=>"12.2.0",
"version"=>
"Darwin Kernel Version 12.2.0: Sat Aug 25 00:48:52 PDT 2012; root:xnu-2050.18.24~1/RELEASE_X86_64",
"machine"=>"x86_64",
"modules"=>{}},
"os"=>"darwin",
"os_version"=>"12.2.0"}
裏で色々と泥臭い処理が走った結果、見事にOSに関するインベントリが収集されている。
相手のOSが何でも同じ構造のハッシュに格納してくれるのは色々と助かるはず。
プラグインの追加実行でアトリビュート追加
"OS"のインベントリ採取が終わった後なら他のプラグインも適当に実行できる。
platform
やohai(plugin)
を実行して、関連するアトリビュートを@data
に追加しておく。
> ohai.require_plugin "platform"
=> true
> ohai.require_plugin "platform"
=> true
> ohai.data
=> {"languages"=>
{"ruby"=>
-- snip --
"os"=>"darwin",
"os_version"=>"12.2.0",
"platform"=>"mac_os_x",
"platform_version"=>"10.8.2",
"platform_build"=>"12C60",
"platform_family"=>"mac_os_x"}
> ohai.require_plugin "ohai"
> ohai.data[:chef_packages]
=> {"ohai"=>
{"version"=>"6.14.0",
"ohai_root"=>
"/Users/sawanoboriyu/.rvm/gems/ruby-1.9.3-p194@chef-labs/gems/ohai-6.14.0/lib/ohai"}}
パスにあるすべてのプラグインを実行
all_plugins
はすべてのプラグインを実行する。
> ohai.all_plugins
> ohai.seen_plugins
=> {"os"=>true,
"kernel"=>true,
"ruby"=>true,
"languages"=>true,
"c"=>true,
"chef"=>true,
"cloud"=>true,
"ec2"=>true,
"hostname"=>true,
"darwin::hostname"=>true,
"network"=>true,
"darwin::network"=>true,
"rackspace"=>true,
"eucalyptus"=>true,
"command"=>true,
"dmi"=>true,
"dmi_common"=>true,
"erlang"=>true,
"groovy"=>true,
"ip_scopes"=>true,
"java"=>true,
"keys"=>true,
"lua"=>true,
"mono"=>true,
"network_listeners"=>true,
"ohai"=>true,
"ohai_time"=>true,
"passwd"=>true,
"perl"=>true,
"php"=>true,
"platform"=>true,
"darwin::platform"=>true,
"python"=>true,
"uptime"=>true,
"virtualization"=>true,
"darwin::virtualization"=>true,
"darwin::filesystem"=>true,
"darwin::kernel"=>true,
"darwin::ps"=>true,
"darwin::ssh_host_key"=>true,
"darwin::system_profiler"=>true,
"darwin::uptime"=>true}
Ohaiプラグインを作成する
インベントリを取得したいノードによってはなにかしらアトリビュートを追加したい時もある。
他のプラグインにならえば、Ohaiプラグインはプロバイダと取得するコマンドラインを指定する形で追加になる。
プロバイダを追加
Pryのまま行う、実際はプラグイン名.rb
ファイルにohai.
を除いた形で書いておく。
> ohai.provides "brew_path", "brew_ver"
=> ["brew_path", "brew_ver"]
> ohai
=> #<Ohai::System:0x007f8ecbbef940
@data={},
@hints={},
@plugin_path="",
@providers=
{"brew_path"=>{"_providers"=>[""]}, "brew_ver"=>{"_providers"=>[""]}},
@seen_plugins={}>
プロバイダの取得方法を定義
簡単な方法の一つ、Ohai::Ststem
のインスタンスメソッドfrom
をつかう。
マルチプラットフォーム対応で実行したコマンドの標準出力を格納できる。
> ohai.brew_path ohai.from("which brew")
=> "/usr/local/bin/brew"
> ohai.brew_ver ohai.from("#{ohai.brew_path} -v")
=> "Homebrew 0.9.3"
> ohai.data
=> {"brew_path"=>"/usr/local/bin/brew", "brew_ver"=>"Homebrew 0.9.3"}
おわりに
Chefは全体的にまずガサ入れをしてからなんぼというツールだが、特にこのOhaiの泥臭さはなかなかだ。