DEV Community

Imran Hayder
Imran Hayder

Posted on • Edited on

3 3

Create a simple VPC Peer between Kubernetes and RDS(postgres)

Create a VPC Peering connection between EKS Kubernetes and RDS Postgres

Note: this script assumes your resources names are prefixed with name of EKS cluster so if EKS cluster name is "myEKS" then the EKS VPC name is myEKS/VPC.

please fix this script variables in Step#1 according to your naming convention or actual names of resources.
all rest of steps are same.

Set some basic information like EKS names / VPC Names

Setting variables for EKS cluster:

EKS_CLUSTER="name_of_EKS_cluster_goes_here"
# set name of VPC in which EKS exists, for me i use eksctl to create eks
# so vpc name is automatically set to name_of_eks_cluster/VPC
# you can change here to whatever your VPC name is
EKS_VPC="$EKS_CLUSTER"/VPC 
# same goes for the VPC public routing table name of EKS
EKS_PUBLIC_ROUTING_TABLE="$EKS_CLUSTER"/PublicRouteTable
Enter fullscreen mode Exit fullscreen mode

and for RDS:

RDS_NAME="name_of_RDS_goes_here"
# set this variable to the name of VPC in which RDS exists 
RDS_VPC="$RDS_NAME"/VPC
# same goes for private routing table of RDS
RDS_PRIVATE_ROUTING_TABLE="$RDS_NAME"/RDSPrivateRoutingTable

RDS_DB_NAME="Name_of_RDS_instance"
Enter fullscreen mode Exit fullscreen mode

Now that all variables are set, the following steps should be run as simply copy-paste

Get VPC ID of acceptor i.e. RDS

echo "getting the VPC ID and CIDR of acceptor(RDS instance)"
ACCEPT_VPC_ID=$(aws ec2 describe-vpcs --filters Name=tag:Name,Values=$RDS_VPC --query=Vpcs[0].VpcId --output text)
ACCEPT_CIDR=$(aws ec2 describe-vpcs --filters Name=tag:Name,Values=$RDS_VPC --query=Vpcs[0].CidrBlockAssociationSet[0].CidrBlock --output text)
Enter fullscreen mode Exit fullscreen mode

Get VPC ID of requestor i.e. EKS

REQUEST_VPC_ID=$(aws ec2 describe-vpcs --filters Name=tag:Name,Values=$EKS_VPC --query=Vpcs[0].VpcId --output text)
REQUEST_CIDR=$(aws ec2 describe-vpcs --filters Name=tag:Name,Values=$EKS_VPC --query=Vpcs[0].CidrBlockAssociationSet[0].CidrBlock --output text)
Enter fullscreen mode Exit fullscreen mode

get Public Route table ID of requestor and acceptor

REQ_ROUTE_ID=$(aws ec2 describe-route-tables --filters Name=tag:Name,Values=$EKS_PUBLIC_ROUTING_TABLE --query=RouteTables[0].RouteTableId --output text)
ACCEPT_ROUTE_ID=$(aws ec2 describe-route-tables --filters Name=tag:Name,Values=$RDS_PRIVATE_ROUTING_TABLE --query=RouteTables[0].RouteTableId --output text)
Enter fullscreen mode Exit fullscreen mode

Create Peering Connection

peerVPCID=$(aws $DRY_RUN ec2 create-vpc-peering-connection --vpc-id $REQUEST_VPC_ID --peer-vpc-id $ACCEPT_VPC_ID --query VpcPeeringConnection.VpcPeeringConnectionId --output text)
aws $DRY_RUN ec2 accept-vpc-peering-connection --vpc-peering-connection-id "$peerVPCID"
aws $DRY_RUN ec2 create-tags --resources "$peerVPCID" --tags 'Key=Name,Value=eks-peer-rds'
Enter fullscreen mode Exit fullscreen mode

Adding the private VPC CIDR block to our public VPC route table as destination

aws $DRY_RUN ec2 create-route --route-table-id "$REQ_ROUTE_ID" --destination-cidr-block "$ACCEPT_CIDR" --vpc-peering-connection-id "$peerVPCID"
aws $DRY_RUN ec2 create-route --route-table-id "$ACCEPT_ROUTE_ID" --destination-cidr-block "$REQUEST_CIDR" --vpc-peering-connection-id "$peerVPCID"
Enter fullscreen mode Exit fullscreen mode

Add a rule that allows inbound RDS (from our Public Instance source)

RDS_VPC_SECURITY_GROUP_ID=$(aws rds describe-db-instances --db-instance-identifier $RDS_DB_NAME --query=DBInstances[0].VpcSecurityGroups[0].VpcSecurityGroupId --output text)
aws ec2 authorize-security-group-ingress --group-id ${RDS_VPC_SECURITY_GROUP_ID} --protocol tcp --port 5432 --cidr "$REQUEST_CIDR"
Enter fullscreen mode Exit fullscreen mode

TESTING CONNECTIONS

  1. Run postgresql container :

    kubectl run -i --tty --rm postgresdebug --image=alpine:3.5 -- 
     restart=Never -- sh
    
  2. install postgresql:

    apk update
    apk add postgresql
    
  3. Run PSQL:

    psql -h <HOST> -U <USER>
    Password for user <USER>:
    psql (9.6.10, server 9.6.15)
    SSL connection (protocol: TLSv1.2, cipher: ECDHE-RSA-AES256-GCM- 
    SHA384, bits: 256, compression: off)
    Type "help" for help.
    <DB_NAME>=
    

Sentry image

See why 4M developers consider Sentry, “not bad.”

Fixing code doesn’t have to be the worst part of your day. Learn how Sentry can help.

Learn more

Top comments (2)

Collapse
 
marktwallace profile image
Mark Wallace

Thanks for the helpful example! I used this to create a script to automate creating peering for my EKS and Aurora VPC's. I found that one step was left out: we also need to allow DNS resolution between the VPC's. The extra command needed, following the pattern above, is:

aws $DRY_RUN ec2 modify-vpc-peering-connection-options \
--vpc-peering-connection-id "$peerVPCID" \
--requester-peering-connection-options '{"AllowDnsResolutionFromRemoteVpc":true}' \
--accepter-peering-connection-options '{"AllowDnsResolutionFromRemoteVpc":true}'

Collapse
 
elepolt profile image
Evan

Thank you this was extremely useful. I have a quick question on how this might work if I need a second EKS VPC to peer to my RDS. Following the same commands gives me an error that there's a duplicate route and rule for 192.168.0.0/16, therefore my second EKS is timing out.

Billboard image

Deploy and scale your apps on AWS and GCP with a world class developer experience

Coherence makes it easy to set up and maintain cloud infrastructure. Harness the extensibility, compliance and cost efficiency of the cloud.

Learn more

👋 Kindness is contagious

Please leave a ❤️ or a friendly comment on this post if you found it helpful!

Okay