simplecov 0.9.1 → 0.10.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (79) hide show
  1. checksums.yaml +7 -7
  2. data/.gitignore +0 -1
  3. data/.rubocop.yml +69 -0
  4. data/.travis.yml +12 -0
  5. data/CHANGELOG.md +59 -21
  6. data/Gemfile +22 -15
  7. data/MIT-LICENSE +1 -1
  8. data/README.md +198 -176
  9. data/Rakefile +17 -8
  10. data/doc/alternate-formatters.md +36 -0
  11. data/doc/commercial-services.md +20 -0
  12. data/doc/editor-integration.md +13 -0
  13. data/features/rspec_basic.feature +3 -2
  14. data/features/rspec_groups_and_filters_complex.feature +2 -0
  15. data/features/rspec_groups_using_filter_class.feature +3 -2
  16. data/features/step_definitions/html_steps.rb +6 -7
  17. data/features/step_definitions/simplecov_steps.rb +18 -16
  18. data/features/step_definitions/transformers.rb +2 -2
  19. data/features/step_definitions/web_steps.rb +4 -4
  20. data/features/support/env.rb +18 -15
  21. data/lib/simplecov/command_guesser.rb +33 -34
  22. data/lib/simplecov/configuration.rb +238 -234
  23. data/lib/simplecov/defaults.rb +37 -36
  24. data/lib/simplecov/exit_codes.rb +7 -5
  25. data/lib/simplecov/file_list.rb +38 -36
  26. data/lib/simplecov/filter.rb +12 -2
  27. data/lib/simplecov/formatter/simple_formatter.rb +1 -1
  28. data/lib/simplecov/formatter.rb +2 -2
  29. data/lib/simplecov/jruby_fix.rb +4 -4
  30. data/lib/simplecov/last_run.rb +15 -13
  31. data/lib/simplecov/merge_helpers.rb +26 -27
  32. data/lib/simplecov/no_defaults.rb +2 -2
  33. data/lib/simplecov/profiles.rb +21 -19
  34. data/lib/simplecov/railtie.rb +1 -1
  35. data/lib/simplecov/railties/tasks.rake +7 -7
  36. data/lib/simplecov/result.rb +5 -5
  37. data/lib/simplecov/result_merger.rb +65 -62
  38. data/lib/simplecov/source_file.rb +23 -24
  39. data/lib/simplecov/version.rb +20 -1
  40. data/lib/simplecov.rb +35 -24
  41. data/simplecov.gemspec +15 -12
  42. data/test/faked_project/Gemfile +5 -5
  43. data/test/faked_project/Rakefile +4 -4
  44. data/test/faked_project/features/step_definitions/my_steps.rb +3 -4
  45. data/test/faked_project/features/support/env.rb +5 -5
  46. data/test/faked_project/lib/faked_project/some_class.rb +3 -4
  47. data/test/faked_project/lib/faked_project.rb +1 -1
  48. data/test/faked_project/spec/faked_spec.rb +2 -2
  49. data/test/faked_project/spec/forking_spec.rb +7 -0
  50. data/test/faked_project/spec/meta_magic_spec.rb +1 -1
  51. data/test/faked_project/spec/some_class_spec.rb +3 -3
  52. data/test/faked_project/spec/spec_helper.rb +4 -8
  53. data/test/faked_project/test/faked_test.rb +2 -2
  54. data/test/faked_project/test/meta_magic_test.rb +1 -1
  55. data/test/faked_project/test/some_class_test.rb +3 -3
  56. data/test/faked_project/test/test_helper.rb +5 -9
  57. data/test/fixtures/app/controllers/sample_controller.rb +1 -1
  58. data/test/fixtures/app/models/user.rb +1 -1
  59. data/test/fixtures/deleted_source_sample.rb +3 -3
  60. data/test/fixtures/frameworks/rspec_bad.rb +4 -4
  61. data/test/fixtures/frameworks/rspec_good.rb +4 -4
  62. data/test/fixtures/frameworks/testunit_bad.rb +3 -3
  63. data/test/fixtures/frameworks/testunit_good.rb +3 -3
  64. data/test/fixtures/resultset2.rb +0 -1
  65. data/test/fixtures/sample.rb +1 -1
  66. data/test/fixtures/utf-8.rb +1 -1
  67. data/test/helper.rb +9 -11
  68. data/test/test_1_8_fallbacks.rb +7 -7
  69. data/test/test_command_guesser.rb +8 -8
  70. data/test/test_deleted_source.rb +3 -3
  71. data/test/test_file_list.rb +9 -7
  72. data/test/test_filters.rb +30 -14
  73. data/test/test_merge_helpers.rb +31 -24
  74. data/test/test_result.rb +32 -23
  75. data/test/test_return_codes.rb +10 -6
  76. data/test/test_source_file.rb +5 -38
  77. data/test/test_source_file_line.rb +17 -17
  78. metadata +146 -64
  79. data/lib/simplecov/json.rb +0 -27
