AWS Identity and Access Management
Account boundaries from [AWS Account Setup, IAM Identity Center and Organizations](/learn/aws-cloud-devops-engineering/aws-account-setup-iam-identity-center-and-organizations) deci
AWS Identity and Access Management
AWS Cloud & DevOps Engineering · Lesson 03 · AWS Cloud Foundations
Lesson Overview
Account boundaries from AWS Account Setup, IAM Identity Center and Organizations decide which house you are in. IAM decides which keys hang by which doors. On the Wednesday after TechLearningPro moved the lesson progress API into a production member account, a well-meaning engineer attached AdministratorAccess to a CI role "just until the pipeline is green." The pipeline went green. So did a later job that listed every secret and every enrollment export the role could reach. CloudTrail attributed the calls correctly. Least privilege would have made the blast radius a deploy failure instead of a data incident.
This lesson is the deep cut on AWS Identity and Access Management (IAM) inside an account: principals (users, roles, groups), identity-based policies, resource-based policies, trust policies, permission boundaries, session policies, and the evaluation logic that turns those documents into allow or deny. You will design access roles for developers, CI/CD, and application workloads for the TechLearningPro learning platform—player APIs, Monday board pipelines, and operators—without hardcoding secrets and without treating managed policies as personality traits.
IAM Identity Center remains the preferred path for human sign-in across accounts. This lesson explains what Identity Center permission sets become inside the account (IAM roles and policies), and how workload identities differ from human identities. AWS CLI, SDKs and Infrastructure Access shows how temporary credentials are obtained and used. Cross-Account Access and Multi-Account Networking extends trust across accounts. Here you learn to read and write the authorization story so those later lessons are not cargo cult.
Planning assumptions:
- Production human access arrives through Identity Center permission sets that provision IAM roles; standing IAM users for people are exceptions with expiry.
- Application tasks (ECS/EKS/EC2/Lambda—introduced later) assume IAM roles; they do not embed long-lived access keys in images or environment variables committed to git.
- Policy examples in this lesson prefer durable patterns (
Effect,Action,Resource,Conditionwith common keys). Verify exact action names and condition keys in current AWS service documentation before production use. Do not invent actions. - Illustrative policy snippets are teaching shapes. They are not a license to paste wildcards into production without review.
Learning Objectives
By the end of this lesson you will be able to:
- Distinguish IAM users, groups, roles, and Identity Center–provisioned roles for TechLearningPro personas and workloads.
- Explain identity-based versus resource-based policies and when each appears on the progress API path.
- Write and review trust policies that control who can assume a role, including CI and cross-account principals at a conceptual level.
- Apply least privilege with scoped actions, resources, and conditions (tags, MFA, source VPC/network where applicable).
- Describe permission boundaries and how they constrain what an administrator or pipeline can delegate.
- Walk the high-level AWS policy evaluation logic to predict allow versus deny for a given request context.
- Design separate roles for developers, CI/CD deployers, and runtime application identities without shared standing admin.
- Reject anti-patterns: access keys in repos,
*on*for convenience, confused-deputy trust, and human credentials on servers. - Use IAM Access Analyzer and CloudTrail as review instruments (conceptually) when tightening policies.
- Hand lesson 4 a set of roles and trust relationships that CLI/SDK sessions can assume safely.
- Connect IAM decisions to the shared responsibility line from lesson 1 and the account ceilings from lesson 2.
- Prepare interview-quality explanations of role assumption, temporary credentials, and deny precedence.
Prerequisites
- Lessons 1–2: Regions/AZs as placement context; accounts, Organizations SCP ceilings, Identity Center permission sets.
- Comfort reading JSON policy documents.
- Awareness that /learn/git review applies to IAM changes; policy merges are production changes.
- Optional: container identity ideas from /learn/docker and /learn/kubernetes only as foreshadowing—IRSA and task roles appear in later AWS lessons.
Detailed Core Concepts
What IAM is for
IAM answers four questions for every AWS API request:
- Who is calling? (principal)
- What are they trying to do? (action)
- On what? (resource)
- Under what request context? (conditions: time, MFA, tags, source IP/VPC, organization ID, and more)
Authentication establishes identity. Authorization evaluates policies. Mixing them produces systems that "log in fine" but cannot deploy, or that deploy with god mode. TechLearningPro needs both: engineers authenticated through Identity Center, and workloads authorized only to the queues, tables, and buckets their feature requires.
Principals you will actually use
IAM user. A long-lived principal inside one account with optional passwords (console) and access keys (API). Prefer not to use IAM users for humans when Identity Center is available. IAM users still appear for break-glass exceptions, legacy automation mid-migration, and some service patterns—each with an owner and a deletion date.
IAM group. A way to attach policies to a set of IAM users. Groups cannot be identities in resource policies the way roles/users can in all contexts—treat them as administrative convenience for user-centric models. In an Identity Center–first design, groups at the IdP/Identity Center layer matter more than IAM groups.
IAM role. An identity that is assumed. Roles have no long-lived passwords. They have trust policies (who may assume them) and permissions policies (what they may do once assumed). Roles are the center of modern AWS design: human permission sets, EC2 instance profiles, Lambda execution roles, ECS task roles, and cross-account deploy roles are all roles.
Root user. Account owner identity. Not for daily IAM. See lesson 2.
Federated principals and Identity Center. Humans federate and receive role sessions. The CloudTrail userIdentity shows the assumed role and, when configured, the human identity—use that for attribution.
Policy types
Identity-based policies attach to users, groups, or roles: "this principal may perform these actions on these resources."
Resource-based policies attach to resources (S3 bucket policies, KMS key policies, SQS queue policies, and others): "these principals may perform these actions on this resource." Some services require resource policies for cross-account access.
Trust policies are resource-based policies on roles (AssumeRole permission to STS). They define the blast radius of who can become the role.
Permission boundaries set the maximum permissions an IAM principal can have—useful when delegating role creation to a platform pipeline so it cannot mint Admin roles.
Service control policies (lesson 2) set organization ceilings; they are not IAM grants.
Session policies can further restrict a role session when assuming a role (passing a policy document to STS). Used to narrow CI sessions temporarily.
Organizations RCPs / other policy types evolve over time—verify current AWS policy evaluation documentation when you encounter a new type. Do not invent evaluation rules.
Least privilege as an engineering practice
Least privilege is not a vibes-based slogan. It is:
- Start from deny by default.
- Add actions required for a named job story ("deploy progress API stack," "read Monday board curated bucket").
- Scope resources with ARNs or patterns that match only those objects.
- Add conditions that encode invariants (require MFA for sensitive actions, require
ec2:ResourceTag/env=devfor developer mutate, require organization ID for cross-account). - Review with Access Analyzer and with a human who asks "what happens if this role is compromised?"
- Iterate when CloudTrail shows denied calls that should succeed—or allowed calls that should not exist.
Avoid the false least privilege of listing fifty actions while leaving Resource: "*". Resource scope is half the privilege.
Trust policies and the confused deputy
A trust policy that allows Principal: { "AWS": "*" } with weak or missing conditions invites anyone who can call AssumeRole under broad network conditions to attempt assumption. Always restrict Principal to specific account roots, specific role ARNs, or service principals such as ec2.amazonaws.com, lambda.amazonaws.com, or ecs-tasks.amazonaws.com as appropriate. For service roles, use the service principal patterns documented by AWS for that service. For cross-account CI, name the deploying role ARN. Consider sts:ExternalId when third parties assume roles into your account—understand why external IDs exist (confused deputy prevention) before implementing.
Managed policies versus customer-managed versus inline
AWS managed policies (for example, read-only job functions) are convenient and AWS-updated, but often broader than your service needs. Use them for early learning and break-glass read-only—not as permanent prod runtime permissions without review.
Customer-managed policies are versioned IAM policy objects you control—preferred for TechLearningPro shared roles.
Inline policies embed directly on a principal—use sparingly; harder to review centrally.
Permission sets in Identity Center typically map to managed or customer-managed policy collections. Keep naming aligned with personas from lesson 2.
Permission boundaries for safe delegation
Suppose the platform team wants the progress-api squad to create roles for their own Lambdas in the dev account without being full IAM admins. A permission boundary can allow iam:CreateRole only if the created role carries a boundary that itself forbids privilege escalation (no iam:*, no org changes, limited services). Boundaries are subtle; misconfiguration either bricks developers or fails to prevent escalation. Treat boundary design as staff-level work: test in sandbox, document allowlisted services, and deny iam:PutRolePermissionsBoundary removals where appropriate.
Policy evaluation mental model
At a teaching level (always confirm against the current AWS documentation diagram when debugging):
- Explicit deny in any applicable policy wins.
- If an SCP denies, the action is denied for constrained accounts.
- Otherwise, there must be an allow from identity-based and/or resource-based policies as required by the service and request type.
- Permission boundaries and session policies can remove permissions that would otherwise be allowed.
- Absence of allow is deny.
When debugging AccessDenied, gather: principal ARN, action, resource ARN, account, Region, and whether SCPs/boundaries exist. Guessing produces * expansions.
Roles for developers, CI/CD, and applications
Developer (human) role via Identity Center: create/update non-prod stacks, read logs, maybe start/stop sandbox resources. Not: prod data plane admin, not: org SCP edits.
CI/CD deploy role in target account: trust the CI principal in the tools account; permissions to mutate the services the pipeline owns (CloudFormation/Terraform-scoped resources, ECR push if colocated, ECS deploy, and so on). Not: iam:CreateUser with keys, not: unmanaged S3 read of unrelated buckets.
Application runtime role: only the AWS APIs the process needs—s3:GetObject on content prefixes, sqs:SendMessage on its queue, kms:Decrypt on its key, secrets retrieval for its secret ARNs. Not: deploy permissions. Not: sibling microservice's tables "for debugging."
Separating these three is how you stop a compromised web process from redeploying itself as ransomware infrastructure.
Conditions that show up often
Without inventing exotic keys, know these categories exist and look up exact names per service:
- MFA / authentication age for sensitive human actions.
aws:RequestedRegionto align with lesson 1 Region ADR.- Resource tags for attribute-based access control (ABAC) when your tagging is reliable.
- Source VPC / private endpoint conditions for sensitive data plane APIs when designed.
- Organization ID / account principals for cross-account resource policies.
ABAC fails when tags are missing or spoofable; combine with preventive controls on who can set tags.
Secrets and IAM
IAM authorizes who may call Secrets Manager or SSM Parameter Store. It does not replace storing secrets there. Never put passwords in policy documents, AMIs, or container env committed to git. Secrets Manager and Systems Manager Parameter Store deepens storage; this lesson forbids the anti-patterns.
Service control policies versus IAM
Teams sometimes ask SCPs to express fine-grained app authorization. That is the wrong layer. SCPs encode org invariants. IAM encodes workload and persona permissions. Using SCPs as a substitute for IAM review creates brittle org-wide outages when apps need a new action.
Worked example: progress API authorization story
Consider the TechLearningPro progress API writing a checkpoint event. The runtime role must be allowed to send a message to the progress queue or write to the progress table—whichever design Module 2 selects—and to read configuration from Parameter Store or Secrets Manager for database credentials. It must not be allowed to change its own IAM role, create access keys, read the enrollment export bucket used by finance, or deploy a new task definition. Those denies are not hostility toward developers; they are recognition that the process listening on the internet is the most attacked principal you will own.
A deploy role used by CI must update the task definition or infrastructure stack and register container images. It must not have daily read access to production learner rows. Humans who investigate a Monday discrepancy use a read-only or carefully scoped operator role through Identity Center, with MFA at the IdP, and leave an audit trail that names the person. If you collapse these three stories into one role because "IAM is hard," you have not simplified security. You have postponed an incident.
Walk a single request through authorization:
- The task retrieves temporary credentials for
tlp-progress-api-taskfrom the container credential provider. - The application calls
secretsmanager:GetSecretValueon a specific secret ARN. - IAM evaluates identity policies on the task role. The action and resource must match.
- The Secrets Manager resource policy, if present, must also allow the role when used.
- KMS key policy must allow decrypt when the secret is encrypted with a customer managed key.
- SCPs in the production OU must not deny the action.
- Network path must reach the API endpoint—authorization success with a closed security group still fails closed, which is good, but operators must not misread it as an IAM bug.
That chain is why "I attached AmazonS3FullAccess" does not finish an IAM design review. Name the secret ARN, the KMS key, the SCP intent, and the network path.
ABAC versus RBAC for TechLearningPro
Role-based access control (RBAC) assigns permissions by persona: developer, operator, deployer. Attribute-based access control (ABAC) grants based on tags: a principal tagged service=progress-api may mutate resources tagged the same way. AWS IAM supports conditions on tags for many services. ABAC scales elegantly when hundreds of microservices would otherwise need hundreds of nearly identical policies. It fails loudly when tags are missing, when anyone can retag a resource into a privileged set, or when production and staging share tag vocabularies without also separating accounts.
A pragmatic approach for this course:
- Use account separation for environment (lesson 2).
- Use RBAC permission sets for humans.
- Use dedicated runtime roles per service for applications.
- Consider ABAC inside a large account only when tagging is mandatory via policy and SCPs/IAM prevent privilege-granting retags.
Do not advertise ABAC in an interview as magic. Explain the tag integrity problem first.
Cross-account role assumption narrative
CI often lives in a tools account. Production lives in tlp-prod-app. The deploy role in production trusts the CI role ARN in tools. The CI role's identity policy must allow sts:AssumeRole on the production deploy role ARN. Production deploy role permissions then allow changing production resources. Two policies, two accounts, one audited session name. If someone instead creates long-lived access keys in production and stores them in the CI system, every CI log leak becomes a production credential leak. Prefer federation patterns documented for your CI vendor (OIDC is common) and verify the exact trust conditions in current AWS and vendor docs—do not invent claim keys from memory.
Inline policy debt
Inline policies accumulate during incidents: "just add this statement to unblock." Six months later nobody can answer what the role is for. Prefer customer-managed policies named after the job story, versioned in git, reviewed in pull requests. If you must inline during an incident, open a ticket to extract the policy within a week. Identity Center permission sets should reference managed policies for the same reason.
IAM and the Monday board
The Monday board's readers need curated metrics, not IAM admin. Grant athena:StartQueryExecution or warehouse read permissions—whatever the serving engine lesson later selects—against specific workgroups or databases. Deny access to raw PII buckets. If board freshness fails, the fix is pipeline ownership, not broader IAM for executives. Broader IAM for executives is how credentials that can dump enrollment tables end up on laptops that also browse the web.
Mapping Identity Center permission sets to IAM
When Identity Center provisions a permission set into an account, it creates an IAM role with a recognizable path/name pattern and attaches the policies you configured. Engineers assume that role through the Identity Center portal or AWS CLI SSO login. You still troubleshoot with IAM tools: attached policies, boundaries, SCPs. Permission sets are a packaging and assignment layer; they do not abolish IAM evaluation. When a user says "SSO is broken," ask whether authentication failed or authorization failed after assumption—the fixes differ.
Safe use of AWS managed policies
AWS managed policies are maintained by AWS and useful for baselines like view-only access. They are often wider than a single microservice needs. Using AdministratorAccess or broad PowerUser style policies on runtime roles is an anti-pattern. Using a managed ReadOnly policy for human investigation in staging can be acceptable while you craft tighter customer-managed policies. Record exceptions with owners.
Encryption authorization coupling
Teams frequently grant s3:GetObject and still see AccessDenied because the object is encrypted with a KMS CMK whose key policy does not allow the role, or the role lacks kms:Decrypt. Conversely, granting decrypt on a key used by many buckets may overshare. Design IAM and KMS together. Lesson 41 deepens KMS; this lesson requires you to put a KMS row on every encrypted-resource design review checklist.
Change management for IAM
Require pull requests for policy JSON. Run an IAM linter or Access Analyzer where your toolchain supports it. Deploy IAM changes through the same pipeline controls as application changes. For emergency breaks-glass policy edits in console, follow with a retroactive PR within one business day so git remains the source of truth. /learn/git discipline applies to authorization as much as to application code.
Capacity and quotas related to IAM
IAM has quotas on policies per role, policy size, and related objects. Large organizations hit them when they inline everything or attach dozens of managed policies to one role. Prefer fewer, clearer policies. When you approach limits, look up current Service Quotas for IAM in your account rather than memorizing numbers from a blog. Quotas are not an excuse for AdministratorAccess; they are a reason to simplify.
Deep dive: statement effects and statement order myths
IAM policy statements within a document are not a first-match firewall ruleset in the way some network engineers expect. Evaluation aggregates applicable statements according to AWS rules: explicit denies dominate, and allows must be present. Reordering statements inside a single policy document is not a security control. What matters is whether any applicable deny exists and whether a sufficient allow exists across the relevant policy types. Teams that "fix" authorization by reshuffling JSON without understanding evaluation waste time and ship false confidence.
Not all services authorize identically for every API. Some management-plane actions are purely identity-based. Some data-plane actions involve resource policies heavily. Always read the service's authorization documentation when an AccessDenied disagrees with your mental model of a simple identity policy.
Deep dive: session names and audit quality
When assuming a role, set a meaningful session name and, where supported, transitive tags. CloudTrail becomes readable: CI-build-4417 is better than session. For Identity Center, ensure the identity source attributes you need for audit are available to your logging pipeline. During an incident, "some role was used" is not enough; you need which pipeline run or which engineer.
Deep dive: resource ARNs and wildcards
Wildcards in ARNs are powerful and dangerous. arn:aws:s3:::tlp-prod-*/* might intentionally cover several buckets or accidentally cover a bucket introduced later with a naming collision. Prefer explicit bucket names for production runtime roles. Use prefixes carefully: object ARNs include the key path; ListBucket is authorized on the bucket ARN and often needs a prefix condition. Misunderstanding List versus Get is one of the most common S3 IAM mistakes—verify with current S3 documentation when writing policies.
Deep dive: service principals and confused pathways
Trusting ec2.amazonaws.com for an instance profile is appropriate for EC2. Trusting a service principal that does not match how the workload runs creates either breakage or unnecessary assumption surface. For ECS tasks and Lambda, use the trust shapes those services document. When introducing VPC Lattice, EventBridge API destinations, or other newer integrations in later lessons, return to trust documentation rather than cloning an EC2 trust out of habit.
Production readiness checklist for any new role
Before attaching a new role to a production workload:
- Written job story in one sentence.
- Trust principals enumerated and justified.
- Permissions mapped to APIs the code actually calls (from design or traced from staging CloudTrail).
- Resource ARNs scoped.
- KMS and secrets dependencies listed.
- SCP compatibility checked.
- Compromise impact stated in one paragraph.
- Owner and review date set.
- Metrics/alarms for unusual AssumeRole or unusual API volumes considered.
- Removal or rotation plan if temporary.
If you cannot complete the list, the role is not ready—only the ticket is.
Relating IAM to shared responsibility
AWS authenticates API callers and evaluates policies you configure. You own the policy content, the human process for granting access, the secret distribution, and the monitoring of suspicious use. A perfect IAM policy with keys pasted into Slack still fails the shared responsibility model on the customer side. Lesson 1's responsibility table should gain rows for "identity provisioning" and "access review cadence" after this lesson.
Architecture and Design Diagrams
mermaidflowchart TBsubgraph humans [Human path]IdP[Corporate IdP]IC[IAM Identity Center]HumRole[Permission set role in account]endsubgraph ci [CI/CD path]Runner[CI runner identity]DeployRole[Deploy role in target account]endsubgraph app [Application path]Task[API task / function]AppRole[Runtime task role]endsubgraph aws [AWS APIs]S3[S3 objects]DB[Data APIs]SM[Secrets Manager]endIdP --> IC --> HumRoleRunner -->|AssumeRole| DeployRoleTask --> AppRoleHumRole -.->|investigate| S3DeployRole -->|mutate stacks| S3AppRole -->|least privilege| S3AppRole --> DBAppRole --> SM
mermaidflowchart TDReq[API request context]Deny{Explicit deny in SCP / IAM / resource / boundary / session?}Allow{Allow from required policy combination?}Denied[Denied]Allowed[Allowed]Req --> DenyDeny -->|yes| DeniedDeny -->|no| AllowAllow -->|yes| AllowedAllow -->|no| Denied
Technical Explanation
AssumeRole mechanics
When a principal assumes a role, AWS STS returns temporary credentials: access key ID, secret access key, and session token, with an expiration. The session principal is the role (with session name). Permissions are the intersection of the role's policies with boundaries and optional session policies. Temporary credentials reduce the value of laptop theft relative to long-lived keys—but a stolen session token remains powerful until expiry. Short session durations for admin roles matter.
Instance profiles pass role credentials to EC2 via the instance metadata service. Harden metadata service usage (IMDSv2 is the modern default recommendation—verify current EC2 guidance). Containers should use task roles rather than copying keys into images.
Identity-based policy structure
A teaching skeleton:
json{"Version": "2012-10-17","Statement": [{"Sid": "ListOwnBucket","Effect": "Allow","Action": ["s3:ListBucket"],"Resource": "arn:aws:s3:::tlp-prod-course-assets","Condition": {"StringEquals": {"aws:PrincipalTag/service": "progress-api"}}},{"Sid": "ReadObjects","Effect": "Allow","Action": ["s3:GetObject"],"Resource": "arn:aws:s3:::tlp-prod-course-assets/public/*"}]}
Notes for learners: Version date is the IAM policy language version string commonly required; look up current requirements if tools complain. ARNs and actions must match real resources. The condition example assumes principals are tagged—only use if your Identity Center or role tagging story is real. Verify action names like s3:ListBucket versus object-level actions when debugging List versus Get denials.
Trust policy structure
json{"Version": "2012-10-17","Statement": [{"Effect": "Allow","Principal": {"AWS": "arn:aws:iam::111122223333:role/tlp-ci-deployer"},"Action": "sts:AssumeRole"}]}
Replace account IDs and role names with yours. Do not use * principals for production deploy roles. Service-trust examples differ—follow the service's documented trust pattern when attaching roles to Lambda or ECS.
Resource policy cross-account sketch
An S3 bucket in the data account might allow a role in the app account to read a prefix. Both the identity policy on the role and the bucket policy must allow the cross-account access (for typical S3 cross-account patterns). Missing either side produces denials that look mysterious until you draw both documents.
Debugging AccessDenied
- Confirm you are in the intended account and Region.
- Confirm which principal you are (STS get-caller-identity—lesson 4).
- Decode the action and resource from the error or API docs.
- Simulate with the IAM policy simulator where available, or review attached policies.
- Check SCPs, boundaries, resource policies, SCP Region denials, and KMS key policies (KMS often surprise people).
- Fix with least privilege, not by attaching AdministratorAccess to "unblock."
IAM Access Analyzer
Access Analyzer helps find resources shared outside a zone of trust and can generate policies from CloudTrail activity in supported workflows. Use it when tightening a role that currently uses managed Admin. Generated policies still need human review—CloudTrail only sees what was called in the window, not everything the app might call on enrollment week.
Practical Implementation or Design Walkthrough
Budget and hygiene
Use a sandbox account. Set a budget alert before creating resources. IAM policy documents themselves are not billable, but role testing often creates companion resources. Tag lab roles with ttl and delete them.
Design the three roles
Document in an ADR:
TLP-DevAppEngineer(Identity Center permission set): non-prod mutate for progress API stacks; read-only in prod.tlp-ci-progress-deploy(IAM role in staging/prod): trust CI; permissions limited to deploying the progress service's CloudFormation/Terraform state resources—enumerate services you actually use.tlp-progress-api-task(runtime role): networked app permissions only.
For each, write:
- Trust principals
- Allowed actions categories (not invented laundry lists—point to service docs)
- Resource ARN patterns
- Explicit denies you want (optional) for dangerous actions
- Boundary requirement (yes/no)
Console walkthrough
In sandbox:
- Create a customer-managed policy with a narrow S3 read on a lab bucket you create.
- Create a role trusted by your user or a test principal.
- Attach the policy.
- Assume the role (console Switch Role or CLI) and prove List/Get works on the lab prefix.
- Prove denial on a second bucket.
- Attach a broader AWS managed policy temporarily, show the difference, then remove it.
- Delete lab bucket objects, bucket, role, and policy when done.
CI trust dry-run (paper)
Even without a real CI account, write the trust policy principal as a future ARN and list the pipeline permissions. Note that GitHub Actions OIDC federation into AWS is a common pattern covered later—do not hardcode long-lived keys into GitHub secrets as the permanent design.
Negative tests
- Runtime role attempting
iam:CreateUser→ deny. - Developer permission set attempting prod data bucket without read assignment → deny.
- CI role assuming without matching trust → deny.
- Role assumption succeeding but KMS key policy missing → deny on decrypt (document the dependency).
Enterprise Real-World Scenarios
Scenario A: Admin on the web task role
A container compromise became full account compromise because the task role had AdministratorAccess for "faster debugging."
Fix. Runtime least privilege; separate debug tooling roles for humans; no standing admin on internet-facing tasks.
Scenario B: Trust *
A role trust allowed any AWS principal. Attackers probed AssumeRole.
Fix. Specific principals; monitor CloudTrail for unexpected assumptions; Access Analyzer findings.
Scenario C: Keys in the image
An AMI and a container image both contained IAM access keys. Rotation required rebuilding every artifact.
Fix. Role-based credentials only; secret scanning in CI; rotate and delete keys immediately.
Scenario D: Boundary missing on delegated create
A squad created a role that could escalate to admin because create-role rights were unbounded.
Fix. Permission boundaries on delegated creators; SCP intents as backup for org-wide forbids.
Scenario E: Monday board role reads OLTP
Analysts received a role that could SELECT through a broad database secret and network path into production OLTP.
Fix. Curated warehouse permissions; separate data account; deny OLTP secrets to analytics roles.
Best Practices
- Prefer roles and temporary credentials over long-lived access keys.
- Separate human, CI, and runtime identities.
- Scope both actions and resources; conditions encode invariants.
- Restrict trust principals tightly; understand external IDs for third parties.
- Use customer-managed policies with code review via git.
- Apply permission boundaries when delegating IAM write powers.
- Review with Access Analyzer and CloudTrail, not only with hope.
- Keep secrets out of policies, images, and tickets.
- Shorten session durations for privileged roles.
- Treat IAM changes as production changes with rollback plans.
- Align IAM resource tags with FinOps and ABAC only when tagging is enforced.
- Document KMS key policy interactions whenever encryption is in play.
Common Mistakes and Anti-Patterns
- AdministratorAccess on runtime roles. Symptom: total compromise from app RCE. Fix: least privilege runtime.
- Resource
*with many actions. Symptom: lateral movement. Fix: ARN patterns. - Long-lived keys on humans and servers. Symptom: leakage and weak attribution. Fix: Identity Center + roles.
- Over-broad trust policies. Symptom: unexpected AssumeRole. Fix: named principals and conditions.
- Using SCPs as app ACLs. Symptom: org-wide breakage. Fix: IAM for apps; SCPs for invariants.
- Ignoring resource policies on S3/KMS. Symptom: confusing denials or unexpected cross-account access. Fix: review both sides.
- Inline policy sprawl. Symptom: unreviewable authorization. Fix: centralized customer-managed policies.
- No MFA story for privileged human actions. Symptom: stolen password becomes admin. Fix: IdP MFA + IAM conditions where applicable.
- Copy-paste policies from blogs with invented actions. Symptom: deploy failures or false confidence. Fix: verify against current docs.
- Shared role for CI and humans. Symptom: untraceable changes. Fix: separate identities.
Troubleshooting and Design Review
AccessDenied after attaching Allow. Check explicit denies, SCPs, boundaries, wrong resource ARN, missing resource-based allow, KMS key policy, and wrong principal session.
Works in console, fails in CI. Different roles; session policies; missing OIDC/trust; different Regions.
Intermittent denial. Tag-based conditions with missing tags; eventual consistency rarely—but mis-targeted resources often.
Design review checklist
- Are human, CI, and runtime roles separate?
- Is trust least privilege?
- Are resources scoped?
- What does compromise of the runtime role allow?
- Are secrets retrieved by role, not baked in?
- Do SCPs still make sense with these IAM allows?
- Is there a removal plan for any temporary Admin?
Interview Questions and Answers
Q1. What is the difference between an IAM role and an IAM user?
A user is a long-lived principal typically with permanent credentials. A role is assumed and yields temporary credentials. Modern designs prefer roles for workloads and federated humans.
Q2. What does a trust policy control?
Who is allowed to call STS to assume the role. It does not by itself grant S3 or EC2 permissions; permissions policies do that after assumption.
Q3. How can an action be denied even if an identity policy allows it?
Explicit denies, SCPs, permission boundaries, session policies, missing resource-based allows when required, or KMS key policy denials are common reasons.
Q4. Why separate CI deploy roles from application runtime roles?
So a compromised application cannot redeploy infrastructure or create users, and so deploy credentials are not exposed on the data path.
Q5. What is a permission boundary?
A maximum permissions ceiling attached to a principal, limiting what permissions can be effective even if identity policies are broader—used to safely delegate IAM administration.
Q6. How does least privilege apply to S3 beyond omitting s3:*?
Scope to bucket and prefix ARNs, separate ListBucket and object actions correctly, and add conditions that match your invariants.
Q7. What is a confused deputy risk in role assumption?
A service or account tricked into using its privilege to act on behalf of an attacker. External IDs and tight trust principals are mitigations in cross-account third-party patterns.
Q8. Should Identity Center replace IAM entirely?
Identity Center federates humans into IAM roles. Workloads still use IAM roles. IAM remains the authorization system of record inside AWS accounts.
Q9. How do you tighten a role that is too broad today?
Gather CloudTrail usage, draft narrower policies, use Access Analyzer where helpful, test denies in non-prod, roll out gradually, monitor denials.
Q10. Where should database passwords live relative to IAM?
In a secrets store with IAM controlling who can retrieve them—not in IAM policies, images, or source control.
Q11. What CloudTrail fields help IAM incident response?
Principal ARN, account, action, resource, source IP, user agent, error code, and for federated sessions the identity provider user attribution when present.
Q12. How do Organizations SCPs and IAM interact?
SCPs set the ceiling for member accounts; IAM must still allow. Both must permit for success when SCPs apply.
Hands-On Exercises
Lab cost warning. Prefer IAM-only labs plus a tiny S3 bucket. Set a budget alert first. Delete buckets, roles, policies, and any EC2 you accidentally start. Never put real learner data in sandbox.
Exercise: Create access roles for developers, CI/CD, and application workloads
Problem. In a sandbox account, implement a miniature of TechLearningPro's three-identity model against a lab S3 bucket representing course assets.
Tasks.
- Configure a budget alert.
- Create lab bucket
tlp-lab-<you>-assetswith Block Public Access on; upload a sample object underpublic/. - Create customer-managed policies for (a) read public prefix, (b) deploy-style write to a
deploy-scratch/prefix only, (c) deny/omit unrelated actions. - Create three roles:
lab-developer,lab-ci-deploy,lab-app-runtimewith distinct trust principals you control (your Identity Center role or IAM user for lab only). - Prove each role's allow and at least two deny paths; capture
get-caller-identityand denial messages. - Write a short ADR mapping these lab roles to production Identity Center / CI / task roles.
- Cleanup: delete objects, bucket, role policies, roles, and lab IAM users/keys if any; confirm budget alert can remain.
Deliverables. Policy JSON, trust JSON, evidence of allows/denies, ADR, cleanup proof.
Challenge. Add a permission boundary that prevents lab-developer from attaching AdministratorAccess to any role it creates. Demonstrate the failure mode in sandbox.
Exercise: Policy review game day
Print or display a deliberately bad policy that allows *.* on * with a trust policy Principal of *. As a team, list five exploitation paths relevant to TechLearningPro (data exfiltration, crypto mining EC2, disabling logs, creating keys, pivoting to the Monday board bucket). Rewrite the policy set into the three-role model. This exercise needs no AWS account if you lack one; if you use sandbox, still set a budget alert and clean up.
Operator notes for enrollment week
Before traffic spikes:
- Confirm runtime roles were not widened "temporarily" during the last incident.
- Confirm CI deploy role trust still points only at the CI principal.
- Confirm break-glass human role assignments are time-boxed.
- Confirm CloudTrail is receiving IAM change events.
- Confirm budget alerts cover the production and tools accounts so a compromised key's spend is visible.
Enrollment week is when forgotten Admin attachments become national-security-level regrets for a learning company that holds learner PII.
Extended enterprise dialogue: the Friday privilege request
It is Friday before enrollment week. A squad lead asks for temporary AdministratorAccess on the progress API task role to "finish load testing tooling." The correct answer is not a moral lecture; it is an alternative path: a separate load-test harness role in staging, synthetic data, explicit metrics, and a time-boxed human operator role if console changes are required. If production must be tested, define the smallest mutate set, put it behind CI, and expire the change before Monday's board meeting. Record who approved the exception. If the exception cannot be written down, it is not an exception—it is an unauthorized privilege escalation.
Extended troubleshooting narrative
An engineer reports that the progress API cannot read course assets after a Region failover tabletop. IAM policies reference bucket ARNs in the primary Region. The replica bucket in the DR Region was created, but neither the runtime role nor the bucket policy was updated. The failure is not "IAM is flaky across AZs"—S3 buckets are Region-scoped resources with distinct ARNs. Multi-Region DR must include IAM and resource policy updates in the runbook. This is another reason lesson 1 forbade calling multi-AZ a DR plan: authorization artifacts are part of recovery, not only database bytes.
Closing synthesis for Module 1 identity arc
Lesson 1 placed the workload. Lesson 2 placed the account and the human SSO door. Lesson 3 placed the keys on the doors inside the account. Without all three, TechLearningPro either cannot ship or ships with an infinite blast radius. The remaining foundations lessons add network paths, compute, storage, and databases—each of which will ask for more IAM statements. Keep the three-role model intact as those statements grow. If a later lesson seems to require Admin, treat that as a smell in the exercise design or in the policy drafting, not as a new normal.
When you leave this lesson, you should be able to open any TechLearningPro architecture diagram and point to each box that calls AWS APIs and name its IAM role, its trust source, and the worst-case impact if that role's credentials leak. If a box has no answer, the diagram is incomplete. If two boxes share an over-broad role "for convenience," the diagram is dishonest. Authorization is part of architecture, not an afterthought for the security team the week after launch. Carry that standard into AWS CLI, SDKs and Infrastructure Access, where those roles become profiles, environment variables done safely, and SDK default credential chains without pasting secrets into shell history.
Lesson Summary
IAM is how TechLearningPro turns trust into enforceable decisions at API speed. Every allow is a bet; every wildcard is a larger bet. Write bets you can defend in a Monday review.
IAM is how TechLearningPro turns account boundaries into enforceable authorization. Roles with tight trust and least-privilege permissions separate humans, pipelines, and runtime workloads. Policy evaluation includes allows and many ways to deny; debugging requires reading the full stack including SCPs, resource policies, and KMS. Avoid long-lived keys, wildcards-for-convenience, and admin-on-the-task-role. The platform's security story is only as strong as the role that answers a progress API request at 2 a.m.
Next, AWS CLI, SDKs and Infrastructure Access makes temporary credentials operational in profiles, SSO sessions, and SDK clients. Networking lessons then decide which principals can reach which private resources at all—IAM allow does not bypass closed security groups.
Further Reading
Read these with a specific TechLearningPro question in mind—for example, "how does evaluation treat a resource policy deny?"—rather than as passive bookmarks. Authorization knowledge sticks when it is tied to a deny you must explain.
- IAM User Guide for identities, policies, and evaluation.
- Policy evaluation logic for the authoritative decision diagram.
- IAM Roles for trust and assumption.
- Permissions boundaries for delegated administration.
- IAM Access Analyzer for external access findings and policy generation workflows.
- STS AssumeRole for temporary credentials behavior.
- Service-specific guides for S3 bucket policies and KMS key policies when those resources appear in your design.