reek 3.10.2 → 3.11

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.
checksums.yaml CHANGED
@@ -1,7 +1,7 @@
1
1
  ---
2
2
  SHA1:
3
- metadata.gz: a251ceb10b65df518731985aac57a7f73b29961b
4
- data.tar.gz: 9490529cdf278161c31bf009b99bbb39dd9d633f
3
+ metadata.gz: 67870a4dc44b9996f80e3daddb3614cbc9a1ee6d
4
+ data.tar.gz: 8eedb66acfa7d1b874a2806ffd7b6aab69769794
5
5
  SHA512:
6
- metadata.gz: f1a8f22deef9a74aa7eb9938e637372e276b5af8ede419383364579950b4d59d3632bce86b8c023749282bd527fe7e27074f7a18154f8a7356157518c4b690c0
7
- data.tar.gz: c2057985478a62c26b33b6e45db1c0dffc11ede4fa188ce6df4191369b8b5d0aba6d3f7b76f3d91004305f965e67e08b31339e6d9f89c3ca65dc2ad209a1ac76
6
+ metadata.gz: ad6862ed6352640db4ff88fbe718c6116579d257a6c83337dd1603e1a8580686da6895be5b478db0d5ebd4fd3e288c3e29a9e56ae25cc5115053eef8a18540f9
7
+ data.tar.gz: 8e1cc3bd8e0d9f6c00dfa21e2cd2ba6c9706b817c0a6c895d75be07f58f28f2ce9159f20edbceb1d1e9d676869f65b7771119ac339af04cc2ade6c01854ae8b9
@@ -2,6 +2,10 @@
2
2
 
3
3
  ## Unreleased
4
4
 
5
+ ## 3.11 (2016-02-18)
6
+
7
+ * (troessner) Add a --todo cli flag that will generate a todo list.
8
+
5
9
  ## 3.10.2 (2016-02-15)
6
10
 
7
11
  * (troessner) Bump parser to 2.3.0.6 as minimum to fix problems with invalid syntax.
data/README.md CHANGED
@@ -16,7 +16,7 @@ Reek is a tool that examines Ruby classes, modules and methods and reports any
16
16
  [Code Smells](docs/Code-Smells.md) it finds.
17
17
 
18
18
  For an excellent introduction to
