Forum Linux.général alternative (plus rapide) à find pour rechercher par date de modification

Posté par  . Licence CC By‑SA.
Étiquettes : aucune
1
24
mai
2018

bonjour,
je dois supprimer tous les fichiers de plus de trois jours dans un répertoire qui contient à peut près 7 millions de fichiers j'ai lancé :

find -type f -mtime +2 -exec /bin/rm -f {} \;
mais en 8 heures il n'a supprimé que 150 000 fichiers.
j'ai regardé pour utiliser fd qui est sensé être plus rapide mais je n'ai pas vu d'options équivalente à -mtime

si quelqu'un a une idée… je suis preneur

  • # sans garantie

    Posté par  . Évalué à 8. Dernière modification le 24 mai 2018 à 12:39.

    je suppose que -exec lance un nouveau process pour chaque fichier. Il se trouve que find a une action -delete qui fait ce que tu veux faire avec les fichiers trouvés, et j'imagine qu'il ne lance pas un nouveau process par fichier pour faire cela.
    Ça vaut peut être le coup de faire une comparaison sur un échantillon réduit.

    EDIT: https://unix.stackexchange.com/questions/167823/find-exec-rm-vs-delete

    • [^] # Re: sans garantie

      Posté par  . Évalué à 2.

      merci je vais tester ça !

    • [^] # Re: sans garantie

      Posté par  . Évalué à 2.

      effectivement c'est plus de 3 fois plus rapide. d'après le lien que tu m'as donné j'aurais pu aussi remplacer \; par + pour avoir le même comportement mais je n'ai pas testé.

      • [^] # Re: sans garantie

        Posté par  . Évalué à 3.

        Si c'est bien la suppression qui prend du temps, tu peux également essayer d'utiliser xargs, avec son option -P qui permet d'exécuter plusieurs commande en parallèle, ou GNU Parallel qui fait également cela. Pour obtenir des performances optimales, il faudra jouer a la fois sur le nombre de fichiers supprime par commande (option -n de xargs) et le nombre d'extinction en parallèle.

        Si tu utilise xargs, c'est une bonne idée d'utiliser son option -0 (zéro) et d'utiliser l'option -print0 de find.

  • # Essaye ça

    Posté par  . Évalué à 2.

    L'idée est de tout paralléliser, la recherche et les rm.

    #!/bin/bash
    
    FIFO=fifo.$$
    mkfifo $FIFO
    
    find -type f -mtime +2 -print > $FIFO &
    
    for i in `cat $FIFO`; do
        rm -f "$i" &
    done
    
    rm $FIFO
    • [^] # Re: Essaye ça

      Posté par  . Évalué à 1. Dernière modification le 28 mai 2018 à 01:01.

      Attention comme le dit bertrand plus bas au dépassement de la taille maximale d'une ligne de commande.
      Bref, il vaut mieux utiliser une boucle cat | while read f; do ... $f; done que l'expansion for f in "`cat ...`" (et tant qu'à faire se passer du fifo: find ... | while read).

  • # find exec +

    Posté par  . Évalué à 2.

    Il me semble que find exec accepte "+" au lien de "{}", qui groupe plusieurs chemins au lieu de traiter un par un. As-tu essayé ?

    find -type f -mtime +2 -exec /bin/rm -f +

    • [^] # Re: find exec +

      Posté par  . Évalué à 1.

      attention, le + va générer la liste de tous les fichiers à supprimer et la passer en paramètre au processus rm.
      Dans le cas de figure cité, il est des plus probable que cela dépasse la limite de taille de la ligne de commande.

      • [^] # Re: find exec +

        Posté par  . Évalué à 1.

        Nope, comme l'indique le man, il se comporte comme xargs.
        Ceci dit, ta remarques est pertinente dans le cadre générale et en l'occurrence à l'astuce de lfb4.

Suivre le flux des commentaires

Note : les commentaires appartiennent à celles et ceux qui les ont postés. Nous n’en sommes pas responsables.