14. Amazon S3: Buckets, Objects, Policies and Presigned URLs
14.3 Block Public Access and Bucket Policies
S3 madhe access teen levels var control hoto. He samjla tar S3 security samjli:
| Layer | What it controls | Our rule |
|---|---|---|
| Block Public Access (account and bucket) | A master switch that overrides any policy or ACL that would make data public | Keep ON for every bucket except a deliberate public website bucket |
| Bucket policy | JSON document on the bucket: who can do which action on which objects | Grant only what is needed |
| IAM policy | JSON attached to a user or role: what that identity may do | Least privilege for apps and people |
| ACLs (legacy) | Old per-object permissions | Keep disabled (Object Ownership = bucket owner enforced) |
A bucket policy has the same shape as every AWS policy – Effect, Principal, Action, Resource, and optional Condition. Example 1 allows only one IAM role (our app server) to read and write objects under videos/:
{
"Version": "2012-10-17",
"Statement": [
{
"Sid": "AppServerReadWriteVideos",
"Effect": "Allow",
"Principal": { "AWS": "arn:aws:iam::111122223333:role/reels-ec2-role" },
"Action": ["s3:GetObject", "s3:PutObject"],
"Resource": "arn:aws:s3:::ravindra-reels-media-pune/videos/*"
}
]
}
Example 2 denies any request that does not use HTTPS – a good line to add to every bucket:
{
"Sid": "DenyInsecureTransport",
"Effect": "Deny",
"Principal": "*",
"Action": "s3:*",
"Resource": [
"arn:aws:s3:::ravindra-reels-media-pune",
"arn:aws:s3:::ravindra-reels-media-pune/*"
],
"Condition": { "Bool": { "aws:SecureTransport": "false" } }
}
Note the two resources: the bucket ARN (for bucket-level actions such as s3:ListBucket) and bucket/* (for object-level actions such as s3:GetObject). 111122223333 is a placeholder account ID – use your own.
aws s3api put-bucket-policy --bucket ravindra-reels-media-pune --policy file://policy.json
aws s3api get-bucket-policy --bucket ravindra-reels-media-pune --query Policy --output text
aws s3api get-public-access-block --bucket ravindra-reels-media-pune
Why this matters for security
"Principal": "*" with "Effect": "Allow" means anyone on the internet. Combined with s3:ListBucket, an attacker can list every file name; with s3:PutObject, they can upload malware or overwrite your site. Block Public Access is your safety net: even if someone pastes a bad policy, S3 refuses to make the data public. Tools such as IAM Access Analyzer and AWS Config flag public buckets – we use them in the cloud security chapter.
Ravindra Bagale's Tip
"Access Denied" aala ki khup students sarvaat aadhi Block Public Access band kartat aani Principal: "*" taktat – problem "solve" hoto aani bucket public hoto! He kadhi karu naka. Access Denied aala tar vichara: request kon karto (kontya user/role ne)? Tya identity la IAM policy aahe ka? Resource ARN madhe /* visarla ka? Ha kram lakshat theva.
Practice task
Write a bucket policy that allows a role named backup-role to s3:PutObject only under backups/, and add the DenyInsecureTransport statement. Explain in one line why the bucket ARN and bucket/* are listed separately.