Exemple #1
0
 def get(self, remotepaths, localpath=''):
     """
     Copies one or more files from the remote host to the local host.
     """
     remotepaths = self._make_list(remotepaths)
     localpath = localpath or os.getcwd()
     globs = []
     noglobs = []
     for rpath in remotepaths:
         if glob.has_magic(rpath):
             globs.append(rpath)
         else:
             noglobs.append(rpath)
     globresults = [self.glob(g) for g in globs]
     remotepaths = noglobs
     for globresult in globresults:
         remotepaths.extend(globresult)
     recursive = False
     for rpath in remotepaths:
         if not self.path_exists(rpath):
             raise exception.BaseException(
                 "Remote file or directory does not exist: %s" % rpath)
     for rpath in remotepaths:
         if self.isdir(rpath):
             recursive = True
             break
     try:
         self.scp.get(remotepaths,
                      local_path=localpath,
                      recursive=recursive)
     except Exception as e:
         log.debug("get failed: remotepaths=%s, localpath=%s",
                   str(remotepaths), localpath)
         raise exception.SCPException(str(e))
Exemple #2
0
 def scp(self):
     """Initialize the SCP client."""
     if not self._scp or not self._scp.transport.is_active():
         log.debug("creating scp connection")
         self._scp = scp.SCPClient(self.transport,
                                   progress=self._file_transfer_progress,
                                   socket_timeout=self._timeout)
     return self._scp
Exemple #3
0
 def switch_user(self, user):
     """
     Reconnect, if necessary, to host as user
     """
     if not self.is_active() or user and self.get_current_user() != user:
         self.connect(username=user)
     else:
         user = user or self._username
         log.debug("already connected as user %s" % user)
Exemple #4
0
 def _load_rsa_key(self, private_key, private_key_pass=None):
     private_key_file = os.path.expanduser(private_key)
     try:
         rsa_key = get_rsa_key(key_location=private_key_file,
                               passphrase=private_key_pass)
         log.debug("Using private key %s (RSA)" % private_key)
         return rsa_key
     except (paramiko.SSHException, exception.SSHError):
         log.error('invalid rsa key or passphrase specified')
Exemple #5
0
 def remove_lines_from_file(self, remote_file, regex):
     """
     Removes lines matching regex from remote_file
     """
     if regex in [None, '']:
         log.debug('no regex supplied...returning')
         return
     lines = self.get_remote_file_lines(remote_file, regex, matching=False)
     log.debug("new %s after removing regex (%s) matches:\n%s" %
               (remote_file, regex, ''.join(lines)))
     f = self.remote_file(remote_file)
     f.writelines(lines)
     f.close()
Exemple #6
0
 def connect(self,
             host=None,
             username=None,
             password=None,
             private_key=None,
             private_key_pass=None,
             port=None,
             timeout=30,
             compress=None):
     host = host or self._host
     username = username or self._username
     password = password or self._password
     compress = compress or self._compress
     port = port if port is not None else self._port
     pkey = self._pkey
     if private_key:
         pkey = self.load_private_key(private_key, private_key_pass)
     log.debug("connecting to host %s on port %d as user %s" %
               (host, port, username))
     try:
         sock = self._get_socket(host, port)
         transport = paramiko.Transport(sock)
         transport.banner_timeout = timeout
     except socket.error:
         raise exception.SSHConnectionError(host, port)
     # Enable/disable compression
     transport.use_compression(compress)
     # Authenticate the transport.
     try:
         transport.connect(username=username, pkey=pkey, password=password)
     except paramiko.AuthenticationException:
         raise exception.SSHAuthException(username, host)
     except paramiko.SSHException as e:
         msg = e.args[0]
         raise exception.SSHError(msg)
     except socket.error:
         raise exception.SSHConnectionError(host, port)
     except EOFError:
         raise exception.SSHConnectionError(host, port)
     except Exception as e:
         raise exception.SSHError(str(e))
     self.close()
     self._transport = transport
     try:
         assert self.sftp is not None
     except paramiko.SFTPError as e:
         if 'Garbage packet received' in e:
             log.debug("Garbage packet received", exc_info=True)
             raise exception.SSHAccessDeniedViaAuthKeys(username)
         raise
     return self
Exemple #7
0
 def load_private_key(self, private_key, private_key_pass=None):
     # Use Private Key.
     log.debug('loading private key %s' % private_key)
     if private_key.endswith('rsa') or private_key.count('rsa'):
         pkey = self._load_rsa_key(private_key, private_key_pass)
     elif private_key.endswith('dsa') or private_key.count('dsa'):
         pkey = self._load_dsa_key(private_key, private_key_pass)
     else:
         log.debug(
             "specified key does not end in either rsa or dsa, trying both")
         pkey = self._load_rsa_key(private_key, private_key_pass)
         if pkey is None:
             pkey = self._load_dsa_key(private_key, private_key_pass)
     return pkey
