实现功能:
利用 paramiko 模块实现
1.远程目录检索
2.远程文件下载
3.远程目录下载(带目录结构)
class SFTPConnection(object): def __init__(self, host, username, password, port=22): try: self.transport = paramiko.Transport(sock=(host, port)) self.transport.connect(username=username, password=password) self.sftp = paramiko.SFTPClient.from_transport(self.transport) except Exception, e: traceback.print_exc() sys.stderr.write("%s\n" % e) sys.exit(-1) def __del__(self): if self.transport: self.transport.close() def traverse_directory(self, base_dir, deep=1): """Traverse directory""" dir_stru = {} base_dir_name = os.path.basename(base_dir) dir_list = self.sftp.listdir(base_dir) for dir_name in dir_list: dir_path = os.path.join(base_dir, dir_name) if not self._is_file(dir_path): if deep > 1: dir_stru.setdefault(base_dir_name, []).append(self.traverse_directory(base_dir=dir_path, deep=deep - 1)) else: dir_stru.setdefault(base_dir_name, []).append(dir_name) else: dir_stru.setdefault(base_dir_name, []).append(dir_name) if not dir_list: dir_stru.setdefault(base_dir_name, []).append("") return dir_stru def _is_file(self, file_path): if not self._exist_path(file_path): sys.stderr.write("File path is not exist.[%s]\n" % file_path) return None return not stat.S_ISDIR(self.sftp.stat(file_path).st_mode) def _exist_path(self, file_path): try: file_stat = self.sftp.stat(file_path) return True except IOError, e: traceback.print_exc() sys.stderr.write("%s\n" % e) return False def file_downloader(self, file_path_src, file_dir_des): file_path_des = os.path.join(file_dir_des, os.path.basename(file_path_src)) if os.path.exists(file_path_des): sys.stderr.write("Download File[%s] have exist. Pass it.\n" % file_path_des) return if not self._exist_path(file_path_src) or not self._is_file(file_path_src): sys.stderr.write("File[%s] is not exist or is not a file.\n" % file_path_src) sys.exit(-1) if not os.path.exists(file_dir_des): os.mkdir(file_dir_des) sys.stdout.write("File[%s] size is %s \n" % (file_path_src, pretty_size(self.sftp.stat(file_path_src).st_size))) self.sftp.get(file_path_src, file_path_des) sys.stdout.write("Download file[%s] to [%s] done.\n" % (file_path_src, file_path_des)) def directory_download(self, dir_path_src, dir_path_des): if not self._exist_path(dir_path_src): sys.stderr.write("path[%s] is not exist in remote machine.\n" % dir_path_src) sys.exit(-1) if not os.path.exists(dir_path_des): os.mkdir(dir_path_des) for sub_dir_name in self.sftp.listdir(dir_path_src): sub_dir_path = os.path.join(dir_path_src, sub_dir_name) if self._is_file(sub_dir_path): self.file_downloader(sub_dir_path, dir_path_des) else: self.directory_download(sub_dir_path, os.path.join(dir_path_des, sub_dir_name)) sys.stdout.write("Download data from directory[%s] to [%s] done.\n" % (dir_path_src, dir_path_des))