19
- [Code Smells](docs/Code-Smells.md) and `Reek` check out [this blog post](https://blog.codeship.com/how-to-find-ruby-code-smells-with-reek/)
19
+ [Code Smells](docs/Code-Smells.md) and Reek check out [this blog post](https://blog.codeship.com/how-to-find-ruby-code-smells-with-reek/)
20
20
  or [that one](https://troessner.wordpress.com/2016/01/01/the-latest-and-greatest-additions-to-reek/). There is also [this talk](https://www.youtube.com/watch?v=ZzqOuHI5MkA) from the RUBYCONF Porto.
21
21
 
22
22
  Install it via rubygems:
@@ -63,7 +63,7 @@ demo.rb -- 8 warnings:
63
63
 
64
64
  ## Supported rubies
65
65
 
66
- `Reek` is officially running on the following MRI rubies:
66
+ Reek is officially running on the following MRI rubies:
67
67
 
68
68
  - 2.0
69
69
  - 2.1
@@ -95,7 +95,7 @@ class Item < ActiveRecord::Base
95
95
  end
96
96
  ```
97
97
 
98
- Running `reek` on this file like this:
98
+ Running Reek on this file like this:
99
99
 
100
100
  ```
101
101
  reek app/models/shopping_cart.rb
@@ -133,13 +133,13 @@ those first when you have a warning that you don't know how to deal with.
133
133
 
134
134
  ## Sources
135
135
 
136
- There are multiple ways you can have `reek` work on sources, the most common one just being
136
+ There are multiple ways you can have Reek work on sources, the most common one just being
137
137
 
138
138
  ```Bash
139
139
  reek lib/
140
140
  ```
141
141
 
142
- If you don't pass any source arguments to `reek` it just takes the current working directory as source.
142
+ If you don't pass any source arguments to Reek it just takes the current working directory as source.
143
143
 
144
144
  So
145
145
 
@@ -153,7 +153,7 @@ is the exact same thing as being explicit:
153
153
  reek .
154
154
  ```
155
155
 
156
- Additionally you can pipe code to `reek` like this:
156
+ Additionally you can pipe code to Reek like this:
157
157
 
158
158
  ```Bash
159
159
  echo "class C; def m; end; end" | reek
@@ -210,7 +210,7 @@ For a summary of those CLI options see [Command-Line Options](docs/Command-Line-
210
210
 
211
211
  Configuring Reek via a configuration file is by far the most powerful way.
212
212
 
213
- There are three ways of passing `reek` a configuration file:
213
+ There are three ways of passing Reek a configuration file:
214
214
 
215
215
  1. Using the CLI `-c` switch (see [_Command-line interface_](#command-line-interface) above)
216
216
  2. Having a file ending with `.reek` either in your current working directory or in a parent directory (more on that later)
@@ -337,6 +337,42 @@ end
337
337
 
338
338
  This is an incredible powerful feature and further explained under [Smell Suppresion](docs/Smell-Suppression.md).
339
339
 
340
+ ### Generating a 'todo' list
341
+
342
+ Integrating tools like Reek into an existing larger codebase can be daunting when you have to fix
343
+ possibly hundreds or thousands of smell warnings first.
344
+ Sure you could manually disable smell warnings like shown above but depending on the size of your
345
+ codebase this might not be an option.
346
+ Fortunately Reek provides a 'todo' flag which you can use to generate a configuration that will
347
+ suppress all smell warnings for the current codebase:
348
+
349
+ ```Bash
350
+ reek --todo lib/
351
+ ```
352
+
353
+ This will create the file '.todo.reek' in your current working directory.
354
+
355
+ You can then use this as your configuration - since your working directory
356
+ probably is your project root in most cases you don't have to tell Reek
357
+ explicitly to use '.todo.reek' because Reek will automatically pick it up
358
+ and use it as configuration file. See [Configuration Loading](#configuration-loading) above.
359
+
360
+ If for whatever reasons you decide to put '.todo.reek' somewhere else where
361
+ Reek won't pick it up automatically you need to tell Reek explicitly to do so
362
+ via:
363
+
364
+ ```Bash
365
+ reek -c whatever/.todo.reek lib/
366
+ ```
367
+
368
+ Note that if you re-run
369
+
370
+ ```Bash
371
+ reek --todo lib/
372
+ ```
373
+
374
+ '.todo.reek' will get overwritten with a possibly updated configuration.
375
+
340
376
  ## Usage
341
377
 
342
378
  Besides the obvious
@@ -386,7 +422,7 @@ If you don't feel like getting your hands dirty with code there are still other
386
422
 
387
423
  ## Output formats
388
424
 
389
- `reek` supports 5 output formats:
425
+ Reek supports 5 output formats:
390
426
 
391
427
  * plain text (default)
392
428
  * HTML (`--format html`)
@@ -429,12 +465,12 @@ Be careful though, Reek does not merge your configuration entries, so if you alr
429
465
 
430
466
  * [overcommit](https://github.com/brigade/overcommit) - a Git commit hook manager with support for
431
467
  Reek
432
- * [ruby-critic](https://github.com/whitesmith/rubycritic) - gem that wraps around static analysis gems such as `reek`, [flay](https://github.com/seattlerb/flay) and [flog](https://github.com/seattlerb/flog)
468
+ * [ruby-critic](https://github.com/whitesmith/rubycritic) - gem that wraps around static analysis gems such as Reek, [flay](https://github.com/seattlerb/flay) and [flog](https://github.com/seattlerb/flog)
433
469
  * [pronto-reek](https://github.com/mmozuras/pronto-reek) - Reek integration for [pronto](https://github.com/mmozuras/pronto)
434
470
 
435
471
  ### Misc
436
472
 
437
- * [Colorful output for `reek`](https://github.com/joenas/preek)
473
+ * [Colorful output for Reek](https://github.com/joenas/preek)
438
474
  (also with [Guard::Preek](https://github.com/joenas/guard-preek))
439
475
 
440
476
  ## Brothers and sisters
@@ -2,7 +2,7 @@
2
2
 
3
3
  ## Introduction
4
4
 
5
- `reek` follows standard Unix convention for passing arguments.
5
+ Reek follows standard Unix convention for passing arguments.
6
6
 
7
7
  Check out
8
8
 
@@ -18,7 +18,7 @@ class Car
18
18
  end
19
19
  ```
20
20
 
21
- `Reek` would emit the following warning:
21
+ Reek would emit the following warning:
22
22
 
23
23
  ```
24
24
  2 warnings:
@@ -32,7 +32,7 @@ end
32
32
 
33
33
  Private methods that are called via dynamic dispatch
34
34
  will trigger a false alarm since detecting something like this is far out of
35
- scope for `Reek`. In this case you can disable this detector via the `exclude`
35
+ scope for Reek. In this case you can disable this detector via the `exclude`
36
36
  configuration option (which is part of the [Basic Smell Options](Basic-Smell-Options.md))
37
37
  for instance like this (an example from `Reek's` own codebase):
38
38
 
@@ -50,7 +50,7 @@ a method scope (like you can see above).
50
50
 
51
51
  ## Known limitations
52
52
 
53
- * Method calls via dynamic dispatch (e.g. via `send`) is something `Reek` (or any other
53
+ * Method calls via dynamic dispatch (e.g. via `send`) is something Reek (or any other
54
54
  static tool for that matter) can not detect.
55
55
  * Method calls via callback like [Rails filters](http://guides.rubyonrails.org/action_controller_overview.html#filters)
56
56
  will trigger this as well, e.g.:
@@ -65,7 +65,7 @@ a method scope (like you can see above).
65
65
  end
66
66
  end
67
67
  ```
68
- * `Reek` works on a per-file base. This means that using something like the [template pattern](https://en.wikipedia.org/wiki/Template_method_pattern)
68
+ * Reek works on a per-file base. This means that using something like the [template pattern](https://en.wikipedia.org/wiki/Template_method_pattern)
69
69
  with private methods will trigger this detector.
70
70
  We do believe though that using private methods to fill out a template in a
71
71
  superclass is not a good idea in general so this probably isn't really a problem
@@ -2,7 +2,7 @@
2
2
 
3
3
  ## Introduction
4
4
 
5
- `Reek`'s `--yaml` option writes on $stdout a YAML dump of the smells found. Each reported smell has a number of standard fields and a number of fields that are specific to the smell's type. The common fields are as follows:
5
+ Reek's `--yaml` option writes on $stdout a YAML dump of the smells found. Each reported smell has a number of standard fields and a number of fields that are specific to the smell's type. The common fields are as follows:
6
6
 
7
7
  | Field | Type | Value |
8
8
  | ---------------|-------------|---------|
@@ -43,6 +43,9 @@ Feature: Reek can be controlled using command-line options
43
43
  -c, --config FILE Read configuration options from FILE
44
44
  --smell SMELL Detect smell SMELL (default: all enabled smells)
45
45
 
46
+ Generate a todo list:
47
+ -t, --todo Generate a todo list
48
+
46
49
  Report format:
47
50
  -f, --format FORMAT Report smells in the given format:
48
51
  html
@@ -0,0 +1,40 @@
1
+ Given(/^a directory 'lib' with one clean file 'clean\.rb' and one dirty file 'dirty\.rb'$/) do
2
+ write_file('lib/clean.rb', <<-EOS.strip_heredoc)
3
+ # clean class for testing purposes
4
+ class Clean
5
+ def super_clean
6
+ puts @janitor.name
7
+ end
8
+ end
9
+ EOS
10
+
11
+ write_file('lib/dirty.rb', <<-EOS.strip_heredoc)
12
+ class Dirty
13
+ def a; end
14
+ def b; end
15
+ end
16
+ EOS
17
+ end
18
+
19
+ Given(/^a configuration file 'config\.reek' that partially masks 'dirty\.rb'$/) do
20
+ write_file('config.reek', <<-EOS.strip_heredoc)
21
+ ---
22
+ IrresponsibleModule:
23
+ exclude:
24
+ - Dirty
25
+ UncommunicativeMethodName:
26
+ exclude:
27
+ - Dirty#b
28
+ EOS
29
+ end
30
+
31
+ Given(/^a directory 'superclean' with one clean file 'clean\.rb'$/) do
32
+ write_file('superclean/clean.rb', <<-EOS.strip_heredoc)
33
+ # clean class for testing purposes
34
+ class Clean
35
+ def super_clean
36
+ puts @janitor.name
37
+ end
38
+ end
39
+ EOS
40
+ end
@@ -0,0 +1,72 @@
1
+ Feature:
2
+
3
+ Write a Reek configuration as a kind of todo list that will prevent Reek
4
+ from reporting smells on the current code.
5
+ This can then be worked on later on.
6
+ The main goal here would be to ease the Reek adoption by allowing developers to:
7
+ - introduce Reek right away (e.g. for CI)
8
+ - exclude the "old" smells from getting reported
9
+ - fix them step by step
10
+ - get rid of the todo file
11
+
12
+ Background:
13
+ Given a directory 'lib' with one clean file 'clean.rb' and one dirty file 'dirty.rb'
14
+ And a directory 'superclean' with one clean file 'clean.rb'
15
+
16
+ Scenario: Generate a proper todo file that disables all found smells
17
+ When I run reek lib
18
+ Then the exit status indicates smells
19
+ And it reports:
20
+ """
21
+ lib/dirty.rb -- 3 warnings:
22
+ [1]:IrresponsibleModule: Dirty has no descriptive comment [https://github.com/troessner/reek/blob/master/docs/Irresponsible-Module.md]
23
+ [2]:UncommunicativeMethodName: Dirty#a has the name 'a' [https://github.com/troessner/reek/blob/master/docs/Uncommunicative-Method-Name.md]
24
+ [3]:UncommunicativeMethodName: Dirty#b has the name 'b' [https://github.com/troessner/reek/blob/master/docs/Uncommunicative-Method-Name.md]
25
+ 3 total warnings
26
+ """
27
+ When I run reek --todo lib
28
+ Then it succeeds
29
+ And a file named ".todo.reek" should exist
30
+ And the file ".todo.reek" should contain:
31
+ """
32
+ ---
33
+ IrresponsibleModule:
34
+ exclude:
35
+ - Dirty
36
+ UncommunicativeMethodName:
37
+ exclude:
38
+ - Dirty#a
39
+ - Dirty#b
40
+ """
41
+ When I run reek -c .todo.reek lib
42
+ Then it succeeds
43
+
44
+ Scenario: Respects an configuration file
45
+ Given a configuration file 'config.reek' that partially masks 'dirty.rb'
46
+ When I run reek -c config.reek --todo lib
47
+ Then it succeeds
48
+ And a file named ".todo.reek" should exist
49
+ And the file ".todo.reek" should contain:
50
+ """
51
+ ---
52
+ UncommunicativeMethodName:
53
+ exclude:
54
+ - Dirty#a
55
+ """
56
+
57
+ Scenario: Print out a helpful message that explains to the user what to do next
58
+ When I run reek --todo lib
59
+ Then it reports:
60
+ """
61
+
62
+ '.todo.reek' generated! You can now use this as a starting point for your configuration.
63
+ """
64
+
65
+ Scenario: Reacts appropiately when there are no smells
66
+ When I run reek --todo superclean/
67
+ Then a file named ".todo.reek" should not exist
68
+ And it reports:
69
+ """
70
+
71
+ '.todo.reek' not generated because there were no smells found!
72
+ """
@@ -1,7 +1,8 @@
1
1
  require_relative 'options'
2
- require_relative 'reek_command'
3
2
  require_relative 'option_interpreter'
4
3
  require_relative '../configuration/app_configuration'
4
+ require_relative 'command/report_command'
5
+ require_relative 'command/todo_list_command'
5
6
 
6
7
  module Reek
7
8
  module CLI
@@ -17,7 +18,7 @@ module Reek
17
18
  @options = configure_options(argv)
18
19
  @status = options.success_exit_code
19
20
  @configuration = configure_app_configuration(options.config_file)
20
- @command = ReekCommand.new(OptionInterpreter.new(options))
21
+ @command = command_class.new(OptionInterpreter.new(options))
21
22
  end
22
23
 
23
24
  def execute
@@ -42,6 +43,10 @@ module Reek
42
43
  $stderr.puts "Error: #{error}"
43
44
  exit Options::DEFAULT_ERROR_EXIT_CODE
44
45
  end
46
+
47
+ def command_class
48
+ options.generate_todo_list ? Command::TodoListCommand : Command::ReportCommand
49
+ end
45
50
  end
46
51
  end
47
52
  end
@@ -0,0 +1,26 @@
1
+ module Reek
2
+ module CLI
3
+ module Command
4
+ #
5
+ # Base class for all commands
6
+ #
7
+ class BaseCommand
8
+ def initialize(options)
9
+ @options = options
10
+ end
11
+
12
+ private
13
+
14
+ attr_reader :options
15
+
16
+ def smell_names
17
+ @smell_names ||= options.smells_to_detect
18
+ end
19
+
20
+ def sources
21
+ @sources ||= options.sources
22
+ end
23
+ end
24
+ end
25
+ end
26
+ end
@@ -0,0 +1,38 @@
1
+ require_relative 'base_command'
2
+ require_relative '../../examiner'
3
+
4
+ module Reek
5
+ module CLI
6
+ module Command
7
+ #
8
+ # A command to collect smells from a set of sources and write them out in
9
+ # text report format.
10
+ #
11
+ class ReportCommand < BaseCommand
12
+ def execute(app)
13
+ populate_reporter_with_smells app
14
+ reporter.show
15
+ result_code
16
+ end
17
+
18
+ private
19
+
20
+ def populate_reporter_with_smells(app)
21
+ sources.each do |source|
22
+ reporter.add_examiner Examiner.new(source,
23
+ smell_names,
24
+ configuration: app.configuration)
25
+ end
26
+ end
27
+
28
+ def result_code
29
+ reporter.smells? ? options.failure_exit_code : options.success_exit_code
30
+ end
31
+
32
+ def reporter
33
+ @reporter ||= options.reporter
34
+ end
35
+ end
36
+ end
37
+ end
38
+ end
@@ -0,0 +1,49 @@
1
+ require_relative 'base_command'
2
+ require_relative '../../examiner'
3
+
4
+ module Reek
5
+ module CLI
6
+ module Command
7
+ #
8
+ # A command to collect smells from a set of sources and writes a configuration
9
+ # file that can serve as a todo list.
10
+ #
11
+ class TodoListCommand < BaseCommand
12
+ FILE_NAME = '.todo.reek'.freeze
13
+
14
+ def execute(app)
15
+ smells = scan_for_smells(app)
16
+ if smells.empty?
17
+ puts "\n'.todo.reek' not generated because "\
18
+ 'there were no smells found!'
19
+ else
20
+ File.write FILE_NAME, groups_for(smells).to_yaml
21
+ puts "\n'.todo.reek' generated! You can now use "\
22
+ 'this as a starting point for your configuration.'
23
+ end
24
+ options.success_exit_code
25
+ end
26
+
27
+ private
28
+
29
+ def scan_for_smells(app)
30
+ sources.map do |source|
31
+ Examiner.new(source,
32
+ smell_names,
33
+ configuration: app.configuration)
34
+ end.map(&:smells).flatten
35
+ end
36
+
37
+ def groups_for(smells)
38
+ @groups ||= begin
39
+ Hash[
40
+ smells.group_by(&:smell_type).map do |smell_type, smells_for_type|
41
+ [smell_type, { 'exclude' => smells_for_type.map(&:context) }]
42
+ end
43
+ ]
44
+ end
45
+ end
46
+ end
47
+ end
48
+ end
49
+ end
@@ -9,7 +9,7 @@ module Reek
9
9
  #
10
10
  # See {file:docs/Command-Line-Options.md} for details.
11
11
  #
12
- # :reek:TooManyInstanceVariables: { max_instance_variables: 9 }
12
+ # :reek:TooManyInstanceVariables: { max_instance_variables: 10 }
13
13
  # :reek:Attribute: { enabled: false }
14
14
  #
15
15
  class Options
@@ -26,18 +26,20 @@ module Reek
26
26
  :show_links,
27
27
  :sorting,
28
28
  :success_exit_code,
29
- :failure_exit_code
29
+ :failure_exit_code,
30
+ :generate_todo_list
30
31
 
31
32
  def initialize(argv = [])
32
- @argv = argv
33
- @parser = OptionParser.new
34
- @report_format = :text
35
- @location_format = :numbers
36
- @show_links = true
37
- @smells_to_detect = []
38
- @colored = color_support?
39
- @success_exit_code = DEFAULT_SUCCESS_EXIT_CODE
40
- @failure_exit_code = DEFAULT_FAILURE_EXIT_CODE
33
+ @argv = argv
34
+ @parser = OptionParser.new
35
+ @report_format = :text
36
+ @location_format = :numbers
37
+ @show_links = true
38
+ @smells_to_detect = []
39
+ @colored = color_support?
40
+ @success_exit_code = DEFAULT_SUCCESS_EXIT_CODE
41
+ @failure_exit_code = DEFAULT_FAILURE_EXIT_CODE
42
+ @generate_todo_list = false
41
43
 
42
44
  set_up_parser
43
45
  end
@@ -55,10 +57,11 @@ module Reek
55
57
  $stdout.tty?
56
58
  end
57
59
 
58
- # :reek:TooManyStatements: { max_statements: 6 }
60
+ # :reek:TooManyStatements: { max_statements: 7 }
59
61
  def set_up_parser
60
62
  set_banner
61
63
  set_configuration_options
64
+ set_generate_todo_list_options
62
65
  set_alternative_formatter_options
63
66
  set_report_formatting_options
64
67
  set_exit_codes
@@ -81,17 +84,6 @@ module Reek
81
84
  EOB
82
85
  end
83
86
 
84
- def set_alternative_formatter_options
85
- parser.separator "\nReport format:"
86
- parser.on(
87
- '-f', '--format FORMAT', [:html, :text, :yaml, :json, :xml, :code_climate],
88
- 'Report smells in the given format:',
89
- ' html', ' text (default)', ' yaml', ' json', ' xml', ' code_climate'
90
- ) do |opt|
91
- self.report_format = opt
92
- end
93
- end
94
-
95
87
  # :reek:TooManyStatements: { max_statements: 6 }
96
88
  def set_configuration_options
97
89
  parser.separator 'Configuration:'
@@ -104,6 +96,24 @@ module Reek
104
96
  end
105
97
  end
106
98
 
99
+ def set_generate_todo_list_options
100
+ parser.separator '\nGenerate a todo list:'
101
+ parser.on('-t', '--todo', 'Generate a todo list') do
102
+ self.generate_todo_list = true
103
+ end
104
+ end
105
+
106
+ def set_alternative_formatter_options
107
+ parser.separator "\nReport format:"
108
+ parser.on(
109
+ '-f', '--format FORMAT', [:html, :text, :yaml, :json, :xml, :code_climate],
110
+ 'Report smells in the given format:',
111
+ ' html', ' text (default)', ' yaml', ' json', ' xml', ' code_climate'
112
+ ) do |opt|
113
+ self.report_format = opt
114
+ end
115
+ end
116
+
107
117
  def set_report_formatting_options
108
118
  parser.separator "\nText format options:"
109
119
  set_up_color_option
@@ -6,6 +6,6 @@ module Reek
6
6
  # @public
7
7
  module Version
8
8
  # @public
9
- STRING = '3.10.2'.freeze
9
+ STRING = '3.11'.freeze
10
10
  end
11
11
  end
@@ -1,6 +1,8 @@
1
1
  require_relative '../../lib/reek/smells'
2
2
  require_relative '../../lib/reek/smells/smell_detector'
3
3
  require_relative '../../lib/reek/smells/smell_warning'
4
+ require_relative '../../lib/reek/cli/option_interpreter'
5
+ require_relative '../../lib/reek/cli/options'
4
6
 
5
7
  FactoryGirl.define do
6
8
  factory :context, class: Reek::Context::CodeContext do
@@ -51,4 +53,14 @@ FactoryGirl.define do
51
53
  parameters: parameters)
52
54
  end
53
55
  end
56
+
57
+ factory :options_interpreter_with_empty_sources, class: Reek::CLI::OptionInterpreter do
58
+ transient do
59
+ options { Reek::CLI::Options.new [] }
60
+ end
61
+
62
+ initialize_with do
63
+ Reek::CLI::OptionInterpreter.new(options)
64
+ end
65
+ end
54
66
  end
@@ -15,17 +15,19 @@ RSpec.describe Reek::CLI::Application do
15
15
  end
16
16
  end
17
17
 
18
- describe '#execute' do
19
- let(:command) { double 'reek_command' }
20
- let(:app) { Reek::CLI::Application.new [] }
18
+ context 'report_command' do
19
+ describe '#execute' do
20
+ let(:command) { double 'reek_command' }
21
+ let(:app) { Reek::CLI::Application.new [] }
21
22
 
22
- before do
23
- allow(Reek::CLI::ReekCommand).to receive(:new).and_return command
24
- end
23
+ before do
24
+ allow(Reek::CLI::Command::ReportCommand).to receive(:new).and_return command
25
+ end
25
26
 
26
- it "returns the command's result code" do
27
- allow(command).to receive(:execute).and_return 'foo'
28
- expect(app.execute).to eq 'foo'
27
+ it "returns the command's result code" do
28
+ allow(command).to receive(:execute).and_return 'foo'
29
+ expect(app.execute).to eq 'foo'
30
+ end
29
31
  end
30
32
  end
31
33
  end
@@ -1,9 +1,9 @@
1
- require_relative '../../spec_helper'
2
- require_lib 'reek/cli/reek_command'
1
+ require_relative '../../../spec_helper'
2
+ require_lib 'reek/cli/command/report_command'
3
3
  require_lib 'reek/cli/options'
4
4
  require_lib 'reek/cli/option_interpreter'
5
5
 
6
- RSpec.describe Reek::CLI::ReekCommand do
6
+ RSpec.describe Reek::CLI::Command::ReportCommand do
7
7
  describe '#execute' do
8
8
  let(:options) { Reek::CLI::Options.new [] }
9
9
  let(:option_interpreter) { Reek::CLI::OptionInterpreter.new(options) }
@@ -0,0 +1,64 @@
1
+ require_relative '../../../spec_helper'
2
+ require_lib 'reek/cli/command/todo_list_command'
3
+ require_lib 'reek/cli/options'
4
+ require_lib 'reek/cli/option_interpreter'
5
+
6
+ RSpec.describe Reek::CLI::Command::TodoListCommand do
7
+ describe '#execute' do
8
+ let(:option_interpreter) { FactoryGirl.build(:options_interpreter_with_empty_sources) }
9
+ let(:app) { double 'app' }
10
+ let(:command) { described_class.new option_interpreter }
11
+
12
+ before do
13
+ $stdout = StringIO.new
14
+ allow(File).to receive(:write)
15
+ end
16
+
17
+ after(:all) do
18
+ $stdout = STDOUT
19
+ end
20
+
21
+ context 'smells found' do
22
+ before do
23
+ smells = [FactoryGirl.build(:smell_warning)]
24
+ allow(command).to receive(:scan_for_smells).and_return(smells)
25
+ end
26
+
27
+ it 'shows a proper message' do
28
+ expected = "\n'.todo.reek' generated! You can now use this as a starting point for your configuration.\n"
29
+ expect { command.execute app }.to output(expected).to_stdout
30
+ end
31
+
32
+ it 'returns a success code' do
33
+ result = command.execute app
34
+ expect(result).to eq(Reek::CLI::Options::DEFAULT_SUCCESS_EXIT_CODE)
35
+ end
36
+ end
37
+
38
+ context 'no smells found' do
39
+ before do
40
+ allow(command).to receive(:scan_for_smells).and_return []
41
+ end
42
+
43
+ it 'shows a proper message' do
44
+ expected = "\n'.todo.reek' not generated because there were no smells found!\n"
45
+ expect { command.execute app }.to output(expected).to_stdout
46
+ end
47
+
48
+ it 'returns a success code' do
49
+ result = command.execute app
50
+ expect(result).to eq Reek::CLI::Options::DEFAULT_SUCCESS_EXIT_CODE
51
+ end
52
+ end
53
+
54
+ describe 'groups_for' do
55
+ let(:command) { described_class.new({}) }
56
+
57
+ it 'returns a proper hash representation of the smells found' do
58
+ smells = [FactoryGirl.build(:smell_warning)]
59
+ expected = { 'FeatureEnvy' => { 'exclude' => ['self'] } }
60
+ expect(command.send(:groups_for, smells)).to eq(expected)
61
+ end
62
+ end
63
+ end
64
+ end
metadata CHANGED
@@ -1,7 +1,7 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: reek
3
3
  version: !ruby/object:Gem::Version
4
- version: 3.10.2
4
+ version: '3.11'
5
5
  platform: ruby
6
6
  authors:
7
7
  - Kevin Rutherford
@@ -11,7 +11,7 @@ authors:
11
11
  autorequire:
12
12
  bindir: bin
13
13
  cert_chain: []
14
- date: 2016-02-15 00:00:00.000000000 Z
14
+ date: 2016-02-18 00:00:00.000000000 Z
15
15
  dependencies:
16
16
  - !ruby/object:Gem::Dependency
17
17
  name: codeclimate-engine-rb
@@ -155,7 +155,9 @@ files:
155
155
  - features/step_definitions/.rubocop.yml
156
156
  - features/step_definitions/reek_steps.rb
157
157
  - features/step_definitions/sample_file_steps.rb
158
+ - features/step_definitions/todo_list_steps.rb
158
159
  - features/support/env.rb
160
+ - features/todo_list.feature
159
161
  - lib/reek.rb
160
162
  - lib/reek/ast/ast_node_class_map.rb
161
163
  - lib/reek/ast/node.rb
@@ -181,11 +183,12 @@ files:
181
183
  - lib/reek/ast/sexp_extensions/when.rb
182
184
  - lib/reek/ast/sexp_extensions/yield.rb
183
185
  - lib/reek/cli/application.rb
184
- - lib/reek/cli/command.rb
186
+ - lib/reek/cli/command/base_command.rb
187
+ - lib/reek/cli/command/report_command.rb
188
+ - lib/reek/cli/command/todo_list_command.rb
185
189
  - lib/reek/cli/input.rb
186
190
  - lib/reek/cli/option_interpreter.rb
187
191
  - lib/reek/cli/options.rb
188
- - lib/reek/cli/reek_command.rb
189
192
  - lib/reek/cli/silencer.rb
190
193
  - lib/reek/cli/warning_collector.rb
191
194
  - lib/reek/code_comment.rb
@@ -271,10 +274,11 @@ files:
271
274
  - spec/reek/ast/reference_collector_spec.rb
272
275
  - spec/reek/ast/sexp_extensions_spec.rb
273
276
  - spec/reek/cli/application_spec.rb
277
+ - spec/reek/cli/command/report_command_spec.rb
278
+ - spec/reek/cli/command/todo_list_command_spec.rb
274
279
  - spec/reek/cli/input_spec.rb
275
280
  - spec/reek/cli/option_interpreter_spec.rb
276
281
  - spec/reek/cli/options_spec.rb
277
- - spec/reek/cli/reek_command_spec.rb
278
282
  - spec/reek/cli/warning_collector_spec.rb
279
283
  - spec/reek/code_comment_spec.rb
280
284
  - spec/reek/configuration/app_configuration_spec.rb
@@ -1,16 +0,0 @@
1
- module Reek
2
- module CLI
3
- #
4
- # Base class for all commands
5
- #
6
- class Command
7
- def initialize(options)
8
- @options = options
9
- end
10
-
11
- private
12
-
13
- attr_reader :options
14
- end
15
- end
16
- end
@@ -1,34 +0,0 @@
1
- require_relative 'command'
2
- require_relative '../examiner'
3
-
4
- module Reek
5
- module CLI
6
- #
7
- # A command to collect smells from a set of sources and write them out in
8
- # text report format.
9
- #
10
- class ReekCommand < Command
11
- def execute(app)
12
- options.sources.each do |source|
13
- reporter.add_examiner Examiner.new(source, smell_names, configuration: app.configuration)
14
- end
15
- reporter.show
16
- result_code
17
- end
18
-
19
- private
20
-
21
- def result_code
22
- reporter.smells? ? options.failure_exit_code : options.success_exit_code
23
- end
24
-
25
- def reporter
26
- @reporter ||= options.reporter
27
- end
28
-
29
- def smell_names
30
- @smell_names ||= options.smells_to_detect
31
- end
32
- end
33
- end
34
- end