The OpenNET Project / Index page

[ новости /+++ | форум | теги | ]




Версия для распечатки Пред. тема | След. тема
Новые ответы [ Отслеживать ]
Разбор файла maillog perl-скриптом., !*! Dorlas, 10-Апр-06, 13:08  [смотреть все]
Добрый день.

Не так давно начал изучать Perl (2 недели), до этого кроме #!/bin/sh ни на чем не программировал.

Поставил себе такую задачку - написать скрипт на Perl-е, который из журнала maillog (почтовый сервер Postfix 2.2.8) выбирает следующие данные: Месяц, число, время, ip-адрес отправителя, поля from и to и размер письма.

Все хорошо, но на некоторых письмах происходит затык - некоторые строки не разбиваются функцией split на элементы - бьюсь второй день, но причину не вижу.

Вот сама программа:

#!/usr/local/bin/perl

# Открыли файл, загнали все в массив @a
open(MAIL, "/home/admin/perl/maillog.0");
@a=<MAIL>;
close(MAIL);

$j=0;


for ($i=0;$i<$#a+1;$i++) {
        $#b=0;
        @b=split(/\s+/,$a[$i]); # Строку дробим на элементы
        if (($b[6] =~ m/client=(.+)/) and ($b[6] ne 'client=localhost.domen.ru[127.0.0.1]'))
                {
                $c1[$j]=$b[5]; # получаем массив @c1, содержащий Message-ID писем, поступивших на обработку
                $j++;
                }
}

$j=0;

for ($i=0;$i<$#a+1;$i++) {
        $#b=0;
        @b=split(/\s+/,$a[$i]);
        if ($b[6] eq 'removed')
                {
                $c2[$j]=$b[5]; # получили массив @c2, содержащий Message-ID писем, успешно обработанных и удаленных из очереди задач
                $j++;
                }
}

