aws-vaultを使った複数のAWS環境管理術
こんにちは、へたれです。
株式会社AidemyでModeloyという伴走型のDXプロジェクト内製化支援サービスを提供するチームに所属しています。
クラウドインフラをメインに、バックエンドからフロントエンドまで幅広く携わっています。
複数のプロジェクトに横断的に関わっており、頻繁に作業環境を切り替えることも多い中で、どのように管理しているか記事にしました。
TL;DR
自社のテスト環境や複数のお客様向けにAWS環境をセキュアに管理するために以下の方針を採用
- シークレットキーの管理はaws-vaultを使う
- profileを使い分け、素早く環境の切り替えが行えるようにする
Terraformの実行はaws-vault exec <profile-name> -- terraform plan
を使う。
CodeCommitの切り替えは.github/config
を使う。
はじめに
Modeloy Engineeringでは同時に複数社のお客様を支援することがあり、それぞれのお客様向けに異なるAWS環境で作業をする必要がありました。
その中でいくつか困りごとが出てきました。
- ローカル環境に生のシークレットキーを置くことの不安
- 複数の環境を頻繁に往来するときの手間
- 誤ったTerraformをapplyしないかの心配
これらの課題を解決するために導入したツールや運用方法をご紹介します。
導入したツールと運用
aws-vaultの導入
aw-vaultはAWSのシークレットキーをmacOSのKeyChainで管理してくれるツールです。
~/.aws/credentials
などに生データ保存せずに済み、アクセスにアカウントのパスワード入力が必要となるため、漏洩によるセキュリティリスクを抑えることが可能です。
またaws-vault実行時にプロファイル指定でき、すべてのコマンドをaws-vault経由で実行することで切り替えが容易になるのもとても便利です。
導入はHomebrew経由で実施できるので非常に簡単です。
使用時の雰囲気はこんな感じです。
# プロファイルにシークレットキーを登録
$ aws-vault add oriishi-t
Enter Access Key ID:
Enter Secret Access Key:
# プロファイルの登録を確認
$ aws-vault list
Profile Credentials Sessions
======= =========== ========
oriishi-t oriishi-t -
# aws-vaultを通じて任意のプロファイルで任意のコマンドを実行
$ aws-vault exec -- aws sts get-caller-identity
XXXXXXXXXXX arn:aws:iam::XXXXXXXXXXX:user/oriishi-t XXXXXXXXXXX
# aws-vaultを通じて任意のプロファイルでAWSコンソールへのログインも可能
$ aws-vault login oriihi-t
またスイッチロールやMFAを利用する場合は、いつもどおり~/.aws/config
に各種設定値を書きます。
[profile oriishi-t]
region=ap-northeast-1
output=text
[profile env1]
source_profile=oriishi-t
role_arn=arn:aws:iam::XXXXXXXXXXX:role/RoleName
aws_mfa_device=arn:aws:iam::XXXXXXXXXXX:mfa/device-name
mfa_serial=arn:aws:iam::XXXXXXXXXXX:mfa/device-name
[profile env2]
source_profile=oriishi-t
role_arn=arn:aws:iam::XXXXXXXXXXX:role/RoleName
aws_mfa_device=arn:aws:iam::XXXXXXXXXXX:mfa/device-name
mfa_serial=arn:aws:iam::XXXXXXXXXXX:mfa/device-name
[profile env3]
source_profile=oriishi-t
role_arn=arn:aws:iam::XXXXXXXXXXX:role/RoleName
aws_mfa_device=arn:aws:iam::XXXXXXXXXXX:mfa/device-name
mfa_serial=arn:aws:iam::XXXXXXXXXXX:mfa/device-name
これだけで使えるようになります。
自分はプロファイル名に以下の情報を含めています。
- プロジェクト名
- 環境名(dev, stg, prdなど)
- IAMロールに付与された権限 (admin, roなど)
そうすることで以下のような効果が得られています。
- どのプロファイルで作業すべきかがすぐにわかる
- 作業するプロファイルを毎回手入力するので、作業環境を間違えることが少なくなる
terraformとの併用
Terraformで利用する際にはバックエンドにprofileパラメタを指定します。
profile = "env1"
実行時はaws-vaultを通すだけです。
$ aws-vault env1 -- terraform init -backend-config=env1.tfbackend
$ aws-vault env1 -- terraform apply
注意
aws-vault exec oriihi-t -- tf apply
のようにexecにそのままコマンドを渡すと、エイリアスが継承されません。
一方でaws-vault exec oriishi-t
を実行すると、シェルが新規に展開されるため、.bashrc
等に設定しているエイリアスも使えるようになります。
codecommitとの併用
aws-vaultを使ったCodeCommitへのクレデンシャル情報の設定も可能です。
GitHubとCodeCommitの併用が必要な場合はリモートリポジトリを複数設定することも可能です。
クレデンシャルヘルパーの設定をしましょう。
...
[remote "prj1"]
url = https://git-codecommit.ap-northeast-1.amazonaws.com/v1/repos/repository-name
fetch = +refs/heads/*:refs/remotes/prj1/*
[credential "https://git-codecommit.ap-northeast-1.amazonaws.com"]
helper = !aws-vault exec env1 -- aws codecommit credential-helper $@
UseHttpPath = true
...
以上の設定ができればCodeCommitとのpush/pull操作が可能になるはずです。
# MFAが有効な場合のみ必要
$ aws-vault exec env1 -- echo ''
# prj1リモートを使用
$ git push prj1 HEAD
注意
gitのクレデンシャルヘルパーはMFAの認証ができません。
aws-vault exec env1 -- echo ''
を実行することで、あらかじめMFAの認証を通しておき、有効期限のうちにgitの操作を済ませてしまいます。
また、aws-vaultで実行している環境下ではAWS_VAULT
環境変数が設定されており、これが設定されているとaws-vaultが使えないためaws-vault exec env1 -- git push prj1 HEAD
のようなコマンドは使えません。
注意
CodeCommitのクレデンシャルヘルパーはKeyChainに認証情報を保存するため、認証情報が切れる時に403エラーを吐き出します。
403エラー時の対応として、KeyChainから対象の情報を削除してください。
終わりに
ここで紹介した運用を導入した結果、シークレットキーの安全な管理と利便性の向上が両立できました。
新しくジョインしたメンバーにもこの運用を広めており、改善を重ねていきがながらこの運用をチームのスタンダードにしていきたいと思っています。
今日も一日、ご安全に!
Discussion
下記設定を使用することで、わざわざ execして認証情報通ったshellを作成しないでも
--profile <profile名>
オプションを使用することができますよaws-vaultがデフォルト1時間なので、
--duration 12h
オプションを渡してあげるのが個人的には好みですおお、ありがとうございます!
credential_process は知らなかったです...情報提供感謝します!
なるほど...頻度が多くなってくるとこういった対策は有効ですね。