Identity and Access Management · Topic 5 of 6
Conditions, ABAC and Delegation
Write precise IAM policies with condition keys, set operators, tag based access control, permission boundaries for delegation and PassRole limits.
- 5 min
- Conditions combine with AND across keys and OR across values of one key.
IfExistshandles missing keys, andForAllValuescan pass for an empty set, so use it with care.aws:PrincipalOrgIDsimplifies cross account allow policies for a whole organization.
What it is
Conditions make a policy statement apply only in certain situations, such as from a specific network, with MFA, or when a resource tag matches a principal tag. They turn a broad permission into a precise one without writing a statement per resource.
This page covers the condition language, attribute based access control (ABAC), and how to let teams create their own roles safely.
How it works
Condition structure
A condition block has an operator, a key and one or more values.
"Condition": {
"StringEquals": { "aws:RequestedRegion": ["eu-west-1", "eu-central-1"] },
"Bool": { "aws:SecureTransport": "true" }
}
The logic rules are easy to test.
- Several operators or keys in one block combine with AND.
- Several values for one key combine with OR.
- Add
IfExiststo an operator to treat a missing key as a match, which matters in deny statements. ForAnyValueandForAllValuesapply to keys with multiple values.ForAllValuesis true when the key is absent or empty, so combine it with a check that the key exists.- Negated operators such as
StringNotEqualsin a deny statement are a common way to write an exception.
Useful global condition keys
| Key | Use |
|---|---|
aws:PrincipalOrgID | Allow only principals in your organization |
aws:ResourceOrgID | Allow access only to resources in your organization |
aws:SourceIp, aws:SourceVpc, aws:SourceVpce | Limit by network location, not valid through service calls on your behalf |
aws:RequestedRegion | Limit which Regions can be used |
aws:SecureTransport | Require TLS |
aws:MultiFactorAuthPresent | Require MFA |
aws:PrincipalTag/key, aws:ResourceTag/key, aws:RequestTag/key | ABAC |
aws:SourceArn, aws:SourceAccount | Stop the confused deputy problem for service principals |
aws:ViaAWSService, aws:PrincipalIsAWSService | Allow or exclude calls made by AWS services on your behalf |
aws:CalledVia | Restrict to calls made through a specific service |
Network keys such as aws:SourceIp apply to the original caller. If an AWS service makes a call on the caller's behalf, the source is the service, so a deny based on IP can break service integrations unless you add aws:ViaAWSService.
Attribute based access control
ABAC grants access when tags match, so permissions scale without editing policies. One policy serves every project.
{
"Version": "2012-10-17",
"Statement": [{
"Effect": "Allow",
"Action": ["ec2:StartInstances", "ec2:StopInstances"],
"Resource": "arn:aws:ec2:*:*:instance/*",
"Condition": { "StringEquals": { "aws:ResourceTag/project": "${aws:PrincipalTag/project}" } }
}]
}
A user tagged project=Alpha can start and stop only instances tagged project=Alpha. New projects need only new tags.
Compare the two models.
| Model | Strength | Weakness |
|---|---|---|
| RBAC (role based) | Simple to understand, one role per job | Roles multiply as teams and projects grow |
| ABAC (tag based) | Scales with tags, fewer policies | Depends on tag governance and tag protection |
ABAC fails if people can change tags. Protect tag keys used for authorisation, by denying tag changes except for a trusted role, and use aws:RequestTag and aws:TagKeys to control tagging at creation. Identity Center and federation can pass user attributes as session tags to feed the principal tag.
Safe delegation with permissions boundaries
Developers often need to create roles for their applications, but they must not create roles that exceed their own limits. Combine a permissions boundary with a condition on role creation.
{
"Version": "2012-10-17",
"Statement": [
{
"Effect": "Allow",
"Action": ["iam:CreateRole", "iam:AttachRolePolicy", "iam:PutRolePolicy"],
"Resource": "arn:aws:iam::111122223333:role/app-*",
"Condition": { "StringEquals": { "iam:PermissionsBoundary": "arn:aws:iam::111122223333:policy/DevBoundary" } }
},
{
"Effect": "Deny",
"Action": ["iam:DeleteRolePermissionsBoundary", "iam:DeleteUserPermissionsBoundary"],
"Resource": "*"
}
]
}
The first statement allows role creation only when the boundary is attached, and the second stops the boundary being removed. Developers can then create roles within the limit and cannot escape it.
Controlling PassRole
iam:PassRole lets a principal give a role to a service. Without limits, a user can pass an administrator role to a Lambda function or EC2 instance and use it to escalate. Limit the resource to specific role ARNs, and use iam:PassedToService to name the service.
{
"Effect": "Allow",
"Action": "iam:PassRole",
"Resource": "arn:aws:iam::111122223333:role/app-lambda-*",
"Condition": { "StringEquals": { "iam:PassedToService": "lambda.amazonaws.com" } }
}
Data perimeter conditions
A resource policy can restrict a bucket to your organization with aws:PrincipalOrgID, and an identity policy or SCP can limit users to resources in your organization with aws:ResourceOrgID. Together with network conditions, these form a perimeter that keeps data in and untrusted identities out.
What to remember for the exam
- Conditions combine with AND across keys and OR across values of one key.
IfExistshandles missing keys, andForAllValuescan pass for an empty set, so use it with care.aws:PrincipalOrgIDsimplifies cross account allow policies for a whole organization.- ABAC compares
aws:PrincipalTagandaws:ResourceTag, and needs strict control of who can change tags. - Permissions boundaries with an
iam:PermissionsBoundarycondition allow safe delegation of role creation. - Limit
iam:PassRoleby resource and withiam:PassedToService. aws:SourceArnandaws:SourceAccountprevent the confused deputy problem for service principals.aws:SourceIpdoes not describe the real client when an AWS service calls on your behalf.
When a question asks to scale permissions as teams and projects grow with minimal policy changes, ABAC with tags is the usual answer.
Common mistakes
Letting users edit the tags that grant access. An attacker can retag themselves into another project.
Using a plain deny on aws:SourceIp. AWS services calling for you fail, so add exceptions for service calls.
Granting iam:PassRole on all roles. This is a classic privilege escalation path.
Relying on ForAllValues alone. It is true for an empty set, so the check can pass when it should not.
A boundary does not stop a user from granting access through a resource policy or other paths outside IAM identity policies, so combine boundaries with SCPs and careful delegation.
Check yourself
How do you let a developer create roles but only with a boundary?
Allow
iam:CreateRolewith a condition thatiam:PermissionsBoundaryequals the required boundary, and deny removal of the boundary.What does
aws:PrincipalOrgIDdo in a bucket policy?It allows access only to principals that belong to the named AWS Organization, without listing each account.
Why protect the tags used by ABAC?
If principals can change tags, they can give themselves access to other projects.
Topic 5 of 6 in Identity and Access Management
Test yourself on Identity and Access Management
The full AWS SCS-C03 question bank has 858 questions, with timed practice exams and an explanation for every answer.
This study guide is independent and is not affiliated with, endorsed by, or sponsored by AWS. Vendor names, certification names and exam codes are trademarks of their respective owners and are used for identification only.