@@ -15,6 +15,7 @@ Feature: Sophisticated grouping and filtering on RSpec
15
15
  src_file.filename =~ /MaGiC/i
16
16
  end
17
17
  add_group 'By string', 'project/meta_magic'
18
+ add_group 'By array', ['project/meta_magic']
18
19
 
19
20
  add_filter 'faked_project.rb'
20
21
  # Remove all files that include "describe" in their source
@@ -29,6 +30,7 @@ Feature: Sophisticated grouping and filtering on RSpec
29
30
  | All Files | 100.0% | 1 |
30
31
  | By block | 100.0% | 1 |
31
32
  | By string | 100.0% | 1 |
33
+ | By array | 100.0% | 1 |
32
34
 
33
35
  And I should see the source files:
34
36
  | name | coverage |
@@ -24,10 +24,10 @@ Feature: Grouping on RSpec using a custom filter class
24
24
  When I open the coverage report generated with `bundle exec rspec spec`
25
25
  Then I should see the groups:
26
26
  | name | coverage | files |
27
- | All Files | 91.23% | 6 |
27
+ | All Files | 91.8% | 7 |
28
28
  | By filter class | 78.26% | 2 |
29
29
  | By string | 100.0% | 1 |
30
- | Ungrouped | 100.0% | 3 |
30
+ | Ungrouped | 100.0% | 4 |
31
31
 
32
32
  And I should see the source files:
33
33
  | name | coverage |
@@ -35,6 +35,7 @@ Feature: Grouping on RSpec using a custom filter class
35
35
  | lib/faked_project/some_class.rb | 80.0 % |
36
36
  | lib/faked_project.rb | 100.0 % |
37
37
  | lib/faked_project/meta_magic.rb | 100.0 % |
38
+ | spec/forking_spec.rb | 100.0 % |
38
39
  | spec/meta_magic_spec.rb | 100.0 % |
39
40
  | spec/some_class_spec.rb | 100.0 % |
40
41
 
@@ -1,15 +1,14 @@
1
1
  module GroupHelpers
2
2
  def available_groups
3
- all('#content .file_list_container')
3
+ all("#content .file_list_container")
4
4
  end
5
5
 
6
6
  def available_source_files
7
- all('.source_files .source_table')
7
+ all(".source_files .source_table")
8
8
  end
9
9
  end
10
10
  World(GroupHelpers)
11
11
 
12
-
13
12
  Then /^I should see the groups:$/ do |table|
14
13
  expected_groups = table.hashes
15
14
  # Given group names should be the same number than those rendered in report
@@ -18,8 +17,8 @@ Then /^I should see the groups:$/ do |table|
18
17
  # Verify each of the expected groups has a file list container and corresponding title and coverage number
19
18
  # as well as the correct number of links to files.
20
19
  expected_groups.each do |group|
21
- with_scope "#content ##{group["name"].gsub(/[^a-z]/i, '')}.file_list_container" do
22
- file_count_in_group = page.all('a.src_link').count
20
+ with_scope "#content ##{group['name'].gsub(/[^a-z]/i, '')}.file_list_container" do
21
+ file_count_in_group = page.all("a.src_link").count
23
22
  expect(file_count_in_group).to eq(group["files"].to_i)
24
23
 
25
24
  with_scope "h2" do
@@ -35,9 +34,9 @@ Then /^I should see the source files:$/ do |table|
35
34
  expect(expected_files.length).to eq(available_source_files.count)
36
35
 
37
36
  # Find all filenames and their coverage present in coverage report
