During Corona times, I'm doing home-office often my home country, Egypt, where setting up and connecting to a VPN to my company's office, Germany, was gruelling at times. On the other hand, I want to access resources protected by AWS security groups.
Hmm, easy-peasy I could just add a Security Group Rule whitelisting my IP, right?
Correct! but I shouldn't get too attached because most likely, my Internet Service Provider (ISP) issues me a dynamic IP address, which means it’s subject to change on me, like when:
- I unplug my router
- I suffer a blackout
If it weren’t a dynamic IP address, it would be referred to as a static IP address…unchanging - then tbh you should haven't landed here for this blog ;).
So to cut it short, I could do that with a lot of clicking on the AWS console, but it's even harder for me cause I usually have more than one AWS account opened, that means jumping between those accounts is wasted effort.
So what about running a script from my local machine doing this for me...!
Here’s how the Bash script would look:
#!/bin/bash
group_id="sg-12345678";
port="27017";
curl v4.ifconfig.co > ip.txt
awk '{ print $0 "/32" }' < ip.txt > ipfull.txt
export foo=$(cat ipfull.txt)
aws ec2 authorize-security-group-ingress --region=eu-central-1 \
--group-id $group_id \
--ip-permissions IpProtocol=tcp,FromPort=$port,ToPort=$port,IpRanges="[{CidrIp=${foo},Description='tmp'}]"
Now let's go through the script line by line:
- In the beginning we need to set the values of the security group ID (better create a new one) and the port number. This example assumes the security group ID as
sg-12345678
and the port number as27017
(as I need it to access MongoDb but the SSH default,22
). - I fetch my IP address from v4.ifconfig.co page and write to a .txt file I'll name
ip.txt
and since I’m using only one>
rather than two, this operation will either create the file or, if it already exists, overwrite any text that might currently live there. - Since a security group requires a full address in CIDR format, I’ll use
awk
to readip.txt
, append the characters/32
, and output it into a new file I'll nameipfull.txt
. That file will now contain my full IP in CIDR format. - Now I’ll export the contents of the
ipfull.txt
file to a shell variable I’ll name$foo
. - Finally, we arrive at the money line. The EC2 subset of the general AWS CLI includes a command called
authorize-security-group-ingress
which can be used to add a new rule to the inbound policies of an existing security group. In this example we set the protocol astcp
and then pass the value of$foo
to the — cidr argument. Also, you could set Description for it, liketmp
or so.
Assuming that you named the script whitelist-ip.sh
, you’ll need to make the file executable and then run it like this:
chmod +x whitelist-ip.sh
./whitelist-ip.sh
UPDATE (30.08.2021)
Of course every time you run this script it will add a new SG rule but without deleting the old ones that you don't want them to be whitelisted anymore, so here will show how you delete SG rules within a SG, but most importantly to take care that it is going to delete all rules within that SG, that'S why we need first to create our own SG and attached it to the main SG as an inbound rule.
Now we can easily edit the script so we first loop through the rules matching this specific port and delete them before adding the new one with the current IP address.
#!/bin/bash
group_id="sg-12345678";
port="27017";
# Get existing IP rules for group matching port
ips=$(aws ec2 describe-security-groups --filters Name=ip-permission.to-port,Values=$port Name=ip-permission.from-port,Values=$port Name=ip-permission.protocol,Values=tcp --group-ids $group_id --output text --query 'SecurityGroups[*].{IP:IpPermissions[?ToPort==`'$port'`].IpRanges}' | sed 's/IP //g');
# Loop through IPs
for ip in $ips
do
# Delete IP rules matching port
aws ec2 revoke-security-group-ingress --group-id $group_id --protocol tcp --port $port --cidr $ip --region=eu-central-1
done
Done.
Here you can check out the whole script as a Github Gist .
I'd love for you to leave me a feedback below in the comments!