复制所有文件和文件夹(不包括OS X上的Subversion文件和文件夹)


14

我正在尝试将所有文​​件和文件夹从一个目录复制到另一个目录,但排除某些文件。具体来说,我想排除Subversion文件和文件夹。但是,我想要一个通用而简洁的解决方案。

我想我会发现在不久的将来需要排除几种类型的文件。例如,我可能要排除.svn,*。bak和* .prj。

这是我为此准备的,但对我不起作用。第一部分,查找作品,但是xargscp我做错了什么。我尝试使用cp和不使用-R。另外,我正在使用OS X,它的xargs版本似乎比linux系统的特征少。

find ./sourcedirectory -not \( -name .svn -a -prune \)
     | xargs -IFILES cp -R FILES ./destinationdirectory

我可能是错的,但是我认为这比您想象的要棘手。即使你的find命令正确使用-prune排除.svn的项目,你再传递-R到标志cp告诉命令是递归的。这样做时,您将失去find命令中所具有的粒度。我将对此进行修补,但是我认为答案应该-Rcp命令中使用。
Telemachus

它似乎在Linux系统上对我有用。您能否更具体地说明“它不起作用”是什么意思?有任何错误讯息吗?您期望的文件正在/不被复制?
暂停,直到另行通知。

这是-R旗帜,我很确定。删除它,您就可以了(尽管我想您可能想添加它-mindepth 1来忽略不想复制的顶层目录文件夹)
Telemachus 09/09/28

我通常通过复制所有内容,然后删除目标目录中不需要的文件来执行这些操作。这通常要简单得多。
Jan Doggen

Answers:


22

(重新阅读问题后进行了编辑。发问者说未安装rsync)

您的find / xargs解决方案可能存在的问题是文件名中的空格。要解决此问题,请告诉find和xargs使用空字符(ASCII 0)分隔找到的文件:

find ./sourcedirectory -not ( -name .svn -a -prune ) -print0 | xargs -0 -IFILES cp FILES ./destinationdirectory

如果您发现rsync可用,我仍然认为rsync是更好的解决方案:

将rsync与-C选项一起使用。从rsync手册页

这对于排除通常不希望在系统之间传输的各种文件非常有用。它使用与CVS类似的算法来确定是否应忽略文件。

这将告诉rsync忽略以下模式:

RCS SCCS CVS CVS.adm RCSLOG cvslog.* tags TAGS .make.state .nse_depinfo *~
#* .#* ,* _$* *$ *.old *.bak *.BAK *.orig *.rej .del-* *.a *.olb *.o *.obj 
*.so *.exe *.Z *.elc *.ln core .svn/ .git/ .bzr/

例如:

rsync -avC /path/to/source/directory /path/to/destination/directory

(注意:如果您还不太熟悉rsync,请确保在该手册页上阅读有关rsync如何处理源路径中尾部斜杠的信息。如果包含斜杠,则与不包含斜杠的行为会有所不同。搜索“ trailing slash”)


噢,老鼠,我只是重新阅读了您的问题,发现您说您没有安装rsync。在我的MacBook Pro(OS X 10.6.1)上,它位于/ usr / bin / rsync中。它也为我安装在Tiger(10.4)和Leopard(10.5)下。
Doug Harris 2009年

我非常确定您(和OP)不要在命令-Rxargs一部分中使用该标志。
Telemachus

很好,我从原始问题中复制了该内容。现在将进行编辑。
道格·哈里斯

1
谢谢道格!我讲的一件事是“使用正确的工具完成工作”。我最近从Windows世界来到OSX,仍然在无知中徘徊。我在Linux频道中发布了相同的问题,有人迅速说,只要在终端中使用“ rsynch”,然后在终端中键入“ rsynch”,便会发现它不存在,并继续进行调查。xargs方法。我有点固执。无论如何,OSX默认情况下确实具有“ rsync”,您的帖子对您​​很有帮助。我在这里没有足够的经验来知道哪个更好,但是rsync当然更加简洁。谢谢!
Michael Prescott

如果您除了要在OS X上使用Linux机器之外还要进行其他工作,那么我认为您值得花时间学习如何使用rsync。它的主要功能是智能地复制已更改的内容(如果您熟悉的话,例如在Windows上进行robocopy)。因为它仅复制增量,所以这是处理(非Time Machine)备份,代码部署等的好方法。
道格·哈里斯

