Trouvez des fichiers plus récents qu'un jour et copiez

12

Je travaille sur un script qui copiera SEULEMENT les fichiers qui ont été créés au cours de la dernière journée de congé dans un autre dossier. Le problème que je rencontre est le script que j'ai copié tous les fichiers dans le répertoire source au lieu des fichiers de moins d'un jour.

Voici ce que j'ai:

find . -mtime -1 -exec cp --preserve --parents -a "{}" /somefolder \;

Le code ci-dessus copie tous les fichiers du répertoire source. Si je supprime tous les arguments pour «cp», cela fonctionne:

find . -mtime -1 -exec cp "{}" /somefolder \;

Le code ci-dessus copie uniquement les fichiers les plus récents comme je le souhaite, mais je dois conserver les attributs à l'aide des arguments cp.

J'ai également essayé des variables et pour les boucles, peut-être que l'option -exec était le problème:

files="$(find -mtime -1)"
for file in "$files"
do
cp --parents --preserve -a file /somefolder

Cependant, ce qui précède pour la boucle entraîne le même problème, tous les fichiers sont copiés. Si je fais écho aux fichiers $, seuls les fichiers dont j'ai besoin sont affichés.

Comment puis-je faire en sorte que cela fonctionne?

mac1234
la source
1
Ok, je pense que je l'ai en utilisant:find /sourcefolder -type f -mtime -1 -exec cp -a "{}" /somefolder \;
mac1234
Rsync ne serait-il pas le meilleur outil pour cette tâche au lieu de cp? rsync -une destination source
Darryl

Réponses:

9

Certaines implémentations cpont une -toption, vous pouvez donc mettre le répertoire cible avant les fichiers:

find . -mtime -1 -exec cp -a --parents -t /somefolder "{}" \+

Notez que cela -aimplique --preservedonc j'ai supprimé ce dernier.

glenn jackman
la source
3

Vous pouvez utiliser paxpour cela comme:

pax -wrT "11$(date +%H%M)," . /destination/folder

