web-dev-qa-db-fra.com

Commande Shell dans le répertoire tar excluant certains fichiers / dossiers

Existe-t-il une simple commande/script de shell permettant d’empêcher l’archivage de certains fichiers/dossiers?

J'ai un répertoire qui doit être archivé avec un sous-répertoire qui contient un certain nombre de très gros fichiers que je n'ai pas besoin de sauvegarder.

Pas tout à fait des solutions:

La commande tar --exclude=PATTERN correspond au modèle donné et exclut ces fichiers, mais j'ai besoin que des fichiers et des dossiers spécifiques soient ignorés (chemin d'accès complet), sinon des fichiers valides pourraient être exclus.

Je pourrais également utiliser la commande find pour créer une liste de fichiers et exclure ceux que je ne souhaite pas archiver et les transmettre à tar, mais cela ne fonctionne que pour une petite quantité de fichiers. J'ai des dizaines de milliers.

Je commence à penser que la seule solution consiste à créer un fichier avec une liste de fichiers/dossiers à exclure, puis à utiliser rsync avec --exclude-from=file pour copier tous les fichiers dans un répertoire tmp, puis à utiliser tar pour archiver ce répertoire.

Quelqu'un peut-il penser à une solution meilleure/plus efficace?

EDIT: La solution de de Charles Ma fonctionne bien. Le gros problème est que le --exclude='./folder'DOIT être au début de la commande tar. Commande complète (cd en premier, la sauvegarde est donc relative à ce répertoire):

cd /folder_to_backup
tar --exclude='./folder' --exclude='./upload/folder2' -zcvf /backup/filename.tgz .
729
deepwell

Vous pouvez avoir plusieurs options d'exclusion pour tar afin

$ tar --exclude='./folder' --exclude='./upload/folder2' -zcvf /backup/filename.tgz .

etc. fonctionnera. Faites bien sûr pour mettre --excludeavant les éléments source et de destination.

939
Charles Ma

Vous pouvez exclure des répertoires avec --exclude pour tar.

Si vous voulez tout archiver sauf /usr, vous pouvez utiliser:

tar -zcvf /all.tgz / --exclude=/usr

Dans votre cas, peut-être quelque chose comme

tar -zcvf archive.tgz arc_dir --exclude=dir/ignore_this_dir
126
Johan Soderberg

Options possibles pour exclure les fichiers/répertoires de la sauvegarde à l'aide de tar:

Exclure des fichiers en utilisant plusieurs modèles

tar -czf backup.tar.gz --exclude=PATTERN1 --exclude=PATTERN2 ... /path/to/backup

Exclure des fichiers à l'aide d'un fichier d'exclusion contenant une liste de modèles

tar -czf backup.tar.gz -X /path/to/exclude.txt /path/to/backup

Exclure des fichiers à l'aide de balises en plaçant un fichier de balise dans un répertoire à ignorer

tar -czf backup.tar.gz --exclude-tag-all=exclude.tag /path/to/backup
58
Stephen Donecker

vieille question avec beaucoup de réponses, mais j’ai trouvé qu’aucune n’était assez claire pour moi, alors j’aimerais ajouter mon essai.

si vous avez la structure suivante

/home/ftp/mysite/

avec les fichiers/dossiers suivants

/home/ftp/mysite/file1
/home/ftp/mysite/file2
/home/ftp/mysite/file3
/home/ftp/mysite/folder1
/home/ftp/mysite/folder2
/home/ftp/mysite/folder3

alors, vous voulez créer un fichier tar contenant tout ce qui se trouve dans/home/ftp/mysite (pour déplacer le site sur un nouveau serveur), mais file3 n’est que du courrier indésirable, et tout ce qui se trouve dans folder3 est également pas nécessaire, alors nous allons sauter ces deux.

nous utilisons le format

tar -czvf <name of tar file> <what to tar> <any excludes>

où c = create, z = Zip et v = verbose (vous pouvez voir les fichiers au fur et à mesure de leur saisie, ce qui est utile pour vous assurer qu'aucun des fichiers que vous avez exclus n'est ajouté). et f = fichier.

alors, ma commande ressemblerait à ceci

cd /home/ftp/
tar -czvf mysite.tar.gz mysite --exclude='file3' --exclude='folder3'

