S3 Bucket Exposure Calculator
Score an S3 bucket's public exposure across Block Public Access, bucket policy, object ACLs, website endpoints, pre-signed URLs and encryption.
Inputs
Exposure Index
62.3/ 100
Exposure Level
High
Sensitivity-Weighted Risk
55.3/ 100
Objects in the Exposed Path
779,366objects
Data in the Exposed Path
2,618.7GB
Dominant Exposure Path
Block Public Access is not fully enforced
Recommended Remediation
Turn on all four Block Public Access settings at the account level today, then re-test
Step by step
Values used
Block Public Access settings = Partially disabled, ACLs permitted — 20; Bucket policy principals = Principal:* on s3:GetObject — 18; Object ACL configuration = ACLs enabled, all objects private — 6; Website or distribution path = Behind CloudFront with origin access control — 5; Default encryption = SSE-S3 AES-256 — 3; Longest pre-signed URL lifetime = 168 hours; Objects in the bucket = 1,250,000 objects; Data stored in the bucket = 4,200 GB; Data classification = Confidential customer data — 3
S3 Bucket Exposure
Exposure index = Block Public Access points + bucket policy points + ACL points + website points + encryption points + min(12, log2(pre-signed URL hours) × 1.4), clamped to 0–100.
Sensitivity weighting
Sensitivity-weighted risk = exposure index × (0.55 + classification × 0.1125), so regulated data carries the full index and public content carries about two thirds of it.
Exposure Index
= 62.3 / 100
Exposure Level
= High
Sensitivity-Weighted Risk
= 55.3 / 100
Objects in the Exposed Path
= 779,366 objects
Data in the Exposed Path
= 2,618.7 GB
Dominant Exposure Path
= Block Public Access is not fully enforced
How it works
Every real path to a public object is scored with the points it contributes: Block Public Access is the strongest single control, so it carries 30 points, while the bucket policy carries 25 and object ACLs 15. Pre-signed URL lifetime scales logarithmically because the difference between fifteen minutes and one hour matters far more than the difference between a week and a month — both are already indefinite in attacker terms. Public buckets remain the most common cause of large cloud data leaks, and the reason is almost never a single setting: it is a bucket policy that survived a Block Public Access rollout, or a pre-signed URL with a seven-day lifetime pasted into a ticket.
Formulas
S3 Bucket Exposure
Exposure index = Block Public Access points + bucket policy points + ACL points + website points + encryption points + min(12, log2(pre-signed URL hours) × 1.4), clamped to 0–100.
- bpaState
- 0–30 points for how completely Block Public Access is enforced
- policyState
- 0–25 points for the broadest principal in the bucket policy
- aclState
- 0–15 points for object ACL grants
- presignedPts
- 0–12 points scaling logarithmically with pre-signed URL lifetime
Sensitivity weighting
Sensitivity-weighted risk = exposure index × (0.55 + classification × 0.1125), so regulated data carries the full index and public content carries about two thirds of it.
- sensitivity
- 1 public, 2 internal, 3 confidential, 4 regulated
- riskScore
- 0–100 risk after weighting for what the objects actually are
Frequently Asked Questions
How is S3 Bucket Exposure calculated?
Exposure index = Block Public Access points + bucket policy points + ACL points + website points + encryption points + min(12, log2(pre-signed URL hours) × 1.4), clamped to 0–100. Every real path to a public object is scored with the points it contributes: Block Public Access is the strongest single control, so it carries 30 points, while the bucket policy carries 25 and object ACLs 15. Pre-signed URL lifetime scales logarithmically because the difference between fifteen minutes and one hour matters far more than the difference between a week and a month — both are already indefinite in attacker terms.
Why does S3 Bucket Exposure matter?
Public buckets remain the most common cause of large cloud data leaks, and the reason is almost never a single setting: it is a bucket policy that survived a Block Public Access rollout, or a pre-signed URL with a seven-day lifetime pasted into a ticket.
What values do I need to enter?
This calculator takes 9 inputs: Block Public Access settings, Bucket policy principals, Object ACL configuration, Website or distribution path, Default encryption, Longest pre-signed URL lifetime, Objects in the bucket, Data stored in the bucket, Data classification. The pre-filled defaults are a realistic starting point — replace them with figures from your own environment for a result you can act on.
Does Block Public Access make the bucket policy irrelevant?
Only while it stays on. Block Public Access is an override, not a fix — the moment somebody disables it for a legitimate static-site migration, the wildcard bucket policy underneath becomes live. That is why this calculator scores both paths and does not zero the policy points when Block Public Access is enforced.
How should I treat pre-signed URLs?
As bearer tokens, because that is what they are: anyone holding the URL has the permissions of the signer until it expires. Keep the lifetime under an hour, sign with a short-lived role rather than a long-lived key, and never log the full URL.
You might also need
- GCP Bucket Exposure CalculatorCommonly used together
- Azure Storage Exposure CalculatorCommonly used together
- Public IP Exposure CalculatorCommonly used together
- Cloud Security Health Score CalculatorAlso in Cloud Security
- Cloud IAM Risk CalculatorAlso in Cloud Security
- Cloud Attack Surface CalculatorAlso in Cloud Security