我有本地文件结构:
/tmp/24
/dir1
/file1
/file2
/dir2
/file3
/file4
我想将其上传到远程计算。当我使用
rsync /tmp/24 host:/target
它target
在远程主机上的目录内创建它(/target/24/dir1/file1
,...)。但是当我这样使用它时
rsync /tmp/24/ host:/target
它做了我想要的事情,那就是像这样创建它们:/target/dir1/file1
。但是,scp
如果目标文件夹已存在,则执行第一件事;如果目标文件夹不存在,则执行第二件事,无论路径/
是否以结尾。我怎样才能强迫像第二个例子scp
那样行事?rsync
答案1
源目录名称后面的“/”是 rsync 的一个微妙之处。注意它。
同步
源文件末尾的斜杠实际上意味着“复制内容该目录的目录,而不是目录本身”。如果没有尾部斜杠,则表示“复制目录”。
所以rsync -a tmp/24/ host:/target
会复制内容将“/tmp/24/”写入“主机:/目标/…”。
但rsync -a tmp/24 host:/target
会复制目录将“/tmp/24/”(及其内容)转换为“host:/target/24/...”。
如果“host:/target/”尚不存在也没关系;如果需要的话将会创建它,并且无论哪种方式结果都是相同的。
(目的地上的尾部斜杠并不重要。)
┌─────────────────────────┬───────────────┬───────────────────────┐
│ rsync │ target exists │ target does not exist │
├─────────────────────────┼───────────────┼───────────────────────┤
│ rsync -a tmp/24 target │ target/24/… │ target/24/… │
├─────────────────────────┼───────────────┼───────────────────────┤
│ rsync -a tmp/24/ target │ target/… │ target/… │
└─────────────────────────┴───────────────┴───────────────────────┘
SCP
斜杠根本不重要,只重要目标目录是否存在。如果存在则复制源目录进入目标目录,否则目标目录将创建为源目录的克隆。
┌───────────────────────┬───────────────┬───────────────────────┐
│ scp │ target exists │ target does not exist │
├───────────────────────┼───────────────┼───────────────────────┤
│ scp -r tmp/24 target │ target/24/… │ target/… │
├───────────────────────┼───────────────┼───────────────────────┤
│ scp -r tmp/24/ target │ target/24/… │ target/… │
└───────────────────────┴───────────────┴───────────────────────┘
所以你是对的,你应该先这样做ssh host mkdir -p /target
,然后行为将与 rsync 相同。
但为什么不直接使用rsync呢?它可以执行更多操作,例如部分传输、中断传输和压缩数据。
rsync -azu tmp/24 host:/target
CP
为了完整起见:在 Mac 上,只要目标已经存在,尾随的“/”就会为您提供 rsync 语义。
┌──────────────────────┬───────────────┬───────────────────────┐
│ cp (Mac) │ target exists │ target does not exist │
├──────────────────────┼───────────────┼───────────────────────┤
│ cp -a tmp/24 target │ target/24/… │ target/… │
├──────────────────────┼───────────────┼───────────────────────┤
│ cp -a tmp/24/ target │ target/… │ target/… │
└──────────────────────┴───────────────┴───────────────────────┘
在 Linux 下,斜杠根本不重要,与 scp 相同:
┌──────────────────────┬───────────────┬───────────────────────┐
│ cp (Linux) │ target exists │ target does not exist │
├──────────────────────┼───────────────┼───────────────────────┤
│ cp -a tmp/24 target │ target/24/… │ target/… │
├──────────────────────┼───────────────┼───────────────────────┤
│ cp -a tmp/24/ target │ target/24/… │ target/… │
└──────────────────────┴───────────────┴───────────────────────┘
同上
添加... ditto(1) 是一个用于克隆目录的 Mac OS 工具。它尽可能精确地复制。
斜杠根本不重要。目标目录是否已存在并不重要。
┌──────────────────────┬──────────┐
│ ditto tmp/24 target │ target/… │
└──────────────────────┴──────────┘
如果目标已经存在,则无条件覆盖先前存在的文件。目标中不在源中的文件将被保留。
答案2
呵呵,所以我的问题可以这样解决:
ssh host "mkdir -p /target"
scp tmp/24/* host:/target