Tarte alle PDFs in einem Verzeichnis und behalte die Verzeichnisstruktur bei


11

Ich versuche, einen komprimierten Tarball zu erstellen, der alle PDF-Dateien enthält, die in einem meiner Verzeichnisse vorhanden sind. Die Verzeichnisstruktur muss beibehalten werden. Leere Verzeichnisse werden nicht benötigt, aber es ist mir wirklich egal, ob sie da sind.

Angenommen, ich hätte ein Verzeichnis, das so aussieht:

dir
dir/subdir1
dir/subdir1/subsubdir1/song.mp3
dir/subdir2
dir/subdir2/subsubdir1
dir/subdir2/subsubdir1/document.pdf
dir/subdir2/subsubdir1/another-song.mp3
dir/subdir2/subsubdir1/top-ten-movies.txt
dir/subdir3
dir/subdir3/another-document.pdf

Nach dem Ausführen des Befehls möchte ich Folgendes dir.tar.gzenthalten:

dir
dir/subdir2
dir/subdir2/subsubdir1
dir/subdir2/subsubdir1/document.pdf
dir/subdir3
dir/subdir3/another-document.pdf

Möglich?

Antworten:


10

Dadurch werden alle PDFs aufgelistet:

$ find dir/ -name '*.pdf'
./dir/subdir2/subsubdir1/document.pdf
./dir/subdir3/another-document.pdf

Sie können das weiterleiten, xargsum es als einzelne durch Leerzeichen getrennte Zeile zu erhalten, und das eingeben, tarum das Archiv zu erstellen:

$ find dir/ -name '*.pdf' | xargs tar czf dir.tar.gz

(Auf diese Weise werden die leeren Verzeichnisse weggelassen.)


1
Das ist so toll, danke für die Hilfe. Folgendes habe ich mir ausgedacht:find docs \( -iname '*.pdf' -o -iname '*.mp3' \) -printf '"%p"\n' | xargs tar czf docs-media.tar.gz
Matt Alexander

3
@mattalexx: Beachten Sie, dass dieser Befehl nicht funktioniert, wenn einer der Dateinamen Leerzeichen oder enthält \'"(Fehler von xargs), und nicht funktioniert, wenn zu viele Dateinamen vorhanden sind (Fehler des Kernels).
Gilles 'SO - hör auf böse zu sein'

2
@ Gilles In Bezug auf Dateinamen mit Leerzeichen und einfachen Anführungszeichen -printf '"%p"\n'kümmert sich der Teil darum (zumindest für mich).
Matt Alexander

1
@ Gilles Interessant an der Kernel-Einschränkung. Wie viele Argumente können Sie in einem Befehl unter Linux haben?
Matt Alexander

5
Beachten Sie, dass der Fehlermodus hier lautet: Wenn die Befehlszeile zu lang ist, wird sie von xargs aufgeteilt, sodass der letzte Teeraufruf Dateien, die von früheren Aufrufen geschrieben wurden, stillschweigend überschreibt .
Gilles 'SO - hör auf böse zu sein'

6

Mit Bash ≥4 oder zsh und GNU tar:

tar -czf dir.tar.gz dir/**/*.pdf

Dies funktioniert möglicherweise nicht, wenn Sie eine sehr große Anzahl von PDF-Dateien haben und die Befehlszeile zu lang ist. Dann benötigen Sie eine komplexere findbasierte Lösung (ebenfalls mit GNU tar):

tar -cf dir.tar -T /dev/null
find dir -name '*.pdf' -exec tar -rf dir.tar {} +
gzip dir.tar

Alternativ (und portabel) können Sie das Archiv mit pax erstellen .

pax -w -x ustar -s '/\.pdf$/&/' -s '/.*//' . | gzip >dir.tar.gz

Der erste -sbesagt, dass alle .pdfDateien eingeschlossen werden sollen, ohne ihren Namen zu ändern. Die zweite -sbesagt, dass alle anderen Dateien in einen leeren Namen umbenannt werden sollen, was eigentlich bedeutet, sie nicht in das Archiv aufzunehmen.


Oh ja, ich wollte zsh's erwähnen **; Ich wusste nicht einmal, dass Bash 4 das jetzt hatte
Michael Mrozek
Durch die Nutzung unserer Website bestätigen Sie, dass Sie unsere Cookie-Richtlinie und Datenschutzrichtlinie gelesen und verstanden haben.
Licensed under cc by-sa 3.0 with attribution required.