Forum Programmation.shell merger des fichiers de logs

Posté par  .
Étiquettes : aucune
0
6
oct.
2008
Hello,
J'ai plusieurs fichiers de logs (100 x 100Mo), avec une premier colonne contenant le temps en unixtime (avec des centièmes de secondes):

1223305330.56 AAAA
1223305331.45 BBBB
...

J'ai plusieurs fichiers comme cela sur la même période de log. J'aimerais tous mettre dans un seul gros fichier (pour en extraire un joli graphe ensuite)

Problème 1): sort ne supporte pas les nombre a virgule
Problème 2): a mon avis sort n'aime pas trier un fichier de 10Go

De plus, les lignes sont triées par fichier.

Comment feriez vous le merge de manière efficace ? Je pense écrire un programme qui va ouvrir tous les fichiers, lire progressivement chacun et faire un output trie, mais si quelqu'un a une meilleure idée...

Merci a tous.
  • # Alors, à vue de nez

    Posté par  . Évalué à 2.

    Il existe l'option -m (merge) pour fusionner des fichiers déjà triés. Si tu veux limiter l'impact en mémoire tout en suivant ta progression, tu peux donc commencer par trier tous tes logs un par un, puis fusionner chaque log trié avec un fichier global de résultat.

    Bilan, 200 opérations dont chacune sera plus lente que la précédente en ce qui concerne les 100 dernières (la fusion avec le fichier final), mais maîtrise complète et possibilité de trier/fusionner plus de 2 fichiers à la fois si tu as de la mémoire, pour accélérer les choses.

    Pour le point décimal, je ne connais pas de solution miracle mais puisque tu vas automatiser le tout avec un script et comme toutes tes lignes commencent par un timestamp dont le format est connu et constant, tu peux peut-être le faire disparaître avec une expression régulière dans tous tes fichiers, et le remettre à sa place de la même façon dans le fichier final (mais il faut des gigas disponibles).
    • [^] # Re: Alors, à vue de nez

      Posté par  . Évalué à 3.

      (On ne peut pas éditer ses commentaires, dommage).

      Je viens de dire une connerie (le -m servant justement à ça). Une fois tous tes fichiers triés un par un, tu fais un gros sort -m *. Ça fait cent fichiers ouverts mais la progression sera linéaire et ne consomera pas plus de mémoire que nécessaire.
      • [^] # Re: Alors, à vue de nez

        Posté par  . Évalué à 1.

        Bien vu !

        Comme quoi on passe a cote de certaines options !

        La solution complete au probleme:

        sort -g -m *

        Encore merci :)
        • [^] # Re: Alors, à vue de nez

          Posté par  . Évalué à 2.

          Vérifie bien -g, toutefois. J'ai fait un test avant de poster et ça ne marchait pas (il restait au tri alphabétique. C'était p'têt dû aux locales).

          Bon courage.
          • [^] # Re: Alors, à vue de nez

            Posté par  . Évalué à 1.

            Ici -g et -n marchent sans prob...
            • [^] # Re: Alors, à vue de nez

              Posté par  . Évalué à 3.

              Comme dit plus bas, c'est parce que tes timestamps ont un nombre de chiffres fixe. Du coup le tri numérique n'a aucun intérêt. À mon avis, tu peux purement et simplement virer ces options, cela fera encore gagner du temps à tes tris.
    • [^] # Re: Alors, à vue de nez

      Posté par  . Évalué à 1.

      sort -m a un léger défaut, il passe quand même par un fichier temporaire. 10 Go, ça commence à faire.

      Si tu n'as pas l'espace disque nécessaire dans /tmp, (ou ailleurs), c'est cuit.

      J'ai été obligé d'écrire un bout de perl pour faire un merge de N fichiers sans passer par un fichier temporaire.
  • # sort et les virgules

    Posté par  . Évalué à 3.

    Je ne comprends pas: si toutes tes lignes sont préfixées avec un timestamp qui contient toujours le même nombre de chiffres, ya même pas besoin de faire un tri numérique, un simple tri alphabétique suffit ... C'est quoi ton problème avec les virgules ?

    Et sinon, tu peux me filer un exemple où `sort -n' se plante ? Parce que là j'ai du mal à comprendre.

    Pour ce qui est de la taille: à mon avis t'as intérêt à dabord découper tes fichiers par heure (ou moins), puis merger les fichiers des crénaux horaires correspondants, et à la fin les concaténer. Va falloir faire un peu de shell, quoi ;)
    • [^] # Re: sort et les virgules

      Posté par  . Évalué à 1.

      Effectivement, tu as raison. C'est bizarre dans mes souvenirs on avait ete embete par sort avec des chiffres a vrigule (peut etre de longueur differents), mais je n'arrive plus a reproduire...

      Pour ta solution de spliter, fusionner et reconcatener les fichiers: oui, mais a ce moment la (c'est a dire travailler un petit moment), autant faire une petite appli qui fais le sort de maniere parallele (et je pourrai la reutiliser) (et pas en shell :-).

      Bon, tout va bien, sort -m fais exactement ce qu'il faut :)

      Merci.
      • [^] # Re: sort et les virgules

        Posté par  . Évalué à 1.

        Pourquoi pas en shell ? En utilisant tcl/perl/python; c'est écrit en 10mn un truc comme ça. C'est juste un peu de preprocessing avant d'appeler sort! Et tu sais que en shell tu peux faire du parralélisme ? Perso, j'utiliserais (Gnu)make, qui gère les dépendances des tâches et sais très bien paralléliser (option -j).

        sort -m te fais très bien le truc, maisle split c'est surtout pour répondre à ton point (2) et profiter de tous les coeurs/processeurs de la machine, si tant est qu'il y en ait plusieurs. Au moins je suis sûr que `cat' gère très bien les fichiers de 10Go !

Suivre le flux des commentaires

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