38
- files = available_source_files.map {|f| {"name" => f.find('h3').text, "coverage" => f.find('h4 > span').text} }
37
+ files = available_source_files.map { |f| {"name" => f.find("h3").text, "coverage" => f.find("h4 > span").text} }
39
38
 
40
- expect(files.sort_by {|hsh| hsh["name"] }).to eq(expected_files.sort_by {|hsh| hsh["name"] })
39
+ expect(files.sort_by { |hsh| hsh["name"] }).to eq(expected_files.sort_by { |hsh| hsh["name"] })
41
40
  end
42
41
 
43
42
  Then /^there should be (\d+) skipped lines in the source files$/ do |expected_count|
@@ -2,7 +2,8 @@
2
2
  # The test project is using separate config files to avoid specifying all of
3
3
  # test/spec_helper in the features every time.
4
4
  Given /^SimpleCov for (.*) is configured with:$/ do |framework, config_body|
5
- framework_dir = case framework
5
+ framework_dir = begin
6
+ case framework
6
7
  when /RSpec/i
7
8
  "spec"
8
9
  when /Test\/Unit/i
@@ -10,53 +11,54 @@ Given /^SimpleCov for (.*) is configured with:$/ do |framework, config_body|
10
11
  when /Cucumber/i
11
12
  "features/support"
12
13
  else
13
- raise ArgumentError, "Could not identify test framework #{framework}!"
14
+ fail ArgumentError, "Could not identify test framework #{framework}!"
15
+ end
14
16
  end
15
17
 
16
- steps %Q{
18
+ steps %(
17
19
  Given a file named "#{framework_dir}/simplecov_config.rb" with:
18
20
  """
19
21
  #{config_body}
20
22
  """
21
- }
23
+ )
22
24
  end
23
25
 
24
26
  When /^I open the coverage report generated with `([^`]+)`$/ do |command|
25
- steps %Q{
27
+ steps %(
26
28
  When I successfully run `#{command}`
27
29
  Then a coverage report should have been generated
28
30
  When I open the coverage report
29
- }
31
+ )
30
32
  end
31
33
 
32
34
  Then /^a coverage report should have been generated(?: in "([^"]*)")?$/ do |coverage_dir|
33
- coverage_dir ||= 'coverage'
34
- steps %Q{
35
+ coverage_dir ||= "coverage"
36
+ steps %(
35
37
  Then the output should contain "Coverage report generated"
36
38
  And a directory named "#{coverage_dir}" should exist
37
39
  And the following files should exist:
38
40
  | #{coverage_dir}/index.html |
39
41
  | #{coverage_dir}/.resultset.json |
40
- }
42
+ )
41
43
  end
42
44
 
43
45
  Then /^no coverage report should have been generated(?: in "([^"]*)")?$/ do |coverage_dir|
44
- coverage_dir ||= 'coverage'
45
- steps %Q{
46
+ coverage_dir ||= "coverage"
47
+ steps %(
46
48
  Then the output should not contain "Coverage report generated"
47
49
  And a directory named "#{coverage_dir}" should not exist
48
50
  And the following files should not exist:
49
51
  | #{coverage_dir}/index.html |
50
52
  | #{coverage_dir}/.resultset.json |
51
- }
53
+ )
52
54
  end
53
55
 
54
56
  Then /^the report should be based upon:$/ do |table|
55
57
  frameworks = table.raw.flatten
56
- steps %Q{
57
- Then the output should contain "Coverage report generated for #{frameworks.join(", ")}"
58
- And I should see "using #{frameworks.join(", ")}" within "#footer"
59
- }
58
+ steps %(
59
+ Then the output should contain "Coverage report generated for #{frameworks.join(', ')}"
60
+ And I should see "using #{frameworks.join(', ')}" within "#footer"
61
+ )
60
62
  end
61
63
 
62
64
  # This is neccessary to ensure timing-dependant tests like the merge timeout
@@ -6,8 +6,8 @@
6
6
  # This is due to the fact that coverage will not include the first loaded spec/test file.
7
7
  # To get predictable coverage results, we need to know which one that is...
8
8
  #
9
- Transform "bundle exec rspec spec" do |t|
9
+ Transform "bundle exec rspec spec" do |_|
10
10
  files = nil # Avoid shadowing
