jotadepicas
jotadepicas

Reputation: 2493

Deny access to AWS S3 to all IPs except specific ranges

I hava an S3 Bucket ("myBucket"), to which only a user has access, let's call it "s3user". I have an IAM policy attached to this user as follows:

{
    "Version": "2012-10-17",
    "Statement": [
        {
            "Sid": "VisualEditor0",
            "Effect": "Allow",
            "Action": [
                "s3:ListBucket",
                "s3:GetBucketLocation"
            ],
            "Resource": "arn:aws:s3:::myBucket"
        },
        {
            "Sid": "VisualEditor1",
            "Effect": "Allow",
            "Action": [
                "s3:PutObject",
                "s3:GetObject",
                "s3:ListBucket",
                "s3:GetObjectVersion"
            ],
            "Resource": "*"
        }
    ]
}

I attached this IAM Policy to user "s3User", granting read-only access to "myBucket". So far so good.

Now, I added a second policy, but now not an IAM policy but an S3 Bucket Policy, as follows:

{
    "Version": "2012-10-17",
    "Id": "S3PolicyId1",
    "Statement": [
        {
            "Sid": "IPAllow",
            "Effect": "Deny",
            "Principal": "*",
            "Action": "s3:*",
            "Resource": "arn:aws:s3:::myBucket/*",
            "Condition": {
                "NotIpAddress": {
                    "aws:SourceIp": [
                        "1.2.3.4/27",
                        "2.3.4.1/28",
                        "5.6.7.8/29"
                    ]
                }
            }
        }
    ]
}

I expected that this explicit deny will deny all requests not coming from the specified source IP ranges. But, it is still letting me list the contents of the bucket from other IPs. It seems as if the bucket policy had no effect at all.

According to this AWS S3 article, when you have multiple policies, they are all applied and explicit denies have precedence over explicit allows, so I think this should be working, but it isn't.

Any ideas why I'm not able to deny requests to a bucket based on sourceIP addresses?

Thanks!

Upvotes: 3

Views: 2054

Answers (1)

John Rotenstein
John Rotenstein

Reputation: 269101

You should update your Deny policy to include operations that are performed on the bucket itself, rather than its content (/*):

{
    "Version": "2012-10-17",
    "Id": "S3PolicyId1",
    "Statement": [
        {
            "Sid": "DenyOutsideIPfromBucket",
            "Effect": "Deny",
            "Principal": "*",
            "Action": [
                "s3:ListBucket",
                "s3:GetBucketLocation",
                "s3:PutObject",
                "s3:GetObject",
                "s3:ListBucket",
                "s3:GetObjectVersion"
            ],
            "Resource": ["arn:aws:s3:::myBucket/*", "arn:aws:s3:::myBucket"],
            "Condition": {
                "NotIpAddress": {
                    "aws:SourceIp": [
                        "1.2.3.4/27",
                        "2.3.4.1/28",
                        "5.6.7.8/29"
                    ]
                }
            }
        }
    ]
}

Of course, if the only users with access to the bucket are the ones with the IAM policy, you could simply add a IpAddress condition on the original IAM policy, so they can only use the bucket from the given set of IP addresses. This would avoid the need for a Deny policy.

Upvotes: 4

Related Questions