aws-dynamodb-dax-create-workload-as
iam:PassRole for a DAX service role + dax:CreateCluster creates a DAX cluster executing DynamoDB requests as the passed role - AWS-specific single-action PassRole pattern.
match
A conjunctive graph pattern. Variables (?x) bind node ids; every clause must hold.
where
?principal has EFFECTIVE dax:CreateCluster
?role trust policy allows dax.amazonaws.com as the service principal
iam:PassRole for ?role permits iam:PassedToService including dax.amazonaws.com (or unconditioned)
emit
| source type | Identity |
|---|---|
| target type | MachineIdentity |
| source | ?principal |
| target | ?role |
| permissions | iam:PassRole dax:CreateCluster |
| conditions | iam_permission role_compatibility |
| state logic | ACTIVE when iam:PassRole is confirmed EFFECTIVE for ?role with iam:PassedToService admitting dax.amazonaws.com AND the principal has dax:CreateCluster effective. The DAX cluster must be deployed into a VPC subnet group (dax:CreateSubnetGroup may be required if no subnet group exists) — CONDITIONAL(iam_permission) when dax:CreateSubnetGroup is also needed but its effectiveness is unresolved. CONDITIONAL(role_compatibility) when the ?role trust policy or iam:PassedToService admission for dax.amazonaws.com is unresolved — downgrade to POTENTIAL(role_compatibility) if trust is unknown. BLOCKED when an SCP or permission-boundary denies iam:PassRole or dax:CreateCluster. |
Narrative
{principal.name} can create a DAX cluster bound to {role.name} (iam:PassRole + dax:CreateCluster), then query DynamoDB through the DAX endpoint, exercising {role.name}'s DynamoDB permissions - executing as {role.name} via the DAX service principal.
Raw rule rules/derived/aws/dynamodb.yaml
id: aws-dynamodb-dax-create-workload-as
emits: CanCreateWorkloadAs
description: "iam:PassRole for a DAX service role + dax:CreateCluster creates a DAX cluster executing\
\ DynamoDB requests as the passed role \u2014 AWS-specific single-action PassRole pattern."
match:
- - principal: null
- CanPassIdentity
- role: null
where:
- ?principal has EFFECTIVE dax:CreateCluster
- ?role trust policy allows dax.amazonaws.com as the service principal
- iam:PassRole for ?role permits iam:PassedToService including dax.amazonaws.com (or unconditioned)
emit:
source_type: Identity
target_type: MachineIdentity
source: ?principal
target: ?role
permissions:
- iam:PassRole
- dax:CreateCluster
conditions:
- iam_permission
- role_compatibility
state_logic: "ACTIVE when iam:PassRole is confirmed EFFECTIVE for ?role with iam:PassedToService admitting\
\ dax.amazonaws.com AND the principal has dax:CreateCluster effective. The DAX cluster must be deployed\
\ into a VPC subnet group (dax:CreateSubnetGroup may be required if no subnet group exists) \u2014\
\ CONDITIONAL(iam_permission) when dax:CreateSubnetGroup is also needed but its effectiveness is unresolved.\
\ CONDITIONAL(role_compatibility) when the ?role trust policy or iam:PassedToService admission for\
\ dax.amazonaws.com is unresolved \u2014 downgrade to POTENTIAL(role_compatibility) if trust is unknown.\
\ BLOCKED when an SCP or permission-boundary denies iam:PassRole or dax:CreateCluster."
confidence: min(contributing_confidences) * 0.90
derived_from:
- ?principal CanPassIdentity ?role
- can-execute-as:execute-as-via-new-workload (canonical CanCreateWorkloadAs -> CanExecuteAs chain cited,
not re-derived)
false_positive_note: "Honor iam:PassedToService: a role passable only to ec2.amazonaws.com does NOT\
\ become a DAX service role \u2014 downgrade to POTENTIAL(role_compatibility). The role MUST trust\
\ dax.amazonaws.com or CreateCluster fails at the IAM service level. DAX clusters require a VPC subnet\
\ group \u2014 if no subnet group exists, the principal may also need dax:CreateSubnetGroup. This\
\ rule derives CanCreateWorkloadAs directly from PassRole + dax:CreateCluster (bypassing the can-control\
\ linchpin's CanDeploy intermediate step) because dax:CreateCluster is an AWS-specific single action\
\ that performs both deployment and identity-passing. This is a pragmatic service-specific exception\
\ to the linchpin canonical chain. A DAX cluster with iam:PassRole does NOT give the calling principal\
\ direct DynamoDB access; it gives them a DAX cache that calls DynamoDB as the passed role on behalf\
\ of DAX API clients. The escalation path: principal creates DAX cluster -> DAX cluster calls DynamoDB\
\ as ?role -> principal queries DAX (dax:GetItem / dax:Query via DAX SDK) -> reads DynamoDB data as\
\ ?role. Cite can-execute-as:execute-as-via-new-workload for the final CanExecuteAs roll-up from CanCreateWorkloadAs;\
\ do not re-derive it here."
narrative: "{principal.name} can create a DAX cluster bound to {role.name} (iam:PassRole + dax:CreateCluster),\
\ then query DynamoDB through the DAX endpoint, exercising {role.name}'s DynamoDB permissions \u2014\
\ executing as {role.name} via the DAX service principal."