2

不是一般的解决方案,但是...您可以使用svn export命令创建工作空间的副本,而不需要.svn元数据文件夹。


不要冒犯,但我不确定为什么这个答案会被投票。我知道svn的功能,但“我想要一个通用而又简洁的解决方案。我想我会在不久的将来发现需要排除几种文件的类型”
Michael Prescott

2
%> mkdir -p FOLDER_OUT && ( tar cf - FOLDER_OR_FILES_IN --exclude=.svn  | tar xvf - -C FOLDER_OUT )

如果愿意,您甚至可以在两个tar进程之间放入“ pv”或类似内容。


2

一种肮脏但快速而简洁的方法:

cp -r source destination
find destination -iname .svn |xargs rm -rf

这会将一个目录复制到另一个目录(因此使用递归选项-r),然后递归擦除所有命名的内容.svn(忽略大小写)。


1

我将使用tar及其排除机制以另一种方式进行处理。

从目标目录中:

tar -X excludefile -C source -f - . | tar xf -

这将使cd变为源文件,将内容压缩(不包括excludefile中列出的内容),然后将其解压缩到当前目录。


确实是优雅的解决方案。
Nick Stinemates 09年

好吧,这是我稍后给出的相同答案。加上您必须在目标目录中... :)
akira

0

编辑答案:问题在于-R使您的复制递归,因此您最终复制了隐藏文件。这是我会用的:

find source/  -mindepth 1 -not \( -name .svn -prune \) | xargs -Iitem cp item target/

-mindepth 1标志find指示忽略顶层目录。由于您要将该目录的所有内容复制到一个新的顶层目录中,因此我假设您不希望这样做。

正如Chris Nava 在他的回答中所说如果我们正在谈论SVN文件夹,则已经有一种内置的方法来执行此操作,但是由于您要求使用更通用的解决方案,因此这可能会有所帮助。


感谢Telemachus,它很有帮助。我没有评论的经验,但是我将重复自从我最初的帖子以来的经历。“ xargs坏了”一位不知名的irc评论员告诉我,这启发了我多看一点,我想道格·哈里斯(Doug Harris)的回答解决了这个问题。告诉xargs使用空字符。我认为那是-0开关?
Michael Prescott

@Michael:xargs没坏,但是在类似Unix的系统上,默认设置是不使用文件名(或目录名)和空格。如果文件名(或目录名)中包含空格或“有趣”字符,则必须做额外的工作来处理。(在GNU find,没有在一整节man被称为“不寻常FILENAMES”因为这个问题页。)该-0xargs-print0用于find帮助处理这些问题。但是,我向您保证,您不想-R在复制命令中使用它。为避免SVN目录,它将撤消所有操作。
Telemachus

0

我想这取决于您的树的大小,但是为什么不先复制所有内容,然后再修剪.svn文件夹,为什么呢?

find /dest-dir -type d -name .svn -exec rm -rf {} \;


没有任何基准测试,我最初的想法是这是CPU周期的双重浪费:复制和删除。编写正确的find命令可能会花费一些额外的人力,但是您只需执行一次。一旦正确使用该命令,您可能会使用数百次。
Telemachus

@Telemachus-是的,但这就是计算机(应该是)擅长的-做一些棘手的事情,所以我们不必这样做!真的-如果仅复制一些文件以使它们很快删除,那有什么害处,如果这意味着您发明的命令非常简单?
史蒂夫·弗利

@Steve:真的没有害处。就目前而言,这是一个很好的解决方案。它遵循我喜欢的一个原则:“做最简单的可行的事情。” 另一方面,它违反了我更喜欢的另一个原则:“学习您的工具”。我宁愿学习如何find更好地使用自身,这样就不必这样做。但是您是对的:此解决方案并没有真正错。
Telemachus

@Telemachus:我同意“学习您的工具”。当我开始时,我确定我上面的find命令对我来说看起来很神秘:-)
Steve Folly


0

您也可以相反。复制所有内容,然后使用以下命令删除.svn文件夹:

find . | grep ".svn" | xargs rm -rf
By using our site, you acknowledge that you have read and understand our Cookie Policy and Privacy Policy.
Licensed under cc by-sa 3.0 with attribution required.