Chefを使ったfluentd(treasure-data-agent)のセットアップ手順
Chefを使ってCentOSにfluentdをセットアップしてみたので、
手順を書き残しておきます。
Installing Fluentd Using Chef | Fluentd
http://docs.fluentd.org/articles/install-by-chef
基本的に上記サイトに記載されている手順に沿いますが、
このエントリでは、
nginxをセットアップし、そのログをS3(AWS)にログを送ってみます。
以下エントリのように、
KnifeSolo+Berkshelfの環境があることを前提に説明します。
Chef(Knife)+Berkshelfを使ってサーバを自動構築する手順
http://takemikami.com/archives/1423
Berkshelfを用いてfluentdのCookbookを取得する
Berksfileを以下の用に変更(nginx/iptablesを追加)します。
Berksfile
site :opscode
cookbook 'nginx'
cookbook 'td_agent', git: 'https://github.com/treasure-data/chef-td-agent.git'
以下のコマンドで、opscodeのリポジトリからnginx,fluentdと依存するcookbookを取得します。
$ bundle exec berks --path=cookbooks
fluentdをセットアップするレシピを作成する
以下のコマンドを実行し、mycookbookというcookbookを作成します。
$ bundle exec knife cookbook create mycookbook -o site-cookbooks/
** Creating cookbook mycookbook
** Creating README for cookbook: mycookbook
** Creating CHANGELOG for cookbook: mycookbook
** Creating metadata for cookbook: mycookbook
作成したCookbookのmetadata.rbにnginx,fluentdへの依存情報を追記します。
site-cookbooks/mycookbook/metadata.rb
depends 'nginx'
depends 'td_agent'
attributesで、fluentdインストール時のパラメータを指定します。
site-cookbooks/mycookbook/attributes/default.rb
default[:td_agent] = {
:api_key => 'foo_bar_buz',
:plugins => [
's3'
]
}
nginx, fluentdをインストールするレシピを作成します。
site-cookbooks/mycookbook/recipes/default.rb
include_recipe "nginx"
include_recipe "td_agent"
以上のレシピで、nginxとfluentd及びS3用pluginがインストールできます。
レシピを適用しfluentdをセットアップする
対象ノード用のjsonファイルを作成します。
nodes/<対象ノートのホスト名>.json
{ "run_list": [ "recipe[mycookbook]" ] }
以下のコマンドを実行し、レシピを対象ノードに適用します。
$ bundle exec knife solo cook <対象ノートのホスト名>
Running Chef on pwebap02...
Checking Chef version...
※省略※
Chef Client finished, 14 resources updated
適用が終わったら、対象ノードにsshで接続して、
以下のコマンドを実行すると、サービスが追加されていることが確認できます。
$ sudo chkconfig --list
※省略※
nginx 0:off 1:off 2:on 3:on 4:on 5:on 6:off
※省略※
td-agent 0:off 1:off 2:on 3:on 4:on 5:on 6:off
※省略※
fluentdでS3にログを送る設定を追加する
fluentd設定ファイルのテンプレートを作成します。
以下のように、
source部で収集するログの情報を設定、
match部で収集したログの転送先を設定します。
site-cookbooks/mycookbook/templates/default/td-agent-nginx.erb
<source>
type tail
format /^(?<remote_addr>[^ ]*) - (?<remote_user>[^ ]*) \[(?<time_local>[^\]]*)\] "(?<request_method>[^ ]*) (?<request_path>[^ ]*) (?<http_version>[^"]*)" (?<response_code>[^ ]*) (?<response_size>[^ ]*) "(?<http_referer>[^"]*)" "(?<remote_client>[^"]*)"/
path /var/log/nginx/access.log
pos_file /var/log/td-agent/nginx-access-log.pos
tag nginx.access
</source>
<match nginx.access>
type s3
aws_key_id <%= @aws_access_key_id %>
aws_sec_key <%= @aws_secret_access_key %>
s3_bucket <%= @aws_s3_bucket %>
s3_endpoint <%= @aws_s3_end_point %>
path logs/
time_slice_format nginx/%Y%m/access.log.%Y%m%d%H
time_slice_wait 10m
buffer_type file
buffer_path /var/log/td-agent/buffer/nginx-access
</match>
レシピに、先ほどのテンプレートを適用する処理を追記します。
# td_agentのレシピを適用すると設定ファイルをデフォルトに戻してしまうので、
# ここでは、fluentd未インストール時のみ適用するようにしています。
# もっとエレガントなやり方があるような気がしますが、、
site-cookbooks/mycookbook/recipes/default.rb
include_recipe "nginx"
unless File.exists?("/etc/init.d/td-agent")
include_recipe "td_agent"
end
template "/etc/td-agent/td-agent.conf" do
source "td-agent-nginx.erb"
mode 644
owner "root"
group "root"
variables({
:aws_access_key_id => "<ここにaccess_key_idを入れる>",
:aws_secret_access_key => "<ここにsecret_access_keyを入れる>",
:aws_s3_end_point => "<ここにs3のendpointを入れる>",
:aws_s3_bucket => "<ここにbucket名を入れる>"
})
notifies :restart, "service[td-agent]"
end
service "td-agent"
次に、以下のコマンドを実行し、レシピを対象ノードに適用します。
$ bundle exec knife solo cook <対象ノートのホスト名>
Running Chef on pwebap02...
Checking Chef version...
※省略※
Chef Client finished, 3 resources updated
fluentdでログが転送される動作を確認する
適用が終わったら、
対象ノードにsshで接続し、fluentdのログを確認してみます。
$ tail /var/log/td-agent/td-agent.log
※省略※
2013-11-13 08:18:30 +0000 [info]: adding source type="tail"
2013-11-13 08:18:30 +0000 [info]: adding match pattern="nginx.access" type="s3"
2013-11-13 08:18:33 +0000 [info]: following tail of /var/log/nginx/access.log
以下のコマンドを実行し、nginxにhttpでアクセスします。
$ curl http://127.0.0.1/
<!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.1//EN" "http://www.w3.org/TR/xhtml11/DTD/xhtml11.dtd">
※省略※
</html>
httpでアクセスすると「/var/log/td-agent/buffer/」配下に、
「nginx-access.nginx」で始まる長いファイル名のファイルができているはずです。
ファイルの中身を見てみると以下のようになっています。
2013-11-13T08:30:51+00:00 nginx.access {"remote_addr":"127.0.0.1","remote_user":"-","time_local":"13/Nov/2013:08:30:51 +0000","request_method":"GET","request_path":"/","http_version":"HTTP/1.1","response_code":"200","response_size":"3698","http_referer":"-","remote_client":"curl/7.19.7 (x86_64-redhat-linux-gnu) libcurl/7.19.7 NSS/3.13.6.0 zlib/1.2.3 libidn/1.18 libssh2/1.4.2"}
このファイルが一定時間経過すると、指定したS3のbucketに転送されます。
あとは、S3に転送さればファイルを、
ElasticMapReduceを使って集計したりすれば美しいですねww