aws:PrincipalArn 条件コンテキストキーで IAM グループのプリンシパル ARN を指定できるのか試してみた
コンバンハ、千葉(幸)です。
とある事情から IAM の AWS ドキュメントを上から下まで読んでいたのですが、IAM アクセスアナライザーの結果(Finding)のフィルタリングに関する記述で気になる部分を見つけました。
- Principal ARN – Use this property to filter on the ARN of the principal (IAM user, role, or group) used in an aws:PrincipalArn condition key. To filter by Principal ARN, type all or part of the ARN of the IAM user, role, or group from an external AWS account reported in a finding.
機械翻訳結果はこちら。
- プリンシパル ARN - aws:PrincipalArn 条件キーで使用されるプリンシパル(IAM ユーザー、ロール、またはグループ)の ARN でフィルタリングするには、このプロパティを使用します。プリンシパルARNでフィルタリングするには、発見で報告された外部AWSアカウントのIAMユーザー、ロール、またはグループのARNのすべてまたは一部を入力します。
IAM アクセスアナライザーによるリソースベースポリシーの分析により「結果(Finding)」が生成されます。その結果をフィルタリングするためにPrincipal ARN
を指定できる、ということが記されています。
気になるのはプリンシパルの中にグループが含まれていることで、これはおそらく IAM グループを指しているのだと考えました。IAM ユーザーやロールはともかく、IAM グループが指定できるとすると違和感あるな……と感じたので調べてみました。
まとめ
aws:PrincipalArn
条件コンテキストキーの値に IAM グループの ARN を指定することはできるが、Effect(Allow / Deny)は正常に機能しない- IAM アクセスアナライザーの結果のフィルタリングに IAM グループのプリンシパル ARN を使用すること自体はできる
- でもそれを使う機会があるのかはちょっと分からない
今回の構成
検証を行う構成は以下のイメージです。
- 実行元アカウント:000000000000
- IAM ユーザー:Batchi
- IAM グループ
Administrator
に所属している - IAM ポリシー
AdministratorAccess
がアタッチされている
- IAM グループ
- IAM ユーザー:Batchi
- 実行先アカウント:999999999999
- S3 バケット:chibayuki-hoge-hoge
S3 バケットchibayuki-hoge-hoge
のバケットポリシーを変更しながら、挙動の変化を確認します。
IAM ユーザー側では AdministratorAccess がアタッチされているため、S3 バケット側で Allow が与えられればクロスアカウントでの S3 へのアクションが成功するようになります。
ドキュメントで aws:PrincipalArn について確認する
実際に手を動かす前に、もう少しドキュメントで調べてみます。
冒頭で引用した文章では、「 aws:PrincipalArn 条件キーで使用されるプリンシパル(IAM ユーザー、ロール、またはグループ)の ARN でフィルタリングするには……」とあります。
条件キーaws:PrincipalArn
については以下から確認できます。
このキーを使用して、リクエストを行ったプリンシパルの Amazon リソースネーム (ARN) をポリシーで指定した ARN と比較します。IAM ロールの場合、リクエストコンテキストは、ロールを引き受けたユーザーの ARN ではなく、ロールの ARN を返します。この条件キーで指定できるプリンシパルのタイプについては、「プリンシパルの指定」を参照してください。
前後の文章から、条件演算子として ARN 演算子と文字列演算子が使用できることと、この条件キーがすべてのリクエストコンテキストに含まれることが分かりました。ここで指定できるプリンシパルのタイプについては別ドキュメントに記載されているためそちらを確認します。
AWS JSON ポリシーの Principal 要素で指定できるプリンシパルとして以下が記載されています。
- AWS アカウントと ルートユーザー
- IAM ユーザー
- フェデレーティッドユーザー(ウェブ ID または SAML フェデレーションを使用)
- IAM ロール
- ロールを引き受けるセッション
- AWS サービス
- 匿名ユーザー(非推奨)
ここに IAM グループが記載されていないため、条件キーaws:PrincipalArn
においてもプリンシパルとしては指定できない、という捉え方をしたくなります。
やってみた
以下のパターンを試行します。
- Principal 要素で IAM グループを指定する
- Principal 要素で IAM ユーザーを指定する
- 条件キー aws:PrincipalArn で IAM グループを指定する
- 条件キー aws:PrincipalArn で IAM ユーザーを指定する
先に結論から言うと以下の結果になります。
パターン | バケットポリシー | アナライザーの結果 |
---|---|---|
1. Principal 要素で IAM グループ | 保存できない | ー |
2. Principal 要素で IAM ユーザー | 正常に機能する | 外部プリンシパルとして検出される |
3. aws:PrincipalArn で IAM グループ | 保存できるが機能しない | 条件の中のプリンシパル ARN として表示される |
4. aws:PrincipalArn で IAM ユーザー | 正常に機能する | 条件の中のプリンシパル ARN として表示される |
1. Principal 要素で IAM グループのプリンシパル ARN を指定してみる
本来の趣旨のaws:PrincipalArn
条件キーの前に、Principal 要素への指定を試してみます。ドキュメントではサポートされているプリンシパルのタイプとして記載されていないため、設定できないことを想像します。
以下のバケットポリシーをペーストし、アナライザーによる外部アクセスプレビューを実行します。
{ "Version": "2012-10-17", "Statement": [ { "Effect": "Allow", "Principal": { "AWS": [ "arn:aws:iam::000000000000:group/Administrator" ] }, "Action": "s3:*", "Resource": [ "arn:aws:s3:::chibayuki-hoge-hoge", "arn:aws:s3:::chibayuki-hoge-hoge/*" ] } ] }
プレビューでは「外部プリンシパル」として IAM グループのプリンシパル ARN が表示されます。
この状態でバケットポリシーの保存を実行すると、エラーとなります。
プレビューでは外部プリンシパルとして記録されるものの、実際にはバケットポリシーとして保存できない無効な値であることが分かりました。
2. Principal 要素で IAM ユーザーのプリンシパル ARN を指定してみる
続いてプリンシパルタイプとしてサポートされている IAM ユーザーを指定してみます。
バケットポリシーは以下の通りです。
{ "Version": "2012-10-17", "Statement": [ { "Effect": "Allow", "Principal": { "AWS": [ "arn:aws:iam::000000000000:user/Batchi" ] }, "Action": "s3:*", "Resource": [ "arn:aws:s3:::chibayuki-hoge-hoge", "arn:aws:s3:::chibayuki-hoge-hoge/*" ] } ] }
外部アクセスのプレビューでは、先ほどと同じように外部プリンシパルとして IAM ユーザーが記録されます。
バケットポリシーは正常に保存できます。
アクセスアナライザーでは IAM ユーザーが外部プリンシパルとして検出されています。
AWS CLI の実行
実行元の IAM ユーザーとして AWS CLI が実行できる状態です。
% aws sts get-caller-identity { "UserId": "AIDARVFQHJ6WFBJFMWCB4", "Account": "000000000000", "Arn": "arn:aws:iam::000000000000:user/Batchi" }
プリンシパルとして Allow が与えられているため、実行先アカウントにある S3 バケットの中身を問題なく参照できました。
% aws s3 ls chibayuki-hoge-hoge 2021-10-17 18:18:35 6 test.txt
3. 条件キー aws:PrincipalArn で IAM グループのプリンシパル ARN を指定してみる
本エントリの本題がここです。
ここまでは Principal 要素で IAM グループやユーザーを指定してきましたが、ここからは条件キーaws:PrincipalArn
にプリンシパル ARN を指定してみます。バケットポリシーは以下の通りです。
{ "Version": "2012-10-17", "Statement": [ { "Effect": "Allow", "Principal": "*", "Action": "s3:*", "Resource": [ "arn:aws:s3:::chibayuki-hoge-hoge", "arn:aws:s3:::chibayuki-hoge-hoge/*" ], "Condition": { "StringEquals": { "aws:PrincipalArn": "arn:aws:iam::000000000000:group/Administrator" } } } ] }
こちらの外部アクセスをプレビューすると以下のようになります。
↑これまでは「外部プリンシパル」にプリンシパル ARN が記載されていましたが、今回の指定では「すべてのプリンシパル」となっています。代わりに「条件」という箇所に IAM グループのプリンシパル ARN が記載されています。
このバケットポリシーを保存します。正常に保存できました。
アナライザーの結果で、IAM グループのプリンシパル ARN を指定してフィルタリングすると当該 S3 バケットの結果が表示されます。
冒頭の AWS ドキュメントはこのことを示していることが分かりました。
AWS CLI の実行
ふたたび実行元アカウントから S3 バケットにアクセスを試みます。アクセスは拒否されました。
% aws sts get-caller-identity { "UserId": "AIDARVFQHJ6WFBJFMWCB4", "Account": "000000000000", "Arn": "arn:aws:iam::000000000000:user/Batchi" } % aws s3 ls chibayuki-hoge-hoge An error occurred (AccessDenied) when calling the ListObjectsV2 operation: Access Denied
この条件キーの指定の仕方では Allow が与えられていないということです。IAM ユーザーBatchi
は IAM グループAdministrator
に所属していますが、aws:PrincipalArn 条件キーの値として IAM グループはサポートされていないためなんの効果ももたらしません。
今回のバケットポリシーは実質的になんの意味も持たず、空であるのと同じです。外部からアクセス可能な状態にはなっていません。
4. 条件キー aws:PrincipalArn で IAM ユーザーのプリンシパル ARN を指定してみる
最後に条件キーに IAM ユーザーの ARN を指定してみます。IAM ユーザーは Principal 要素でサポートされているプリンシパルタイプであるため、条件キーが正常に機能することを期待します。
{ "Version": "2012-10-17", "Statement": [ { "Effect": "Allow", "Principal": "*", "Action": "s3:*", "Resource": [ "arn:aws:s3:::chibayuki-hoge-hoge", "arn:aws:s3:::chibayuki-hoge-hoge/*" ], "Condition": { "StringEquals": { "aws:PrincipalArn": "arn:aws:iam::000000000000:user/Batchi" } } } ] }
バケットポリシー変更時に外部アクセスのプレビューを行うと、ロールを指定した時と同様に、外部プリンシパルがすべて・条件として IAM ユーザーのプリンシパル ARN が記載される状態となります。
バケットポリシーは正常に保存できました。アナライザーを確認するとプレビューと同様の内容で結果が表示されていました。
AWS CLI の実行
この状態で指定した IAM ユーザーから S3 へのアクセスを試みます。正常にアクセスが行えました。
% aws sts get-caller-identity { "UserId": "AIDARVFQHJ6WFBJFMWCB4", "Account": "000000000000", "Arn": "arn:aws:iam::000000000000:user/Batchi" } % aws s3 ls chibayuki-hoge-hoge 2021-10-17 18:18:35 6 test.txt
もちろん条件キーで指定している IAM ユーザー以外からのアクセスは拒否されます。
% aws sts get-caller-identity { "UserId": "AIDARVFQHJ6WHQVDP4LLE", "Account": "000000000000", "Arn": "arn:aws:iam::000000000000:user/Test-User" } % aws s3 ls chibayuki-hoge-hoge An error occurred (AccessDenied) when calling the ListObjectsV2 operation: Access Denied
4パターンのまとめ
冒頭で示した通り以下の結果となりました。
パターン | バケットポリシー | アナライザーの結果 |
---|---|---|
1. Principal 要素で IAM グループ | 保存できない | ー |
2. Principal 要素で IAM ユーザー | 正常に機能する | 外部プリンシパルとして検出される |
3. aws:PrincipalArn で IAM グループ | 保存できるが機能しない | 条件の中のプリンシパル ARN として表示される |
4. aws:PrincipalArn で IAM ユーザー | 正常に機能する | 条件の中のプリンシパル ARN として表示される |
終わりに
aws:PrincipalArn 条件キーでプリンシパルとして IAM グループを指定できるのか?という確認でした。結果としては、「指定自体はできるが正常に機能しない(何の効果も及ぼさない)」であることが分かりました。
正直に言うと冒頭で引用した AWS ドキュメントの以下記載は誤りなのではないか(グループがここに含まれているのは誤りではないか)と考えていたのですが、そうではありませんでした。
aws:PrincipalArn 条件キーで使用されるプリンシパル(IAM ユーザー、ロール、またはグループ)の ARN でフィルタリングするには、このプロパティを使用します。
(効果は及ぼさないものの)条件キーで設定自体はできるので、アナライザーの結果のフィルタリングで IAM グループのプリンシパル ARN を指定することもできるというわけです。
理想を言えば効果を及ぼさないのであれば設定自体ができないようになっていれば嬉しいのですが、そうもいかないのだろうと想像します。改めて IAM って難しいなと思いました。(そしてそこがわたしを惹きつけて止まないのでしょう。)
以上、 チバユキ (@batchicchi) がお送りしました。