SimpleCov有多个应用程序 - 或者简而言之,Simplecov如何工作?

时间:2012-02-29 15:11:50

标签: ruby-on-rails ruby-on-rails-3 testing code-coverage

我正在尝试设置SimpleCov来为3个应用程序生成报告,这些应用程序共享来自本地gem的大部分代码(模型,控制器)但是每个应用程序使用的代码的规范都在每个./spec内部而不是宝石本身。

更清楚的例子。当我在app_1中运行bundle exec rspec spec时,它使用本地gem中的共享模型,我希望得到这个app_1内部所有规格的(准确)报告./spec。

本地gem还有一些专门用于app_2的模型,位于命名空间内,所以当我在app_1中运行测试套件时,我想跳过这些文件的报告。

我正在尝试通过app_1 / spec / spec_helper中的以下代码实现此目的。

# This couple of lines are needed to generate report for the models, etc. inside the local gem.
SimpleCov.adapters.delete(:root_filter)
SimpleCov.filters.clear

SimpleCov.adapters.define 'my_filter' do
  root = SimpleCov.root.split("/")
  root.pop
  add_filter do |src|
    !(src.filename =~ /^#{root.join("/")}/)
  end

  add_filter "/app_2_namespace/"
end

if ENV["COVERAGE"] == "true"
  SimpleCov.start 'rails'
end

这有效,直到一些问题开始出现。

为什么我获得了85%的宝石内部模型的覆盖范围,但规格在app_2内(我在app_1中运行规范)。

第一次出现问题,当我试图改进该模型时,我点击了它的报告,看到哪些行被发现,我试图修复它们在app_2 / spec / namespace /上为它们编写测试my_model_spec.rb。

但是,这并没有什么差别,我试图更积极的测试,我会清除spec文件的所有内容,但不知何故,我还是渐渐覆盖的85%,所以my_model_spec.rb是不相关的my_model.rb的覆盖率结果。出乎意料。

但由于此文件位于app_2,我决定在app_1 spec_helper上的SimpleCov.start块上添加一个过滤器,例如:

add_filter "/app_2_name_space/"

然后我移动到app_2文件夹并开始设置SimpleCov,看看我会得到什么结果。结果他们变得怪异了。

对于相同的型号,我获得了100%的覆盖率,我做了同样的测试,清空了my_model_spec.rb文件并且仍然获得了100%。所以这真的很好,或者我不明白。

这是如何工作的?(with the Ruby 1.9 Coverage module你说,当我在本地运行官方文档中的示例时,我会得到不同的结果,所以我认为那里有一个错误或过时的文档)

ruby-doc: {"foo.rb"=>[1, 1, 10, nil, nil, 1, 1, nil, 0, nil]} 
locally:  {"foo.rb"=>[1, 1, 10, nil, nil, 1, 0, nil, 1, nil]}

我希望报告不会显示在应用代码的某处评估的行的正面结果,无论在何处。

我认为预期的行为是模型的结果与其规格相关,控制器的结果相同等。

是这样的吗?如果是这样,为什么我会得到这个奇怪的结果。

或者你认为我的应用程序的结构可能会搞乱SimpleCov和Coverage?

感谢您花时间阅读本文,如果您需要更详细的信息,请询问。

1 个答案:

答案 0 :(得分:2)

关于你对100%覆盖的模型的困惑,因为我不确定我是否理解正确:Coverage(因此SimpleCov)无法知道你的代码是从规范还是“其他地方”执行的”。假设我有一个方法“foo”和一个调用foo的方法“bar”。如果我在我的规范中调用bar,当然foo也会显示为覆盖。

关于您的一般问题:我认为应该可以报告覆盖范围。仅仅因为源代码与项目根目录不同,不应导致覆盖率报告丢失。

基本配置中的两件事:删除基本适配器(第2行)是不必要的,因为适配器基本上是美化的配置块,此时你已经执行它(因为它在加载Simplecov时被调用)。重置过滤器就足够了。

此外,未使用您定义的自定义适配器。有关如何正确设置适配器的信息,请参阅自述文件,但我认为您现在可以在SimpleCov配置块中使用它时可以正常运行:

SimpleCov.start 'rails' do
  your_custom_config
end

您可能想要的是所有应用的合并报道报告。为此,您必须首先在配置块中为每个规范套件定义command_name,如下所示:command_name 'App1 Specs'

您还必须定义一个核心coverage_path,它会在您的应用套件中存储您的报道报告。假设您有~/projects/my_project/app[1-3],那么将其放入my_project/coverage可能有意义。这将导致您将不同的测试套件结果合并到一个单独的报告中,就像使用SimpleCov with Cucumber&例如RSpec。合并的默认超时约为10分钟,因此您可能需要在配置中使用merge_timeout 3600将其设置为更高的值(这些是秒)。有关这些配置选项的具体信息,请再次查看README和SimpleCov :: Configuration文档。这些事情在那里有详细的概述。

因此,总而言之,您的每个应用应该看起来像这样:

require 'SimpleCov'
SimpleCov.start 'rails' do
  reset_filters!
  command_name 'App1 Spec'
  coverage_path File.dirname(__FILE__) + '../../coverage' # Assuming this is in my_project/app1/spec/spec_helper.rb
  merge_timeout 3600
end

接下来你可能想要添加过滤器以按路径拒绝所有非项目宝石,你应该起来&运行