— Developer Tools

Free AWS IAM Policy Explainer

Paste an IAM, bucket or trust policy to see what each statement allows or denies, with risky grants flagged by severity.

— Samples
Statements 2High severity 0Valid
Live

What is an AWS IAM Policy Explainer?

AWS IAM policies are JSON documents that decide who can do what in an AWS account. They’re easy to get subtly wrong. This explainer reads a policy statement by statement, says in plain language what each one allows or denies, and flags the patterns that grant more than intended.

It follows the IAM JSON policy element reference for Version, Statement, Sid, Effect, Principal, Action, Resource, their Not forms, and Condition. Structural mistakes IAM would reject are errors. Valid but risky grants, such as administrator access, iam:PassRole on every role or a public principal, are findings ranked by severity.

Key Features

Each Statement in Plain Language

Actions, resources, principals and conditions are listed per statement, with wildcards spelled out as every action or every resource.

Risky Grants Flagged

Administrator access, PassRole on any role, service-wide wildcards, Allow with NotAction and anonymous principals are ranked high, medium or low.

Syntax Errors IAM Would Reject

A wrong Effect, a malformed action, a missing Resource, duplicate Sids and unknown condition operators are reported with the statement number.

Identity, Resource and Trust Policies

Policies with a Principal, such as bucket and role trust policies, are read without requiring Resource, as IAM reads them.

Your Account Details Stay Local

Account IDs, bucket names and role ARNs are parsed in the browser and never uploaded.

Perfect for everyone

  • Cloud engineers writing IAM policies
  • Security teams reviewing access
  • Developers reading a policy someone else wrote
  • Anyone preparing for an AWS audit

How to Use the AWS IAM Policy Explainer

Paste the policy, read each statement, and fix what’s flagged.

1

Copy the Policy JSON

Take it from the IAM console’s JSON tab, a Terraform or CloudFormation file, or aws iam get-policy-version output. Paste just the policy document.

2

Read Each Statement

Explain lists every statement with its effect, actions, resources, principals and conditions in plain language.

3

Review the Findings

High findings grant far more than most roles need. Medium and low findings are worth tightening. Switch to Findings only for a quick review.

4

Tighten and Re-Check

Replace wildcards with specific actions and ARNs, then paste the policy again. Confirm with IAM Access Analyzer before deploying.

Worked Examples

IAM Policies, Explained

We ran each policy below through the explainer in the chip’s mode and copied the result exactly, errors included. Work out what each policy grants first, then reveal the explanation.

REF_001Read-only bucket access

“{"Version":"2012-10-17","Statement":[{"Sid":"ReadLogs","Effect":"Allow","Action":["s3:GetObject","s3:ListBucket"],"Resource":["arn:aws:s3:::acme-logs","arn:aws:s3:::acme-logs/*"]}]}”

REF_002Administrator access

“{"Version":"2012-10-17","Statement":{"Effect":"Allow","Action":"*","Resource":"*"}}”

REF_003PassRole on everything

“{"Version":"2012-10-17","Statement":[{"Effect":"Allow","Action":["ec2:RunInstances","iam:PassRole"],"Resource":"*"}]}”

REF_004Trust policy

“{"Version":"2012-10-17","Statement":[{"Effect":"Allow","Principal":{"Service":"lambda.amazonaws.com"},"Action":"sts:AssumeRole"}]}”

REF_005Public bucket

“{"Version":"2012-10-17","Statement":[{"Effect":"Allow","Principal":"*","Action":"s3:GetObject","Resource":"arn:aws:s3:::acme-site/*"}]}”

REF_006Allow with NotAction

“{"Version":"2012-10-17","Statement":[{"Effect":"Allow","NotAction":"iam:*","Resource":"*"}]}”

REF_007Deny with a condition

“{"Version":"2012-10-17","Statement":[{"Sid":"Read","Effect":"Allow","Action":"s3:GetObject","Resource":"arn:aws:s3:::acme/*"},{"Sid":"NoDeleteWithoutMfa","Effect":"Deny","Action":"s3:DeleteObject","Resource":"*","Condition":{"BoolIfExists":{"aws:MultiFactorAuthPresent":"false"}}}]}”

REF_008Invalid Effect

“{"Version":"2012-10-17","Statement":[{"Effect":"Permit","Action":"s3:GetObject","Resource":"*"}]}”

REF_009Missing Resource

“{"Version":"2012-10-17","Statement":[{"Effect":"Allow","Action":"s3:GetObject"}]}”

REF_010Malformed action

“{"Version":"2012-10-17","Statement":[{"Effect":"Allow","Action":"s3 GetObject","Resource":"*"}]}”

Policy Elements

The Elements of an IAM Policy

Every IAM policy is built from the same handful of elements. These ten explain how AWS reads them.

01 / VERSION

Version

Always 2012-10-17 for new policies. The older 2008-10-17 language, used when Version is missing, doesn’t support policy variables.

“Which Version should a new policy use?”

02 / STATEMENT

Statement

One statement object or a list of them. Each statement is evaluated on its own, then the results are combined.

“Can Statement be a single object?”

03 / EFFECT

Effect

Exactly Allow or Deny. Anything not explicitly allowed is denied by default.

“What happens to an action no statement mentions?”

