AWS Certified Solutions Architect - Associate (SAA-C03) #2 Domain 1-1 安全なアーキテクチャ — IAM の深掘り
#1 試験の紹介 で SAA-C03 の 4 つのドメインのうち セキュリティが 30% で最も大きい と述べました。そのセキュリティドメインの中心に IAM があります。IAM は単に「ユーザーを作る場所」ではなく、AWS のすべてのリクエストが通過する認可 (authorization) レイヤー です。試験は IAM を「誰が、何に、どんな条件でアクセスするか」という設計問題に変形して問います。
この記事は CLF-C02 の IAM 基礎 の上に Associate レベルの深さを加えます。User・Group・Role・Policy の定義はすばやく通り過ぎ、ポリシー評価ロジック・STS・クロスアカウント・権限境界 のような、試験で正解を分ける箇所に時間を使います。
IAM の 4 構成要素のすばやい復習 #
| 構成要素 | 一行定義 | 認証情報 |
|---|---|---|
| User | 人またはアプリケーション一つに対応する永続的なアイデンティティ | 長期認証情報 (パスワード、アクセスキー) |
| Group | User の束。ポリシーをまとめて付与する単位 | なし |
| Role | 誰でも一時的に「引き受けられる」アイデンティティ | 一時的な認証情報 (STS が発行) |
| Policy | 権限を定義した JSON ドキュメント | 該当なし |
ここで試験が繰り返し狙う区別は User と Role の認証情報の違い です。User は永続的なアクセスキーを持ちますが、Role は認証情報を保存せず、引き受けた瞬間に STS が一時的な認証情報を発行 します。「EC2 のコードが S3 にアクセスしなければならない」というシナリオの正解が、常に「アクセスキーを埋め込む」ではなく「Role を付与する」である理由がここにあります。
IAM は グローバルサービス です。リージョンを選ばず、User・Role・Policy はすべてのリージョンで同じように見えます。
ポリシー (Policy) の構造 #
IAM ポリシーは JSON ドキュメントで、核心は Statement 配列です。各 Statement は次の要素で構成されます。
- Effect —
AllowまたはDeny - Action — 許可/拒否する API 動作 (例:
s3:GetObject) - Resource — 対象リソースの ARN
- Condition (任意) — 適用条件 (例: 特定 IP、MFA 使用時、特定タグ)
- Principal (リソースベースポリシーのみ) — 誰に適用されるか
{
"Version": "2012-10-17",
"Statement": [
{
"Effect": "Allow",
"Action": ["s3:GetObject", "s3:PutObject"],
"Resource": "arn:aws:s3:::my-bucket/*",
"Condition": {
"Bool": { "aws:MultiFactorAuthPresent": "true" }
}
}
]
}Condition は SAA によく登場します。「MFA を使った場合のみ許可」「特定の VPC Endpoint 経由のアクセスのみ許可」「特定のタグが付いたリソースのみ制御」といった要件は、すべて Condition で表現されます。
Identity ベースポリシー vs Resource ベースポリシー #
| 区分 | Identity ベース | Resource ベース |
|---|---|---|
| 付く対象 | User / Group / Role | リソース (S3 バケット、SQS キュー、KMS キーなど) |
| Principal 要素 | なし (すでにアイデンティティに付く) | あり (誰に許可するか明示) |
| 代表的な用途 | 「このユーザーが何をできるか」 | 「このリソースに誰がアクセスできるか」 |
| クロスアカウント | Role の委任が必要 | 他アカウントの Principal を直接許可可能 |
この区別が クロスアカウントアクセス問題 の核心です。他アカウントに S3 アクセスを与える方法は 2 つあります。(1) バケットポリシー (リソースベース) に相手アカウントの Principal を直接許可するか、(2) 自分のアカウントに Role を作り、相手アカウントが AssumeRole するようにする方法です。
ポリシー評価ロジック (試験の定番) #
複数のポリシーが同時にかかるとき、AWS が許可/拒否を判断する順序は試験にほぼ必ず出ます。核心ルールは 3 つです。
- 基本は暗黙的な拒否 (implicit deny) — どのポリシーも許可しなければ拒否されます。
- 明示的な許可 (explicit Allow) があれば許可 — ただし拒否がないとき。
- 明示的な拒否 (explicit Deny) はすべての許可に勝つ — どこか一度でも Deny が出れば、最終結果は拒否です。
ここに SCP (Service Control Policy)、権限境界、セッションポリシーが絡むと評価はさらに複雑になります。しかし試験で覚えるべき一文はこれです。
明示的な Deny は常に最優先。一つでも Deny があれば終わり。
Role と STS — 一時的な認証情報 #
Role は 認証情報を保存しないアイデンティティ です。誰かが Role を「引き受ける (assume)」と、AWS Security Token Service (STS) が 一時的な認証情報の 3 点セット (アクセスキー ID、シークレットキー、セッショントークン) を発行します。この認証情報には有効期限があり、漏洩しても被害が限定されます。
信頼ポリシー vs 権限ポリシー #
Role には 異なる 2 つのポリシー が付きます。この 2 つを区別できないと、クロスアカウントの問題で混乱しやすくなります。
| ポリシー | 問い | どこに |
|---|---|---|
| 信頼ポリシー (Trust Policy) | 誰が この Role を引き受けられるか | Role の AssumeRolePolicyDocument |
| 権限ポリシー (Permission Policy) | この Role が 何を できるか | Role にアタッチされたポリシー |
信頼ポリシーの Principal に EC2 サービスが入れば EC2 インスタンスが、他アカウント ID が入ればそのアカウントのアイデンティティが Role を引き受けられます。
AssumeRole の代表的な形 #
- EC2 → Role (インスタンスプロファイル) — EC2 に Role を付けると、インスタンスメタデータ経由で一時的な認証情報が自動的に供給されます。アクセスキーをコードやインスタンスに保存する必要がありません。
- Lambda 実行ロール — Lambda 関数が他のサービスにアクセスするときに使う Role です。
- クロスアカウント AssumeRole — B アカウントのユーザーが A アカウントの Role を引き受けて A のリソースを制御します。
- ウェブ ID フェデレーション (AssumeRoleWithWebIdentity) — Cognito や OIDC プロバイダで認証したユーザーに一時的な認証情報を与えます。
クロスアカウントアクセスの設計 #
会社が複数のアカウントを運用するのは SAA の基本前提です。アカウント間のアクセスを設計する 2 つの軸を整理します。
- Role 委任方式 — A アカウントに Role を作り、信頼ポリシーに B アカウントを入れます。B のユーザーは
sts:AssumeRoleで A の Role を引き受けて A のリソースを制御します。制御権限が複数のサービスにまたがるときに適しています。 - リソースベースポリシー方式 — S3 バケットポリシー、KMS キーポリシーのように、リソースに直接他アカウントの Principal を許可します。単一リソースの共有に向いています。
大規模では AWS Organizations + IAM Identity Center でマルチアカウントアクセスを中央から管理します。SCP は Organizations レベルで アカウントが持てる権限の上限 (guardrail) を定めます。SCP は権限を付与せず、許可可能な範囲を制限するだけ という点が重要です。
権限境界 (Permission Boundary) #
権限境界は 一つの IAM アイデンティティが持てる最大権限を制限する ポリシーです。SCP と同様に「上限」を定めますが、適用単位が異なります。
| メカニズム | 適用単位 | 役割 |
|---|---|---|
| SCP | Organizations のアカウント / OU | アカウント全体の権限上限 |
| Permission Boundary | 個別の IAM User / Role | そのアイデンティティの権限上限 |
| Identity ベースポリシー | User / Role | 実際の権限付与 |
最終的な権限は 付与されたポリシーと上限 (境界・SCP) の積集合 です。例えば管理者に権限を委任しつつ「IAM ユーザーの作成は権限境界の中だけで」のような制約を与えるときに使います。
試験の出題パターン #
- 「EC2 のアプリケーションが S3 にアクセスしなければならない。最も安全な方法は?」 → IAM Role (インスタンスプロファイル)。アクセスキー保存の答案は不正解。
- 「B アカウントのユーザーが A アカウントのリソースを制御しなければならない。」 → A に Role 作成 + 信頼ポリシーで B を許可 + B が AssumeRole。
- 「複数のポリシーが衝突する。結果は?」 → 明示的な Deny があれば拒否。
- 「組織全体で特定リージョンの使用を禁止せよ。」 → SCP (権限付与ではなく上限制限)。
- 「開発者に権限を委任しつつ限度を設けたい。」 → Permission Boundary。
- 「モバイルアプリのユーザーに一時的な AWS アクセスを与えるには?」 → Cognito / AssumeRoleWithWebIdentity (アプリに長期キーを配布するのは禁止)。
よく出会う落とし穴 #
1) Role にアクセスキーがあると思う #
Role には長期アクセスキーがありません。引き受けた瞬間に STS が一時的な認証情報を発行するだけです。
2) SCP が権限を付与すると誤解する #
SCP は 上限を定めるだけ です。SCP に Allow があっても、IAM ポリシーで別途許可しなければ権限はありません。
3) 信頼ポリシーと権限ポリシーを混同する #
「誰が引き受けるか」は信頼ポリシー、「何をするか」は権限ポリシーです。クロスアカウント問題で 2 つを入れ替えて適用すると間違えます。
4) クロスアカウントに IAM User を複製する #
他アカウントの利用のためにそのアカウントに User をまた作る答案は、たいてい不正解です。Role の委任 が定石です。
5) EC2 に長期キーを保存する #
「コードでアクセスキーを環境変数から読む」類の答案は、SAA ではほぼ常に不正解です。Role を使えばキー自体がありません。
まとめ #
この記事で押さえたこと:
- IAM は グローバルな認可レイヤー。User は永続的な認証情報、Role は STS の一時的な認証情報
- ポリシーは Effect・Action・Resource・Condition (+ リソースベースは Principal)。Condition で MFA・IP・タグ条件を表現
- 評価ロジック — 基本は拒否、明示的な Allow で許可、明示的な Deny がすべてに勝つ
- Role には 信頼ポリシー (誰が引き受けるか) と 権限ポリシー (何をするか) の 2 つが付く
- クロスアカウント — Role 委任 (AssumeRole) またはリソースベースポリシー。大規模は Organizations + Identity Center
- 上限メカニズム — SCP (アカウント単位)、Permission Boundary (アイデンティティ単位)。どちらも付与ではなく 制限
次へ — Domain 1-2 KMS と暗号化 #
アイデンティティと権限を押さえたので、次は データそのものを保護する暗号化 です。
#3 Domain 1-2 KMS と暗号化 では、KMS のキーの種類 (AWS マネージド・カスタマーマネージド・カスタマー提供)、エンベロープ暗号化 (envelope encryption) の動作、at rest と in transit の暗号化の違い、S3・EBS・RDS の暗号化オプション、そしてキーポリシーとクロスアカウントのキー共有までまとめます。