来自 Linux 的 Python pysftp get_r 在 Linux 上运行良好,但在 Windows 上不起作用

use*_*495 5 python linux windows sftp pysftp

我想使用 Python 2.7 使用 SFTP 递归地将包含文件和子文件夹的整个目录结构从 Linux 服务器复制到本地计算机(Windows 和 Linux)。

我可以在同一台机器上使用 WinSCP ping 服务器并下载文件。

我尝试了以下代码,在 Linux 上运行良好,但在 Windows 上不起作用。

我试过\/os.join,全部给了我同样的错误,检查权限也是如此。

import os
import pysftp

cnopts = pysftp.CnOpts()
cnopts.hostkeys = None    # disable host key checking.
sftp=pysftp.Connection('xxxx.xxx.com', username='xxx', password='xxx', cnopts=cnopts)
sftp.get_r('/abc/def/ghi/klm/mno', 'C:\pqr', preserve_mtime=False)
Run Code Online (Sandbox Code Playgroud)
import os
import pysftp

cnopts = pysftp.CnOpts()
cnopts.hostkeys = None    # disable host key checking.
sftp=pysftp.Connection('xxxx.xxx.com', username='xxx', password='xxx', cnopts=cnopts)
sftp.get_r('/abc/def/ghi/klm/mno', 'C:\pqr', preserve_mtime=False)
Run Code Online (Sandbox Code Playgroud)

Mar*_*ryl 8

确实,pysftpget_r在 Windows 上不起作用。它为远程 SFTP 路径使用os.sepos.path运行,有什么问题,因为 SFTP 路径总是使用正斜杠。

但是您可以轻松实现便携式替换:

import os
from stat import S_ISDIR, S_ISREG
Run Code Online (Sandbox Code Playgroud)
def get_r_portable(sftp, remotedir, localdir, preserve_mtime=False):
    for entry in sftp.listdir_attr(remotedir):
        remotepath = remotedir + "/" + entry.filename
        localpath = os.path.join(localdir, entry.filename)
        mode = entry.st_mode
        if S_ISDIR(mode):
            try:
                os.mkdir(localpath)
            except OSError:     
                pass
            get_r_portable(sftp, remotepath, localpath, preserve_mtime)
        elif S_ISREG(mode):
            sftp.get(remotepath, localpath, preserve_mtime=preserve_mtime)
Run Code Online (Sandbox Code Playgroud)

像这样使用它:

get_r_portable(sftp, '/abc/def/ghi/klm/mno', 'C:\\pqr', preserve_mtime=False) 
Run Code Online (Sandbox Code Playgroud)

可能的代码修改:


有关类似的问题put_r,请参阅:
Python pysftp put_r 在 Windows 上不起作用


旁注:不要“禁用主机密钥检查”。您正在失去针对MITM 攻击的保护。

有关正确的解决方案,请参阅使用 pysftp 验证主机密钥