将perl脚本的所有输出复制到文件中

时间:2009-10-27 16:05:18

标签: perl

我想将我的Perl脚本的stdout和stderr复制到一个文件中,同时也将它保留在屏幕上,并且最好在脚本本身内部使用一些技巧。即我想要类似于

的东西

./ test.pl 2>& 1 | tee foo.bar

但隐藏在perl脚本实现中。目前我刚刚编写了一个子程序,可以在屏幕上和文件句柄上打印所有消息,但缺点是如果脚本死掉,则消息将不会出现在日志中。 有办法吗?

5 个答案:

答案 0 :(得分:7)

请参阅Perl食谱中的“13.15.9。绑定示例:多个接收文件句柄”部分。

最重要的是tie *TEE, "Tie::Tee", @handles;

注意:Tie :: Tee包是您需要自己创建的,代码在本书的相同部分。

注意:然后您可以执行select(TEE),并且会在每个常规print语句中使用它,因此您无需执行print TEE xxx

注意:要让任何STDERRy输出(包括die)转到同一个文件句柄,请将STDERR更改为TEE,如下所示:

use Tie::Tee; 
use Symbol; 
@handles = (*STDOUT); 
push(@handles, $handle = gensym( )); 
open($handle, ">/tmp/teetest.xxx"); 
tie *TEE, "Tie::Tee", @handles; 
select(TEE); 
*STDERR = *TEE; 
print "raw print\n"; 
die "XXXX\n";

输出将是:

raw print
XXXX

文件内容为:

raw print
XXXX

答案 1 :(得分:4)

看看Log::Dispatch
将消息分发到一个或多个输出。

   use Log::Dispatch;

   # Simple API
   #
   my $log =
       Log::Dispatch->new
           ( outputs =>
                 [ [ 'File',   min_level => 'debug', filename => 'logfile' ],
                   [ 'Screen', min_level => 'warning' ],
                 ],
           );

   $log->info('Blah, blah');

   # More verbose API
   #
   my $log = Log::Dispatch->new();
   $log->add( Log::Dispatch::File->new
                         ( name      => 'file1',
                           min_level => 'debug',
                           filename  => 'logfile'
                         )
                   );
   $log->add( Log::Dispatch::Screen->new
                         ( name      => 'screen',
                           min_level => 'warning',
                         )
                   );

   $log->log( level => 'info', message => 'Blah, blah' );

   my $sub = sub { my %p = @_; return reverse $p{message}; };
   my $reversing_dispatcher = Log::Dispatch->new( callbacks => $sub );

它也有一些辅助/实用程序模块,你也应该看一下。

  

Log :: Dispatch :: DBI - 将输出记录到数据库表。

     

Log :: Dispatch :: FileRotate - 定期轮换日志文件作为其一部分   的使用。

     

Log :: Dispatch :: File :: Stamped - Stamps log   包含日期和时间信息的文件。

     

Log :: Dispatch :: Jabber - Logs   通过Jabber的消息。

     

Log :: Dispatch :: Tk - Logs   消息到Tk窗口。

     

Log :: Dispatch :: Win32EventLog - 日志   消息到Windows事件日志。

     

Log :: Dispatch :: Config - 允许   通过文本记录的配置   文件类似(或者我被告知)如何   它是用log4j完成的。

答案 2 :(得分:1)

根据脚本的大小,我强烈建议使用Log :: Log4perl ...每次编写脚本时都会保存重新实现的日志记录。

如果您在简易模式下使用Log4perl,它只会增加大约10行代码并且非常有用。

Log4perl可以非常灵活地将输出重定向到您想要的任何地方,包括一次输出多个输出。

答案 3 :(得分:0)

This听起来就像你需要的那样,不幸的是它是一个bash脚本,你希望这一切都在你的perl代码中处理。

答案 4 :(得分:0)

Capture::Tiny有一个tee子。