simplecov 0.5.3 → 0.5.4
Sign up to get free protection for your applications and to get access to all the features.
- data/.travis.yml +2 -2
- data/CHANGELOG.md +13 -0
- data/README.md +414 -0
- data/features/rspec_fails_on_initialization.feature +14 -0
- data/features/rspec_groups_using_filter_class.feature +40 -0
- data/features/test_unit_groups_using_filter_class.feature +40 -0
- data/lib/simplecov.rb +2 -3
- data/lib/simplecov/defaults.rb +8 -3
- data/lib/simplecov/filter.rb +10 -5
- data/lib/simplecov/version.rb +1 -1
- data/simplecov.gemspec +1 -1
- data/test/test_filters.rb +14 -14
- metadata +26 -21
- data/README.rdoc +0 -359
- data/lib/simplecov/jruby_float_fix.rb +0 -14
data/.travis.yml
CHANGED
data/CHANGELOG.md
CHANGED
@@ -1,3 +1,16 @@
|
|
1
|
+
v0.5.4 (2011-10-12)
|
2
|
+
===================
|
3
|
+
|
4
|
+
* Do not give exit code 0 when there are exceptions prior to tests
|
5
|
+
(see https://github.com/colszowka/simplecov/issues/41, thanks @nbogie)
|
6
|
+
* The API for building custom filter classes is now more obvious, using #matches? instead of #passes? too.
|
7
|
+
(see https://github.com/colszowka/simplecov/issues/85, thanks @robinroestenburg)
|
8
|
+
* Mailers are now part of the Rails adapter as their own group (see
|
9
|
+
https://github.com/colszowka/simplecov/issues/79, thanks @geetarista)
|
10
|
+
* Removed fix for JRuby 1.6 RC1 float bug because it's been fixed
|
11
|
+
(see https://github.com/colszowka/simplecov/issues/86)
|
12
|
+
* Readme formatted in Markdown :)
|
13
|
+
|
1
14
|
v0.5.3 (2011-09-13)
|
2
15
|
===================
|
3
16
|
|
data/README.md
ADDED
@@ -0,0 +1,414 @@
|
|
1
|
+
SimpleCov [![Build Status](https://secure.travis-ci.org/colszowka/simplecov.png)][Continuous Integration]
|
2
|
+
=========
|
3
|
+
*Code coverage for Ruby 1.9*
|
4
|
+
|
5
|
+
* [Source Code]
|
6
|
+
* [API documentation]
|
7
|
+
* [Changelog]
|
8
|
+
* [Rubygem]
|
9
|
+
* [Continuous Integration]
|
10
|
+
|
11
|
+
[Coverage]: http://www.ruby-doc.org/ruby-1.9/classes/Coverage.html "API doc for Ruby 1.9's Coverage library"
|
12
|
+
[Source Code]: https://github.com/colszowka/simplecov "Source Code @ GitHub"
|
13
|
+
[API documentation]: http://rubydoc.info/gems/simplecov/frames "RDoc API Documentation at Rubydoc.info"
|
14
|
+
[Configuration]: http://rubydoc.info/gems/simplecov/SimpleCov/Configuration "Configuration options API documentation"
|
15
|
+
[Changelog]: https://github.com/colszowka/simplecov/blob/master/CHANGELOG.md "Project Changelog"
|
16
|
+
[Rubygem]: http://rubygems.org/gems/simplecov "SimpleCov @ rubygems.org"
|
17
|
+
[Continuous Integration]: http://travis-ci.org/colszowka/simplecov "SimpleCov is built around the clock by travis-ci.org"
|
18
|
+
[simplecov-html]: https://github.com/colszowka/simplecov-html "SimpleCov HTML Formatter Source Code @ GitHub"
|
19
|
+
|
20
|
+
|
21
|
+
SimpleCov is a code coverage analysis tool for Ruby 1.9. It uses [1.9's built-in Coverage][Coverage] library to gather code
|
22
|
+
coverage data, but makes processing its results much easier by providing a clean API to filter, group, merge, format
|
23
|
+
and display those results, thus giving you a complete code coverage suite that can be set up with just a couple lines of
|
24
|
+
code.
|
25
|
+
|
26
|
+
In most cases, you'll want overall coverage results for your projects, including all types of tests, cucumber features
|
27
|
+
etc. SimpleCov automatically takes care of this by caching and then merging results when generating reports, so your
|
28
|
+
report actually includes coverage across your test suites and thereby gives you a better picture of blank spots.
|
29
|
+
|
30
|
+
The official formatter of SimpleCov is packaged as a separate gem called [simplecov-html] but will be installed and configured
|
31
|
+
automatically when you launch SimpleCov. If you're curious, you can find it [on Github, too][simplecov-html].
|
32
|
+
|
33
|
+
|
34
|
+
|
35
|
+
Getting started
|
36
|
+
---------------
|
37
|
+
|
38
|
+
1. Add SimpleCov to your `Gemfile` and `bundle install`:
|
39
|
+
|
40
|
+
gem 'simplecov', :require => false, :group => :test
|
41
|
+
|
42
|
+
2. Load and launch SimpleCov **at the very top** of your `test/test_helper.rb` (*or `spec_helper.rb`, cucumber `env.rb`, or whatever
|
43
|
+
your preferred test framework uses*):
|
44
|
+
|
45
|
+
require 'simplecov'
|
46
|
+
SimpleCov.start
|
47
|
+
|
48
|
+
# Previous content of test helper now starts here
|
49
|
+
|
50
|
+
**Note:** If SimpleCov starts after your application code is already loaded (via `require`), it won't be able to track your files and their coverage!
|
51
|
+
The `SimpleCov.start` **must** be issued **before any of your application code is required!**
|
52
|
+
|
53
|
+
3. Run your tests, open up `coverage/index.html` in your browser and check out what you've missed so far.
|
54
|
+
|
55
|
+
If you're making a Rails application, SimpleCov comes with a built-in adapter (see below for more information on what adapters are)
|
56
|
+
which will get you started with groups for your Controllers, Views, Models and Helpers. To use it, the first two lines of
|
57
|
+
your test_helper should be like this:
|
58
|
+
|
59
|
+
require 'simplecov'
|
60
|
+
SimpleCov.start 'rails'
|
61
|
+
|
62
|
+
|
63
|
+
|
64
|
+
## Example output
|
65
|
+
|
66
|
+
**Coverage results report, fully browsable locally with sorting and much more:**
|
67
|
+
|
68
|
+
![SimpleCov coverage report](http://colszowka.github.com/simplecov/devise_result-0.5.3.png)
|
69
|
+
|
70
|
+
|
71
|
+
**Source file coverage details view:**
|
72
|
+
|
73
|
+
![SimpleCov source file detail view](http://colszowka.github.com/simplecov/devise_source_file-0.5.3.png)
|
74
|
+
|
75
|
+
|
76
|
+
|
77
|
+
## Use it with any framework!
|
78
|
+
|
79
|
+
Similarily to the usage with Test::Unit described above, the only thing you have to do is to add the simplecov
|
80
|
+
config to the very top of your Cucumber/RSpec/whatever setup file.
|
81
|
+
|
82
|
+
Add the setup code to the **top** of `features/support/env.rb` (for Cucumber) or `spec/spec_helper.rb` (for RSpec).
|
83
|
+
Other test frameworks should work accordingly, whatever their setup file may be:
|
84
|
+
|
85
|
+
require 'simplecov'
|
86
|
+
SimpleCov.start 'rails'
|
87
|
+
|
88
|
+
You could even track what kind of code your UI testers are touching if you want to go overboard with things. SimpleCov does not
|
89
|
+
care what kind of framework it is running in, it just looks at what code is being executed and generates a report about it.
|
90
|
+
|
91
|
+
|
92
|
+
|
93
|
+
## Configuring SimpleCov
|
94
|
+
|
95
|
+
[Configuration] settings can be applied in three formats, which are completely equivalent:
|
96
|
+
|
97
|
+
* The most common way is to configure it directly in your start block:
|
98
|
+
|
99
|
+
SimpleCov.start do
|
100
|
+
some_config_option 'foo'
|
101
|
+
end
|
102
|
+
|
103
|
+
* You can also set all configuration options directly:
|
104
|
+
|
105
|
+
SimpleCov.some_config_option 'foo'
|
106
|
+
|
107
|
+
* If you do not want to start coverage immediately after launch or want to add additional configuration later on in a concise way, use:
|
108
|
+
|
109
|
+
SimpleCov.configure do
|
110
|
+
some_config_option 'foo'
|
111
|
+
end
|
112
|
+
|
113
|
+
Please check out the [Configuration] API documentation to find out what you can customize.
|
114
|
+
|
115
|
+
|
116
|
+
## Using .simplecov for centralized config
|
117
|
+
|
118
|
+
If you use SimpleCov to merge multiple test suite results (i.e. Test/Unit and Cucumber) into a single report, you'd normally have to
|
119
|
+
set up all your config options twice, once in `test_helper.rb` and once in `env.rb`.
|
120
|
+
|
121
|
+
To avoid this, you can place a file called `.simplecov` in your project root. You can then just leave the `require 'simplecov'` in each
|
122
|
+
test setup helper and move the `SimpleCov.start` code with all your custom config options into `.simplecov`:
|
123
|
+
|
124
|
+
# test/test_helper.rb
|
125
|
+
require 'simplecov'
|
126
|
+
|
127
|
+
# features/support/env.rb
|
128
|
+
require 'simplecov'
|
129
|
+
|
130
|
+
# .simplecov
|
131
|
+
SimpleCov.start 'rails' do
|
132
|
+
# any custom configs like groups and filters can be here at a central place
|
133
|
+
end
|
134
|
+
|
135
|
+
|
136
|
+
## Filters
|
137
|
+
|
138
|
+
Filters can be used to remove selected files from your coverage data. By default, a filter is applied that removes all files
|
139
|
+
OUTSIDE of your project's root directory - otherwise you'd end up with a billion of coverage reports for source files in the
|
140
|
+
gems you are using.
|
141
|
+
|
142
|
+
Of course you can define your own to remove things like configuration files, tests or whatever you don't need in your coverage
|
143
|
+
report.
|
144
|
+
|
145
|
+
### Defining custom filters
|
146
|
+
|
147
|
+
You can currently define a filter using either a String (that will then be Regexp-matched against each source file's path),
|
148
|
+
a block or by passing in your own Filter class.
|
149
|
+
|
150
|
+
#### String filter
|
151
|
+
|
152
|
+
SimpleCov.start do
|
153
|
+
add_filter "/test/"
|
154
|
+
end
|
155
|
+
|
156
|
+
This simple string filter will remove all files that match "/test/" in their path.
|
157
|
+
|
158
|
+
#### Block filter
|
159
|
+
|
160
|
+
SimpleCov.start do
|
161
|
+
add_filter do |source_file|
|
162
|
+
source_file.lines.count < 5
|
163
|
+
end
|
164
|
+
end
|
165
|
+
|
166
|
+
Block filters receive a SimpleCov::SourceFile instance and expect your block to return either true (if the file is to be removed
|
167
|
+
from the result) or false (if the result should be kept). Please check out the RDoc for SimpleCov::SourceFile to learn about the
|
168
|
+
methods available to you. In the above example, the filter will remove all files that have less then 5 lines of code.
|
169
|
+
|
170
|
+
#### Custom filter class
|
171
|
+
|
172
|
+
class LineFilter < SimpleCov::Filter
|
173
|
+
def matches?(source_file)
|
174
|
+
source_file.lines.count < filter_argument
|
175
|
+
end
|
176
|
+
end
|
177
|
+
|
178
|
+
SimpleCov.add_filter LineFilter.new(5)
|
179
|
+
|
180
|
+
Defining your own filters is pretty easy: Just inherit from SimpleCov::Filter and define a method 'matches?(source_file)'. When running
|
181
|
+
the filter, a true return value from this method will result in the removal of the given source_file. The filter_argument method
|
182
|
+
is being set in the SimpleCov::Filter initialize method and thus is set to 5 in this example.
|
183
|
+
|
184
|
+
|
185
|
+
## Groups
|
186
|
+
|
187
|
+
You can separate your source files into groups. For example, in a rails app, you'll want to have separate listings for
|
188
|
+
Models, Controllers, Helpers, Libs and Plugins. Group definition works similar to Filters (and indeed also accepts custom
|
189
|
+
filter classes), but source files end up in a group when the filter passes (returns true), as opposed to filtering results,
|
190
|
+
which exclude files from results when the filter results in a true value.
|
191
|
+
|
192
|
+
Add your groups with:
|
193
|
+
|
194
|
+
SimpleCov.start do
|
195
|
+
add_group "Models", "app/models"
|
196
|
+
add_group "Controllers", "app/controllers"
|
197
|
+
add_group "Long files" do |src_file|
|
198
|
+
src_file.lines.count > 100
|
199
|
+
end
|
200
|
+
add_group "Short files", LineFilter.new(5) # Using the LineFilter class defined in Filters section above
|
201
|
+
end
|
202
|
+
|
203
|
+
## Merging results
|
204
|
+
|
205
|
+
Normally, you want to have your coverage analyzed across ALL of your test suites, right?
|
206
|
+
|
207
|
+
Simplecov automatically caches coverage results in your (coverage_path)/resultset.yml. Those results will then
|
208
|
+
be automatically merged when generating the result, so when coverage is set up properly for cucumber and your
|
209
|
+
unit / functional / integration tests, all of those test suites will be taken into account when building the
|
210
|
+
coverage report.
|
211
|
+
|
212
|
+
There are two things to note here though:
|
213
|
+
|
214
|
+
### Test suite names
|
215
|
+
|
216
|
+
Simplecov tries to guess the name of the currently running test suite based upon the shell command the tests are running
|
217
|
+
on. This should work fine for Unit Tests, RSpec and Cucumber. If it fails, it will use the shell command
|
218
|
+
that invoked the test suite as a command name.
|
219
|
+
|
220
|
+
If you have some non-standard setup and still want nicely labeled test suites, you have to give Simplecov a cue what the
|
221
|
+
name of the currently running test suite is. You can do so by specifying SimpleCov.command_name in one test file that is
|
222
|
+
part of your specific suite.
|
223
|
+
|
224
|
+
So, to customize the suite names on a Rails app (yeah, sorry for being Rails biased, but everyone knows what
|
225
|
+
the structure of those projects is. You can apply this accordingly to the RSpecs in your Outlook-WebDAV-Calendar-Sync gem),
|
226
|
+
you could do something like this:
|
227
|
+
|
228
|
+
# test/unit/some_test.rb
|
229
|
+
SimpleCov.command_name 'test:units'
|
230
|
+
|
231
|
+
# test/functionals/some_controller_test.rb
|
232
|
+
SimpleCov.command_name "test:functionals"
|
233
|
+
|
234
|
+
# test/integration/some_integration_test.rb
|
235
|
+
SimpleCov.command_name "test:integration"
|
236
|
+
|
237
|
+
# features/support/env.rb
|
238
|
+
SimpleCov.command_name "features"
|
239
|
+
|
240
|
+
Note that this has only to be invoked ONCE PER TEST SUITE, so even if you have 200 unit test files, specifying it in
|
241
|
+
some_test.rb is fair enough.
|
242
|
+
|
243
|
+
[simplecov-html] prints the used test suites in the footer of the generated coverage report.
|
244
|
+
|
245
|
+
### Timeout for merge
|
246
|
+
|
247
|
+
Of course, your cached coverage data is likely to become invalid at some point. Thus, result sets that are older than
|
248
|
+
SimpleCov.merge_timeout will not be used any more. By default, the timeout is 600 seconds (10 minutes), and you can
|
249
|
+
raise (or lower) it by specifying `SimpleCov.merge_timeout 3600` (1 hour), or, inside a configure/start block, with
|
250
|
+
just "merge_timeout 3600".
|
251
|
+
|
252
|
+
You can deactivate merging altogether with `SimpleCov.use_merging false`.
|
253
|
+
|
254
|
+
|
255
|
+
## Running coverage only on demand
|
256
|
+
|
257
|
+
The Ruby STDLIB Coverage library that SimpleCov builds upon is *very* fast (i.e. on a ~10 min Rails test suite, the speed drop was
|
258
|
+
only a couple seconds for me), and therefore it's SimpleCov's policy to just generate coverage every time you run your tests because
|
259
|
+
it doesn't do your test speed any harm and you're always equipped with the latest and greatest coverage results.
|
260
|
+
|
261
|
+
Because of this, SimpleCov has no explicit built-in mechanism to run coverage only on demand.
|
262
|
+
|
263
|
+
However, you can still accomplish this very easily by introducing a ENV variable conditional into your SimpleCov setup block, like this:
|
264
|
+
|
265
|
+
SimpleCov.start if ENV["COVERAGE"]
|
266
|
+
|
267
|
+
Then, SimpleCov will only run if you execute your tests like this:
|
268
|
+
|
269
|
+
$ COVERAGE=true rake test
|
270
|
+
|
271
|
+
|
272
|
+
## Adapters
|
273
|
+
|
274
|
+
By default, Simplecov's only config assumption is that you only want coverage reports for files inside your project
|
275
|
+
root. To save you from repetitive configuration, you can use predefined blocks of configuration, called 'adapters',
|
276
|
+
or define your own.
|
277
|
+
|
278
|
+
You can then pass the name of the adapter to be used as the first argument to SimpleCov.start. For example, simplecov
|
279
|
+
comes bundled with a 'rails' adapter. It looks somewhat like this:
|
280
|
+
|
281
|
+
SimpleCov.adapters.define 'rails' do
|
282
|
+
add_filter '/test/'
|
283
|
+
add_filter '/config/'
|
284
|
+
|
285
|
+
add_group 'Controllers', 'app/controllers'
|
286
|
+
add_group 'Models', 'app/models'
|
287
|
+
add_group 'Helpers', 'app/helpers'
|
288
|
+
add_group 'Libraries', 'lib'
|
289
|
+
add_group 'Plugins', 'vendor/plugins'
|
290
|
+
end
|
291
|
+
|
292
|
+
As you can see, it's just a glorified SimpleCov.configure block. In your test_helper.rb, launch simplecov with:
|
293
|
+
|
294
|
+
SimpleCov.start 'rails'
|
295
|
+
|
296
|
+
**OR**
|
297
|
+
|
298
|
+
SimpleCov.start 'rails' do
|
299
|
+
# additional config here
|
300
|
+
end
|
301
|
+
|
302
|
+
### Custom adapters
|
303
|
+
|
304
|
+
You can load additional adapters with the SimpleCov.load_adapter('xyz') method. This allows you to build upon an existing
|
305
|
+
adapter and customize it so you can reuse it in unit tests and cucumber features, for example.
|
306
|
+
|
307
|
+
# lib/simplecov_custom_adapter.rb
|
308
|
+
require 'simplecov'
|
309
|
+
SimpleCov.adapters.define 'myadapter' do
|
310
|
+
load_adapter 'rails'
|
311
|
+
add_filter 'vendor' # Don't include vendored stuff
|
312
|
+
end
|
313
|
+
|
314
|
+
# features/support/env.rb
|
315
|
+
require 'simplecov_custom_adapter'
|
316
|
+
SimpleCov.start 'myadapter'
|
317
|
+
|
318
|
+
# test/test_helper.rb
|
319
|
+
require 'simplecov_custom_adapter'
|
320
|
+
SimpleCov.start 'myadapter'
|
321
|
+
|
322
|
+
|
323
|
+
|
324
|
+
## Customizing exit behaviour
|
325
|
+
|
326
|
+
You can define what simplecov should do when your test suite finishes by customizing the at_exit hook:
|
327
|
+
|
328
|
+
SimpleCov.at_exit do
|
329
|
+
SimpleCov.result.format!
|
330
|
+
end
|
331
|
+
|
332
|
+
Above is the default behaviour. Do whatever you like instead!
|
333
|
+
|
334
|
+
|
335
|
+
## Using your own formatter
|
336
|
+
|
337
|
+
You can use your own formatter with:
|
338
|
+
|
339
|
+
SimpleCov.formatter = SimpleCov::Formatter::HTMLFormatter
|
340
|
+
|
341
|
+
When calling SimpleCov.result.format!, it will be invoked with SimpleCov::Formatter::YourFormatter.new.format(result), "result"
|
342
|
+
being an instance of SimpleCov::Result. Do whatever your wish with that!
|
343
|
+
|
344
|
+
|
345
|
+
## Using multiple formatters
|
346
|
+
|
347
|
+
There is currently no built-in support for this, but you could help yourself with a wrapper class:
|
348
|
+
|
349
|
+
class SimpleCov::Formatter::MergedFormatter
|
350
|
+
def format(result)
|
351
|
+
SimpleCov::Formatter::HTMLFormatter.new.format(result)
|
352
|
+
SimpleCov::Formatter::CSVFormatter.new.format(result)
|
353
|
+
end
|
354
|
+
end
|
355
|
+
|
356
|
+
Then configure the formatter to use the new merger:
|
357
|
+
|
358
|
+
SimpleCov.formatter = SimpleCov::Formatter::MergedFormatter
|
359
|
+
|
360
|
+
## Available formatters
|
361
|
+
|
362
|
+
Apart from the direct companion [simplecov-html], there are other formatters
|
363
|
+
available:
|
364
|
+
|
365
|
+
### [simplecov-rcov](https://github.com/fguillen/simplecov-rcov)
|
366
|
+
*by Fernando Guillen*
|
367
|
+
|
368
|
+
"The target of this formatter is to cheat on Hudson so I can use the Ruby metrics plugin with SimpleCov."
|
369
|
+
|
370
|
+
#### [simplecov-csv](https://github.com/fguillen/simplecov-csv)
|
371
|
+
*by Fernando Guillen*
|
372
|
+
|
373
|
+
CSV formatter for SimpleCov code coverage tool for ruby 1.9+
|
374
|
+
|
375
|
+
|
376
|
+
|
377
|
+
## Ruby version compatibility
|
378
|
+
|
379
|
+
[![Build Status](https://secure.travis-ci.org/colszowka/simplecov.png)](http://travis-ci.org/colszowka/simplecov)
|
380
|
+
|
381
|
+
Only Ruby 1.9+ ships with the coverage library that SimpleCov depends upon. SimpleCov is built against various other Rubies,
|
382
|
+
including Rubinius and JRuby, in [Continuous Integration], but this happens only to ensure that SimpleCov does not make your
|
383
|
+
test suite crash right now. Whether SimpleCov will support JRuby/Rubinius in the future depends solely on whether those Ruby
|
384
|
+
interpreters add the coverage library.
|
385
|
+
|
386
|
+
SimpleCov is built in [Continuous Integration] on 1.8.7, ree, 1.9.2, 1.9.3.
|
387
|
+
|
388
|
+
|
389
|
+
|
390
|
+
## Contributions
|
391
|
+
|
392
|
+
To fetch & test the library for development, do:
|
393
|
+
|
394
|
+
$ git clone https://github.com/colszowka/simplecov
|
395
|
+
$ cd simplecov
|
396
|
+
$ bundle
|
397
|
+
$ bundle exec rake test && bundle exec cucumber features
|
398
|
+
|
399
|
+
If you wont to contribute, please:
|
400
|
+
|
401
|
+
* Fork the project.
|
402
|
+
* Make your feature addition or bug fix.
|
403
|
+
* Add tests for it. This is important so I don't break it in a future version unintentionally.
|
404
|
+
* Send me a pull request on Github.
|
405
|
+
|
406
|
+
## Kudos
|
407
|
+
|
408
|
+
Thanks to Aaron Patterson (http://engineering.attinteractive.com/2010/08/code-coverage-in-ruby-1-9/) for the original idea
|
409
|
+
for this!
|
410
|
+
|
411
|
+
|
412
|
+
## Copyright
|
413
|
+
|
414
|
+
Copyright (c) 2010-2011 Christoph Olszowka. See LICENSE for details.
|
@@ -0,0 +1,14 @@
|
|
1
|
+
@rspec
|
2
|
+
Feature:
|
3
|
+
|
4
|
+
Running specs with a failing rspec setup
|
5
|
+
|
6
|
+
Scenario: Fail if rspec fails before starting its tests
|
7
|
+
Given a file named "spec/spec_helper.rb" with:
|
8
|
+
"""
|
9
|
+
require 'simplecov'
|
10
|
+
SimpleCov.start
|
11
|
+
raise "some exception in the class loading before the tests start"
|
12
|
+
"""
|
13
|
+
When I run `bundle exec rspec spec`
|
14
|
+
Then the exit status should not be 0
|
@@ -0,0 +1,40 @@
|
|
1
|
+
@rspec
|
2
|
+
Feature: Grouping on RSpec using a custom filter class
|
3
|
+
|
4
|
+
Next to passing a block or a string to define a group, you can also pass
|
5
|
+
a filter class. The filter class inherits from SimpleCov::Filter and
|
6
|
+
must implement the matches? method, which is used to determine whether
|
7
|
+
or not a file should be added to the group.
|
8
|
+
|
9
|
+
Scenario:
|
10
|
+
Given SimpleCov for RSpec is configured with:
|
11
|
+
"""
|
12
|
+
require 'simplecov'
|
13
|
+
class CoverageFilter < SimpleCov::Filter
|
14
|
+
def matches?(source_file)
|
15
|
+
source_file.covered_percent < filter_argument
|
16
|
+
end
|
17
|
+
end
|
18
|
+
SimpleCov.start do
|
19
|
+
add_group 'By filter class', CoverageFilter.new(90)
|
20
|
+
add_group 'By string', 'project/meta_magic'
|
21
|
+
end
|
22
|
+
"""
|
23
|
+
|
24
|
+
When I open the coverage report generated with `bundle exec rspec spec`
|
25
|
+
Then I should see the groups:
|
26
|
+
| name | coverage | files |
|
27
|
+
| All Files | 90.74% | 6 |
|
28
|
+
| By filter class | 78.26% | 2 |
|
29
|
+
| By string | 100.0% | 1 |
|
30
|
+
| Ungrouped | 100.0% | 3 |
|
31
|
+
|
32
|
+
And I should see the source files:
|
33
|
+
| name | coverage |
|
34
|
+
| lib/faked_project/framework_specific.rb | 75.0 % |
|
35
|
+
| lib/faked_project/some_class.rb | 80.0 % |
|
36
|
+
| lib/faked_project.rb | 100.0 % |
|
37
|
+
| lib/faked_project/meta_magic.rb | 100.0 % |
|
38
|
+
| spec/meta_magic_spec.rb | 100.0 % |
|
39
|
+
| spec/some_class_spec.rb | 100.0 % |
|
40
|
+
|
@@ -0,0 +1,40 @@
|
|
1
|
+
@test_unit
|
2
|
+
Feature: Grouping on Test/Unit using a custom filter class
|
3
|
+
|
4
|
+
Next to passing a block or a string to define a group, you can also pass
|
5
|
+
a filter class. The filter class inherits from SimpleCov::Filter and
|
6
|
+
must implement the matches? method, which is used to determine whether
|
7
|
+
or not a file should be added to the group.
|
8
|
+
|
9
|
+
Scenario:
|
10
|
+
Given SimpleCov for Test/Unit is configured with:
|
11
|
+
"""
|
12
|
+
require 'simplecov'
|
13
|
+
class CoverageFilter < SimpleCov::Filter
|
14
|
+
def matches?(source_file)
|
15
|
+
source_file.covered_percent < filter_argument
|
16
|
+
end
|
17
|
+
end
|
18
|
+
SimpleCov.start do
|
19
|
+
add_group 'By filter class', CoverageFilter.new(90)
|
20
|
+
add_group 'By string', 'project/meta_magic'
|
21
|
+
end
|
22
|
+
"""
|
23
|
+
|
24
|
+
When I open the coverage report generated with `bundle exec rake test`
|
25
|
+
Then I should see the groups:
|
26
|
+
| name | coverage | files |
|
27
|
+
| All Files | 91.38% | 6 |
|
28
|
+
| By filter class | 78.26% | 2 |
|
29
|
+
| By string | 100.0% | 1 |
|
30
|
+
| Ungrouped | 100.0% | 3 |
|
31
|
+
|
32
|
+
And I should see the source files:
|
33
|
+
| name | coverage |
|
34
|
+
| lib/faked_project/framework_specific.rb | 75.0 % |
|
35
|
+
| lib/faked_project/some_class.rb | 80.0 % |
|
36
|
+
| lib/faked_project.rb | 100.0 % |
|
37
|
+
| lib/faked_project/meta_magic.rb | 100.0 % |
|
38
|
+
| test/meta_magic_test.rb | 100.0 % |
|
39
|
+
| test/some_class_test.rb | 100.0 % |
|
40
|
+
|
data/lib/simplecov.rb
CHANGED
@@ -60,7 +60,7 @@ module SimpleCov
|
|
60
60
|
def filtered(files)
|
61
61
|
result = files.clone
|
62
62
|
filters.each do |filter|
|
63
|
-
result = result.
|
63
|
+
result = result.reject {|source_file| filter.matches?(source_file) }
|
64
64
|
end
|
65
65
|
SimpleCov::FileList.new result
|
66
66
|
end
|
@@ -72,7 +72,7 @@ module SimpleCov
|
|
72
72
|
grouped = {}
|
73
73
|
grouped_files = []
|
74
74
|
groups.each do |name, filter|
|
75
|
-
grouped[name] = SimpleCov::FileList.new(files.select {|source_file|
|
75
|
+
grouped[name] = SimpleCov::FileList.new(files.select {|source_file| filter.matches?(source_file)})
|
76
76
|
grouped_files += grouped[name]
|
77
77
|
end
|
78
78
|
if groups.length > 0 and (other_files = files.reject {|source_file| grouped_files.include?(source_file)}).length > 0
|
@@ -103,7 +103,6 @@ module SimpleCov
|
|
103
103
|
end
|
104
104
|
|
105
105
|
$LOAD_PATH.unshift(File.join(File.dirname(__FILE__)))
|
106
|
-
require 'simplecov/jruby_float_fix'
|
107
106
|
require 'simplecov/configuration'
|
108
107
|
SimpleCov.send :extend, SimpleCov::Configuration
|
109
108
|
require 'simplecov/adapters'
|
data/lib/simplecov/defaults.rb
CHANGED
@@ -24,6 +24,7 @@ SimpleCov.adapters.define 'rails' do
|
|
24
24
|
|
25
25
|
add_group 'Controllers', 'app/controllers'
|
26
26
|
add_group 'Models', 'app/models'
|
27
|
+
add_group 'Mailers', 'app/mailers'
|
27
28
|
add_group 'Helpers', 'app/helpers'
|
28
29
|
add_group 'Libraries', 'lib'
|
29
30
|
add_group 'Plugins', 'vendor/plugins'
|
@@ -35,14 +36,18 @@ SimpleCov.configure do
|
|
35
36
|
# Exclude files outside of SimpleCov.root
|
36
37
|
load_adapter 'root_filter'
|
37
38
|
end
|
38
|
-
|
39
39
|
at_exit do
|
40
40
|
# Store the exit status of the test run since it goes away after calling the at_exit proc...
|
41
|
-
|
41
|
+
if $! #was an exception thrown?
|
42
|
+
#if it was a SystemExit, use the accompanying status
|
43
|
+
#otherwise set a non-zero status representing termination by some other exception
|
44
|
+
#(see github issue 41)
|
45
|
+
@exit_status = $!.is_a?(SystemExit) ? $!.status : 1
|
46
|
+
end
|
42
47
|
SimpleCov.at_exit.call
|
43
48
|
exit @exit_status if @exit_status # Force exit with stored status (see github issue #5)
|
44
49
|
end
|
45
50
|
|
46
51
|
# Autoload config from .simplecov if present
|
47
52
|
config_path = File.join(SimpleCov.root, '.simplecov')
|
48
|
-
load config_path if File.exist?(config_path)
|
53
|
+
load config_path if File.exist?(config_path)
|
data/lib/simplecov/filter.rb
CHANGED
@@ -16,24 +16,29 @@ module SimpleCov
|
|
16
16
|
@filter_argument = filter_argument
|
17
17
|
end
|
18
18
|
|
19
|
-
def
|
19
|
+
def matches?(source_file)
|
20
20
|
raise "The base filter class is not intended for direct use"
|
21
21
|
end
|
22
|
+
|
23
|
+
def passes?(source_file)
|
24
|
+
warn "DEPRECATION: SimpleCov::Filter#passes?(x) has been renamed to #matches?. Please update your custom filters accordingly!"
|
25
|
+
matches?(source_file)
|
26
|
+
end
|
22
27
|
end
|
23
28
|
|
24
29
|
class StringFilter < SimpleCov::Filter
|
25
30
|
# Returns true when the given source file's filename matches the
|
26
31
|
# string configured when initializing this Filter with StringFilter.new('somestring)
|
27
|
-
def
|
28
|
-
|
32
|
+
def matches?(source_file)
|
33
|
+
(source_file.filename =~ /#{filter_argument}/)
|
29
34
|
end
|
30
35
|
end
|
31
36
|
|
32
37
|
class BlockFilter < SimpleCov::Filter
|
33
38
|
# Returns true if the block given when initializing this filter with BlockFilter.new {|src_file| ... }
|
34
39
|
# returns true for the given source file.
|
35
|
-
def
|
36
|
-
|
40
|
+
def matches?(source_file)
|
41
|
+
filter_argument.call(source_file)
|
37
42
|
end
|
38
43
|
end
|
39
44
|
end
|
data/lib/simplecov/version.rb
CHANGED
data/simplecov.gemspec
CHANGED
@@ -16,7 +16,7 @@ Gem::Specification.new do |gem|
|
|
16
16
|
gem.add_dependency 'simplecov-html', '~> 0.5.3'
|
17
17
|
gem.add_development_dependency 'aruba', '~> 0.4'
|
18
18
|
gem.add_development_dependency 'capybara', '~> 1.0'
|
19
|
-
gem.add_development_dependency 'cucumber', '~> 1.0'
|
19
|
+
gem.add_development_dependency 'cucumber', '~> 1.0.5'
|
20
20
|
gem.add_development_dependency 'rake', '~> 0.8'
|
21
21
|
gem.add_development_dependency 'rspec', '~> 2.6'
|
22
22
|
gem.add_development_dependency 'shoulda', '~> 2.10'
|
data/test/test_filters.rb
CHANGED
@@ -7,32 +7,32 @@ class TestFilters < Test::Unit::TestCase
|
|
7
7
|
@source_file = SimpleCov::SourceFile.new(source_fixture('sample.rb'), [nil, 1, 1, 1, nil, nil, 1, 0, nil, nil])
|
8
8
|
end
|
9
9
|
|
10
|
-
should "
|
11
|
-
assert SimpleCov::StringFilter.new('foobar').
|
10
|
+
should "not match a new SimpleCov::StringFilter 'foobar'" do
|
11
|
+
assert !SimpleCov::StringFilter.new('foobar').matches?(@source_file)
|
12
12
|
end
|
13
13
|
|
14
|
-
should "
|
15
|
-
assert SimpleCov::StringFilter.new('some/path').
|
14
|
+
should "not match a new SimpleCov::StringFilter 'some/path'" do
|
15
|
+
assert !SimpleCov::StringFilter.new('some/path').matches?(@source_file)
|
16
16
|
end
|
17
17
|
|
18
|
-
should "
|
19
|
-
assert
|
18
|
+
should "match a new SimpleCov::StringFilter 'test/fixtures'" do
|
19
|
+
assert SimpleCov::StringFilter.new('test/fixtures').matches?(@source_file)
|
20
20
|
end
|
21
21
|
|
22
|
-
should "
|
23
|
-
assert
|
22
|
+
should "match a new SimpleCov::StringFilter 'test/fixtures/sample.rb'" do
|
23
|
+
assert SimpleCov::StringFilter.new('test/fixtures/sample.rb').matches?(@source_file)
|
24
24
|
end
|
25
25
|
|
26
|
-
should "
|
27
|
-
assert
|
26
|
+
should "match a new SimpleCov::StringFilter 'sample.rb'" do
|
27
|
+
assert SimpleCov::StringFilter.new('sample.rb').matches?(@source_file)
|
28
28
|
end
|
29
29
|
|
30
|
-
should "
|
31
|
-
assert SimpleCov::BlockFilter.new(Proc.new {|s| File.basename(s.filename) == 'foo.rb'}).
|
30
|
+
should "not match a new SimpleCov::BlockFilter that is not applicable" do
|
31
|
+
assert !SimpleCov::BlockFilter.new(Proc.new {|s| File.basename(s.filename) == 'foo.rb'}).matches?(@source_file)
|
32
32
|
end
|
33
33
|
|
34
|
-
should "
|
35
|
-
assert
|
34
|
+
should "match a new SimpleCov::BlockFilter that is applicable" do
|
35
|
+
assert SimpleCov::BlockFilter.new(Proc.new {|s| File.basename(s.filename) == 'sample.rb'}).matches?(@source_file)
|
36
36
|
end
|
37
37
|
end
|
38
38
|
|
metadata
CHANGED
@@ -1,7 +1,7 @@
|
|
1
1
|
--- !ruby/object:Gem::Specification
|
2
2
|
name: simplecov
|
3
3
|
version: !ruby/object:Gem::Version
|
4
|
-
version: 0.5.
|
4
|
+
version: 0.5.4
|
5
5
|
prerelease:
|
6
6
|
platform: ruby
|
7
7
|
authors:
|
@@ -9,12 +9,12 @@ authors:
|
|
9
9
|
autorequire:
|
10
10
|
bindir: bin
|
11
11
|
cert_chain: []
|
12
|
-
date: 2011-
|
12
|
+
date: 2011-10-12 00:00:00.000000000 +02:00
|
13
13
|
default_executable:
|
14
14
|
dependencies:
|
15
15
|
- !ruby/object:Gem::Dependency
|
16
16
|
name: multi_json
|
17
|
-
requirement: &
|
17
|
+
requirement: &70223996324480 !ruby/object:Gem::Requirement
|
18
18
|
none: false
|
19
19
|
requirements:
|
20
20
|
- - ~>
|
@@ -22,10 +22,10 @@ dependencies:
|
|
22
22
|
version: 1.0.3
|
23
23
|
type: :runtime
|
24
24
|
prerelease: false
|
25
|
-
version_requirements: *
|
25
|
+
version_requirements: *70223996324480
|
26
26
|
- !ruby/object:Gem::Dependency
|
27
27
|
name: simplecov-html
|
28
|
-
requirement: &
|
28
|
+
requirement: &70223996323980 !ruby/object:Gem::Requirement
|
29
29
|
none: false
|
30
30
|
requirements:
|
31
31
|
- - ~>
|
@@ -33,10 +33,10 @@ dependencies:
|
|
33
33
|
version: 0.5.3
|
34
34
|
type: :runtime
|
35
35
|
prerelease: false
|
36
|
-
version_requirements: *
|
36
|
+
version_requirements: *70223996323980
|
37
37
|
- !ruby/object:Gem::Dependency
|
38
38
|
name: aruba
|
39
|
-
requirement: &
|
39
|
+
requirement: &70223996323380 !ruby/object:Gem::Requirement
|
40
40
|
none: false
|
41
41
|
requirements:
|
42
42
|
- - ~>
|
@@ -44,10 +44,10 @@ dependencies:
|
|
44
44
|
version: '0.4'
|
45
45
|
type: :development
|
46
46
|
prerelease: false
|
47
|
-
version_requirements: *
|
47
|
+
version_requirements: *70223996323380
|
48
48
|
- !ruby/object:Gem::Dependency
|
49
49
|
name: capybara
|
50
|
-
requirement: &
|
50
|
+
requirement: &70223996322760 !ruby/object:Gem::Requirement
|
51
51
|
none: false
|
52
52
|
requirements:
|
53
53
|
- - ~>
|
@@ -55,21 +55,21 @@ dependencies:
|
|
55
55
|
version: '1.0'
|
56
56
|
type: :development
|
57
57
|
prerelease: false
|
58
|
-
version_requirements: *
|
58
|
+
version_requirements: *70223996322760
|
59
59
|
- !ruby/object:Gem::Dependency
|
60
60
|
name: cucumber
|
61
|
-
requirement: &
|
61
|
+
requirement: &70223996322160 !ruby/object:Gem::Requirement
|
62
62
|
none: false
|
63
63
|
requirements:
|
64
64
|
- - ~>
|
65
65
|
- !ruby/object:Gem::Version
|
66
|
-
version:
|
66
|
+
version: 1.0.5
|
67
67
|
type: :development
|
68
68
|
prerelease: false
|
69
|
-
version_requirements: *
|
69
|
+
version_requirements: *70223996322160
|
70
70
|
- !ruby/object:Gem::Dependency
|
71
71
|
name: rake
|
72
|
-
requirement: &
|
72
|
+
requirement: &70223996321600 !ruby/object:Gem::Requirement
|
73
73
|
none: false
|
74
74
|
requirements:
|
75
75
|
- - ~>
|
@@ -77,10 +77,10 @@ dependencies:
|
|
77
77
|
version: '0.8'
|
78
78
|
type: :development
|
79
79
|
prerelease: false
|
80
|
-
version_requirements: *
|
80
|
+
version_requirements: *70223996321600
|
81
81
|
- !ruby/object:Gem::Dependency
|
82
82
|
name: rspec
|
83
|
-
requirement: &
|
83
|
+
requirement: &70223996321120 !ruby/object:Gem::Requirement
|
84
84
|
none: false
|
85
85
|
requirements:
|
86
86
|
- - ~>
|
@@ -88,10 +88,10 @@ dependencies:
|
|
88
88
|
version: '2.6'
|
89
89
|
type: :development
|
90
90
|
prerelease: false
|
91
|
-
version_requirements: *
|
91
|
+
version_requirements: *70223996321120
|
92
92
|
- !ruby/object:Gem::Dependency
|
93
93
|
name: shoulda
|
94
|
-
requirement: &
|
94
|
+
requirement: &70223996320600 !ruby/object:Gem::Requirement
|
95
95
|
none: false
|
96
96
|
requirements:
|
97
97
|
- - ~>
|
@@ -99,7 +99,7 @@ dependencies:
|
|
99
99
|
version: '2.10'
|
100
100
|
type: :development
|
101
101
|
prerelease: false
|
102
|
-
version_requirements: *
|
102
|
+
version_requirements: *70223996320600
|
103
103
|
description: Code coverage for Ruby 1.9 with a powerful configuration library and
|
104
104
|
automatic merging of coverage across test suites
|
105
105
|
email:
|
@@ -114,7 +114,7 @@ files:
|
|
114
114
|
- CHANGELOG.md
|
115
115
|
- Gemfile
|
116
116
|
- LICENSE
|
117
|
-
- README.
|
117
|
+
- README.md
|
118
118
|
- Rakefile
|
119
119
|
- cucumber.yml
|
120
120
|
- features/config_adapters.feature
|
@@ -129,8 +129,10 @@ files:
|
|
129
129
|
- features/cucumber_basic.feature
|
130
130
|
- features/merging_test_unit_and_rspec.feature
|
131
131
|
- features/rspec_basic.feature
|
132
|
+
- features/rspec_fails_on_initialization.feature
|
132
133
|
- features/rspec_groups_and_filters_basic.feature
|
133
134
|
- features/rspec_groups_and_filters_complex.feature
|
135
|
+
- features/rspec_groups_using_filter_class.feature
|
134
136
|
- features/rspec_without_simplecov.feature
|
135
137
|
- features/skipping_code_blocks_manually.feature
|
136
138
|
- features/step_definitions/html_steps.rb
|
@@ -141,6 +143,7 @@ files:
|
|
141
143
|
- features/test_unit_basic.feature
|
142
144
|
- features/test_unit_groups_and_filters_basic.feature
|
143
145
|
- features/test_unit_groups_and_filters_complex.feature
|
146
|
+
- features/test_unit_groups_using_filter_class.feature
|
144
147
|
- features/test_unit_without_simplecov.feature
|
145
148
|
- features/unicode_compatiblity.feature
|
146
149
|
- lib/simplecov.rb
|
@@ -152,7 +155,6 @@ files:
|
|
152
155
|
- lib/simplecov/filter.rb
|
153
156
|
- lib/simplecov/formatter.rb
|
154
157
|
- lib/simplecov/formatter/simple_formatter.rb
|
155
|
-
- lib/simplecov/jruby_float_fix.rb
|
156
158
|
- lib/simplecov/merge_helpers.rb
|
157
159
|
- lib/simplecov/result.rb
|
158
160
|
- lib/simplecov/result_merger.rb
|
@@ -238,8 +240,10 @@ test_files:
|
|
238
240
|
- features/cucumber_basic.feature
|
239
241
|
- features/merging_test_unit_and_rspec.feature
|
240
242
|
- features/rspec_basic.feature
|
243
|
+
- features/rspec_fails_on_initialization.feature
|
241
244
|
- features/rspec_groups_and_filters_basic.feature
|
242
245
|
- features/rspec_groups_and_filters_complex.feature
|
246
|
+
- features/rspec_groups_using_filter_class.feature
|
243
247
|
- features/rspec_without_simplecov.feature
|
244
248
|
- features/skipping_code_blocks_manually.feature
|
245
249
|
- features/step_definitions/html_steps.rb
|
@@ -250,6 +254,7 @@ test_files:
|
|
250
254
|
- features/test_unit_basic.feature
|
251
255
|
- features/test_unit_groups_and_filters_basic.feature
|
252
256
|
- features/test_unit_groups_and_filters_complex.feature
|
257
|
+
- features/test_unit_groups_using_filter_class.feature
|
253
258
|
- features/test_unit_without_simplecov.feature
|
254
259
|
- features/unicode_compatiblity.feature
|
255
260
|
- test/faked_project/Gemfile
|
data/README.rdoc
DELETED
@@ -1,359 +0,0 @@
|
|
1
|
-
= SimpleCov http://travis-ci.org/colszowka/simplecov.png
|
2
|
-
|
3
|
-
* Source code: https://github.com/colszowka/simplecov
|
4
|
-
* API documentation: http://rubydoc.info/gems/simplecov/frames
|
5
|
-
* Changelog: https://github.com/colszowka/simplecov/blob/master/CHANGELOG.md
|
6
|
-
* Rubygems: http://rubygems.org/gems/simplecov
|
7
|
-
|
8
|
-
SimpleCov is a code coverage analysis tool for Ruby 1.9. It uses 1.9's built-in Coverage library to gather code
|
9
|
-
coverage data, but makes processing its results much easier by providing a clean API to filter, group, merge, format
|
10
|
-
and display those results, thus giving you a complete code coverage suite that can be set up with just a couple lines of
|
11
|
-
code.
|
12
|
-
|
13
|
-
In most cases, you'll want overall coverage results for your projects, including all types of tests, cucumber features
|
14
|
-
etc. Simplecov automatically takes care of this by caching and then merging results when generating reports, so your
|
15
|
-
report actually covers coverage across your test suites and thereby gives you a better picture of blank spots.
|
16
|
-
|
17
|
-
The official formatter of SimpleCov is packaged as a separate gem called simplecov-html but will be installed and configured
|
18
|
-
automatically when you launch SimpleCov. If you're curious, you can find it at http://github.com/colszowka/simplecov-html
|
19
|
-
|
20
|
-
== Basic usage
|
21
|
-
|
22
|
-
Update your Gemfile with this and do a bundle install:
|
23
|
-
|
24
|
-
gem 'simplecov', '>= 0.5.3', :require => false, :group => :test
|
25
|
-
|
26
|
-
Then, add the following to your test/test_helper.rb (right at the top, line 00) or spec_helper.rb or cucumber env.rb or whatever
|
27
|
-
test framework you prefer, really - just make sure simplecov is loaded and started BEFORE your app code is loaded:
|
28
|
-
|
29
|
-
require 'simplecov'
|
30
|
-
SimpleCov.start
|
31
|
-
|
32
|
-
Now, when running tests you'll get a coverage/ folder inside your app's root where you can browse your code coverage.
|
33
|
-
|
34
|
-
If you're making a Rails application, SimpleCov comes with a built-in adapter (see below for more information on what adapters are)
|
35
|
-
for it which will give you handy tabs in the output webpage for your Controllers, Views, Models, etc. To use it, the first two lines of your test_helper should be like this:
|
36
|
-
|
37
|
-
require 'simplecov'
|
38
|
-
SimpleCov.start 'rails'
|
39
|
-
|
40
|
-
== Example output
|
41
|
-
|
42
|
-
<b>Coverage results report, fully browsable locally with sorting and much more:</b>
|
43
|
-
http://colszowka.github.com/simplecov/devise_result-0.5.3.png
|
44
|
-
|
45
|
-
<b>Source file coverage details view:</b>
|
46
|
-
http://colszowka.github.com/simplecov/devise_source_file-0.5.3.png
|
47
|
-
|
48
|
-
== Use it with any framework!
|
49
|
-
|
50
|
-
Similarily to the usage with Test::Unit described above, the only thing you have to do is to add the simplecov
|
51
|
-
config to the very top of your Cucumber/RSpec/whatever setup file.
|
52
|
-
|
53
|
-
Add the setup code to the <b>top</b> of +features/support/env.rb+ (for Cucumber) or +spec/spec_helper.rb+ (for RSpec).
|
54
|
-
Other test frameworks should work accordingly, whatever their setup file may be:
|
55
|
-
|
56
|
-
require 'simplecov'
|
57
|
-
SimpleCov.start 'rails'
|
58
|
-
|
59
|
-
You could even track what kind of code your UI testers are touching if you want to go overboard with things. SimpleCov does not
|
60
|
-
care what kind of framework it is running in, it just looks at what code is being executed and generates a report about it.
|
61
|
-
|
62
|
-
== Configuration
|
63
|
-
|
64
|
-
Configuration settings can be applied in three formats.
|
65
|
-
|
66
|
-
The 'direct' way:
|
67
|
-
|
68
|
-
SimpleCov.some_config_option 'foo'
|
69
|
-
|
70
|
-
Using a block:
|
71
|
-
|
72
|
-
SimpleCov.configure do
|
73
|
-
some_config_option 'foo'
|
74
|
-
end
|
75
|
-
|
76
|
-
Using a block and automatically starting the coverage:
|
77
|
-
|
78
|
-
SimpleCov.start do
|
79
|
-
some_config_option 'foo'
|
80
|
-
end
|
81
|
-
|
82
|
-
Most times, you'll want to use the latter, so loading and setting up simplecov is in one place at the top of your test helper.
|
83
|
-
|
84
|
-
== Running coverage only on demand
|
85
|
-
|
86
|
-
The Ruby STDLIB Coverage library that SimpleCov builds upon is *very* fast (i.e. on a ~10 min Rails test suite, the speed drop was
|
87
|
-
only a couple seconds for me), and therefore it's SimpleCov's policy to just generate coverage every time you run your tests because
|
88
|
-
it doesn't do your test speed any harm and you're always equipped with the latest and greatest coverage results.
|
89
|
-
|
90
|
-
Because of this, SimpleCov has no explicit built-in mechanism to run coverage only on demand.
|
91
|
-
|
92
|
-
However, you can still accomplish this very easily by introducing a ENV variable conditional into your SimpleCov setup block, like this:
|
93
|
-
|
94
|
-
SimpleCov.start if ENV["COVERAGE"]
|
95
|
-
|
96
|
-
Then, SimpleCov will only run if you execute your tests like this:
|
97
|
-
|
98
|
-
$ COVERAGE=true rake test
|
99
|
-
|
100
|
-
== Filters
|
101
|
-
|
102
|
-
Filters can be used to remove selected files from your coverage data. By default, a filter is applied that removes all files
|
103
|
-
OUTSIDE of your project's root directory - otherwise you'd end up with a billion of coverage reports for source files in the
|
104
|
-
gems you are using.
|
105
|
-
|
106
|
-
Of course you can define your own to remove things like configuration files, tests or whatever you don't need in your coverage
|
107
|
-
report.
|
108
|
-
|
109
|
-
=== Defining custom filters
|
110
|
-
|
111
|
-
You can currently define a filter using either a String (that will then be Regexp-matched against each source file's path),
|
112
|
-
a block or by passing in your own Filter class.
|
113
|
-
|
114
|
-
==== String filter
|
115
|
-
|
116
|
-
SimpleCov.start do
|
117
|
-
add_filter "/test/"
|
118
|
-
end
|
119
|
-
|
120
|
-
This simple string filter will remove all files that match "/test/" in their path.
|
121
|
-
|
122
|
-
==== Block filter
|
123
|
-
|
124
|
-
SimpleCov.start do
|
125
|
-
add_filter do |source_file|
|
126
|
-
source_file.lines.count < 5
|
127
|
-
end
|
128
|
-
end
|
129
|
-
|
130
|
-
Block filters receive a SimpleCov::SourceFile instance and expect your block to return either true (if the file is to be removed
|
131
|
-
from the result) or false (if the result should be kept). Please check out the RDoc for SimpleCov::SourceFile to learn about the
|
132
|
-
methods available to you. In the above example, the filter will remove all files that have less then 5 lines of code.
|
133
|
-
|
134
|
-
==== Custom filter class
|
135
|
-
|
136
|
-
class LineFilter < SimpleCov::Filter
|
137
|
-
def passes?(source_file)
|
138
|
-
source_file.lines.count < filter_argument
|
139
|
-
end
|
140
|
-
end
|
141
|
-
|
142
|
-
SimpleCov.add_filter LineFilter.new(5)
|
143
|
-
|
144
|
-
Defining your own filters is pretty easy: Just inherit from SimpleCov::Filter and define a method 'passes?(source_file)'. When running
|
145
|
-
the filter, a true return value from this method will result in the removal of the given source_file. The filter_argument method
|
146
|
-
is being set in the SimpleCov::Filter initialize method and thus is set to 5 in this example.
|
147
|
-
|
148
|
-
== Groups
|
149
|
-
|
150
|
-
You can separate your source files into groups. For example, in a rails app, you'll want to have separate listings for
|
151
|
-
Models, Controllers, Helpers, Libs and Plugins. Group definition works similar to Filters (and indeed also accepts custom
|
152
|
-
filter classes), but source files end up in a group when the filter passes (returns true), as opposed to filtering results,
|
153
|
-
which exclude files from results when the filter results in a true value.
|
154
|
-
|
155
|
-
Add your groups with:
|
156
|
-
|
157
|
-
SimpleCov.start do
|
158
|
-
add_group "Models", "app/models"
|
159
|
-
add_group "Controllers", "app/controllers"
|
160
|
-
add_group "Long files" do |src_file|
|
161
|
-
src_file.lines.count > 100
|
162
|
-
end
|
163
|
-
add_group "Short files", LineFilter.new(5) # Using the LineFilter class defined in Filters section above
|
164
|
-
end
|
165
|
-
|
166
|
-
== Merging results
|
167
|
-
|
168
|
-
Normally, you want to have your coverage analyzed across ALL of your test suites, right?
|
169
|
-
|
170
|
-
Simplecov automatically caches coverage results in your (coverage_path)/resultset.yml. Those results will then
|
171
|
-
be automatically merged when generating the result, so when coverage is set up properly for cucumber and your
|
172
|
-
unit / functional / integration tests, all of those test suites will be taken into account when building the
|
173
|
-
coverage report.
|
174
|
-
|
175
|
-
There are two things to note here though:
|
176
|
-
|
177
|
-
=== Test suite names
|
178
|
-
|
179
|
-
Simplecov tries to guess the name of the currently running test suite based upon the shell command the tests are running
|
180
|
-
on (from v0.3.2+). This should work fine for Unit Tests, RSpec and Cucumber. If it fails, it will use the shell command
|
181
|
-
that invoked the test suite as a command name.
|
182
|
-
|
183
|
-
If you have some non-standard setup and still want nicely labeled test suites, you have to give Simplecov a cue what the
|
184
|
-
name of the currently running test suite is. You can do so by specifying SimpleCov.command_name in one test file that is
|
185
|
-
part of your specific suite.
|
186
|
-
|
187
|
-
So, to customize the suite names on a Rails app (yeah, sorry for being Rails biased, but everyone knows what
|
188
|
-
the structure of those projects is. You can apply this accordingly to the RSpecs in your Outlook-WebDAV-Calendar-Sync gem),
|
189
|
-
you could do something like this:
|
190
|
-
|
191
|
-
# test/unit/some_test.rb
|
192
|
-
SimpleCov.command_name 'test:units'
|
193
|
-
|
194
|
-
# test/functionals/some_controller_test.rb
|
195
|
-
SimpleCov.command_name "test:functionals"
|
196
|
-
|
197
|
-
# test/integration/some_integration_test.rb
|
198
|
-
SimpleCov.command_name "test:integration"
|
199
|
-
|
200
|
-
# features/steps/web_steps.rb
|
201
|
-
SimpleCov.command_name "features"
|
202
|
-
|
203
|
-
Note that this has only to be invoked ONCE PER TEST SUITE, so even if you have 200 unit test files, specifying it in
|
204
|
-
some_test.rb is fair enough.
|
205
|
-
|
206
|
-
simplecov-html prints the used test suites in the footer of the generated coverage report.
|
207
|
-
|
208
|
-
=== Timeout for merge
|
209
|
-
|
210
|
-
Of course, your cached coverage data is likely to become invalid at some point. Thus, result sets that are older than
|
211
|
-
SimpleCov.merge_timeout will not be used any more. By default, the timeout is 600 seconds (10 minutes), and you can
|
212
|
-
raise (or lower) it by specifying SimpleCov.merge_timeout 3600 (1 hour), or, inside a configure/start block, with
|
213
|
-
just "merge_timeout 3600".
|
214
|
-
|
215
|
-
You can deactivate merging altogether with "SimpleCov.use_merging false".
|
216
|
-
|
217
|
-
== Adapters
|
218
|
-
|
219
|
-
By default, Simplecov's only config assumption is that you only want coverage reports for files inside your project
|
220
|
-
root. To save you from repetitive configuration, you can use predefined blocks of configuration, called 'adapters',
|
221
|
-
or define your own.
|
222
|
-
|
223
|
-
You can then pass the name of the adapter to be used as the first argument to SimpleCov.start. For example, simplecov
|
224
|
-
comes bundled with a 'rails' adapter. It looks somewhat like this:
|
225
|
-
|
226
|
-
SimpleCov.adapters.define 'rails' do
|
227
|
-
add_filter '/test/'
|
228
|
-
add_filter '/config/'
|
229
|
-
|
230
|
-
add_group 'Controllers', 'app/controllers'
|
231
|
-
add_group 'Models', 'app/models'
|
232
|
-
add_group 'Helpers', 'app/helpers'
|
233
|
-
add_group 'Libraries', 'lib'
|
234
|
-
add_group 'Plugins', 'vendor/plugins'
|
235
|
-
end
|
236
|
-
|
237
|
-
As you can see, it's just a glorified SimpleCov.configure block. In your test_helper.rb, launch simplecov with:
|
238
|
-
|
239
|
-
SimpleCov.start 'rails'
|
240
|
-
|
241
|
-
OR
|
242
|
-
|
243
|
-
SimpleCov.start 'rails' do
|
244
|
-
# additional config here
|
245
|
-
end
|
246
|
-
|
247
|
-
=== Custom adapters
|
248
|
-
|
249
|
-
You can load additional adapters with the SimpleCov.load_adapter('xyz') method. This allows you to build upon an existing
|
250
|
-
adapter and customize it so you can reuse it in unit tests and cucumber features, for example.
|
251
|
-
|
252
|
-
# lib/simplecov_custom_adapter.rb
|
253
|
-
require 'simplecov'
|
254
|
-
SimpleCov.adapters.define 'myadapter' do
|
255
|
-
load_adapter 'rails'
|
256
|
-
add_filter 'vendor' # Don't include vendored stuff
|
257
|
-
end
|
258
|
-
|
259
|
-
# features/support/env.rb
|
260
|
-
require 'simplecov_custom_adapter'
|
261
|
-
SimpleCov.start 'myadapter'
|
262
|
-
|
263
|
-
# test/test_helper.rb
|
264
|
-
require 'simplecov_custom_adapter'
|
265
|
-
SimpleCov.start 'myadapter'
|
266
|
-
|
267
|
-
== Customizing exit behaviour
|
268
|
-
|
269
|
-
You can define what simplecov should do when your test suite finishes by customizing the at_exit hook:
|
270
|
-
|
271
|
-
SimpleCov.at_exit do
|
272
|
-
SimpleCov.result.format!
|
273
|
-
end
|
274
|
-
|
275
|
-
Above is the default behaviour. Do whatever you like instead!
|
276
|
-
|
277
|
-
== Using your own formatter
|
278
|
-
|
279
|
-
You can use your own formatter with:
|
280
|
-
|
281
|
-
SimpleCov.formatter = SimpleCov::Formatter::HTMLFormatter
|
282
|
-
|
283
|
-
When calling SimpleCov.result.format!, it will be invoked with SimpleCov::Formatter::YourFormatter.new.format(result), "result"
|
284
|
-
being an instance of SimpleCov::Result. Do whatever your wish with that!
|
285
|
-
|
286
|
-
== Using multiple formatters
|
287
|
-
|
288
|
-
There is currently no built-in support for this, but you could help yourself with a wrapper class:
|
289
|
-
|
290
|
-
class SimpleCov::Formatter::MergedFormatter
|
291
|
-
def format(result)
|
292
|
-
SimpleCov::Formatter::HTMLFormatter.new.format(result)
|
293
|
-
SimpleCov::Formatter::CSVFormatter.new.format(result)
|
294
|
-
end
|
295
|
-
end
|
296
|
-
|
297
|
-
Then configure the formatter to use the new merger:
|
298
|
-
|
299
|
-
SimpleCov.formatter = SimpleCov::Formatter::MergedFormatter
|
300
|
-
|
301
|
-
== Available formatters
|
302
|
-
|
303
|
-
Apart from the direct companion simplecov-html (https://github.com/colszowka/simplecov-html), there are other formatters
|
304
|
-
available:
|
305
|
-
|
306
|
-
==== simplecov_rcov
|
307
|
-
by Fernando Guillen
|
308
|
-
|
309
|
-
https://github.com/fguillen/simplecov-rcov
|
310
|
-
|
311
|
-
"The target of this formatter is to cheat on Hudson so I can use the Ruby metrics plugin with SimpleCov."
|
312
|
-
|
313
|
-
==== simplecov_csv
|
314
|
-
by Fernando Guillen
|
315
|
-
|
316
|
-
https://github.com/fguillen/simplecov-csv
|
317
|
-
|
318
|
-
CSV formatter for SimpleCov code coverage tool for ruby 1.9+
|
319
|
-
|
320
|
-
== Configuration options
|
321
|
-
|
322
|
-
Please have a look at our documentation[http://rubydoc.info/gems/simplecov/frames], specifically the Configuration class.
|
323
|
-
|
324
|
-
== Kudos
|
325
|
-
|
326
|
-
Thanks to Aaron Patterson (http://engineering.attinteractive.com/2010/08/code-coverage-in-ruby-1-9/) for the original idea
|
327
|
-
for this!
|
328
|
-
|
329
|
-
== Ruby version compatibility
|
330
|
-
|
331
|
-
http://travis-ci.org/colszowka/simplecov.png
|
332
|
-
|
333
|
-
Only Ruby 1.9+ ships with the coverage library that SimpleCov depends upon. SimpleCov is built against various other Rubies,
|
334
|
-
including Rubinius and JRuby, in {continuous integration}[http://travis-ci.org/colszowka/simplecov], but this happens only to
|
335
|
-
ensure that SimpleCov does not make your test suite crash right now. Whether SimpleCov will support JRuby/Rubinius in the future
|
336
|
-
depends solely on whether those Ruby interpreters add the coverage library.
|
337
|
-
|
338
|
-
SimpleCov is built in {continuous integration}[http://travis-ci.org/colszowka/simplecov] on 1.8.6, 1.8.7, 1.9.2, ree, ruby-head,
|
339
|
-
rbx and jruby.
|
340
|
-
|
341
|
-
== Contributions
|
342
|
-
|
343
|
-
To fetch & test the library for development, do:
|
344
|
-
|
345
|
-
$ git clone https://github.com/colszowka/simplecov
|
346
|
-
$ cd simplecov
|
347
|
-
$ bundle
|
348
|
-
$ bundle exec rake test && bundle exec cucumber features
|
349
|
-
|
350
|
-
If you wont to contribute, please:
|
351
|
-
|
352
|
-
* Fork the project.
|
353
|
-
* Make your feature addition or bug fix.
|
354
|
-
* Add tests for it. This is important so I don't break it in a future version unintentionally.
|
355
|
-
* Send me a pull request on Github.
|
356
|
-
|
357
|
-
== Copyright
|
358
|
-
|
359
|
-
Copyright (c) 2010-2011 Christoph Olszowka. See LICENSE for details.
|
@@ -1,14 +0,0 @@
|
|
1
|
-
# Temporary fix for JRuby 1.6.0 RC1 wrong round method
|
2
|
-
if defined?(RUBY_ENGINE) and RUBY_ENGINE == 'jruby' and RUBY_VERSION == '1.9.2'
|
3
|
-
class Float
|
4
|
-
alias_method :precisionless_round, :round
|
5
|
-
def round(precision = nil)
|
6
|
-
if precision
|
7
|
-
magnitude = 10.0 ** precision
|
8
|
-
(self * magnitude).round / magnitude
|
9
|
-
else
|
10
|
-
precisionless_round
|
11
|
-
end
|
12
|
-
end
|
13
|
-
end
|
14
|
-
end
|