libcloud-notifications mailing list archives

Site index · List index
Message view « Date » · « Thread »
Top « Date » · « Thread »
From to...@apache.org
Subject svn commit: r1461394 - in /libcloud/branches/0.12.x: ./ CHANGES libcloud/compute/base.py
Date Wed, 27 Mar 2013 03:05:58 GMT
Author: tomaz
Date: Wed Mar 27 03:05:58 2013
New Revision: 1461394

URL: http://svn.apache.org/r1461394
Log:
Backport commits from trunk.

Modified:
    libcloud/branches/0.12.x/   (props changed)
    libcloud/branches/0.12.x/CHANGES
    libcloud/branches/0.12.x/libcloud/compute/base.py

Propchange: libcloud/branches/0.12.x/
------------------------------------------------------------------------------
  Merged /libcloud/trunk:r1460094-1460106

Modified: libcloud/branches/0.12.x/CHANGES
URL: http://svn.apache.org/viewvc/libcloud/branches/0.12.x/CHANGES?rev=1461394&r1=1461393&r2=1461394&view=diff
==============================================================================
--- libcloud/branches/0.12.x/CHANGES (original)
+++ libcloud/branches/0.12.x/CHANGES Wed Mar 27 03:05:58 2013
@@ -8,6 +8,11 @@ Changes with Apache Libcloud in developm
       (LIBCLOUD-310)
       [Jason Johnson]
 
+    - Allow user to pass alternate ssh usernames to deploy_node
+      (ssh_alternate_usernames kwarg) which are used for authentication if the
+      default one doesn't work. (LIBCLOUD-309)
+      [Chris Psaltis, Tomaz Muraus]
+
 Changes with Apache Libcloud 0.12.3:
 
   *) General

Modified: libcloud/branches/0.12.x/libcloud/compute/base.py
URL: http://svn.apache.org/viewvc/libcloud/branches/0.12.x/libcloud/compute/base.py?rev=1461394&r1=1461393&r2=1461394&view=diff
==============================================================================
--- libcloud/branches/0.12.x/libcloud/compute/base.py (original)
+++ libcloud/branches/0.12.x/libcloud/compute/base.py Wed Mar 27 03:05:58 2013
@@ -592,6 +592,11 @@ class NodeDriver(BaseDriver):
                                   SSH server (default is root)
         @type       ssh_username: C{str}
 
+        @keyword    ssh_alternate_usernames: Optional list of ssh usernames to
+                                             try to connect with if using the
+                                             default one fails
+        @type       ssh_alternate_usernames: C{list}
+
         @keyword    ssh_port: Optional SSH server port (default is 22)
         @type       ssh_port: C{int}
 
@@ -647,42 +652,53 @@ class NodeDriver(BaseDriver):
         if 'generates_password' in self.features['create_node']:
             password = node.extra.get('password')
 
+        ssh_interface = kwargs.get('ssh_interface', 'public_ips')
+
+        # Wait until node is up and running and has IP assigned
         try:
-            # Wait until node is up and running and has IP assigned
-            ssh_interface = kwargs.get('ssh_interface', 'public_ips')
             node, ip_addresses = self.wait_until_running(
                 nodes=[node],
                 wait_period=3, timeout=NODE_ONLINE_WAIT_TIMEOUT,
                 ssh_interface=ssh_interface)[0]
-
-            if password:
-                node.extra['password'] = password
-
-            ssh_username = kwargs.get('ssh_username', 'root')
-            ssh_port = kwargs.get('ssh_port', 22)
-            ssh_timeout = kwargs.get('ssh_timeout', 10)
-            ssh_key_file = kwargs.get('ssh_key', None)
-            timeout = kwargs.get('timeout', SSH_CONNECT_TIMEOUT)
-
-            ssh_client = SSHClient(hostname=ip_addresses[0],
-                                   port=ssh_port, username=ssh_username,
-                                   password=password,
-                                   key=ssh_key_file,
-                                   timeout=ssh_timeout)
-
-            # Connect to the SSH server running on the node
-            ssh_client = self._ssh_client_connect(ssh_client=ssh_client,
-                                                  timeout=timeout)
-
-            # Execute the deployment task
-            self._run_deployment_script(task=kwargs['deploy'],
-                                        node=node,
-                                        ssh_client=ssh_client,
-                                        max_tries=max_tries)
         except Exception:
             e = sys.exc_info()[1]
             raise DeploymentError(node=node, original_exception=e, driver=self)
 
