Двойной вывод в файл журнала Log4perl

Я работаю над новой функцией в существующей кодовой базе Perl, которая позволит нам регистрировать команды, отправляемые в базу данных. Я основываю решение на Log4perl, что избавляет меня от необходимости заново изобретать несколько колес.

К сожалению, я столкнулся с проблемой: каждое сообщение отправляется в файл журнала дважды. Я бы хотел, чтобы это прекратилось.

Мое исследование (Google) показало, что отправка одного и того же сообщения в два разных файла журнала является достаточно распространенной проблемой, но это не то, что я вижу. Каждое сообщение появляется дважды в одном файле журнала.

Есть ли у кого-нибудь какие-либо советы о том, где я должен начать искать способы исправить это поведение?


Редактировать: Файл конфигурации выглядит следующим образом:

my $log_packages = undef;

sub _get_logging_modifications {
    # Hash that is keyed by a package name
    # and the value is the level at which
    # to log that package
    return %{$log_packages} if defined $log_packages;
    $log_packages = {};

    my $log_info = $ENV{PROJECT_LOG_INFO} || '';

    for my $log_specification (split(/,/, $log_info)) {
        # Skip to the next log specification unless we have
        # a well formed log spec. i.e., Package::Name/LOGLEVEL
        next unless $log_specification =~ m!([^/]+)/([A-Z]+)!i;

        my $package   = $1;
        my $log_level = $2;

        $log_packages->{$package} = $log_level;
    }

    return %{$log_packages};
}

BEGIN {
    my $layout = Log::Log4perl::Layout::PatternLayout->new(
        '[%d] +%X{user_name}+ ||%X{request_uri}||%n  ' .
        '%C:%L - %P - %p - %n  ' .
        '%m%n'
    );

    my $web_data_path = $ENV{PROJECT_DATA_DIR}
        || File::Temp::tempdir( CLEANUP => 1 );

    my $logfile = "${web_data_path}/app.log";
    my $log = Log::Log4perl->get_logger('');

    my $app = Log::Log4perl::Appender->new(
        "Log::Dispatch::File",
        name     => 'APP',
        filename => $logfile,
    );

    $app->layout($layout);
    $log->add_appender($app);
    $log->level($WARN);

    my %levels = (
        FATAL => $FATAL,
        ERROR => $ERROR,
        WARN  => $WARN,
        INFO  => $INFO,
        DEBUG => $DEBUG,
    );

    my %mods = _get_logging_modifications();

    for my $cat (keys %mods) {
        my $level = uc($mods{$cat});
        next unless exists($levels{$level});
        my $other_log = Log::Log4perl->get_logger($cat);
        $other_log->level($levels{$level});
    }

    # NEW BLAIRHIPPO CODE STARTS HERE
    my $dbi_log = Log::Log4perl->get_logger('Project::NewLoggerThing');
    my $dbi_layout = Log::Log4perl::Layout::PatternLayout->new('%m%n');
    my $dbi_logfile = "/opt/home/blairhippo/test.log"; # FIXME: Make this configurable
    my $dbi_app = Log::Log4perl::Appender->new(
        "Log::Dispatch::File",
        name     => 'APP',
        filename => $dbi_logfile,
    );

    $dbi_app->layout($dbi_layout);
    $dbi_log->add_appender($dbi_app);
    $dbi_log->level($DEBUG); # FIXME:  Make this configurable   
}

1;

Я бы хотел, чтобы это был красивый файл .conf, но я работаю с существующим кодом.


person BlairHippo    schedule 14.03.2011    source источник
comment
Можете ли вы опубликовать код инициализации log4perl или конфигурацию, чтобы помочь с отладкой? Это не проблема, которую я видел с Log4perl.   -  person justkt    schedule 14.03.2011
comment
Создайте компактный тестовый пример, который воспроизводит проблему, и опубликуйте его здесь.   -  person a'r    schedule 14.03.2011
comment
Характер существующего кода делает компактный тестовый пример значительно более сложным, чем мне хотелось бы. Я посмотрю, что я могу с этим сделать, вместе с разрешением опубликовать информацию о конфигурации. (К сожалению, он помечен как служебный и конфиденциальный.)   -  person BlairHippo    schedule 14.03.2011
comment
Вы можете обнаружить, что преобразование вашего кода Log4perl выше в простой файл .conf решает проблему. Если вы не можете понять это, я бы сделал это, так как это нужно сделать в любом случае.   -  person Ether    schedule 14.03.2011
comment
@Ether: Согласен, что .conf был бы гораздо предпочтительнее, но я новичок в проекте, поэтому я довольно консервативен, когда рекомендую изменения в укоренившихся битах, которые на самом деле не ломаются.   -  person BlairHippo    schedule 14.03.2011


Ответы (2)


В Log::Log4perl FAQ есть вопрос: Я продолжаю получать повторяющиеся сообщения журнала! Что не так?.

person bvr    schedule 14.03.2011
comment
Это привело меня к решению, которое заключается в том, чтобы вставить $dbi_log->additivity(0); перед вызовом add_appender. Спасибо! - person BlairHippo; 14.03.2011

У меня были похожие проблемы с библиотеками log4*; это указывает на использование двух разных экземпляров ведения журнала, где внутренне оба связаны с синглтоном. Насколько я помню, вам нужно будет выбрать две отдельные строки ведения журнала.

person Paul Nathan    schedule 14.03.2011