perl - 如何在使用 DBI 的 Perl 模块中获得 100% 的测试覆盖率?

标签 perl testing code-coverage dbi

我对 Devel::Cover 模块有点陌生,但发现它在确保我没有遗漏测试方面非常有用。

我遇到的一个问题是理解来自 Devel::Cover 的报告。我查看了文档,但无法弄清楚我需要测试什么才能获得 100% 的覆盖率。

Edit - I should make it clear that I am not saying I need 100% coverage, because as multiple people point out, 100% coverage is a loose term, does not mean that my code is bug free, and may not always be completely necessary. Since I am new at Devel::Cover, I am interested to know why my code is not 100% coverage, in case I am missing some important tests.

这是封面报告的输出:

line  err   stmt   bran   cond    sub    pod   time   code
...
36                                                    sub connect_database {
37             3                    3      1   1126       my $self = shift;
38             3    100                          24       if ( !$self->{dsn} ) {
39             1                                  7           croak 'dsn not supplied - cannot connect';
40                                                        }
41    ***      2            33                   21       $self->{dbh} = DBI->connect( $self->{dsn}, q{}, q{} )
42                                                          || croak "$DBI::errstr";
43             1                                 11       return $self;
44                                                    }
...
line  err      %      l  !l&&r !l&&!r   expr
----- --- ------ ------ ------ ------   ----
41    ***     33      1      0      0   'DBI'->connect($$self{'dsn'}, '', '') || croak("$DBI::errstr")

下面是我测试这一行的代码示例:

my $database = MyModule::Database->new( { dsn => 'Invalid DSN' });
throws_ok( sub { $database->connect_database() }, 
   qr/Can't connect to data source/, 
   'Test connection exception (invalid dsn)' );

此测试通过 - 连接确实抛出错误并完成我的“throws_ok”测试。

我确实有一些测试成功连接的测试,这就是为什么我认为我有 33% 的覆盖率,但如果我没看错的话,cover 认为我没有测试陈述。我以为我是,通过“throws_ok”测试,但显然我遗漏了一些东西。

有人对我如何成功测试我的 DBI->connect 线路有什么建议吗?

谢谢!

编辑:

brian 向我提供了 HTML 报告和真值表,它解释了为什么第 41 行没有通过。唯一的问题是我无法弄清楚它在告诉我什么。我想我问题的真正核心是为什么这条特定线路没有通过覆盖范围。

这是真值表:

LINE # %  # coverage    # condition
41   # 33 # A | B | dec # 'DBI'->connect($$self{'dsn'}, '', '') || croak("$DBI::errstr")
     #    # 0 | 0 | 0   #
     #    # 0 | 1 | 1   #
     #    # 1 | X | 1   # (THIS LINE IS Green - the rest are red)

如果有人能帮助解释这个真值表,我将不胜感激。还提到要通过覆盖率,我需要一个模拟数据库对象,但我不太明白覆盖率结果中有什么可以给我提供线索。

再次感谢!

最佳答案

另外,不要太执着于 100% 的测试覆盖率。目标是全面测试您的应用程序,而不是在 Devel::Cover 中获得满分。请参阅 Ovid 关于该主题的帖子:

在您的情况下,您似乎没有涵盖所有分支,因此您没有获得满分。您需要对 || 的两侧进行测试。你得到了 33% 的覆盖率,因为你只处理了该行三分之一的案例。 Devel::Cover 的 HTML 报告向您展示了真值表以及您遗漏了哪些案例。

真值表向您显示了分支必须涵盖的可能状态。 1 表示条件为真,0 表示条件为假,X 表示条件不成立抵达。您必须测试所有可以执行的组合。由于 || 是一个短路运算符,一旦其中一个条件通过,您就不必测试条件:

 0 || 1     connect to database fails and croak succeeds
 0 || 0     connect to database fails and croak fails (unlikely)
 1 || X     connect to database succeeds, so short circuit

这与您的特定问题有点无关,但我发现它经常出现在这些问题中。虽然Effective Perl Programming距离上架还有一个月的时间,Josh McAdams 花了相当多的时间谈论 Perl 中的依赖注入(inject)。如果您在测试代码时遇到困难,通常是设计问题。例如,如果您在子例程中内部生成数据库对象,那么您就是在把自己逼到墙角。这就是为什么它可能很难测试。这可能不是您遇到的问题,但值得考虑。

关于perl - 如何在使用 DBI 的 Perl 模块中获得 100% 的测试覆盖率?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/2470904/

相关文章:

perl - 哪个模块可以有效地一次性解析 .pdf 文件? CAM::PDF 或 PDF::API2

ruby-on-rails - 不包含 spec_helper 的测试在 rspec 运行中被忽略

database - 有效地测试数据库后端

java - Sonarqube 未涵盖主要代码

bash - 在多个文件中将每第 4 次出现的 char "_"替换为 "@"

perl - 为什么在内部范围内重新声明变量时 perl 不发出警告?

regex - YAPE::Regex::Explain 不适用于 use 5.014;

python - Scikit-学习管道 : Size of predictions on test set is equal to size of training set

Azure DevOps - 比较不同分支的代码覆盖率

java - 如何在执行java代码时打印行号