![通过 ssh 复制大量文件](https://linux22.com/image/711848/%E9%80%9A%E8%BF%87%20ssh%20%E5%A4%8D%E5%88%B6%E5%A4%A7%E9%87%8F%E6%96%87%E4%BB%B6.png)
我通过 ssh 挂载了一个远程服务器(使用 sshfs)。我想将大量文件从远程服务器复制到本地:
cp -rnv /mounted_path/source/* /local_path/destination
该命令运行递归复制,不会覆盖现有文件。但复制过程相当慢。我注意到它没有按顺序复制文件。所以我的问题是:我可以通过打开多个终端并运行上述相同的命令来加快复制过程吗?复制过程是否足够智能,不会覆盖其他进程复制的文件?
答案1
…回答最初的问题……
这里有两件事需要讨论。
使用 SSHFS
SSHFS 使用 SSH 协议的 SFTP“子系统”使远程文件系统看起来像是在本地安装的。
这里需要注意的是,SSHFS 会转换低级 系统调用转换为相对高级的 SFTP 命令,然后由 SFTP 服务器转换为服务器上执行的系统调用,然后将其结果发送回客户端并向后转换。
造成此过程缓慢的原因有多种:
- 针对文件的不同操作有不同的系统调用,它们按照客户端发出的顺序执行。比如,客户端
stat(2)
-s 文件信息,然后open(2)
-s 该文件,然后读取其数据 — 通过read(2)
连续执行几个调用,最后close(2)
-s 文件,所有这些系统调用都必须转换为 SFTP 命令,发送到服务器并在那里进行处理,然后将结果发送回客户端,然后再转换回来。 尽管 SSHFS 似乎实现了某些巧妙的黑客技术,例如“预读”(推测读取比客户端请求的更多数据),但每个系统调用仍然会导致往返服务器。也就是说,我们将数据发送到服务器,然后等待它响应,然后处理它的响应。IIUC,SFTP 不实现“流水线”——一种在命令完成之前发送命令的操作模式,所以基本上每个系统调用都是如此。虽然它是技术上可行 在一定程度上进行这样的处理,
sshfs
似乎并没有实现。换句话说,
cp
客户端计算机上的每个系统调用都会转换为对服务器的请求,然后等待服务器响应并接收其响应。
多个cp -n
进程并行运行
对于是否可以采用多个进程并行复制文件这个问题的答案cp -n
取决于几个考虑因素。
首先,如果他们都跑过去相同SSHFS 挂载,显然不会加速,因为多个发出的所有系统调用cp
最终都会击中同一个 SFTP 客户端连接,并会由于上述原因被它序列化。
cp -n
二、运行多次实例清楚的
SSHFS 挂载点可能是值得的 — 取决于网络吞吐量和目标文件系统下的介质/媒体的 I/O 吞吐量所提供的限制。在这种情况下,重要的是要了解,由于 SSHFS 不会在服务器上使用任何锁定,因此不同的实例cp -n
必须在不同的目录层次结构上运行 — 只是为了不互相干扰。
不同/更合理的方法
首先,管道传输由 或其他流式归档器创建的数据流tar
并cpio
对其进行远程处理的优点是可以避免文件系统操作的所有往返:本地归档器以源文件系统上的 I/O 吞吐量允许的最快速度创建流,并以网络允许的最快速度发送流;删除归档器从流中提取数据并以其允许的最快速度更新其本地文件系统。无需往返执行基本“命令”:您只需以该管道中最慢的 I/O 点允许的最快速度运行即可;根本不可能再快了。
其次,另一个答案建议使用rsync
,但你拒绝了该建议,理由是
rsync 很慢,因为它必须对文件进行校验。
这完全是错误的。引用rsync
手册页:
-c
,--checksum
这会改变 rsync 检查文件是否已更改且需要传输的方式。如果没有此选项,rsync 将使用“快速检查”,默认情况下,它会检查发送方和接收方之间每个文件的大小和上次修改时间是否匹配。此选项会将其更改为比较每个大小匹配的文件的 128 位校验和。
和
-I
,--ignore-times
通常,rsync 会跳过任何大小相同且修改时间戳相同的文件。此选项关闭此“快速检查”行为,从而更新所有文件。
--size-only
这修改了 rsync 查找需要传输的文件的“快速检查”算法,将其从默认的传输大小或上次修改时间已更改的文件更改为仅查找大小已更改的文件。在使用其他可能无法准确保留时间戳的镜像系统后开始使用 rsync 时,这很有用。
最后
--existing
跳过在接收方上创建新文件
--ignore-existing
跳过更新接收器上存在的文件
那是,
- 默认情况下,
rsync
不会对文件的内容进行散列来查看文件是否已更改。 - 您可以告诉它完全像那样行事
cp -n
,也就是说,如果文件仅仅存在于远程,则跳过更新文件。
答案2
我建议使用两个实例tar
或cpio
通过 SSH 通道传输,例如
$ tar -C src/path -cf - . | ssh user@server tar -C dst/path -xf -
与在服务器和客户端之间进行多次往返的(和)| pv
相比,这种方法的优点是只需一个数据流就可以消耗“全管道”(如果您想要一些交互性,您也可以停留在中间以查看其运行情况)。SSHFS
SFTP
这里的关键是 SSH 不仅仅是“远程登录”(很多人认为它是),它还运行任何命令远程连接,同时将其标准 I/O 流连接至本地 SSH 客户端实例。
请注意,如果这种情况发生在安全的 LAN 或其他受控环境中,最好放弃 SSH,使用一对nc
或socat
实例 — 服务器上的监听实例和客户端上的发送实例。这种方法不会花费 CPU 周期来加密数据,因此您可能会受到以下三个组件之一的 I/O 限制:源 FS、网络和目标 FS。
答案3
不,复制过程并不智能,不会覆盖其他进程复制的文件。执行多个命令来复制相同的文件/文件夹并不是一个好主意。
有时,当源计算机和目标计算机距离太远且网络速度较慢时,您无能为力。以下是邮政讨论为什么 SSHFS 很慢。
答案4
我建议你使用rsync
标志avP
。例如:
rsync -avP <Source> <Destination>