04 / ACTION

Action and NotAction

Actions are written service:Action, such as s3:GetObject, with * wildcards. NotAction means every action except those listed.

“Does s3:Get* match s3:GetObjectAcl?”

05 / RESOURCE

Resource and NotResource

The ARNs the statement applies to. A bucket and its objects are different resources, so listing objects needs both forms.

“Does arn:aws:s3:::logs cover objects inside the bucket?”

06 / PRINCIPAL

Principal

Who the statement applies to, used only in resource-based and trust policies. Identity policies apply to whoever they’re attached to.

“Can an identity policy have a Principal?”

07 / CONDITION

Condition

Extra tests on request context, such as source IP, MFA, tags or time. All conditions in a statement must be true.

“Do multiple condition keys in one statement combine with AND or OR?”

08 / SID

Sid

An optional label for a statement. Within a policy, each Sid must be unique.

“Can two statements share a Sid?”

09 / EXPLICIT

Explicit Deny Wins

A Deny that matches overrides every Allow, in any attached policy, SCP or boundary. It’s the strongest statement there is.

“Allow s3:* and Deny s3:DeleteObject. Can the role delete?”

10 / IFEXISTS

IfExists and Set Operators

Adding IfExists to an operator makes it pass when the key is absent. ForAnyValue and ForAllValues compare multi-valued keys such as tag lists.

“What does BoolIfExists do when the key is missing?”

Kinds of IAM Policy

The same JSON shape is used in several places, and where it’s attached changes how it’s read.

Identity-Based Policies

Attached to users, groups or roles, and say what that identity can do. They have no Principal and must name Resources.

Resource-Based Policies

Attached to resources such as S3 buckets, SQS queues and KMS keys, and say who can use them. They need a Principal.

Trust Policies

Attached to a role, and say who can assume it with sts:AssumeRole. They name a Principal and usually have no Resource.

Permissions Boundaries

Set the maximum an identity policy can grant. An action must be allowed by both the boundary and the identity policy.

Service Control Policies

Set guardrails across an AWS Organizations account. They never grant access on their own, only limit it.

Session Policies

Passed when assuming a role to narrow that session further. The effective access is the overlap with the role’s own policies.

IAM Policy Mistakes

These are the most common ways a policy grants more, or less, than intended.

Tip 01

Wildcard Actions on Wildcard Resources

Action * on Resource * is full admin, and s3:* on * covers every bucket in the account. Start from the actions the code really calls.

Tip 02

PassRole on Every Role

iam:PassRole on * lets someone hand an admin role to a service they control. Scope it to the specific role ARNs.

Tip 03

Forgetting Object ARNs

arn:aws:s3:::bucket covers the bucket, not its objects. GetObject needs arn:aws:s3:::bucket/* to work.

Tip 04

Allow With NotAction

It grants every action except those listed, including new actions AWS adds later. Prefer listing allowed actions.

Tip 05

Public Principals Without Conditions

Principal * makes a resource public. Pair it with conditions such as aws:SourceVpce or aws:PrincipalOrgID unless it truly is public.

Tip 06

Typos in Condition Operators

StringEqual instead of StringEquals makes the whole policy invalid. Copy operator names from the documentation.

Tip 07

Missing Version

Without Version 2012-10-17, policy variables such as aws:username are read literally. Always include it.

Tip 08

Assuming Allow Overrides Deny

An explicit Deny anywhere wins, including in SCPs and permission boundaries. Check those when an allowed action still fails.

Least-Privilege Patterns

Ways to grant exactly what a workload needs, and nothing more.

Tip 01

Start From Access Activity

IAM Access Advisor and CloudTrail show which actions a role actually used. Generate a policy from that history rather than guessing.

Tip 02

Scope Resources to ARNs

Name the exact bucket, table or queue ARNs, with wildcards only for object paths such as bucket/uploads/*.

Tip 03

Use Conditions to Narrow Access

aws:SourceVpce, aws:PrincipalOrgID and aws:ResourceTag keys limit where and on what an action is allowed.

Tip 04

Separate Read and Write

Give most services a read-only role, and a separate role for the few that write. Breaches of the reader can’t change data.

Tip 05

Guard PassRole With Specific ARNs

When a deploy role must pass roles, list them, and add iam:PassedToService to restrict which service can receive them.

Tip 06

Prefer Roles Over Users

Roles give temporary credentials that expire, while user access keys last until someone rotates them.

When to Explain a Policy

Whenever a policy is about to be attached, or nobody remembers what one does.

Reviewing a Pull Request

Paste the policy from a Terraform or CloudFormation change to see what it really grants before approving.

Understanding an Inherited Role

Read each statement of a role nobody documented, and spot what can be removed.

Debugging Access Denied

Check whether the action and resource are actually covered, or whether a Deny or condition blocks them.

Preparing for a Security Audit

Find administrator grants, public principals and PassRole wildcards before an auditor does.

Writing a Least-Privilege Policy

Draft the policy, read it back in plain language, and confirm nothing broader slipped in.

Checking a Bucket Policy

Confirm that only the intended accounts, roles or CloudFront distribution can read a bucket.

Learning IAM

Change one element at a time and watch the explanation and findings respond.

Frequently Asked Questions