notez que les fichiers/dossiers exclus sont relatifs à la racine de votre fichier tar (j'ai essayé le chemin complet ici par rapport à/mais je ne peux pas le faire fonctionner).

j'espère que cela aidera quelqu'un (et moi la prochaine fois, je le google)

42
Sverre

Vous pouvez utiliser la "notation ant" standard pour exclure les répertoires relatifs.
Ceci fonctionne pour moi et exclut tous les répertoires .git ou node_module.

tar -cvf myFile.tar --exclude=**/.git/* --exclude=**/node_modules/*  -T /data/txt/myInputFile.txt 2> /data/txt/myTarLogFile.txt

myInputFile.txt contient:

/ dev2/Java
/dev2/javascript

17
Eric Manley

Je l’ai expérimenté, du moins avec la version Cygwin de tar utilisée ("CYGWIN_NT-5.1 1.7.17 (0.262/5/3 ) 2012-10-19 14:39 i686 Cygwin "sur un ordinateur Windows XP Home Edition SP3), l’ordre des options est important.

Alors que cette construction a fonctionné pour moi:

tar cfvz target.tgz --exclude='<dir1>' --exclude='<dir2>' target_dir

celui-là n'a pas travail:

tar cfvz --exclude='<dir1>' --exclude='<dir2>' target.tgz target_dir

Ceci, alors que tar --help révèle ce qui suit:

tar [OPTION...] [FILE]

Donc, la deuxième commande devrait également fonctionner, mais apparemment, cela ne semble pas être le cas ...

Meilleurs Rgds,

16
GeertVc

Ce modèle d’exclusion gère le suffixe du nom de fichier comme png ou mp3, ainsi que les noms de répertoire tels que .git et node_modules

tar --exclude={*.png,*.mp3,*.wav,.git,node_modules} -Jcf ${target_tarball}  ${source_dirname}
13
Scott Stensland

Pour ceux qui ont des problèmes avec cela, certaines versions de tar ne fonctionneraient correctement que sans le './' dans la valeur d'exclusion.

Tar --version

tar (GNU tar) 1.27.1

Une syntaxe de commande qui fonctionne:

tar -czvf ../allfiles-butsome.tar.gz * --exclude=acme/foo

Ceux-ci ne fonctionneront pas:

$ tar -czvf ../allfiles-butsome.tar.gz * --exclude=./acme/foo
$ tar -czvf ../allfiles-butsome.tar.gz * --exclude='./acme/foo'
$ tar --exclude=./acme/foo -czvf ../allfiles-butsome.tar.gz *
$ tar --exclude='./acme/foo' -czvf ../allfiles-butsome.tar.gz *
$ tar -czvf ../allfiles-butsome.tar.gz * --exclude=/full/path/acme/foo
$ tar -czvf ../allfiles-butsome.tar.gz * --exclude='/full/path/acme/foo'
$ tar --exclude=/full/path/acme/foo -czvf ../allfiles-butsome.tar.gz *
$ tar --exclude='/full/path/acme/foo' -czvf ../allfiles-butsome.tar.gz *
10
J. Lawson

J'ai trouvé cela ailleurs, donc je ne prendrai pas le crédit, mais cela a fonctionné mieux que l'une des solutions ci-dessus pour mes problèmes spécifiques mac (même si cela est fermé):

tar zc --exclude __MACOSX --exclude .DS_Store -f <archive> <source(s)>
10
Rob

Pour Mac OSX je devais faire

tar -zcv --exclude='folder' -f theOutputTarFile.tar folderToTar

Notez le -f après le --exclude=

7
Jerinaw

Je conviens que le drapeau --exclude est la bonne approche.

$ tar --exclude='./folder_or_file' --exclude='file_pattern' --exclude='fileA'

Un mot de warning pour un effet secondaire que je n'ai pas trouvé immédiatement évident: l'exclusion de 'fileA' dans cet exemple va rechercher 'fileA' RÉCURSIVEMENT !

Exemple: un répertoire avec un seul sous-répertoire contenant un fichier du même nom (data.txt)

data.txt
config.txt
--+dirA
  |  data.txt
  |  config.docx
  • Si vous utilisez --exclude='data.txt', l’archive ne contiendra pas NI fichier data.txt. Cela peut entraîner des résultats inattendus si vous archivez des bibliothèques tierces, telles qu'un répertoire node_modules.

  • Pour éviter ce problème, assurez-vous de donner le chemin complet, comme --exclude='./dirA/data.txt'

6
Aaron Votre

Pour éviter les erreurs possibles 'xargs: Argument list too long' dues à l'utilisation de find ... | xargs ... lors du traitement de dizaines de milliers de fichiers, vous pouvez diriger la sortie de find directement vers tar à l'aide de find ... -print0 | tar --null ....

# archive a given directory, but exclude various files & directories 
# specified by their full file paths
find "$(pwd -P)" -type d \( -path '/path/to/dir1' -or -path '/path/to/dir2' \) -Prune \
   -or -not \( -path '/path/to/file1' -or -path '/path/to/file2' \) -print0 | 
   gnutar --null --no-recursion -czf archive.tar.gz --files-from -
   #bsdtar --null -n -czf archive.tar.gz -T -
5
carlo

Après avoir lu ce fil de discussion, j’ai fait un petit test sur RHEL 5 et voici mes résultats pour l’organisation du répertoire abc:

Cela exclura l’erreur des répertoires, les journaux et tous les fichiers sous les répertoires:

tar cvpzf abc.tgz abc/ --exclude='abc/error' --exclude='abc/logs'

Ajouter un caractère générique après le répertoire exclu exclura les fichiers mais préservera les répertoires:

tar cvpzf abc.tgz abc/ --exclude='abc/error/*' --exclude='abc/logs/*'
5
Mike

Utilisez la commande find en conjonction avec l'option tar append (-r). De cette façon, vous pouvez ajouter des fichiers à un fichier tar existant en une seule étape, au lieu d'une solution en deux étapes (créer une liste de fichiers, créer un fichier tar).

find /dir/dir -Prune ... -o etc etc.... -exec tar rvf ~/tarfile.tar {} \;
4
Alex B

Vous pouvez également utiliser l'une des options "--exclude-tag" en fonction de vos besoins:

  • --exclude-tag = FILE
  • --exclude-tag-all = FILE
  • --exclude-tag-under = FILE

Le dossier hébergeant le FICHIER spécifié sera exclu.

3
frommelmak

gnu tar v 1.26, le --exclude doit venir après les arguments du fichier d'archive et du répertoire de sauvegarde, ne doit comporter aucune barre oblique de fin ni de fin, et préfère ne pas utiliser de guillemets (simples ou doubles). Donc, par rapport au répertoire PARENT à sauvegarder, c’est:

tar cvfz /path_to/mytar.tgz ./dir_to_backup --exclude=some_path/to_exclude

2
Andrew

Vous pouvez utiliser cpio (1) pour créer des fichiers tar. cpio prend les fichiers à archiver sur stdin, donc si vous avez déjà compris la commande de recherche que vous voulez utiliser pour sélectionner les fichiers de l’archive, dirigez-la vers cpio pour créer le fichier tar:

find ... | cpio -o -H ustar | gzip -c > archive.tar.gz
2
camh

Après avoir lu toutes ces bonnes réponses pour différentes versions et résolu le problème moi-même, je pense qu'il existe de très petits détails qui sont très importants et rares pour une utilisation générale de GNU/Linux , qui n'est pas assez stressé et mérite plus que des commentaires.

Donc, je ne vais pas essayer de répondre à la question pour chaque cas, mais plutôt d'essayer d'enregistrer où regarder lorsque les choses ne fonctionnent pas.

IT IS TRÈS IMPORTANT AVIS:

  1. L'ORDRE DES OPTIONS IMPORTANTE: ce n'est pas la même chose mettez le --exclude avant qu'après l'option de fichier et les répertoires à sauvegarder. Ceci est au moins inattendu pour moi, car selon mon expérience, dans les commandes GNU/Linux, l'ordre des options n'a généralement pas d'importance.
  2. Différentes versions de tar attendent ces options dans un ordre différent: par exemple, la réponse de @ Andrew indique que, dans GNU tar v 1.26 et 1.28 l'exclude vient en dernier, alors que dans mon cas, avec GNU tar 1.29, c'est l'inverse.
  3. LA TRAILING SLASHES MATTER : au moins dans GNU tar 1.29, cela ne devrait pas être tout .

Dans mon cas, pour GNU tar 1.29 sur l’extension Debian, la commande qui a fonctionné était

tar --exclude="/home/user/.config/chromium" --exclude="/home/user/.cache" -cf file.tar  /dir1/ /home/ /dir3/

Les citations importaient peu, cela fonctionnait avec ou sans elles.

J'espère que cela sera utile à quelqu'un.

2
user2553863
tar -cvzf destination_folder source_folder -X /home/folder/excludes.txt

-X indique un fichier contenant une liste de noms de fichiers devant être exclus de la sauvegarde. Par exemple, vous pouvez spécifier * ~ dans ce fichier pour ne pas inclure les noms de fichiers se terminant par ~ dans la sauvegarde.

1
Ashwini Gupta

Votre meilleur pari est d'utiliser find avec tar, via xargs (pour gérer le grand nombre d'arguments). Par exemple:

find / -print0 | xargs -0 tar cjf tarfile.tar.bz2
1
Joe

Vérifiez-le

tar cvpzf Zip_folder.tgz . --exclude=./public --exclude=./tmp --exclude=./log --exclude=fileName
0
RohitPorwal

Je n’ai pas eu la chance d’obtenir tar pour exclure un sous-répertoire de 5 gigaoctets de quelques niveaux. En fin de compte, je viens d'utiliser la commande unix Zip. Cela a fonctionné beaucoup plus facilement pour moi.

Donc, pour cet exemple particulier du post original
(tar --exclude = './dossier' --exclude = './upload/folder2' -zcvf /backup/nom_fichier.tgz.)

L'équivalent serait:

Zip -r /backup/filename.Zip. -x upload/folder/**\* upload/folder2/**\*

(NOTE: Voici le message que j'ai utilisé à l'origine qui m'a aidé https://superuser.com/questions/312301/unix-Zip-directory-but-excluded-specific-subdirectories-and-everything-within-t) )

0
user2792605

Réponse redondante possible mais depuis que je l’ai trouvée utile, la voici:

Alors qu’une racine FreeBSD (c’est-à-dire en utilisant csh), je voulais copier tout mon système de fichiers racine dans/mnt mais sans/usr et (évidemment)/mnt. C'est ce qui a fonctionné (je suis à /):

tar --exclude ./usr --exclude ./mnt --create --file - . (cd /mnt && tar xvd -)

Tout ce que je veux dire, c’est qu’il était nécessaire (en mettant le ./) de de spécifier pour ne pas inclure les répertoires exclus du plus grand répertoire en cours de copie.

Mes € 0.02

0
George