Exemple #8
0
def get_private_rsa_fingerprint(key_location=None,
                                key_file_obj=None,
                                passphrase=None):
    """
    Returns the fingerprint of a private RSA key as a 59-character string (40
    characters separated every 2 characters by a ':'). The fingerprint is
    computed using the SHA1 (hex) digest of the DER-encoded (pkcs8) RSA private
    key.
    """
    k = get_rsa_key(key_location=key_location,
                    key_file_obj=key_file_obj,
                    passphrase=passphrase,
                    use_pycrypto=True)
    sha1digest = hashlib.sha1(k.exportKey('DER', pkcs=8)).hexdigest()
    fingerprint = insert_char_every_n_chars(sha1digest, ':', 2)
    key = key_location or key_file_obj
    log.debug("rsa private key fingerprint (%s): %s" % (key, fingerprint))
    return fingerprint
Exemple #9
0
 def put(self, localpaths, remotepath='.'):
     """
     Copies one or more files from the local host to the remote host.
     """
     localpaths = self._make_list(localpaths)
     recursive = False
     for lpath in localpaths:
         if os.path.isdir(lpath):
             recursive = True
             break
     try:
         self.scp.put(localpaths,
                      remote_path=remotepath,
                      recursive=recursive)
     except Exception as e:
         log.debug("put failed: localpaths=%s, remotepath=%s",
                   str(localpaths), remotepath)
         raise exception.SCPException(str(e))
Exemple #10
0
def get_public_rsa_fingerprint(key_location=None,
                               key_file_obj=None,
                               passphrase=None):
    """
    Returns the fingerprint of the public portion of an RSA key as a
    47-character string (32 characters separated every 2 characters by a ':').
    The fingerprint is computed using the MD5 (hex) digest of the DER-encoded
    RSA public key.
    """
    privkey = get_rsa_key(key_location=key_location,
                          key_file_obj=key_file_obj,
                          passphrase=passphrase,
                          use_pycrypto=True)
    pubkey = privkey.publickey()
    md5digest = hashlib.md5(pubkey.exportKey('DER')).hexdigest()
    fingerprint = insert_char_every_n_chars(md5digest, ':', 2)
    key = key_location or key_file_obj
    log.debug("rsa public key fingerprint (%s): %s" % (key, fingerprint))
    return fingerprint
Exemple #11
0
 def __del__(self):
     """Attempt to clean up if not explicitly closed."""
     log.debug('__del__ called')
     self.close()
Exemple #12
0
    def execute(self,
                command,
                silent=True,
                only_printable=False,
                ignore_exit_status=False,
                log_output=True,
                detach=False,
                source_profile=True,
                raise_on_failure=True):
        """
        Execute a remote command and return stdout/stderr

        NOTE: this function blocks until the process finishes

        kwargs:
        silent - don't print the command's output to the console
        only_printable - filter the command's output to allow only printable
                         characters
        ignore_exit_status - don't warn about non-zero exit status
        log_output - log all remote output to the debug file
        detach - detach the remote process so that it continues to run even
                 after the SSH connection closes (does NOT return output or
                 check for non-zero exit status if detach=True)
        source_profile - if True prefix the command with "source /etc/profile"
        raise_on_failure - raise exception.SSHError if command fails
        returns List of output lines
        """
        channel = self.transport.open_session()
        if detach:
            command = "nohup %s &" % command
            if source_profile:
                command = "source /etc/profile && %s" % command
            channel.exec_command(command)
            channel.close()
            self.__last_status = None
            return
        if source_profile:
            command = "source /etc/profile && %s" % command
        log.debug("executing remote command: %s" % command)
        channel.exec_command(command)
        output = self._get_output(channel,
                                  silent=silent,
                                  only_printable=only_printable)
        exit_status = channel.recv_exit_status()
        self.__last_status = exit_status
        out_str = b'\n'.join(output)
        if exit_status != 0:
            msg = "remote command '%s' failed with status %d"
            msg %= (command, exit_status)
            if log_output:
                msg += ":\n%s" % out_str
            else:
                msg += " (no output log requested)"
            if not ignore_exit_status:
                if raise_on_failure:
                    raise exception.RemoteCommandFailed(
                        msg, command, exit_status, out_str)
                else:
                    log.error(msg)
            else:
                log.debug("(ignored) " + msg)
        else:
            if log_output:
                log.debug("output of '%s':\n%s" % (command, out_str))
            else:
                log.debug("output of '%s' has been hidden" % command)
        return output
Exemple #13
0
 def sftp(self):
     """Establish the SFTP connection."""
     if not self._sftp or self._sftp.sock.closed:
         log.debug("creating sftp connection")
         self._sftp = paramiko.SFTPClient.from_transport(self.transport)
     return self._sftp