SSH Keys...Background: I am currently building a private IaaS cloud using the open source cloudstack software.
Did you know that cloudstack comes with the ability to offer cloud clients the ability to authenticate into their instance's using ssh keys? I didn't.
So, I'm reading the cloudstack api documentation and ... Before you say anything, yes, I was actually reading an api doc. So, I see an api method entitled createSSHKeyPair and I wondered if it did what I think it did. It did.
Unfortunately, I couldn't find any documentation on this, so I thought I'd help the community out and share what I learned.
I should also mention that Cloudstack also supports another form of user authentication. That is random root/admin password generation. A user is given a random password for use on their instance. I've tested this an it seems to work fine. This works on linux, unix, and windows. This is not covered in this article however.
A quick primer on SSH keys and why this would be useful:
If you know all about ssh keypairs, then please feel free to skip to the next section.
If you don't know, an ssh key pair can be used to login into a system with a 'ssh key file' versus using a known password. Please feel free to reference other material to learn about ssh keys.
Using ssh keys and infrastructure as a service (iaas) clouds is useful for a couple reasons. First, every cloud user would be using their own ssh key. This, in itself, offers some additional security to your cloud solution. This ensures that one cloud user can not access another cloud user's instances (unless they shared their ssh key files). Secondly, when people choose to use clouds, they often are doing it because they know the value of programmatically being able to access and modifuy thier infrastructure (instances). And, one way to do that is to use ssh keys. This would allow to easily manage many instances with a simple, secure method.
By the way, Amazon's EC2 uses SSH KeyPairs pretty heavily.
Now, what work is needed to make this happen on a cloudstack cloud?
First, some restrictions, notes and disclaimers. This should work on most unix/linux variants. I don't think this works with Windows atm (since I don't think is has a built in SSH server =]). I've personally tested it on CentOs linux. Also, SSH Key management is not available via the cloudstack GUI (currently). That means that the only way to create instances that use ssh keys is via the API (for now). My work was done on cloudstack 3.0.0. However, I think it also works on older versions as well.
The only thing a cloudstack administrator needs to do is:
- Create a instance template that supports SSH Keys
The process for the cloud user would be:
- Create an SSH Key in cloudstack
- Create an instance using the SSHKey enabled temaplate and specifying their personal ssh key
- Login to the instance using their ssh key (not their password)
Create a instance template that supports SSH Keys
The folks @ Cloudstack published a script that enables SSH Key support on a linux instance. What does this script do? Well, the script will run on instance startup. It will communicate to the instance's virtual router and ask cloudstack for the SSH key private key. The script will then download the ssh key and install it on the instance for the cloud user to authenticate against. What we, as the cloud admin, will need to do is install this script on an instance and save the instance as a template. This way, cloud users will be able to use this feature.
Here is what I did on a CentOs instance in order to get this to work:
- Create a new instance using the CentOs template provided by cloudstack.
- Download the cloudstack script from here to the centos instance: http://sourceforge.net/projects/cloudstack/files/SSH%20Key%20Gen%20Script/
- Copy the file to /etc/init.d and have it run on startup.
- Stop the instance (via the cloudstack GUI)
- Create a template (via the cloudstack GUI)
Here are the commands I ran on the CentOs host before I created a template.
# download the script
# copy the script to the proper place
cp cloud-set-guest-sshkey.in /etc/init.d/
# set permissions on the script
chmod +x /etc/init.d/cloud-set-guest-sshkey.in
# tell the OS to start the script on start up
chkconfig --add cloud-set-guest-sshkey.in
The Cloud User work flow
1. Create an ssh key:
We will need to make a call to the createSSHKeyPair api method. I personally use the cloudstack python api library that jason hancock published. But, for a better example of how to do this via the api, I'll show example curl commands to the cloudstack api.
Note: I am making the below call from my cloudstack server itself. If you are making the api call from a different server, your URL/PORT will be different and you will need to use api keys.
Here, I am creating a ssh keypair called "keypair-test1" for the admin account in the root domain. (Please adjust these values to meet yoru needs)
My curl command:
curl --globoff "http://localhost:8096/?command=createSSHKeyPair&name=keypair-test1&account=admin&domainid=5163440e-c44b-42b5-9109-ad75cae8e8a2"
The output will look something like this:
<?xml version="1.0" encoding="ISO-8859-1"?><createsshkeypairresponse cloud-stack-version="220.127.116.1120228045507"><keypair><name>keypair-test1</name><fingerprint>f6:77:39:d5:5e:77:02:22:6a:d8:7f:ce:ab:cd:b3:56</fingerprint><privatekey>-----BEGIN RSA PRIVATE KEY-----
-----END RSA PRIVATE KEY-----
What you will want to do, is copy the key data into a file so that file looks like this:
-----BEGIN RSA PRIVATE KEY-----
-----END RSA PRIVATE KEY-----
Save the file. I called my file keypair-test1
2. Create an instance
Now, we need to create a new instance in cloudstack. We have to use the template we created above. We also will have to use the ssh key name from above. Note: you can not create the instance via the gui at this time and associate the instance with the newly created ssh keypair. A sample curl command to create a new instance would be:
Note: Please substitute the template, service offering and security group IDs (you may not need to specify a security group if you are not using that feature) that are in your cloudstack environment:
curl --globoff http://localhost:8096/?command=deployVirtualMachine\&zoneId=1\&serviceOfferingId=18727021-7556-4110-9322-d625b52e0813\&templateId=e899c18a-ce13-4bbf-98a9-625c5026e0b5\&securitygroupids=ff03f02f-9e3b-48f8-834d-91b822da40c5\&account=admin\&domainid=1\&keypair=keypair-test1
3. Login using the ssh key
Assuming everything above went well, you should be able to login into you new instance without using a password, but instead using your keypair:
From a linux cli, I ran this:
ssh -i ~/.ssh/keypair-test1 192.168.1.100
The -i parameter tells the ssh client to use a ssh key found at ~/.ssh/keypair-test1.
Notice it just works and doesn't ask for a password:
[root@cloudstack1]# ssh -i ~/.ssh/keypair-test1 192.168.1.100
Last login: Mon Mar 26 19:58:30 2012 from 18.104.22.168
[root@faa9ccca-30fe-4e4b-9645-d878514f0966 ~]# hostname
[root@faa9ccca-30fe-4e4b-9645-d878514f0966 ~]# cat /etc/redhat-release
CentOS release 5.6 (Final)
[root@faa9ccca-30fe-4e4b-9645-d878514f0966 ~]# uname -a
Linux faa9ccca-30fe-4e4b-9645-d878514f0966 2.6.18-238.el5xen #1 SMP Thu Jan 13 16:41:45 EST 2011 x86_64 x86_64 x86_64 GNU/Linux
Good luck and happy hunting.