From ae38d4583a4ba5e2f509a10e4e403e433e10a17e Mon Sep 17 00:00:00 2001 From: Steve Baker Date: Sat, 27 Jul 2013 16:06:44 +1200 Subject: [PATCH] Replace rackspace PublicKey property with key_name. This fetches a keypair that is registered with nova and uses the public key, instead of having to specify the entire public key as a launch parameter. Tested to work on instances launched in DFW. This shares the keypair lookup method with AWS::EC2::Instance but adopts the property name of the underlying nova API. This property name will align with the yet-to-be-written OS::Nova::Server. Change-Id: I2dceb93a4544e5f99d246233f240fe99667efadf --- heat/engine/resources/instance.py | 14 ++++++++++---- heat/engine/resources/rackspace/cloud_server.py | 12 +++++++----- 2 files changed, 17 insertions(+), 9 deletions(-) diff --git a/heat/engine/resources/instance.py b/heat/engine/resources/instance.py index 1ac08554..0ef36e69 100644 --- a/heat/engine/resources/instance.py +++ b/heat/engine/resources/instance.py @@ -319,17 +319,23 @@ class Instance(resource.Resource): raise exception.FlavorMissing(flavor_id=flavor) return flavor_id + def _get_keypair(self, key_name): + for keypair in self.nova().keypairs.list(): + if keypair.name == key_name: + return keypair + raise exception.UserKeyPairMissing(key_name=key_name) + def handle_create(self): security_groups = self._get_security_groups() userdata = self.properties['UserData'] or '' flavor = self.properties['InstanceType'] - key_name = self.properties['KeyName'] availability_zone = self.properties['AvailabilityZone'] - keypairs = [k.name for k in self.nova().keypairs.list()] - if key_name not in keypairs and key_name is not None: - raise exception.UserKeyPairMissing(key_name=key_name) + key_name = self.properties['KeyName'] + if key_name: + # confirm keypair exists + self._get_keypair(key_name) image_name = self.properties['ImageId'] diff --git a/heat/engine/resources/rackspace/cloud_server.py b/heat/engine/resources/rackspace/cloud_server.py index 26f73c36..d87badba 100644 --- a/heat/engine/resources/rackspace/cloud_server.py +++ b/heat/engine/resources/rackspace/cloud_server.py @@ -34,7 +34,7 @@ class CloudServer(instance.Instance): 'Flavor': {'Type': 'String', 'Required': True}, 'ImageName': {'Type': 'String', 'Required': True}, 'UserData': {'Type': 'String'}, - 'PublicKey': {'Type': 'String'}, + 'key_name': {'Type': 'String'}, 'Volumes': {'Type': 'List'}} attributes_schema = {'PrivateDnsName': ('Private DNS name of the specified' @@ -294,7 +294,6 @@ zypper --non-interactive in cloud-init python-boto python-pip gcc python-devel """ # Retrieve server creation parameters from properties flavor = self.properties['Flavor'] - user_public_key = self.properties['PublicKey'] or '' # Generate SSH public/private keypair if self._private_key is not None: @@ -302,9 +301,12 @@ zypper --non-interactive in cloud-init python-boto python-pip gcc python-devel else: rsa = RSA.generate(1024) self.private_key = rsa.exportKey() - public_key = rsa.publickey().exportKey('OpenSSH') - public_keys = public_key + "\n" + user_public_key - personality_files = {"/root/.ssh/authorized_keys": public_keys} + public_keys = [rsa.publickey().exportKey('OpenSSH')] + if self.properties.get('key_name'): + key_name = self.properties['key_name'] + public_keys.append(self._get_keypair(key_name).public_key) + personality_files = { + "/root/.ssh/authorized_keys": '\n'.join(public_keys)} # Create server client = self.nova().servers -- 2.45.2