IAMというのは例のAWSのアレ。ユーザのアカウントと権限を管理するやつ。
このサービス、機能が多くてややこしいところがあり、具体的には以下のポリシーで運用するときにそのものズバリの情報がすぐに見つからなかったので、この場でまとめとこうかなって思った。
- 原則、ユーザ管理操作は禁止
- しかしそれぞれのユーザは自分のパスワードを更新できるようにしたい
- さらにそれぞれのユーザは、自分だけAPI AccessKeyの発行をしたい
なお管理のために miam を使う。miamの使い方は説明しませんが、簡単なのでREADMEなど見て入れてください。
原則、ユーザ管理操作は禁止
最初に NotAction
でiam系のAPI利用を前面禁止する。許可がホワイトリスト型になる。
group "PowerUser" do policy "PowerUser-NotAllowIam" do {"Version"=>"2012-10-17", "Statement"=>[{"Effect"=>"Allow", "NotAction"=>"iam:*", "Resource"=>"*"}]} end end
しかしそれぞれのユーザは自分のパスワードを更新できるようにしたい
こんな感じの許可でOK。というか、公式にだいたい書いてある通り。
iam:ListUsers
も許可しないと、AWSのコンソールからユーザリストを表示できないので、操作があまりにも不便になる点に注意。
group "PowerUser" do policy "PowerUser-ChangePassword" do {"Version"=>"2012-10-17", "Statement"=> {"Effect"=>"Allow", "Action"=> ["iam:ListUsers", "iam:ChangePassword", "iam:GetAccountPasswordPolicy"], "Resource"=>"*"}} end end
さらにそれぞれのユーザは、自分だけAPI AccessKeyの発行をしたい
「自分だけ」というのが鍵で、 "Resource"=>"*"
などと指定してしまうと他人のAPI Keyも発行できて、そういう便利さは要らないので。
自分のユーザのarnだけに絞って操作可能な状態にしないといけない。
ということで、以下のようなマクロ的なメソッドを、オープンクラスで定義する。 IAMFile
はただのルビーファイルなので冒頭に書いとけばいい。
追記: コメントにある通り、オープンクラスを使うよりmiamのテンプレート機能を使う方がよく、そもそも ${aws::*}
といったAWS側で用意された変数を使うことも可能なようなので、この実装は「ふ〜んこんな手もあるんだ〜」といった程度のものと捉えてください。
AWS_ACCOUNT_ID = 12345678... class Miam::DSL::Context::User def attach_accesskey_policy_for(username) policy "#{username}-accesskey-creatable" do {"Version"=>"2012-10-17", "Statement"=> [{"Sid"=>"Stmt#{username.gsub(/[^a-zA-Z0-9]/, '')}20160107", "Effect"=>"Allow", "Action"=>["iam:GetUser", "iam:*AccessKey*"], "Resource"=>["arn:aws:iam::#{AWS_ACCOUNT_ID}:user/#{username}"]}]} end end end
気をつけることとして、 Sid
は アルファベットと数字 しか使えないらしい。ユーザ名にはその他の文字列も使えるのでRuby側でなんとかしておく。
その後、それぞれのユーザのカスタムポリシーとしてこんな感じにできる。
user "udzura", :path=>"/" do login_profile :password_reset_required=>true groups( "PowerUser" ) attach_accesskey_policy_for("udzura") end
あとは miam
コマンドで確認しつつ適用。
こんな感じで、いい感じのIAMポリシーは難しいですが、やっていき方を共有するといいと思います。あととにかく miam は素晴らしいと思います。
それでは、良いお年を!