我怎么可以挂钩Perl的打印?
这是一个场景您有大量的遗留脚本,全部使用通用库。所述脚本使用’print’语句进行诊断输出。脚本不允许更改 – 它们范围广泛,有其批准,并且早已离开了富有成果的监督和控制的山谷。
现在已经到了新的需求:现在必须将日志记录添加到库中。这必须自动而透明地进行,没有标准库的用户需要更改其脚本。通用库方法可以简单地添加日志调用;这是很容易的部分。困难的部分在于,这些脚本的诊断输出始终使用’print’语句显示。必须存储此诊断输出,但同样重要的是进行处理。 作为这个处理的一个例子,库应该只记录包含单词“warning”,“error”,“notice”或“attention”的打印行。以下极其简单和有争议的示例代码(tm)将记录一些所述输出: sub CheckPrintOutput { my @output = @_; # args passed to print eventually find their way here. foreach my $value (@output) { Log->log($value) if $value =~ /warning|error|notice|attention/i; } } (我想避免这样的问题,应该实际记录什么,打印不应该用于诊断,“perl吸”,或者“这个例子有缺点xy和z”…这是大大简化为了简洁和清晰。) 基本的问题在于捕获和处理传递给打印的数据(或按照这些推理方式,任何perl内置的)。可能吗?有没有办法干净地做?有没有任何记录模块有钩可以让你这样做?还是应该像瘟疫那样避免这样的事情,我应该放弃永远捕捉和处理打印输出? 附加:这必须运行跨平台的Windows和* nix。运行脚本的过程必须保持不变,与脚本的输出一样。 附加补充:在codelogic答案的评论中提出了一个有趣的建议:
这可能有两个注意事项: 1)我需要一种将此功能导出到使用公共库的任何人的方法。它必须自动应用于STDOUT,也可能是STDERR。 2)the IO::Handle文件说你不能对它进行子类化,到目前为止我的尝试是无效的。有什么特别需要使子类化IO :: Handle工作吗?标准的’use base’IO :: Handle’然后覆盖新的/打印方法似乎什么都不做。 最终编辑:看起来像IO :: Handle是一个死胡同,但Tie :: Handle可能会这样做。感谢所有的建议;他们都很好我要试穿Tie :: Handle路线。如果造成问题,我会回来的! 附录:注意,在使用这一点后,我发现Tie :: Handle将会工作,如果你不做任何棘手的事情。如果您使用绑定的STDOUT或STDERR的IO :: Handle的任何功能,它基本上是使其工作可靠的难题 – 我找不到一种方法来获取IO :: Handle的自动冲洗方法来处理我的绑定处理。如果我在绑定手柄之前启用了自动冲洗,它将会工作。如果这适用于您,Tie :: Handle路线可能是可以接受的。 解决方法
有一些内置的可以覆盖(见
perlsub)。然而,print是其中一种不能以这种方式工作的内置函数。在
perlmonk’s thread年,详细介绍了印刷版的困难。
但是,你可以 >创建一个包 现在有几个人给了基本的框架,但它的工作原理就是这样的: package IO::Override; use base qw<Tie::Handle>; use Symbol qw<geniosym>; sub TIEHANDLE { return bless geniosym,__PACKAGE__ } sub PRINT { shift; # You can do pretty much anything you want here. # And it's printing to what was STDOUT at the start. # print $OLD_STDOUT join( '','NOTICE: ',@_ ); } tie *PRINTOUT,'IO::Override'; our $OLD_STDOUT = select( *PRINTOUT ); 您可以以相同的方式覆盖printf: sub PRINTF { shift; # You can do pretty much anything you want here. # And it's printing to what was STDOUT at the start. # my $format = shift; print $OLD_STDOUT join( '',sprintf( $format,@_ )); } 请参阅Tie::Handle您可以覆盖STDOUT的行为。 (编辑:李大同) 【声明】本站内容均来自网络,其相关言论仅代表作者个人观点,不代表本站立场。若无意侵犯到您的权利,请及时与联系站长删除相关内容! |