11
- in_current_dir { files = Dir['spec/**/*_spec.rb'] }
11
+ in_current_dir { files = Dir["spec/**/*_spec.rb"] }
12
12
  "bundle exec rspec #{files.sort.join(' ')}"
13
13
  end
@@ -6,7 +6,7 @@ end
6
6
  World(WithinHelpers)
7
7
 
8
8
  When /^I open the coverage report$/ do
9
- visit '/'
9
+ visit "/"
10
10
  end
11
11
 
12
12
  Given /^(?:|I )am on (.+)$/ do |path|
@@ -38,7 +38,7 @@ end
38
38
  Then /^(?:|I )should see \/([^\/]*)\/(?: within "([^"]*)")?$/ do |regexp, selector|
39
39
  regexp = Regexp.new(regexp)
40
40
  with_scope(selector) do
41
- expect(page).to have_xpath('//*', :text => regexp)
41
+ expect(page).to have_xpath("//*", :text => regexp)
42
42
  end
43
43
  end
44
44
 
@@ -51,12 +51,12 @@ end
51
51
  Then /^(?:|I )should not see \/([^\/]*)\/(?: within "([^"]*)")?$/ do |regexp, selector|
52
52
  regexp = Regexp.new(regexp)
53
53
  with_scope(selector) do
54
- expect(page).to have_no_xpath('//*', :text => regexp)
54
+ expect(page).to have_no_xpath("//*", :text => regexp)
55
55
  end
56
56
  end
57
57
 
58
58
  Then /^show me the page$/ do
59
- save_and_open_page
59
+ save_and_open_page # rubocop:disable Lint/Debugger
60
60
  end
61
61
 
62
62
  Then /^print the page$/ do
@@ -1,36 +1,39 @@
1
- unless '1.9'.respond_to?(:encoding)
1
+ if RUBY_VERSION < "1.9"
2
2
  $stderr.puts "Sorry, Cucumber features are only meant to run on Ruby 1.9+ :("
3
3
  exit 0
4
4
  end
5
5
 
6
- require 'bundler'
6
+ require "bundler"
7
7
  Bundler.setup
8
- require 'aruba/cucumber'
9
- require 'aruba/jruby' if RUBY_ENGINE == 'jruby'
10
- require 'capybara/cucumber'
11
- require 'phantomjs/poltergeist'
8
+ require "aruba/cucumber"
9
+ require "aruba/jruby" if RUBY_ENGINE == "jruby"
10
+ require "capybara/cucumber"
11
+ require "minitest/autorun"
12
+ require "phantomjs/poltergeist"
12
13
 
13
14
  # Fake rack app for capybara that just returns the latest coverage report from aruba temp project dir
14
15
  Capybara.app = lambda { |env|
15
- request_path = env['REQUEST_PATH'] || '/'
16
- request_path = '/index.html' if request_path == '/'
17
-
18
- [200, {'Content-Type' => 'text/html'},
19
- [File.read(File.join(File.dirname(__FILE__), '../../tmp/aruba/project/coverage', request_path))]]
16
+ request_path = env["REQUEST_PATH"] || "/"
17
+ request_path = "/index.html" if request_path == "/"
18
+ [
19
+ 200,
20
+ {"Content-Type" => "text/html"},
21
+ [File.read(File.join(File.dirname(__FILE__), "../../tmp/aruba/project/coverage", request_path))],
22
+ ]
20
23
  }
21
24
 
22
25
  Capybara.default_driver = Capybara.javascript_driver = :poltergeist
23
26
 
24
27
  Before do
25
28
  # JRuby takes it's time... See https://github.com/cucumber/aruba/issues/134
26
- @aruba_timeout_seconds = RUBY_ENGINE == 'jruby' ? 60 : 20
29
+ @aruba_timeout_seconds = RUBY_ENGINE == "jruby" ? 60 : 20
27
30
 
28
31
  this_dir = File.dirname(__FILE__)
29
32
 
30
33
  # Clean up and create blank state for fake project
31
34
  in_current_dir do
32
- FileUtils.rm_rf 'project'
33
- FileUtils.cp_r File.join(this_dir, '../../test/faked_project/'), 'project'
35
+ FileUtils.rm_rf "project"
36
+ FileUtils.cp_r File.join(this_dir, "../../test/faked_project/"), "project"
34
37
  end
