ども、 cloudpackかっぱ (@inokara) です。

はじめに

fluentd 復習シリーズ第二弾。fluentd-plugin-secure-forward をざっくりと試してみたい。

参考

fluent-plugin-secure-forward について

機能

fluent-plugin-secure-forward は以下のような機能を提供する。

  • SSL によるセキュアなデータ転送(自己証明書利用可能)
  • 共有鍵を利用した認証によるデータ転送
  • ユーザー名とパスワードを利用した認証によるデータ転送
  • 接続元 IP アドレスによってデータ転送の許可、拒否の設定

上記のような機能を提供することにより拠点間(データセンター間)等でも安全なデータ転送が可能になるかと思われる。

気になるセキュアな転送の仕組み

以下の資料で 8 ページ〜 13 ページに out_secure_forwardin_secure_forward 間の遷移が記載されている。

また、ドキュメントにも同様の内容が記載されている。

検証構成とデータの流れ

今回の構成

以下のようにシンプルな構成で。
fluentd-plugin-secure-forward を利用したセキュアなログデータ転送: 構成図
通常の fluentd では TCP 24224 ポートと UDP 24224 ポートを利用しているが、fluent-plugin-secure-forward では TCP 24284 ポート を利用することになる。

今回のデータの流れ

fluent-cat を叩いてローカルホストの in_forward でレコードを受け付け、out_secure_forward から別のホストの in_secureforward に転送し type stdout を利用して td-agent.log に出力する。
fluentd-plugin-secure-forward を利用したセキュアなログデータ転送: データの流れ

インストールと設定

インストール

td-agent にて試す。

/usr/lib64/fluent/ruby/bin/gem install --no-ri --no-rdoc -V fluent-plugin-secure-forward

fluentd のバージョンは以下の通り。

$ /usr/lib64/fluent/ruby/bin/fluentd --version
fluentd 0.10.55

Client(out_secure_forward)側の設定

こちらの Minimal configurations を参考に以下のように設定した。

<source>
  type forward
  port 24224
  bind 0.0.0.0
</source>

<match secure.data.**>
  type secure_forward
  shared_key    foo
  self_hostname 172.17.0.3 # Client(自分自身の IP アドレス)
  <server>
    host 172.17.0.2 # Server(転送先の IP アドレス)
  </server>
</match>

shared_key は Client と Server 側で同じ内容にしておく必要がある。

Server(in_secure_forward)側の設定

同じく こちら の Minimal configurations を参考に以下のように設定した。

<source>
  type secure_forward
  shared_key      foo
  self_hostname   172.17.0.2 # Server(自分自身の IP アドレス)
  cert_auto_generate  yes
</source>

<match secure.**>
  type stdout
</match>

<match **>
  type file
  path /tmp/unmatch.log
</match>

Client 側と shared_key を合わせておく。また、 cert_auto_generate yes にしておくことで証明書を自動生成する。そして、 secure.** タグにマッチするレコード(fluent-plugin-secure-forward を利用して転送されたレコード)は type stdout でログに出力される。それ以外のレコードは type file/tmp/unmatch.log に出力される。

試す

セキュアな転送

out_secure_forward 側で…

$ echo '{"status":"2xx","method":"GET"}' | /usr/lib64/fluent/ruby/bin/fluent-cat secure.data.`hostname`
$ echo '{"status":"2xx","method":"GET"}' | /usr/lib64/fluent/ruby/bin/fluent-cat secure.data.`hostname`
$ echo '{"status":"2xx","method":"GET"}' | /usr/lib64/fluent/ruby/bin/fluent-cat secure.data.`hostname`

in_secure_forward 側で…受信(/var/log/td-agent/td-agent.log を確認)を確認。

2015-03-10 00:11:27 +0000 secure.data.b1045fb1a7e0: {"status":"2xx","method":"GET"}
2015-03-10 00:11:28 +0000 secure.data.b1045fb1a7e0: {"status":"2xx","method":"GET"}
2015-03-10 00:11:29 +0000 secure.data.b1045fb1a7e0: {"status":"2xx","method":"GET"}

