unoh.github.com

サーバ情報を収集する Ruby スクリプトを書くには

Sun Feb 20 17:57:51 -0800 2011

こんにちは。kyagi です。今回はサーバ情報を収集する Ruby スクリプトを書く方法をお知らせいたします。具体的にはサーバ情報収集ツール facter (※1)の紹介と使い方になります。

facter はサーバのホスト名、IP アドレス、OS、ハードウェアなど様々な情報を収集するためのツールです。RPM では「facter」というパッケージ名で提供されており 「yum install facter」 でインストールが可能です。インストール後はターミナルから 「facter」 というコマンド(※2) を実施するだけでサーバの色々な情報を一度に取得することができます。

$ facter 
(... snip ...)
architecture => x86_64
domain => local.hoge.bar.net
(... snip ...)
ipaddress_eth0 => 10.x.y.z
processor0 => Intel(R) Xeon(R) CPU           E5504  @ 2.00GHz
memorysize => 8.04 GB
(... snip ...)


facter を rpm でインストールすると ruby 用のインターフェイスとして Facter というモジュールが /usr/lib/ruby/site_ruby/ 配下にインストールされます。Ruby スクリプトの中で使用するにはこの Facter モジュールを require した後に、任意のクラスに include すれば OK です。コマンドラインから取得できる情報は Facter.value(:要素名) で取得可能です。以下に基本的なサーバを示すクラスとして「BaseServer」を定義した後、そのサブクラスであるWeb サーバ専用クラス「HttpdServer」, Mysql サーバクラス「MysqldServer」を定義したコードを紹介します。

■facter を rpm でインストールすると Ruby 用に Facter module がインストールされる

$ rpm -ql facter | grep rb$ 
/usr/lib/ruby/site_ruby/1.8/facter.rb
(... snip ...)
$ grep -r Facter /usr/lib/ruby/site_ruby/1.8 | grep module
/usr/lib/ruby/site_ruby/1.8/facter.rb:module Facter


■基本的なサーバを表すクラスとして「BaseServer」クラスを作成する

require 'facter' 
class BaseServer
  include Facter
  attr_accessor :name, :role, :ipaddress
  def initialize(*)
    @name = Facter.value(:fqdn)
    @role = self.class.name
    @ipaddress = Facter.value(:ipaddress)
  end
  def getKernel
    return Facter.value(:kernelrelease)
  end
  def getUptime
    return Facter.value(:uptime)
  end
end


■ Web サーバクラスを「BaseServer」のサブクラスとして作成する

require 'BaseServer'
class BaseServer::HttpdServer < BaseServer
  def getApacheStatus
    (... snip ...)
  end
end


■ Mysqld サーバクラスを「BaseServer」のサブクラスとして作成する(※別途 ruby-mysql を使用し、専用のインスタンス変数を準備する)

require 'BaseServer'
require 'mysql'
class BaseServer::MysqldServer < BaseServer
  attr_accessor :host, :user, :pass, :database
  def initialize(host, user, pass, database)
    super
    @host = host
    @user = user
    @pass = pass
    @database = database
  end
  def countTable(table)
    my = Mysql::new(host, user, pass, database)
    res = my.query("select count(*) from #{table}")
    return res
  end
end


以上、サーバ情報収集ツールを Ruby で書いている方の参考になれば幸いです。

(※1) サーバ管理ツール Puppet も内部的に facter を使用しています。

(※2) 「要素」という意味を表す英単語としては「facter」という単語はミススペルのようです。正しくは「factor」ですが既に coreutils パッケージに因数分解をする同名のコマンドが含まれているため、故意に facter という名前にしたのではと思われます。数学に興味がある方は古い方の「factor」を使用して「seq 1 100 | factor」(=1 から 100 までを素因数分解する)、「seq 1 100 | factor | awk 'NF == 2 { print $NF }'」(=1 から 100 までの素数を抽出する) などの使い方を試してみると面白いかもしれません。