← All posts
2 min read

Read an S3 bucket policy line by line

#aws#cli#s3#storage#security#policy
📑 On this page

Part 31 of AWS from Zero. This lesson keeps the scope to one S3 behavior you can verify from the terminal.

What we are learning

A bucket policy is a resource policy. Its Principal says who, Action says what, Resource says where, and optional Condition narrows when.

Before you run it

ACCOUNT_ID=$(aws sts get-caller-identity --query Account --output text)
BUCKET="replace-with-your-private-demo-bucket"
READER_ROLE="S3ReadOnlyDemoRole"

This lesson builds and validates a policy file but does not attach it, so it cannot accidentally change live access.

The command

cat > bucket-policy.json <<EOF
{
  "Version": "2012-10-17",
  "Statement": [{
    "Sid": "AllowNamedRoleToReadObjects",
    "Effect": "Allow",
    "Principal": {"AWS": "arn:aws:iam::$ACCOUNT_ID:role/$READER_ROLE"},
    "Action": "s3:GetObject",
    "Resource": "arn:aws:s3:::$BUCKET/private/*"
  }]
}
EOF

The trailing /* targets objects under the prefix. The bucket itself would use arn:aws:s3:::bucket-name without the wildcard.

Inspect the result

aws accessanalyzer validate-policy \
  --policy-type RESOURCE_POLICY \
  --validate-policy-resource-type AWS::S3::Bucket \
  --policy-document file://bucket-policy.json \
  --output table

Review every error, security warning, warning, and suggestion before considering the policy for attachment.

One tiny variation

aws s3api get-bucket-policy \
  --bucket "$BUCKET" \
  --query Policy \
  --output text

This reads the currently attached policy, if one exists. It does not apply the local example.

Common mistake

Never use "Principal":"*" as a shortcut while learning. That changes the policy from a named identity to everyone and can create public or broad cross-account access.

Cleanup

rm bucket-policy.json

Only a local file was created. No bucket permission changed.

Next, we will learn Check whether an S3 bucket policy is public.

Official AWS CLI reference