$k=0;
for ($i=0;$i<$#c1+1;$i++)
        { for ($j=0;$j<$#c2+1;$j++) {
                if ($c1[$i] eq $c2[$j]) { $c[$k]=$c1[$i]; $k++; }}}
# Получили массив @c, содержащий пересечение массивов @c1 и @c2

$j=0;
for ($i=0;$i<$#a+1;$i++) {
        $#b=0;
        @b=split(/\s+/,$a[$i]);
        if (($b[6] =~ m/client=(.+)/) and ($b[6] ne 'client=localhost.domen.ru[127.0.0.1]') and ($b[5] eq $c[$j]))
                {
                $d[$j]=$b[0]."\t".$b[1]."\t".$b[2]."\t";
                $b[6] =~ s/client=(.+)\[(.+)\]/$2/g;
                $d[$j].=$b[6].="\t\t";
                $j++;
                }
}

# Формируем массив @d, который будем заполнять нужными данными.
# До этого момента все работает нормально, а вот с полями from, to и size - беда - на некоторых строках не работает функция split.

$j=0;
for ($i=0;$i<$#a+1;$i++) {
        $#b=0;
        @b=split(/\s+/,$a[$i]);
        if (($b[5] eq $c[$j]) and ($b[7] =~ m/size=(.+?),/))
                {
                $b[7] =~ s/size=(.+?),/$1/g;
                $d[$j] .= $b[7];
                $d[$j] .= "\t";
                $j++;
                }
}

Привожу кусок maillog-а, именно в этом месте скрипт затыкается:

Apr  6 02:10:33 newgateway postfix/smtpd[63214]: 61F8561C0E: client=unknown[68.56.22.107]
Apr  6 02:10:35 newgateway postfix/cleanup[63215]: 61F8561C0E: message-id=<20060405201033.61F8561C0E@newgateway.domen.ru>
Apr  6 02:10:35 newgateway postfix/qmgr[70203]: 61F8561C0E: from=<bj21@com2com.ru>, size=1335, nrcpt=1 (queue active)
Apr  6 02:10:36 newgateway postfix/lmtp[63170]: 61F8561C0E: to=<egor@domen.ru>, relay=127.0.0.1[127.0.0.1], delay=4, status=sent (250 2.0.0 Ok (2.0.0 <igor@domen.ru> OK ))
Apr  6 02:10:36 newgateway postfix/qmgr[70203]: 61F8561C0E: removed

  • Разбор файла maillog perl-скриптом., !*! Dorlas, 14:43 , 10-Апр-06 (1)
    В чем была проблема понял смутно (то есть не понял), но задачку решил полным перебором:

    #!/usr/local/bin/perl

    open(MAIL, "/home/admin/perl/maillog.0");
    @a=<MAIL>;
    close(MAIL);

    $j=0;

    for ($i=0;$i<$#a+1;$i++) {
            $#b=0;
            @b=split(/\s+/,$a[$i]);
            if (($b[6] =~ m/client=(.+)/) and ($b[6] ne 'client=localhost.domen.ru[127.0.0.1]'))
                    {
                    $c1[$j]=$b[5];
                    $j++;
                    }
    }

    $j=0;

    for ($i=0;$i<$#a+1;$i++) {
            $#b=0;
            @b=split(/\s+/,$a[$i]);
            if ($b[6] eq 'removed')
                    {
                    $c2[$j]=$b[5];
                    $j++;
                    }
    }
    $k=0;
    for ($i=0;$i<$#c1+1;$i++)
            { for ($j=0;$j<$#c2+1;$j++) {
                    if ($c1[$i] eq $c2[$j]) { $c[$k]=$c1[$i]; $k++; }}}

    for ($j=0;$j<$#c+1;$j++)
            { for ($i=0;$i<$#a+1;$i++)
            {
                    $#b=0;
                    @b=split(/\s+/,$a[$i]);
                    if ($c[$j] eq $b[5])
                    {
                            if (($b[6] =~ m/client=(.+)/) and ($b[6] ne 'client=localhost.domen.ru[127.0.0.1]'))
                            {
                            $d[$j]=$b[0]." ".$b[1]." ".$b[2]." ";
                            $b[6] =~ s/client=(.+)\[(.+)\]/$2/g;
                            $d[$j].=$b[6].=" ";
                            }
                            if ($b[6] =~ m/from=<(.+)>,/)
                            {
                            $b[6] =~ s/from=<(.+)>,/$1/g;
                            $d[$j] .= $b[6];
                            $d[$j] .= " ";
                            }
                            if ($b[7] =~ m/size=(.+),/)
                            {
                            $b[7] =~ s/size=(.+),/$1/g;
                            $d[$j] .= $b[7];
                            $d[$j] .= " ";
                            }
                            if ($b[6] =~ m/to=<(.+)>,/)
                            {
                            $b[6] =~ s/to=<(.+)>,/$1/g;
                            $d[$j] .= $b[6];
                    }
            }
            print $d[$j], "\n";
            }

    Но этот скрипт работает слишком медленно.
    Укажите пожалуйста пути к увеличению скорости работы (кроме замены железа, конечно) :)

    • Разбор файла maillog perl-скриптом., !*! chip, 19:04 , 10-Апр-06 (2)

      >Но этот скрипт работает слишком медленно.
      >Укажите пожалуйста пути к увеличению скорости работы (кроме замены железа, конечно) :)

      Открыть, наконец, для себя проект mailgraph.


      • Разбор файла maillog perl-скриптом., !*! Dorlas, 07:43 , 11-Апр-06 (3)
        Спасибо за совет, но у меня другая цель.

        Готовое решение мне не нужно.

        • Разбор файла maillog perl-скриптом., !*! chip, 15:57 , 12-Апр-06 (4)
          >Спасибо за совет, но у меня другая цель.
          >
          >Готовое решение мне не нужно.

          Взять готовое, разобраться в нем и создать своё. Проявите ф0нтазию. Или Вы предлагаете, чтобы Вам разжевали на форуме проект mailgraph и Вы потом создали своё решение?

          • Разбор файла maillog perl-скриптом., !*! Dorlas, 13:22 , 13-Апр-06 (5)
            Вы меня не поняли - я изучаю Perl, взялся написать программу - как задачку. Написал. Задачу решил. Теперь интересуюсь мнением профессиональных программистов на Perl - с помощью каких методов можно улучшить программу.

            И проект mailgraph тут совершенно не причем!!!

            • Разбор файла maillog perl-скриптом., !*! madskull, 14:29 , 13-Апр-06 (6)
              ну, в общем, я бы сделал примерно так. Занося в хэш отдельные поля по мере поступления инфы, а потом вывести все разом.
              Правда, возможны всякие варнинги и тому подобное - это просто руководство к действию :)
              --------- тута начало

              open(MAIL, "mail.log") or die "$!";

              %result = ();

              while ( <MAIL> ) {
                  ($time,$id) = /^(\w+\s+\d+\s+[0-9:]+)\s+.+?:\s+(\w{10}):/ or next; # не сработало, значит, что-то вроде warning
                  $result{$id}{time} = $time;
                  # далее заносим значения полей, которые есть в строке, в хэш
                  /client=\[(.+?)\]/ and $result{$id}{ip} = $1;
                  /from=<(.+?)>/ and $result{$id}{from} = $1;
                  /to=<(.+?)>/ and $result{$id}{to} = $1;
                  /size=(\d+?),/ and $result{$id}{size} = $1;
              }

              close(MAIL);

              # теперь можно вывести то, что мы насобирали. Правда, без всякой сортировки
              print "$_->{time} $_->{ip} $_->{from} $_->{to} $_->{size}\n" foreach (%result);

              --------- тута конец

            • Разбор файла maillog perl-скриптом., !*! chip, 14:37 , 13-Апр-06 (7)
              >Вы меня не поняли - я изучаю Perl, взялся написать программу -
              >как задачку. Написал. Задачу решил.

              А эту строчку Вы в features к программе запишите?!:

              "Привожу кусок maillog-а, именно в этом месте скрипт затыкается"

              >Теперь интересуюсь мнением профессиональных программистов на
              >Perl - с помощью каких методов можно улучшить программу.

              www.google.com /log analize perl




Партнёры:
PostgresPro
Inferno Solutions
Hosting by Hoster.ru
Хостинг:

Закладки на сайте
Проследить за страницей
Created 1996-2025 by Maxim Chirkov
Добавить, Поддержать, Вебмастеру