哪个脚本初始化模块?

时间:2011-08-23 14:19:26

标签: perl logging perl-module log4perl

在Perl中,有没有办法告诉哪个.pl脚本初始化这个模块的实例?

具体来说,我想得到一个调用模块的脚本名称,该模块有一个Log4perl对象。这样,我就会知道我想在模块中写哪个.log文件。

我这样做错了吗?如果我在.pl脚本中定义$logger,模块中的任何$logger调用是否会写入与调用脚本相同的.log文件?

我还没有任何示例代码,但已在Log4perl上阅读。基本上,如果我将Appender设置为文件caller.log,这是我的调用脚本caller.pl的文件追加器,我希望在自定义导入模块中定义的任何日志记录也写入caller.log(隐含地,如果可能的话 - 显然我可以在初始化模块实例时传递日志名称的名称)。

这是否可以在不传递参数的情况下指定模块应该写入哪个File Appender? Log4perl只使用一个$logger实例吗?

另外,如果我出路了,请告诉我,如果有不同的方法我应该考虑。

谢谢

编辑:抱歉,我发布此消息后,我查看了相关链接,我猜我的搜索措辞不正确。看起来这是一个非常好的解决方案:Self logging Perl modules (without Moose)

如果有人有任何其他想法,请告诉我。

编辑2:最后经过测试,让它按照我想要的方式工作 - 比制作出来要容易得多!

这是我的设置,非常多:

Module.pm

package Module;

use Log::Log4perl qw(get_logger :levels);
use Data::Dumper;

my $logger = get_logger("Module");

sub new {
    my ($class, $name) = @_;

    my @caller = caller(0);
    $logger->debug("Creating new Module. Called by " . Dumper(\@caller));

    my $object = { 'name' => $name };

    return bless($object, $class);  
}

caller.pl

use Module;
use Log::Log4perl qw(get_logger :levels);
use Data::Dumper;

my $PATH = "$ENV{'APPS'}/$ENV{'OUTDIR'}";
my $SCRIPT = "caller";

my $logger = get_logger("Module");
$logger->level($DEBUG);

my $file_appender = Log::Log4perl::Appender->new("Log::Dispatch::File", 
                        filename=> "$PATH/$SCRIPT.log", 
                        mode => "append",);
$logger->add_appender($file_appender);

my $layout = Log::Log4perl::Layout::PatternLayout->new("%d %p> %F{1}:%L %M - %m%n");
$file_appender->layout($layout);

my $lib = Module->new('Chris');

$logger->info(Dumper($lib));

3 个答案:

答案 0 :(得分:2)

您可以继承Log4perl,覆盖其构造函数。在自定义构造函数中,使用caller()获取调用构造函数的文件名并将其放在$self中。

答案 1 :(得分:2)

您可以将子例程挂钩放入可以运行任意代码的@INC,如perldoc -f require中所述。例如:

# UseLogger.pm
package UseLogger;
sub import { unshift @INC, \&UseLogger::log_use }
sub log_use {
    my ($self, $filename) = @_;
    my @c = caller(0);
    print "Module $filename required in file $c[1] line $c[2]\n";
    return 0;
}
1;

$ perl -MUseLogger my_script.pl
Module feature.pm required in file my_script.pl line 2
Module Encode.pm required in file my_script.pl line 5
Module XSLoader.pm from /usr/lib/perl5/5.14.0/cygwin-thread-multi-64int/Encode.pm line 13
...

答案 2 :(得分:2)

$0包含脚本的路径。如果您想要文件名组件,可以使用File :: Basename的basename