AWS – S3: Allow public access to objects over VPN

Goal:

Allow public read access for all objects in the S3 bucket only using a VPN connection, objects must be non-public to connect from the world. OpenVPN is used as a VPN service, which can be deployed anywhere, so we will build an allow a rule to check the IP address.

 

First you need to find out the list of networks that belong to the endpoints of the S3 service in the region we need, so as not to wrap all traffic through the VPN. To do this, download the current list of networks and parse it:

jq '.prefixes[] | select(.region=="eu-central-1") | select(.service=="S3") | .ip_prefix' < ip-ranges.json

 

Where, "eu-central-1" is the region where the necessary S3 bucket is located.

 

You should get an output like:

"52.219.170.0/23"
"52.219.168.0/24"
"3.5.136.0/22"
"52.219.72.0/22"
"52.219.44.0/22"
"52.219.169.0/24"
"52.219.140.0/24"
"54.231.192.0/20"
"3.5.134.0/23"
"3.65.246.0/28"
"3.65.246.16/28"

 

Now we translate the subnet mask into a 4-byte format and add the parameters to the OpenVPN server configuration as "push" parameters:

push "route 52.219.170.0 255.255.254.0"
push "route 52.219.168.0 255.255.255.0"
push "route 3.5.136.0 255.255.252.0"
push "route 52.219.72.0 255.255.252.0"
push "route 52.219.44.0 255.255.252.0"
push "route 52.219.169.0 255.255.255.0"
push "route 52.219.140.0 255.255.255.0"
push "route 54.231.192.0 255.255.240.0"
push "route 3.5.134.0 255.255.254.0"
push "route 3.65.246.0 255.255.255.240"
push "route 3.65.246.16 255.255.255.240"

 

We restart the OpenVPN server service and after reconnecting we should get a list of required networks and traffic that will go through the VPN connection.

 

Now it remains to add the following policy to the S3 bucket:

{
    "Version": "2012-10-17",
    "Statement": [
        {
            "Sid": "Allow only from VPN",
            "Effect": "Allow",
            "Principal": "*",
            "Action": [
                "s3:GetObject",
                "s3:ListBucket"
            ],
            "Resource": [
                "arn:aws:s3:::artem-services",
                "arn:aws:s3:::artem-services/*"
            ],
            "Condition": {
                "IpAddress": {
                    "aws:SourceIp": "1.2.3.4"
                }
            }
        }
    ]
}

 

Where, "artem-services" is the name of the S3 bucket and "1.2.3.4" is the IP address of the OpenVPN server.

Tagged: Tags

Subscribe
Notify of
guest
0 Comments
Inline Feedbacks
View all comments