Ich möchte alle Dateien in einem Verzeichnis kopieren, mit Ausnahme einiger Dateien in einem bestimmten Unterverzeichnis. Ich habe festgestellt, dass der Befehl 'cp' keine Option --exclude hatte. Wie kann ich das erreichen?
tar -c | tar -x
?
Ich möchte alle Dateien in einem Verzeichnis kopieren, mit Ausnahme einiger Dateien in einem bestimmten Unterverzeichnis. Ich habe festgestellt, dass der Befehl 'cp' keine Option --exclude hatte. Wie kann ich das erreichen?
tar -c | tar -x
?
Antworten:
rsync ist schnell und einfach:
rsync -av --progress sourcefolder /destinationfolder --exclude thefoldertoexclude
Sie können --exclude
mehrere Male verwenden.
rsync -av --progress sourcefolder /destinationfolder --exclude thefoldertoexclude --exclude anotherfoldertoexclude
Beachten Sie, dass die Option dir thefoldertoexclude
after --exclude
relativ zu sourcefolder
, dh , sourcefolder/thefoldertoexclude
.
Sie können auch einen -n
Trockenlauf hinzufügen, um zu sehen, was kopiert wird, bevor der eigentliche Vorgang ausgeführt wird. Wenn alles in Ordnung ist, entfernen Sie ihn -n
aus der Befehlszeile.
--exclude
thefoldertoexclude
relativ zum sourcefolder
oder dem aktuellen Arbeitsverzeichnis? danke
rsync -av --progress --exclude="thefoldertoexclude" sourcefolder /destinationfolder
- ohnehin upvote für den rsync anstelle des find - verwenden, da Sie leicht absolute Pfade für die Quelle verwenden können, während es im find schwieriger ist, als {}
im dst.
$ rsync user@example.com:/var/www/mypage /var/www/mylocalpage/
oder vom lokalen zum Remote- $ rsync /var/www/mylocalpage/ user@example.com:/var/www/mypage
Nun, wenn das Ausschließen bestimmter Dateinamenmuster von jedem Unix-ish-Dateidienstprogramm (wie cp, mv, rm, tar, rsync, scp, ...) durchgeführt werden müsste, würde eine immense Doppelarbeit auftreten. Stattdessen können solche Dinge als Teil des Globbings ausgeführt werden , dh durch Ihre Shell.
man 1 bash
, / extglob .
Beispiel:
$ shopt -s extglob $ echo images / * images / 004.bmp images / 033.jpg images / 1276338351183.jpg images / 2252.png $ echo images /! (*. jpg) images / 004.bmp images / 2252.png
Sie fügen also einfach ein Muster ein !()
und es negiert die Übereinstimmung. Das Muster kann beliebig komplex sein, angefangen bei der Aufzählung einzelner Pfade (wie Vanwaril in einer anderen Antwort zeigt) !(filename1|path2|etc3)
bis hin zu regexartigen Dingen mit Sternen und Zeichenklassen. Weitere Informationen finden Sie in der Manpage.
man 1 zshexpn
, / Dateinamengenerierung .
Sie können setopt KSH_GLOB
bashartige Muster erstellen und verwenden. Oder,
% setopt EXTENDED_GLOB % echo images / * images / 004.bmp images / 033.jpg images / 1276338351183.jpg images / 2252.png % echo images / * ~ * .jpg images / 004.bmp images / 2252.png
Entspricht also dem x~y
Muster x
, schließt jedoch das Muster aus y
. Weitere Informationen finden Sie auf der Manpage.
Die Fischschale hat eine viel schönere Antwort darauf:
🐟 cp (Zeichenfolgenübereinstimmung -v '* .excluded.names' - srcdir / *) destdir
Tippen Sie cp *
, drücken Sie CtrlX*und sehen Sie, was passiert. Es ist nicht schädlich, das verspreche ich
zsh
.
setopt -u extglob
.
Warum verwenden, rsync
wenn Sie Folgendes tun können:
find . -type f -not -iname '*/not-from-here/*' -exec cp '{}' '/dest/{}' ';'
Dies setzt voraus, dass die Zielverzeichnisstruktur mit der der Quelle übereinstimmt.
-path
Argument, um Pfadhierarchien zu testen, nicht -iname
find . -type f -not -path '*/not-from-here/*' -exec cp '{}' '/dest/{}' \;
rsync
? Weil es möglicherweise nicht im System vorhanden ist! während find
, cp
ist immer auf ihren Plätzen. Oder Sie von Leuten, die 2 Gig-Sachen installiert haben, um einfache Dinge zu tun?
cp -r `ls -A | grep -v "c"` $HOME/
# $1 = source path # $2 = destination path # $3 = filter copy_from_source_to_destination_except_filter() { cp -r $(ls -A $1 | grep -v -w $3 | awk -v path=$1 '{printf "%s/%s ", path, $1}') $2 }
Der einfachste Weg, den ich gefunden habe, bei dem Sie alle Dateien außer Dateien und Ordnern kopieren können, indem Sie ihre Namen in Klammern einfügen:
shopt -s extglob
cp -r !(Filename1 | FoldernameX | Filename2) Dest/
-bash: !: event not found
Dies erweitert den Kommentar von mvds und funktioniert für mich
cd dotfiles
tar -c --exclude .git --exclude README . | tar -x -C ~/dotfiles2
Es ist relativ zum Quellverzeichnis.
Dadurch wird das Verzeichnis source/.git
vom Kopieren ausgeschlossen.
rsync -r --exclude '.git' source target
rsync
rsync -r --verbose --exclude 'exclude_pattern' ./* /to/where/
und versuchen Sie es zuerst mit der Option -n, um zu sehen, was kopiert werden soll
Ich nehme an, Sie verwenden Bash oder Dash. Würde das funktionieren?
shopt -s extglob # sets extended pattern matching options in the bash shell
cp $(ls -laR !(subdir/file1|file2|subdir2/file3)) destination
Führen Sie ein ls aus, ohne die Dateien auszuschließen, die Sie nicht möchten, und verwenden Sie dies als erstes Argument für cp
ls
und einfach tun cp !(file1|file1) dest
.
cp $(ls folder/!exclude_folder0|exclude_folder1)) dest
rsync
ist eigentlich ziemlich knifflig. müssen mehrere Tests durchführen, damit es funktioniert.
Angenommen, Sie kopieren möchten /var/www/html
zu /var/www/dev
müssen aber ausschließen /var/www/html/site/video/
vielleicht Verzeichnis aufgrund seiner Größe. Der Befehl wäre:
rsync -av --exclude 'sites/video' /var/www/html/ /var/www/dev
Einige Einschränkungen :
/
in der Quelle wird benötigt, andernfalls wird auch das Quellverzeichnis anstelle seines Inhalts kopiert und wird/var/www/dev/html/xxxx
, was möglicherweise nicht das ist, was Sie wollen.Der --exclude
Pfad ist direkt relativ zur Quelle. Selbst wenn Sie den vollständigen absoluten Pfad angeben, funktioniert dies nicht.
-v
ist für ausführlich, -a
ist für den Archivierungsmodus, was bedeutet, dass Sie eine Rekursion wünschen und fast alles beibehalten möchten.
cp -rv `ls -A | grep -vE "dirToExclude|targetDir"` targetDir
Bearbeiten: Ich habe vergessen, auch den Zielpfad auszuschließen (andernfalls würde er rekursiv kopiert).
Dies ist eine Modifikation von Linus Kleens Antwort. Seine Antwort hat bei mir nicht funktioniert, weil es eine geben würde. vor dem Dateipfad hinzugefügt, den cp nicht mag (der Pfad würde wie source / .destination / file aussehen).
Dieser Befehl hat bei mir funktioniert:
find . -type f -not -path '*/exlude-path/*' -exec cp --parents '{}' '/destination/' \;
Der Befehl --parents behält die Verzeichnisstruktur bei.
mv tobecopied/tobeexcluded .
cp -r tobecopied dest/
mv tobeexcluded tobecopied/
Verschieben Sie es einfach vorübergehend in ein verstecktes Verzeichnis (und benennen Sie es anschließend um, falls gewünscht).
mkdir .hiddendir
cp * .hiddendir -R
mv .hiddendir realdirname
cp
einer Standard-POSIX-Shell funktioniert sh
.
Ich benutze eine "do while" -Schleife, um die Ausgabe des Befehls find zu lesen. In diesem Beispiel stimme ich mit bestimmten Mustern überein (anstatt sie auszuschließen), da es eine begrenzte Anzahl von Musterübereinstimmungen gibt, die ich möchte, als die ich nicht möchte. Sie können die Logik mit einem -not vor den -iname-Flags umkehren:
find . -type f -iname "*.flac" -o -print0 -iname "*.mp3" -print0 -o -iname "*.wav" -print0 -o -iname "*.aac" -print0 -o -iname "*.wma" -print0 | while read -d $'\0' file; do cp -ruv "$file" "/media/wd/network_sync/music/$file"; done
Ich verwende das oben Gesagte, um alle Musiktypdateien zu kopieren, die auf meinem Server neuer sind als die Dateien auf einem Western Digital TV Live Hub, den ich unter / media / wd gemountet habe. Ich benutze das oben genannte, weil ich viele DVD-Dateien, MPEGs usw. habe, die ich ausschließen möchte UND weil rsync aus irgendeinem Grund so aussieht, als würde es kopiert, aber nachdem ich mir das wd-Gerät angesehen habe, sind die Dateien trotz nein nicht da Fehler während der Rsync mit diesem Befehl:
rsync -av --progress --exclude=*.VOB --exclude=*.avi --exclude=*.mkv --exclude=*.ts --exclude=*.mpg --exclude=*.iso --exclude=*ar --exclude=*.vob --exclude=*.BUP --exclude=*.cdi --exclude=*.ISO --exclude=*.shn --exclude=*.MPG --exclude=*.AVI --exclude=*.DAT --exclude=*.img --exclude=*.nrg --exclude=*.cdr --exclude=*.bin --exclude=*.MOV --exclude=*.goutputs* --exclude=*.flv --exclude=*.mov --exclude=*.m2ts --exclude=*.cdg --exclude=*.IFO --exclude=*.asf --exclude=*.ite /media/2TB\ Data/data/music/* /media/wd/network_sync/music/
ls -I "filename1" -I "filename2" | xargs cp -rf -t destdir
Der erste Teil ls
alle Dateien aber versteckte bestimmte Dateien mit Flag -I
. Die Ausgabe von ls
wird als Standardeingabe für den zweiten Teil verwendet. xargs
Befehl cp -rf -t destdir
aus Standardeingabe erstellen und ausführen . die Flag - -r
Mittel kopieren Verzeichnisse rekursiv, -f
mittels Kopieren von Dateien mit Gewalt , welche die Dateien in die überschrieben werden destdir
, -t
um das Zielverzeichnis kopieren angeben.
cp -r ls -A | grep -v "Excluded_File_or_folder"
../$target_location -v