35
38
 
36
39
  step 'I cd to "project"'
@@ -39,6 +42,6 @@ end
39
42
  # Workaround for https://github.com/cucumber/aruba/pull/125
40
43
  Aruba.configure do |config|
41
44
  config.before_cmd do
42
- set_env('JRUBY_OPTS', '-X-C --1.9')
45
+ set_env("JRUBY_OPTS", "-X-C --1.9")
43
46
  end
44
47
  end
@@ -1,32 +1,32 @@
1
1
  #
2
2
  # Helper that tries to find out what test suite is running (for SimpleCov.command_name)
3
3
  #
4
- module SimpleCov::CommandGuesser
5
- class << self
6
- # Storage for the original command line call that invoked the test suite.
7
- # This has got to be stored as early as possible because i.e. rake and test/unit 2
8
- # have a habit of tampering with ARGV, which makes i.e. the automatic distinction
9
- # between rails unit/functional/integration tests impossible without this cached
10
- # item.
11
- attr_accessor :original_run_command
4
+ module SimpleCov
5
+ module CommandGuesser
6
+ class << self
7
+ # Storage for the original command line call that invoked the test suite.
8
+ # This has got to be stored as early as possible because i.e. rake and test/unit 2
9
+ # have a habit of tampering with ARGV, which makes i.e. the automatic distinction
10
+ # between rails unit/functional/integration tests impossible without this cached
11
+ # item.
12
+ attr_accessor :original_run_command
12
13
 
13
- def guess
14
- from_env || from_command_line_options || from_defined_constants
15
- end
14
+ def guess
15
+ from_env || from_command_line_options || from_defined_constants
16
+ end
16
17
 
17
18
  private
18
19
 
19
- def from_env
20
- # If being run from inside parallel_tests set the command name according to the process number
21
- if ENV['PARALLEL_TEST_GROUPS'] && ENV['TEST_ENV_NUMBER']
22
- number = ENV['TEST_ENV_NUMBER']
23
- number = '1' if number == ''
20
+ def from_env
21
+ # If being run from inside parallel_tests set the command name according to the process number
22
+ return unless ENV["PARALLEL_TEST_GROUPS"] && ENV["TEST_ENV_NUMBER"]
23
+ number = ENV["TEST_ENV_NUMBER"]
24
+ number = "1" if number.empty?
24
25
  "(#{number}/#{ENV['PARALLEL_TEST_GROUPS']})"
25
26
  end
26
- end
27
27
 
28
- def from_command_line_options
29
- case original_run_command
28
+ def from_command_line_options
29
+ case original_run_command
30
30
  when /test\/functional\//, /test\/\{.*functional.*\}\//
31
31
  "Functional Tests"
32
32
  when /test\/integration\//
@@ -37,23 +37,22 @@ module SimpleCov::CommandGuesser
37
37
  "RSpec"
38
38
  when /cucumber/, /features/
39
39
  "Cucumber Features"
40
- else
41
- nil
40
+ end
42
41
  end
43
- end
44
42
 
45
- def from_defined_constants
46
- # If the command regexps fail, let's try checking defined constants.
47
- if defined?(RSpec)
48
- "RSpec"
49
- elsif defined?(Test::Unit)
50
- "Unit Tests"
51
- elsif defined?(MiniTest)
52
- "MiniTest"
53
- else
54
- # TODO: Provide link to docs/wiki article
55
- warn "SimpleCov failed to recognize the test framework and/or suite used. Please specify manually using SimpleCov.command_name 'Unit Tests'."
56
- 'Unknown Test Framework'
43
+ def from_defined_constants
44
+ # If the command regexps fail, let's try checking defined constants.
45
+ if defined?(RSpec)
46
+ "RSpec"
47
+ elsif defined?(Test::Unit)
48
+ "Unit Tests"
49
+ elsif defined?(MiniTest)
50
+ "MiniTest"
51
+ else
52
+ # TODO: Provide link to docs/wiki article
53
+ warn "SimpleCov failed to recognize the test framework and/or suite used. Please specify manually using SimpleCov.command_name 'Unit Tests'."
54
+ "Unknown Test Framework"
55
+ end
57
56
  end
58
57
  end
59
58
  end