One small EC2 instance replaces all your SSH tunnels, bastion hosts, and VPN clients.
You have an RDS database, an Elasticache cluster, and a DynamoDB table sitting in a private VPC. No public endpoints. To access them from your laptop, the traditional options are: SSH tunnels through a bastion host, AWS Client VPN ($0.10/hour per connection), or SSM port forwarding with arcane aws ssm start-session commands that nobody remembers.
There's a simpler approach. A Tailscale subnet router running on a small EC2 instance advertises your VPC's private CIDR range to your Tailscale network. Once it's set up, you connect to RDS, Elasticache, and DynamoDB endpoints from your laptop as if you were inside the VPC. No tunnels, no port forwarding, no VPN clients.
Launch a t4g.nano (or t3.micro) in a private subnet of your VPC. Amazon Linux 2023 or Ubuntu work fine. The instance needs outbound internet access (through a NAT gateway) so Tailscale can establish its connection.
SSH into the instance and install Tailscale:
curl -fsSL https://tailscale.com/install.sh | sh
Start Tailscale with subnet routing enabled. Replace the CIDR with your VPC's range:
sudo tailscale up --advertise-routes=10.0.0.0/16 --hostname=aws-subnet-router
This tells Tailscale to advertise the entire 10.0.0.0/16 range through this machine. Any device on your Tailscale network can now route traffic to private IPs in that range through this instance.
The instance needs IP forwarding enabled so it can route packets between Tailscale and the VPC:
echo 'net.ipv4.ip_forward = 1' | sudo tee -a /etc/sysctl.d/99-tailscale.conf
echo 'net.ipv6.conf.all.forwarding = 1' | sudo tee -a /etc/sysctl.d/99-tailscale.conf
sudo sysctl -p /etc/sysctl.d/99-tailscale.conf
Go to the Tailscale admin console, find your subnet router machine, and approve the advertised routes. Until you approve them, no traffic flows.
If you're using Tailscale ACLs, you may need to add an autoApprovers section to automatically approve subnet routes for specific users or groups.
The subnet router needs security group rules that allow it to reach your private resources. Create a security group for the subnet router (or use an existing one) and add it as an inbound source on each resource's security group.
On the RDS instance's security group, add an inbound rule:
| Type | Port | Source |
|---|---|---|
| PostgreSQL | 5432 | sg-subnet-router |
| MySQL/Aurora | 3306 | sg-subnet-router |
On the Elasticache cluster's security group:
| Type | Port | Source |
|---|---|---|
| Redis | 6379 | sg-subnet-router |
| Memcached | 11211 | sg-subnet-router |
DynamoDB is a managed service accessed via the AWS API, not a direct TCP connection. To access it through the subnet router, you need a VPC gateway endpoint for DynamoDB (which is free) and your route tables must include the endpoint. The subnet router routes your API calls through the VPC where the endpoint resolves.
If you don't have a DynamoDB VPC endpoint, create one:
aws ec2 create-vpc-endpoint \
--vpc-id vpc-abc123 \
--service-name com.amazonaws.us-east-1.dynamodb \
--route-table-ids rtb-abc123
With the subnet router running and routes approved, you can now connect directly to private endpoints from your local machine. Tailscale routes the traffic transparently.
psql -h mydb.abc123.us-east-1.rds.amazonaws.com -U postgres -d myapp
That's it. No tunnel. No port forwarding. The RDS DNS name resolves to a private IP, Tailscale recognizes it's in the advertised range, and routes it through the subnet router.
redis-cli -h my-cluster.abc123.0001.use1.cache.amazonaws.com -p 6379
Same principle. The Elasticache endpoint resolves to a private IP in the VPC, and Tailscale handles the routing.
For DynamoDB, set your AWS CLI to route through the VPC endpoint. If your subnet router is working and DNS resolves correctly, you can use the standard endpoint:
aws dynamodb list-tables --region us-east-1
If you need to force traffic through the VPC endpoint specifically, use the endpoint URL:
aws dynamodb list-tables --endpoint-url https://dynamodb.us-east-1.amazonaws.com --region us-east-1
If you use yaw as your terminal, you can save these database connections in the connection manager. Your RDS PostgreSQL endpoint, Elasticache Redis cluster, and any SSH hosts on the Tailscale network are all available as saved connections with one-click access.
Yaw automatically discovers Tailscale machines on your network and lets you save them as SSH connections. For database connections, add the RDS or Elasticache endpoint as a PostgreSQL, MySQL, or Redis connection in the connection manager. Next time you need to check something in production, it's one click instead of remembering an endpoint URL and typing credentials.
The subnet router is a t4g.nano: about $3/month. Tailscale is free for personal use (up to 100 devices) and starts at $5/user/month for teams. The DynamoDB VPC endpoint is free. That's it.
Compare that to AWS Client VPN at $0.10/hour per active connection ($73/month if you're connected 8 hours a day) or the operational overhead of maintaining bastion hosts, SSH keys, and tunnel scripts.
Enable the Tailscale service so it starts automatically:
sudo systemctl enable tailscaled
For infrastructure-as-code deployments, generate a reusable auth key in the Tailscale admin console and pass it to tailscale up --authkey=tskey-... in your user data script. No interactive login needed.
Tailscale ACLs let you control which users or groups can access the subnet routes. You might allow the engineering team to access the staging VPC but restrict production access to the SRE team. This is more granular than security groups alone.
If you have multiple VPCs (staging, production, different regions), run a subnet router in each one. Each advertises its own CIDR range. From your laptop, you can reach any of them simultaneously — something that's painful with traditional VPNs that conflict with each other's routes.
One t4g.nano replaces your bastion host, your SSH tunnel scripts, your VPN client, and the 15 minutes you spend every morning re-establishing connections. You open your terminal, type psql -h mydb.abc123.us-east-1.rds.amazonaws.com, and you're in. Private resources, no ceremony.
Published by Yaw Labs.
Try yaw on Windows
Free to use, no account required. Install from PowerShell:
irm https://yaw.sh/install-win.ps1 | iex