tcpdump で確認

out_secure_forward 側で…

$ echo '{"status":"2xx","method":"GET"}' | /usr/lib64/fluent/ruby/bin/fluent-cat secure.data.`hostname`

を実行。

in_secure_forward 側で…

tcpdump tcp port 24284 -A

で待ち構えていると…。

00:16:55.863459 IP 172.17.0.3.50366 > c5f3ba9263c6.24284: Flags [P.], seq 2981446686:2981446723, ack 7202417, win 273, options [nop,nop,TS val 57989554 ecr 57959048], length 37
E..Y?.@.@.............^...D..m.q....Xs.....
.t...tb..... H..k.g.....;'.]..HV.7.U.|.Zf..G
00:16:55.863512 IP c5f3ba9263c6.24284 > 172.17.0.3.50366: Flags [.], ack 37, win 252, options [nop,nop,TS val 57989554 ecr 57989554], length 0
E..4.T@.@..H........^....m.q..DC....XN.....
.t...t..
00:16:55.863698 IP 172.17.0.3.50366 > c5f3ba9263c6.24284: Flags [P.], seq 37:90, ack 1, win 273, options [nop,nop,TS val 57989554 ecr 57989554], length 53
E..i?.@.@..u..........^...DC.m.q....X......
.t...t......0t..$/l.:..!......b.vi....N.T.b
~$.....Pi.E.
00:16:55.863727 IP c5f3ba9263c6.24284 > 172.17.0.3.50366: Flags [.], ack 90, win 252, options [nop,nop,TS val 57989554 ecr 57989554], length 0
E..4.U@.@..G........^....m.q..Dx....XN.....
.t...t..
00:16:55.863873 IP 172.17.0.3.50366 > c5f3ba9263c6.24284: Flags [P.], seq 90:127, ack 1, win 273, options [nop,nop,TS val 57989554 ecr 57989554], length 37
E..Y?.@.@.............^...Dx.m.q....Xs.....
.t...t...... |.X..y.......m...'....;.....T.y.
00:16:55.863899 IP c5f3ba9263c6.24284 > 172.17.0.3.50366: Flags [.], ack 127, win 252, options [nop,nop,TS val 57989554 ecr 57989554], length 0
E..4.V@.@..F........^....m.q..D.....XN.....
.t...t..
00:16:55.864034 IP 172.17.0.3.50366 > c5f3ba9263c6.24284: Flags [P.], seq 127:196, ack 1, win 273, options [nop,nop,TS val 57989554 ecr 57989554], length 69
E..y?.@.@..c..........^...D..m.q....X......
.t...t......@q.q=)....0Y._. ...Cf..8.g.........Aw.L.....f..I.(....s._......7.
00:16:55.864059 IP c5f3ba9263c6.24284 > 172.17.0.3.50366: Flags [.], ack 196, win 252, options [nop,nop,TS val 57989554 ecr 57989554], length 0
E..4.W@.@..E........^....m.q..D.....XN.....
.t...t..

上記の通り転送されるデータはランダムな文字列となり内容を読み取ることが出来ない。

ということで

fluentd-plugin-secure-forward を利用することで…

  • SSL を利用して拠点間のセキュアなログデータ転送が行える
  • 認証や IP アドレス制限を行うことで更に安心

気になるところ

  • データの暗号化、復号化時の負荷→後で比較してみる
  • その他のオプション→ソースを見てみる

fluentd-plugin-secure-forward をざっくりと触ってみましたが、データセンター間等で安全なログデータ転送を行いたい場合等にお手軽に利用出来るので是非選択したいプラグインだと思う。

元記事はこちらです。
fluentd 復習(2)〜 fluentd-plugin-secure-forward を利用したセキュアなログデータ転送〜