+        if password:
+            node.extra['password'] = password
+
+        ssh_username = kwargs.get('ssh_username', 'root')
+        ssh_alternate_usernames = kwargs.get('ssh_alternate_usernames', [])
+        ssh_port = kwargs.get('ssh_port', 22)
+        ssh_timeout = kwargs.get('ssh_timeout', 10)
+        ssh_key_file = kwargs.get('ssh_key', None)
+        timeout = kwargs.get('timeout', SSH_CONNECT_TIMEOUT)
+
+        deploy_error = None
+
+        for username in ([ssh_username] + ssh_alternate_usernames):
+            try:
+                self._connect_and_run_deployment_script(
+                    task=kwargs['deploy'], node=node,
+                    ssh_hostname=ip_addresses[0], ssh_port=ssh_port,
+                    ssh_username=username, ssh_password=password,
+                    ssh_key_file=ssh_key_file, ssh_timeout=ssh_timeout,
+                    timeout=timeout, max_tries=max_tries)
+            except Exception:
+                # Try alternate username
+                # Todo: Need to fix paramiko so we can catch a more specific
+                # exception
+                e = sys.exc_info()[1]
+                deploy_error = e
+            else:
+                # Script sucesfully executed, don't try alternate username
+                deploy_error = None
+                break
+
+        if deploy_error is not None:
+            raise DeploymentError(node=node, original_exception=deploy_error,
+                                  driver=self)
+
         return node
 
     def create_volume(self, size, name, location=None, snapshot=None):
@@ -757,14 +773,16 @@ class NodeDriver(BaseDriver):
                             ssh_interface='public_ips', force_ipv4=True):
         # This is here for backward compatibility and will be removed in the
         # next major release
-        return wait_until_running(nodes=[node], wait_period=wait_period,
-                                  timeout=timeout, ssh_interface=ssh_interface,
-                                  force_ipv4=force_ipv4)
+        return self._wait_until_running(nodes=[node], wait_period=wait_period,
+                                        timeout=timeout,
+                                        ssh_interface=ssh_interface,
+                                        force_ipv4=force_ipv4)
 
     def wait_until_running(self, nodes, wait_period=3, timeout=600,
                            ssh_interface='public_ips', force_ipv4=True):
         """
-        Block until the given nodes are fully booted and have an IP address assigned.
+        Block until the given nodes are fully booted and have an IP address
+        assigned.
 
         @keyword    nodes: list of node instances.
         @type       nodes: C{List} of L{Node}
@@ -817,13 +835,14 @@ class NodeDriver(BaseDriver):
 
             if len(nodes) > len(uuids):
                 found_uuids = [n.uuid for n in nodes]
-                raise LibcloudError(value=('Unable to match specified uuids ' +
-                                           '(%s) with existing nodes. Found ' % uuids +
-                                           'multiple nodes with same uuid: (%s)' % found_uuids),
-                                    driver=self)
+                msg = ('Unable to match specified uuids ' +
+                       '(%s) with existing nodes. Found ' % (uuids) +
+                       'multiple nodes with same uuid: (%s)' % (found_uuids))
+                raise LibcloudError(value=msg, driver=self)
 
             running_nodes = [n for n in nodes if n.state == NodeState.RUNNING]
-            addresses = [filter_addresses(getattr(n, ssh_interface)) for n in running_nodes]
+            addresses = [filter_addresses(getattr(n, ssh_interface)) for n in
+                         running_nodes]
             if len(running_nodes) == len(uuids) == len(addresses):
                 return list(zip(running_nodes, addresses))
             else:
@@ -869,6 +888,25 @@ class NodeDriver(BaseDriver):
         raise LibcloudError(value='Could not connect to the remote SSH ' +
                             'server. Giving up.', driver=self)
 
+    def _connect_and_run_deployment_script(self, task, node, ssh_hostname,
+                                           ssh_port, ssh_username,
+                                           ssh_password, ssh_key_file,
+                                           ssh_timeout, timeout, max_tries):
+        ssh_client = SSHClient(hostname=ssh_hostname,
+                               port=ssh_port, username=ssh_username,
+                               password=ssh_password,
+                               key=ssh_key_file,
+                               timeout=ssh_timeout)
+
+        # Connect to the SSH server running on the node
+        ssh_client = self._ssh_client_connect(ssh_client=ssh_client,
+                                              timeout=timeout)
+
+        # Execute the deployment task
+        self._run_deployment_script(task=task, node=node,
+                                    ssh_client=ssh_client,
+                                    max_tries=max_tries)
+
     def _run_deployment_script(self, task, node, ssh_client, max_tries=3):
         """
         Run the deployment script on the provided node. At this point it is
@@ -894,6 +932,7 @@ class NodeDriver(BaseDriver):
             try:
                 node = task.run(node, ssh_client)
             except Exception:
+                e = sys.exc_info()[1]
                 tries += 1
                 if tries >= max_tries:
                     e = sys.exc_info()[1]



Mime
View raw message