どの扉が開くかを、誰が決めるのか
社員証は、事務室の扉を開けますが、金庫室の扉は開けません。どの証でどの扉を開けてよいかは、誰かが書き出して決めています。
クラウドも同じです。IAM ポリシーは、人やプログラムがしてよいことを書いた一覧です。このレッスンでは、ポリシーを読み、1つの呼び出しが許されるかどうかを答える方法を学びます。
このレッスンのゴール
メモ
ポリシーを読み、呼び出しが許されるかどうかを答えることができる。
キーワード
| ことば | いみ | れい |
|---|---|---|
| ポリシー | してよいことと、いけないことを並べた文書 | |
| ステートメント | ポリシーの中の、1つのルール | |
| Effect | ステートメントが許すか、拒むか | |
| Action | 行う呼び出し | s3:GetObject |
| Resource | 呼び出しの対象になるもの | |
| 最小権限 | 仕事に要るだけの権限を渡すこと |
学生が入力するセルは、このプレビューでは空白です。
ポリシーはステートメントの並び
ポリシーは、JSON の文書です。Version と、Statement という並びを持ちます。各ステートメントは、effect、action、resource の3つを言います。
effect は Allow か Deny です。action は、s3:GetObject (1つのファイルを読む) のような呼び出しです。resource は、呼び出しの対象で、ARN という長い文字で書きます。ここのポリシーは作り物で、アカウントは要りません。
実行: ポリシーを読む
policy = {
"Version": "2012-10-17",
"Statement": [
{
"Effect": "Allow",
"Action": ["s3:GetObject", "s3:PutObject"],
"Resource": "arn:aws:s3:::photos-demo/*",
},
{
"Effect": "Deny",
"Action": "s3:*",
"Resource": "arn:aws:s3:::photos-demo/private/*",
},
],
}
for statement in policy["Statement"]:
print(statement["Effect"], statement["Action"], statement["Resource"])
# "Deny" を "Allow" に変えましょう。プログラムはそれでも読めます。意味は変わりますか。
ワイルドカード * は、任意の長さの文字に合う
ファイル名を全部書いていたら、きりがありません。そこで、パターンには星が使えます。星は、任意の長さの文字に合います。長さがゼロでも合います。
resource の "arn:aws:s3:::photos-demo/" は、そのバケットのすべてのオブジェクトに合います。action の "s3:" は、S3 のすべての呼び出しに合います。星のないパターンは、文字がまったく同じでなければ合いません。
例: パターンが合う文字
| パターン | 文字 | 合うか |
|---|---|---|
| s3:* | s3:GetObject | 合う |
| s3:* | sqs:SendMessage | 合わない。s3: で始まらない |
| s3:Get* | s3:GetObject | 合う |
| s3:Get* | s3:PutObject | 合わない |
| photos/* | photos/ | 合う。星はゼロ文字に合う |
| *.jpg | cat.jpg | 合う |
| s3:GetObject | s3:GetObjectAcl | 合わない。星がないので、まったく同じ |
学生が入力するセルは、このプレビューでは空白です。
Deny は、いつも勝つ
1つの呼び出しを決めるには、action と resource の両方が合うステートメントを、すべて探します。そして3つのルールを使います。
合うステートメントに Deny が1つでもあれば、呼び出しは拒まれます。これが明示的な拒否で、どの Allow にも勝ちます。Deny がなく、Allow があれば、許されます。何も合わなければ、それでも拒まれます。これが暗黙の拒否です。
例: 写真のポリシーでの3つの呼び出し
| 呼び出し | 合うステートメント | 結果 |
|---|---|---|
| photos-demo/cat.jpg への s3:GetObject | Allow だけ | 許される |
| photos-demo/private/id.jpg への s3:GetObject | Allow と Deny | 拒まれる。明示的な拒否が勝つ |
| キューへの sqs:SendMessage | なし | 拒まれる。暗黙の拒否 |
学生が入力するセルは、このプレビューでは空白です。
よくある間違い
注意
ポリシーが禁じなければ、呼び出しは許される、と考える人が多いです。実は逆です。Allow するステートメントがなければ、呼び出しは拒まれます。そして、Deny はどの Allow にも勝ちます。
実行: 3つのルールをコードで
matched = ["Allow", "Deny"]
if "Deny" in matched:
result = "拒まれる: 明示的な拒否"
elif "Allow" in matched:
result = "許される"
else:
result = "拒まれる: 暗黙の拒否"
print(result)
# matched を ["Allow"] に、次に [] に変えましょう。それぞれ何が出ますか。
足りる最小限を渡す
写真サイトに要るのは、写真を読むことと、足すことです。消すことや、キューを触ることは要りません。だから、ポリシーには、その2つの action だけを、そのバケットだけに対して書きます。
これが最小権限です。サイトがもし悪用されても、被害は、ポリシーが許した範囲で止まります。