aws-ssh-resolver - Resolve AWS EC2 HostNames for OpenSSH configuration - $Release:0.0.4$
aws-ssh-resolver
keeps AWS EC2 HostNames in OpenSSH configuration
file in sync with Amazon cloud making it easier for to use OpenSSH,
and related tools, on Amazon Platform.
The Problem
Amazon EC2 Instance IP Addressing sets several challenges for SSH usage, and for any tool using SSH connections e.g. ansible, fabric, serverspec etc.
-
Amazon Public DNS Names encode Public IP Addresses. Each time an instance is assigned a new IP address, it also gets a new Public DNS name. In essence this means that the task of managing DNS names becomes comparable to the task of managing IP addresses.
-
Using an IP address to contact an instance is complicated, because Public IP Address, once released, cannot be reused. Using fixed IP addresses requires keeping track of reserved address, and comes with extra costs.
-
EC2 instances, with only a Private IP Address, cannot be reached directly from the Internet.
-
Private DNS names also encode the IP address they map to. On top of that, Private DNS names cannot resolved outside the cloud network.
The Solution
aws-ssh-resolver addresses the challenges above
-
It accepts output of Amazon Command Line Interface to create OpenSSH Configuration entries mapping persistent, and human-understandable, EC2 Tag names to mutable EC2 DNS names.
-
Tag-name/DNS name mapping can be updated to reflect current cloud configuration.
-
Tag-name/DNS mapping together with ProxyCommand with Netcat configuration in OpenSSH allows users to create a transparent multihop SSH connection to EC2 instances with Private IP Address only
For more background information, see blog post.
Usage
Installation
Add following lines to Gemfile
source 'https://rubygems.org'
gem 'aws-ssh-resolver'
and run
bundle install
Configuration
Create an initial
OpenSSH Configuration
file ssh/config.aws
with any fixed configuration. Running
aws-ssh-resolver updates this file, but does not interfere with
the content user has entered.
Notice: The first aws-ssh-resolver run creates the initial
version of ssh/config.aws
automatically using ssh/config.init
, if
ssh/config.aws
-file does not exist, . This avoids the need to check
in the mutable ssh/config.aws
into a version control system.
Update OpenSSH Configuration file
To update OpenSSH configuration with EC2 Tag/DNS mappings pipe the
result of aws ec2 describe-instances
to aws-ssh-resolver
command:
aws ec2 describe-instances | bundle exec aws-ssh-resolver.rb resolve
The command extracts EC2 Tag/DNS information, and writes
host
/HostName
configuration entries in ssh/config.aws
-file. In
this file host
value is taken from Name
tag on an EC2 instance,
and HostName
value is taken from PublicDnsName
on an EC2
instance. If PublicDnsName
is not defined, the command uses
PrivateDnsName
instead.
When the network topology changes, i.e. an instance gets a new IP
address, an instance is terminated, or a new instance is launched,
rerun the command again to update content in ssh/config.aws
to
reflect the new situation.
An Example
Example Setup
The example uses two Ubuntu EC2 instances with Name
-tags myFront
and myBack1
. Instance myFront
has an internal IP
10.0.0.246
. Instances on subnet 10.0.0.0/24
can be reached over
Internet, and myFront
has been assigned a public IP 52.19.117.227
,
and an externally resolvable DNS name
c2-52-19-117-227.eu-west-1.compute.amazonaws.com
. Instance myBack1
belongs to private subnet 10.0.1.0/24
, and cannot reached directly
from Internet. It has a private IP address 10.0.1.242
with a DNS
name ip-10-0-1-242.eu-west-1.compute.internal
. Both of these
instances have been created using
Amazon EC2 Key Pair
demo_key
.
+----------------------------------------------------------------+
| Tags: [ "Name": "myFront" ], Ubuntu 14.04 LTS Trusty |
| 52.19.117.227/c2-52-19-117-227.eu-west-1.compute.amazonaws.com |
| 10.0.0.246/ip-10-0-0-246.eu-west-1.compute.internal |
! 10.0.0.0/24 |
| .ssh/demo_key.pub |
+----------------------------------------------------------------+
+----------------------------------------------------------------+
| Tags: [ "Name": "myBack1" ], Ubuntu 14.04 LTS Trusty |
| |
|10.0.1.242//ip-10-0-1-242.eu-west-1.compute.internal |
|10.0.1.0/24 |
|.ssh/demo_key.pub |
+----------------------------------------------------------------+
Initial Configuration
We start by creating ssh/config.aws
configuration file with the
following initial content
Host *.compute.internal
ProxyCommand ssh myFront1 -F ssh/config.aws nc -q0 %h 22
Host *
user ubuntu
StrictHostKeyChecking no
UserKnownHostsFile=/dev/null
IdentityFile ~/.ssh/demo-key/demo-key
This configuration instructs OpenSSH to use user name ubuntu
and SSH
private key in ~/.ssh/demo-key/demo-key
for all SSH connections.
Amazon assigns DNS names ending with compute.internal
to map to
Private IP address. The configuration tells OpenSSH to use myFront1
as a proxy to connect to instances with Private DNS name.
Read Network Topology, and Update OpenSSH Configuration
Running command
aws ec2 describe-instances | bundle exec aws-ssh-resolver.rb resolve
reads EC2 information from Amazon platform, extracts Name
tags and
DNS names, and updates ssh/config.aws
with host
and HostName
information as shown below:
# +++ aws-ssh-resolver-cli update start here +++
# Content generated 2015-09-06-21:57:37
host myFront1
HostName ec2-52-19-117-227.eu-west-1.compute.amazonaws.com
host myBack1
HostName ip-10-0-1-242.eu-west-1.compute.internal
# +++ aws-ssh-resolver-cli update end here +++
Host *.compute.internal
ProxyCommand ssh myFront1 -F ssh/config.aws nc -q0 %h 22
Host *
user ubuntu
StrictHostKeyChecking no
UserKnownHostsFile=/dev/null
IdentityFile ~/.ssh/demo-key/demo-key
This configuration adds the host definition for myFront1
, and
instructs OpenSSH to use a Public DNS name to connect the instance.
The HostName for myBack1
ends with compute.internal
, and the
OpenSSH uses the proxy definition to access it.
Using OpenSSH Configuration to Access ASW Instances
The configuration in ssh/config.aws
allows us to use tag name
myFront1
to make a SSH connection to machine with the DNS name
c2-52-19-117-227.eu-west-1.compute.amazonaws.com
simply with command
ssh myFront1 -F ssh/config.aws
Warning: Permanently added 'ec2-52-19-117-227.eu-west-1.compute.amazonaws.com,52.19.117.227' (ECDSA) to the list of known hosts.
The instance on subnet 10.0.1.0/24
cannot reached directly, and the
configuration instructs OpenSSH to use myFront
as a intermediary to
create a
transparent ssh connection
to myBack1
. This all takes place transparently, and the simple
command
ssh myBack1 -F ssh/config.aws
Warning: Permanently added 'ec2-52-19-117-227.eu-west-1.compute.amazonaws.com,52.19.117.227' (ECDSA) to the list of known hosts.
Warning: Permanently added 'ip-10-0-1-242.eu-west-1.compute.internal' (ECDSA) to the list of known hosts.
creates a SSH connection to myBack1
.
Warnings shown above, are due to parameters UserKnownHostsFile
and
StrictHostKeyChecking
, which prevent ssh from updating the default
.ssh/known_hosts
file with the fingerprints of the (temporary)
instances used in testing.
Updating OpenSSH Configuration
If the network configuration changes, rerunning
aws ec2 describe-instances | bundle exec aws-ssh-resolver.rb resolve
refreshes configuration in ssh/config.aws
.
Changes
See RELEASES
License
MIT