サーバー設定ツール「Chef」をより便利に使うためのテクニック 5ページ

データを暗号化する

 Data Bagではデータを暗号化した上で格納することも可能だ。パスワードやそのハッシュなど、閲覧されると問題が発生する可能性のあるデータを格納する場合などに利用できる。なお、暗号化にはopensslコマンドで作成した鍵ファイルを使用し、この鍵ファイルは設定対象のマシンそれぞれに格納しておく必要がある。公開鍵方式ではなく、1つの鍵ファイルで暗号化も復号もできるため、この鍵ファイルの管理には注意してほしい。

 暗号化に使用する鍵ファイルは、以下のようにして作成できる。

$ openssl rand -base64 512 > secret_key

 これで、secret_keyというファイルに鍵情報が格納される。

 データを暗号化してData Bagに格納するには、「knife data bag from file」コマンドを「–secret-file <鍵ファイル>」オプション付きで実行する。

$ knife data bag create initial_accounts_secret
Created data_bag[initial_accounts_secret]
$ knife data bag from file initial_accounts_secret default.json --secret-file secret_key
Updated data_bag_item[initial_accounts_secret::default]

 このように鍵ファイルを指定して格納したデータは、showコマンドで表示させてもその中身は分からない。

$ knife data bag show initial_accounts_secret default
groups:
  cipher:         aes-256-cbc
  encrypted_data: TLa/BNAc26FSpOABekf7ALvd3KhQ/iXZzggP/hSAiqBn3WYk63h7hX+Aguta
  0zMW

  iv:             v6fzk6WYzYayr6IGj7j38A==

  version:        1
id:     default
users:
  cipher:         aes-256-cbc
  encrypted_data: x98kLVBQr0k3YoDmOtyRWtbgpOMAEeZFGJJ2kAGeEz1JHc92a3fb/O+Ky/j1
  9kJRbgFDkrXBkN7UDLpXbAAx0YPbOhhXQdOs/kDXOyVsjztBRgzdJB/I/6ZO
  +LytQpz7px6M8Jk8sd2V1lGYgUFm7Fq+DQjXlo3SLKMPqGVLxjJjanHLtm2f
  zZa/op2kAFWlGDamhBoWwrXbPGNcWiBeArRPvMzJe4BT52/czse36WU5OyGz
  TcOKpWVhl03lnh5vZ/v+cthDLl+hxsWGuPUvGY3suIrxd2SKHDGKl+X+HWc=

  iv:             aYvs9pPh5wRPAoBGu+DDSQ==

  version:        1

 もし暗号化されたデータの内容を確認したい場合は、「–secret-file <鍵ファイル>で暗号化に使用した鍵ファイルを指定すれば良い。

$ knife data bag show --secret-file secret_key initial_accounts_secret default
groups:
  gid:  1000
  name: taro
id:     default
users:
  gid:      taro
  home:     /home/taro
  name:     taro
  password: $6$OmC3KootOURrqOaP$63rwQ2bSE8op8wXa.ZWzgxm/iGvePTzEL5lOntmkPyYh5Qwh4lWs2DtyoEHcvsbYV5Q6a2ezzrZueb2ydrkhz0
  shell:    /bin/bash
  uid:      1000

 いっぽう、暗号化されたData Bag項目にアクセスしたい設定対象サーバーには、あらかじめ鍵ファイルを配置しておく必要がある。鍵ファイルのデフォルトの保存先は、/etc/chef/encrypted_data_bag_secretだ。scpコマンドなどを利用してサーバーにコピーし、配置しておこう。

# cp secret_key /etc/chef/encrypted_data_bag_secret

 Recipeから暗号化されたData Bag項目にアクセスするには、data_bag_item関数の代わりにChef::EncryptedDataBagItem.load関数を使用する。以下の例は、先に紹介したRecipeを、暗号化されたData Bag項目を使用するよう書き換えたものだ。

accounts = data_bag('initial_accounts_secret')
accounts.each do |id|
  # item = data_bag_item('initial_accounts_secret', id)
  item = Chef::EncryptedDataBagItem.load('initial_accounts_secret', id)

  item['groups'].each do |g|
    group g['name'] do
      gid g['gid']
      action :create
    end
  end

  item['users'].each do |u|
    user u['name'] do
      home u['home']
      password u['password']
      shell u['shell']
      uid u['uid']
      gid u['gid']
      supports :manage_home => true
      action :create
    end
  end
end

chef-solo環境でData Bagを使う

 Chef Serverを使用しないchef-solo環境ではデータを一元管理するデータベースがあるわけではなく、knifeコマンドも利用できない。その代わりとして、任意のディレクトリにJSONファイルを配置することでData Bagとして利用できるようになっている。

 Data Bagとして利用するディレクトリは、chef-soloの設定ファイルである/etc/chef/solo.rb内で指定できる。たとえば「/root/chef-repo/data_bags」ディレクトリをData Bagの格納先として利用する場合、以下の行をsolo.rbファイルに追加しておけば良い。

data_bag_path "/root/chef-repo/data_bags"

 chef-solo環境では、ここで指定したディレクトリ内にサブディレクトリを作成し、そこにJSONファイルを配置する。作成したサブディレクトリData Bag名として認識される。

 たとえば、/root/chef-repoというディレクトリをChefリポジトリとして使っている場合、「initial_accounts」というData Bagを作成するには以下のようにする。

# mkdir -p /root/chef-repo/data_bags/initial_accounts

 このディレクトリにJSONファイルを配置することで、Data Bag項目としてそこに記述されたデータにアクセスできる。

$ cp default.json /root/chef-repo/data_bags/initial_accounts/

 CookbooksやRecipe側の記述内容についてはChef-Solo環境でもChef Server環境の場合と同じだ。

knife-solo環境でData Bagを使う

 knife-soloでは、内部的にはchef-soloが使われているため、基本的にはchef-soloの場合と同様にJSONファイルでData Bagが管理される。作業用マシン側のknife.rbファイルに作業用マシン上でData Bagが格納されているディレクトリを指定しておけば、「knife solo cook」コマンドの実行時にそのディレクトリも設定対象のマシンに転送される。

Chef Server構築の手間なしに利用できるknife-soloは有力な選択肢に

 今回解説したknife-soloは、Chef Serverを構築することなしに、複数台サーバーの設定を容易に行えるツールだ。これを利用することで複数台サーバーの設定管理を一元管理できるようになるので、Chefを導入するハードルを大幅に下げることができる。とはいえ、knife-soloではサーバーの管理者が複数いる場合、作業用マシン上のCookbookなどの同期が必要となる。そのため、そういった環境ではChef Serverを利用したほうが良い場合もある。環境に応じて、最適な構成を検討するべきだろう。

 また、Data Bagは作業内容と設定内容を分離するためのツールだ。これは、一般的なプログラミングにおけるプログラムとデータの分離に相当すると考えれば分かりやすいだろう。プログラムとデータを分離することで保守性能や再利用性が向上するが、これをサーバーの環境設定においても導入したのがData Bagとなる。やや導入は面倒であるが、Data Bagを使うことで保守性の高いCookbookを作成できるので、うまく活用すると良いだろう。