By default, S3 buckets can be accessed through HTTP and HTTPs protocols.
As HTTP is a clear-text protocol, it lacks the encryption of transported data, as well as the capability to build an authenticated connection. It
means that a malicious actor who is able to intercept traffic from the network can read, modify or corrupt the transported content.
Ask Yourself Whether
- The S3 bucket stores sensitive information.
- The infrastructure has to comply with AWS Foundational Security Best Practices standard.
There is a risk if you answered yes to any of those questions.
Recommended Secure Coding Practices
It’s recommended to deny all HTTP requests:
- for all objects (
*
) of the bucket
- for all principals (
*
)
- for all actions (
*
)
Sensitive Code Example
No secure policy is attached to this bucket:
import aws_cdk.aws_s3 as s3
import aws_cdk.aws_iam as iam
bucket = s3.Bucket(self, "bucket") # Sensitive
A policy is defined but forces only HTTPs communication for some users, some objects of the bucket and for some actions:
bucket = s3.Bucket(self, "bucket")
bucket.add_to_resource_policy(iam.PolicyStatement( # Sensitive
effect=iam.Effect.DENY,
resources=[bucket.bucket_arn],
actions=["s3:SomeAction"],
principals=[roles],
conditions=[{"Bool": {"aws:SecureTransport": False}}]
)
)
Compliant Solution
A bucket policy that complies with s3-bucket-ssl-requests-only rule should be used. To adhere to it, the bucket policies need to explicitly deny
access to HTTP requests.
A secure policy that enforces SSL on requests (default: False):
bucket = S3.Bucket(self,
"bucket",
enforce_ssl=True
)
A secure policy that denies all HTTP requests is used:
bucket = s3.Bucket(self, "bucket")
result = bucket.add_to_resource_policy(iam.PolicyStatement(
effect=iam.Effect.DENY,
resources=["*"],
actions=["s3:*"],
principals=["*"],
conditions=["SecureTransport:False"]
)
)
See