La ligne de commande bit par bit:

  • -wr- quand paxest remis à la fois les options de -write et d' -read qu'il copie. Peut-être aussi utile ici. (mais non inclus dans la commande ci-dessus)

    • -lencre - qui crée des liens physiques si possible plutôt que de copier les données du fichier.

    • -Xpour restreindre paxau même périphérique source et / ou système de fichiers.

    • -s/src regex/replace/ - qui modifie les noms de fichiers in-stream

    • -verbose - pour créer des rapports sur les fichiers provenant / ciblés.

  • -T- l' -Toption ime de fichiers pour l'archive cible (ou simplement de copier lorsqu'il est utilisé avec -wr) en fonction de leur /modification ou inode /changer (ou les deux) fois. Il s'agit par défaut de l'heure du mod. De...

homme pax

  • ... Les comparaisons de temps utilisant les deux temps de fichier sont utiles lorsque pax est utilisé pour créer une archive incrémentielle basée sur le temps (seuls les fichiers qui ont été modifiés pendant une plage de temps spécifiée seront archivés).

  • Une plage de temps est composée de six champs différents et chaque champ doit contenir deux chiffres. Le format est:

    [[[[[cc]yy]mm]dd]HH]MM[.SS]

  • ccsont les deux premiers chiffres de l'année (le siècle), yyles deux derniers chiffres de l'année, le premier mmest le mois (de 01 à 12), ddle jour du mois (de 01 à 31), HHest le heure du jour (de 00 à 23), MMest la minute (de 00 à 59), et SSest les secondes (de 00 à 59). Le champ minute MMest obligatoire, tandis que les autres champs sont facultatifs et doivent être ajoutés dans l'ordre suivant:

    HH, dd, mm, yy, cc

  • Le SSchamp peut être ajouté indépendamment des autres champs. Les plages horaires sont relatives à l'heure actuelle, donc ...

    -T 1234/cm

  • ... sélectionnerait tous les fichiers avec une heure de modification ou de changement d'inode de 12h34 aujourd'hui ou plus tard.

  • Plusieurs -Tplages de temps peuvent être fournies et la vérification des arrêts avec le premier match.

... donc 11là-haut dans mon exemple de commande est relatif à aujourd'hui - c'est un de moins que la date d'aujourd'hui - qui est le douzième - et le reste est juste un "$(date)"format standard suivi d'une virgule.

... sauf - et la dernière chose à mentionner - j'utilise un chemin absolu pour le répertoire cible - et vous devriez le faire si vous le faites. Les documents font tous référence à un comportement non spécifié pour les chemins cibles relatifs - et la première fois que j'ai essayé d'utiliser, paxje jurais sous mon souffle pendant une heure en confusion avec tous les résultats étranges jusqu'à ce que j'utilise un chemin absolu.

mikeserv
la source
2

Remercie tout le monde pour l'aide, l'a fait fonctionner en utilisant une combinaison de vos suggestions:

est allé avec le code ci-dessous et cela fonctionne parfaitement.

find /sourcefolder -type f -mtime -1 -exec cp -a "{}" /somefolder \;

Merci encore!

mac1234
la source
2

Je faisais exactement la même fonctionnalité mais j'avais besoin de préserver la structure des dossiers. Par conséquent, ce que j'ai fait est un peu différent.

cd sourcedir
find . -type f -mtime -$days -print0 | tar -czvf ${tarpath}/testtar.tar.gz --null -T -

où $ jours est le nombre de jours $ tarpath est un chemin temporaire pour stocker ces fichiers. et quand je voulais restaurer.

cd $destdir
tar -xvzf ${tarpath}/testtar.tar.gz

Cela a fait l'affaire pour moi.

Remarque: si vous souhaitez exclure un dossier lors de la sauvegarde, vous pouvez utiliser la commande suivante

find . -type f -mtime -$days ! -path '*/FolderToavoidSearch/*' -print0 | tar -czvf ${tarpath}/testtar.tar.gz --null -T -

Avantage: 1. J'ai toujours eu une copie de ce que j'ai restauré la dernière fois au format compressé.

  1. J'ai aussi une pause entre les restaurations où je peux aller voir quels sont ces fichiers et si tout va bien, alors continuez avec le script.

  2. Il préserve la structure des dossiers, donc il a juste écrasé les fichiers modifiés du répertoire source dans le répertoire de destination

Remarque: D'un autre côté, si l'exigence n'est pas limitée à la journée, j'utiliserais rsync

rsync -avz --exclude 'FolderToavoidSearch' --backup --backup-dir="/backup/dir/test/backup_$(date +\%Y-\%m-\%d)" /source/dir/ /dest/dir/

plus pour rsyc avec date ici

Amol Patil
la source
1

On peut également sélectionner la date et l'heure exactes autres que de revenir à un certain nombre de jours

(Cela ne fonctionne bien que si vos noms de fichiers ne contiennent ni espace, ni tabulation, ni caractère générique)

cp `find . -type f -newermt '17 dec 2016 20:10:00'` FOLDER

Ci-dessus copie tous les fichiers du répertoire créés après le 17 décembre 2016 20:10:00 dans le DOSSIER (1 jour avant aujourd'hui :)

Soyez prudent avec le symbole de la commande find, ce n'est PAS celui-ci: «c'est ceci, un backtick:« la sélection de la date est avec ceci: »

Pour les fichiers contenant des espaces, des tabulations, des sauts de ligne ou des caractères génériques dans leurs noms, vous pouvez utiliser l'une des solutions de Stéphane Chazelas, la première pour GNU, la seconde pour GNU ou certains BSD:

find . -type f -newermt '17 dec 2016 20:10:00' -exec cp -t FOLDER {} + 
find . -type f -newermt '17 dec 2016 20:10:00' -exec sh -c 'cp "$@" FOLDER' sh {} +
FatihSarigol
la source
1
Vous voudrez peut-être lire Pourquoi le bouclage sur la sortie de find est-il une mauvaise pratique?
Stéphane Chazelas
Merci Stéphane, c'est peut-être pourquoi je n'ai trouvé cela dans aucun article, bien que pour mon cas, cela a fonctionné comme un charme. lorsque vous faites cela, trouvez seulement. -type f -newermt '17 déc 2016 20:10:00 '
FatihSarigol
... il imprime les fichiers créés après cette heure, je ne sais pas quel genre de problème cela peut causer. puis j'utilise simplement des astuces pour sélectionner ces fichiers à copier. cheers
FatihSarigol
Je crois que le message que vous avez partagé concerne le "bouclage", mon code est-il en boucle sur le résultat de find? ou s'agit-il simplement de sélectionner le résultat de la recherche à utiliser par copie? (Désolé pour 3 commentaires, je ne suis apparemment pas encore autorisé à modifier mes commentaires
FatihSarigol
1
Utilisez find . -type f -newermt '17 dec 2016 20:10:00' -exec cp -t FOLDER {} +(GNU) ou find . -type f -newermt '17 dec 2016 20:10:00' -exec sh -c 'cp "$@" FOLDER' sh {} +(GNU ou certains BSD (le facteur limitant par rapport à la portabilité est le -newermtprédicat ici)).
Stéphane Chazelas