読者です 読者をやめる 読者になる 読者になる

OS X キーチェーンから環境変数をセットするツールを作りました

ツール セキュリティ 開発環境

こんにちは、技術部の福森 (@sora_h) です。

最近は環境変数に API トークンや credential といった認証情報を入れる事が増えてきています。 たとえば、AWS を利用するツールでは AWS_ACCESS_KEY_ID, AWS_SECRET_ACCESS_KEY といった環境変数にだいたいの場合で対応しています。

そのため、~/.bashrc~/.zshrc などシェルの設定に export を書いておき常に使える状態にしている方も多いと思いますが、 それって実は危険ではないでしょうか?

例えば、下記のようなリスクが考えられます:

  • 意図せず情報が利用されて意図しない副作用が発生してしまう危険性
    • 本番に変更を与えるつもりはなかったけれど事故を起こしてしまう等
  • 悪意のあるスクリプトを実行した際に環境変数を送信などされてしまう危険性

事故や漏洩を防ぐためにも、筆者はかならずセットする必要はあまりないと考えています。 前から個人的に aws-exec() { env AWS_ACCESS_KEY_ID=... $* } のようなシェル関数を利用していたのですが、 この方法をもっと広めたほうが良いのでは?、と社内で意見を貰ったため汎用的なツールにしてみました。

大きな特長は、平文ではなく OS X のキーチェーンに値を保存するようにした点です。 これにより plain text で残らない上、パスフレーズの確認といったアクセスコントロールを調整できるようになりました。 (設定次第ですが) 読み出しが発生するタイミングでプロンプトさせる事ができ、意図しない読み出しを防ぐことができます。

また、このツールを利用して気軽にいくつかの環境変数の組合せ (アカウントや設定類) を簡単に切り替えながら開発する事ができるようになりました。 同じサービスのトークンを複数切り替える、といった際にも便利だと思います。

注意

  • OS X の keychain を利用するため、OS X のみのサポートです

インストール

homebrew

$ brew install https://raw.githubusercontent.com/sorah/envchain/master/brew/envchain.rb

make

$ git clone https://github.com/sorah/envchain.git
$ cd envchain
$ make

$ make install
(あるいは手動で)
$ cp ./envchain ~/bin/

使い方

環境変数をセットする

envchain --set <namespace> <variable name> <variable name>... のように呼び出す事で環境変数を keychain に登録できます。 envchain では複数の環境変数をセットとして登録して切り替えて利用する事ができます。

$ envchain --set foo SECRET_TOKEN USERNAME
foo.SECRET_TOKEN: foobar
foo.USERNAME: alice
$ envchain --set bar SECRET_TOKEN
bar.SECRET_TOKEN: hogehoge

セットした環境変数を利用する

envchain <namespace> <cmd> <arg>... のように呼び出す事で namespace から登録してある環境変数を読み込んでコマンドを実行する事ができます。

$ printenv SECRET_TOKEN || echo 'not found'
not found

$ envchain foo printenv SECRET_TOKEN
foobar
$ envchain foo printenv USERNAME
alice

$ envchain bar printenv SECRET_TOKEN
foobar

その他

envchain --set --noechoenvchain --set --require-passphrase といったオプションも存在します。詳細は envchain コマンド (引数無し) のヘルプを参照してください。

セキュリティについて

環境変数に機密情報を入れる上でのセキュリティに関して、筆者の見解を、個人のブログに書いたのでこちらを参照ください: http://diary.sorah.jp/2014/06/05/securing-environment-variables

仕組み

OS X の Security framework に含まれる Keychain Service を利用しています。 (リファレンス)
namespace の前に "envchain-" をつけたもの (例: envchain-foo, envchain-bar) を KeychainItem のサービス名、環境変数名をアカウント名としてデフォルトの keychain に登録するようにしています。

OS X のキーチェーンアクセス (/Applications/Utilities/Keychain Access.app) からアイテムを探す事で登録されている様子を見る事ができます。

Keychain Access

/* */ @import "/css/theme/report/report.css"; /* */ /* */ body{ background-image: url('http://cdn-ak.f.st-hatena.com/images/fotolife/c/cookpadtech/20140527/20140527163350.png'); background-repeat: repeat-x; background-color:transparent; background-attachment: scroll; background-position: left top;} /* */ body{ border-top: 3px solid orange; color: #3c3c3c; font-family: 'Helvetica Neue', Helvetica, 'ヒラギノ角ゴ Pro W3', 'Hiragino Kaku Gothic Pro', Meiryo, Osaka, 'MS Pゴシック', sans-serif; line-height: 1.8; font-size: 16px; } a { text-decoration: underline; color: #693e1c; } a:hover { color: #80400e; text-decoration: underline; } .entry-title a{ color: rgb(176, 108, 28); cursor: auto; display: inline; font-family: 'Helvetica Neue', Helvetica, 'ヒラギノ角ゴ Pro W3', 'Hiragino Kaku Gothic Pro', Meiryo, Osaka, 'MS Pゴシック', sans-serif; font-size: 30px; font-weight: bold; height: auto; line-height: 40.5px; text-decoration: underline solid rgb(176, 108, 28); width: auto; line-height: 1.35; } .date a { color: #9b8b6c; font-size: 14px; text-decoration: none; font-weight: normal; } .urllist-title-link { font-size: 14px; } /* Recent Entries */ .recent-entries a{ color: #693e1c; } .recent-entries a:visited { color: #4d2200; text-decoration: none; } .hatena-module-recent-entries li { padding-bottom: 8px; border-bottom-width: 0px; } /*Widget*/ .hatena-module-body li { list-style-type: circle; } .hatena-module-body a{ text-decoration: none; } .hatena-module-body a:hover{ text-decoration: underline; } /* Widget name */ .hatena-module-title, .hatena-module-title a{ color: #b06c1c; margin-top: 20px; margin-bottom: 7px; } /* work frame*/ #container { width: 970px; text-align: center; margin: 0 auto; background: transparent; padding: 0 30px; } #wrapper { float: left; overflow: hidden; width: 660px; } #box2 { width: 240px; float: right; font-size: 14px; word-wrap: break-word; } /*#blog-title-inner{*/ /*margin-top: 3px;*/ /*height: 125px;*/ /*background-position: left 0px;*/ /*}*/ /*.header-image-only #blog-title-inner {*/ /*background-repeat: no-repeat;*/ /*position: relative;*/ /*height: 200px;*/ /*display: none;*/ /*}*/ /*#blog-title {*/ /*margin-top: 3px;*/ /*height: 125px;*/ /*background-image: url('http://cdn-ak.f.st-hatena.com/images/fotolife/c/cookpadtech/20140527/20140527172848.png');*/ /*background-repeat: no-repeat;*/ /*background-position: left 0px;*/ /*}*/