Perl::Critic "Don't use this method" -type rule



我们一直在使用Perl::Critic来执行我们的代码约定。最近,我们遇到了由于Temp::File::tempdir函数而导致/tmp目录被填满的问题。tempdir在Perl进程终止时进行清理,但由于我们的整个后端都是一个Perl进程,因此只有在服务器本身重新启动时才会发生这种情况(不经常发生)。我们希望鼓励开发人员将来使用newdir对象方法,一旦对象超出范围,它就会自行清理。

基本上,我们试图将Temp::File::tempdir标记为违反代码约定,但我似乎在CPAN上找不到任何类似的规则。我知道这在动态类型语言中很难在不引入误报的情况下强制执行,但我预计有人在过去使用另一个不推荐使用的函数时也遇到过类似的问题。我们也不希望捕捉到所有棘手的情况,只捕捉到Temp::File::tempdir最明显的用法。这个想法是为了在newdir可以完成任务时阻止意外使用tempdir,而不是抓住所有欺骗批评者的企图(开发人员总是可以只使用## no critic)。如果定义了use Temp::File(最好检查是否没有其他内容重新定义tempdir)并且使用了Temp::File::tempdir,那么在使用tempdir时抱怨可能就足够了。

已经有类似的东西了吗?还是我应该从头开始?感谢

Perl::Critic中目前没有任何东西可以提供您所需要的东西,但很可能添加一个策略来执行类似的操作。不幸的是,PPI并不全面,无法正确识别程序中的每个令牌在做什么,因此它需要比实际更多的编码。

该程序检查use File::Temp语句,该语句试图使用中的任何一个导入tempdir

use File::Temp 'tempdir';
use File::Temp q(tempdir);
use File::Temp "tempdir";
use File::Temp qq(tempdir);
use File::Temp qw/ tempdir /;

(具有用于qqqqw形式的任何分隔符)。它还检查看起来像函数调用并且等于File::Temp::tempdirPPI::Token::Word节点。

package Perl::Critic::Policy::Prohibit_tempdir;
use strict;
use warnings;
use Perl::Critic::Utils qw{ is_function_call :severities };
use Scalar::Util 'blessed';
use base 'Perl::Critic::Policy';
my $DESC = 'Temp::File::tempdir function';
my $EXPL = 'The tempdir function from Temp::File is deprecated. Use newdir method instead';
sub default_severity { $SEVERITY_HIGH };
sub applies_to{ qw/ PPI::Statement::Include PPI::Token::Word / }
sub violates {
my ($self, $elem) = @_;
if ($elem->isa('PPI::Statement::Include')) {
return unless $elem->type eq 'use';
my $module = $elem->module;
return unless $module and $module eq 'File::Temp';
for my $kid ($elem->children) {
next unless blessed($kid) =~ /^PPI::Token::Quote/;
if ($kid->can('string') and $kid->string eq 'tempdir'
or $kid->can('literal') and grep $_ eq 'tempdir', $kid->literal) {
return $self->violation($DESC, $EXPL, $elem);
}
}
}
else {
if (is_function_call($elem) and $elem eq 'File::Temp::tempdir') {
return $self->violation($DESC, $EXPL, $elem);
}
}
return;
}
1;

使用此代码

use strict;
use warnings;
use File::Temp 'tempdir';
use File::Temp "tempdir";
use File::Temp qw/ tempdir /;
my $dir = tempdir();
$dir = tempdir;
$dir = File::Temp::tempdir;
my $ft = File::Temp->new;
$dir = $ft->newdir;

perlcritic -4 test.pl生成此输出

Code not contained in explicit package at line 1, column 1.  Violates encapsulation.  (Severity: 4)
Temp::File::tempdir function at line 4, column 1.  The tempdir function from Temp::File is deprecated. Use newdir method instead.  (Severity: 4)
Temp::File::tempdir function at line 5, column 1.  The tempdir function from Temp::File is deprecated. Use newdir method instead.  (Severity: 4)
Temp::File::tempdir function at line 6, column 1.  The tempdir function from Temp::File is deprecated. Use newdir method instead.  (Severity: 4)
Temp::File::tempdir function at line 10, column 8.  The tempdir function from Temp::File is deprecated. Use newdir method instead.  (Severity: 4)
Module does not end with "1;" at line 13, column 1.  Must end with a recognizable true value.  (Severity: 4)

相关内容

  • 没有找到相关文章

最新更新