reek 1.5.1 → 1.6.0

Sign up to get free protection for your applications and to get access to all the features.
Files changed (120) hide show
  1. checksums.yaml +4 -4
  2. data/CHANGELOG +9 -0
  3. data/README.md +54 -5
  4. data/Rakefile +1 -1
  5. data/features/command_line_interface/smell_selection.feature +4 -4
  6. data/features/command_line_interface/smells_count.feature +9 -8
  7. data/features/configuration_files/masking_smells.feature +16 -51
  8. data/features/configuration_files/overrides_defaults.feature +1 -1
  9. data/features/rake_task/rake_task.feature +14 -14
  10. data/features/reports/reports.feature +21 -19
  11. data/features/reports/yaml.feature +35 -63
  12. data/features/samples.feature +55 -54
  13. data/features/support/env.rb +8 -1
  14. data/lib/reek/cli/application.rb +22 -7
  15. data/lib/reek/cli/command.rb +4 -2
  16. data/lib/reek/cli/help_command.rb +1 -1
  17. data/lib/reek/cli/options.rb +3 -3
  18. data/lib/reek/cli/reek_command.rb +4 -8
  19. data/lib/reek/cli/report/formatter.rb +8 -5
  20. data/lib/reek/cli/report/report.rb +6 -5
  21. data/lib/reek/cli/report/strategy.rb +3 -2
  22. data/lib/reek/cli/version_command.rb +1 -1
  23. data/lib/reek/configuration/app_configuration.rb +75 -0
  24. data/lib/reek/configuration/configuration_file_finder.rb +56 -0
  25. data/lib/reek/core/code_context.rb +2 -6
  26. data/lib/reek/core/module_context.rb +4 -0
  27. data/lib/reek/core/smell_repository.rb +5 -3
  28. data/lib/reek/core/sniffer.rb +12 -8
  29. data/lib/reek/examiner.rb +7 -6
  30. data/lib/reek/rake/task.rb +10 -12
  31. data/lib/reek/smell_warning.rb +25 -43
  32. data/lib/reek/smells/attribute.rb +7 -12
  33. data/lib/reek/smells/boolean_parameter.rb +9 -9
  34. data/lib/reek/smells/class_variable.rb +7 -13
  35. data/lib/reek/smells/control_parameter.rb +8 -11
  36. data/lib/reek/smells/data_clump.rb +16 -21
  37. data/lib/reek/smells/duplicate_method_call.rb +11 -18
  38. data/lib/reek/smells/feature_envy.rb +8 -8
  39. data/lib/reek/smells/irresponsible_module.rb +6 -10
  40. data/lib/reek/smells/long_parameter_list.rb +7 -15
  41. data/lib/reek/smells/long_yield_list.rb +13 -15
  42. data/lib/reek/smells/module_initialize.rb +4 -7
  43. data/lib/reek/smells/nested_iterators.rb +6 -13
  44. data/lib/reek/smells/nil_check.rb +9 -7
  45. data/lib/reek/smells/prima_donna_method.rb +5 -7
  46. data/lib/reek/smells/repeated_conditional.rb +19 -15
  47. data/lib/reek/smells/smell_detector.rb +21 -1
  48. data/lib/reek/smells/too_many_instance_variables.rb +9 -16
  49. data/lib/reek/smells/too_many_methods.rb +10 -17
  50. data/lib/reek/smells/too_many_statements.rb +14 -14
  51. data/lib/reek/smells/uncommunicative_method_name.rb +9 -10
  52. data/lib/reek/smells/uncommunicative_module_name.rb +9 -10
  53. data/lib/reek/smells/uncommunicative_parameter_name.rb +9 -9
  54. data/lib/reek/smells/uncommunicative_variable_name.rb +9 -9
  55. data/lib/reek/smells/unused_parameters.rb +8 -20
  56. data/lib/reek/smells/utility_function.rb +12 -10
  57. data/lib/reek/source.rb +0 -1
  58. data/lib/reek/source/code_comment.rb +1 -0
  59. data/lib/reek/source/source_code.rb +3 -13
  60. data/lib/reek/source/source_file.rb +0 -14
  61. data/lib/reek/source/source_repository.rb +7 -0
  62. data/lib/reek/spec/should_reek_of.rb +3 -3
  63. data/lib/reek/spec/should_reek_only_of.rb +2 -2
  64. data/lib/reek/version.rb +1 -1
  65. data/reek.gemspec +4 -2
  66. data/spec/factories/factories.rb +32 -0
  67. data/spec/matchers/smell_of_matcher.rb +3 -2
  68. data/spec/reek/cli/report_spec.rb +2 -1
  69. data/spec/reek/configuration/app_configuration_spec.rb +67 -0
  70. data/spec/reek/configuration/configuration_file_finder_spec.rb +35 -0
  71. data/spec/reek/core/code_context_spec.rb +1 -1
  72. data/spec/reek/core/module_context_spec.rb +5 -1
  73. data/spec/reek/core/smell_configuration_spec.rb +21 -13
  74. data/spec/reek/core/warning_collector_spec.rb +4 -1
  75. data/spec/reek/examiner_spec.rb +19 -1
  76. data/spec/reek/smell_warning_spec.rb +42 -36
  77. data/spec/reek/smells/attribute_spec.rb +6 -2
  78. data/spec/reek/smells/boolean_parameter_spec.rb +11 -12
  79. data/spec/reek/smells/class_variable_spec.rb +16 -6
  80. data/spec/reek/smells/control_parameter_spec.rb +17 -19
  81. data/spec/reek/smells/data_clump_spec.rb +25 -15
  82. data/spec/reek/smells/duplicate_method_call_spec.rb +18 -12
  83. data/spec/reek/smells/feature_envy_spec.rb +29 -10
  84. data/spec/reek/smells/irresponsible_module_spec.rb +7 -7
  85. data/spec/reek/smells/long_parameter_list_spec.rb +16 -10
  86. data/spec/reek/smells/long_yield_list_spec.rb +2 -2
  87. data/spec/reek/smells/module_initialize_spec.rb +26 -0
  88. data/spec/reek/smells/nested_iterators_spec.rb +21 -10
  89. data/spec/reek/smells/nil_check_spec.rb +0 -2
  90. data/spec/reek/smells/prima_donna_method_spec.rb +3 -3
  91. data/spec/reek/smells/repeated_conditional_spec.rb +0 -26
  92. data/spec/reek/smells/smell_detector_shared.rb +4 -4
  93. data/spec/reek/smells/too_many_instance_variables_spec.rb +3 -3
  94. data/spec/reek/smells/too_many_methods_spec.rb +16 -11
  95. data/spec/reek/smells/too_many_statements_spec.rb +55 -18
  96. data/spec/reek/smells/uncommunicative_method_name_spec.rb +3 -2
  97. data/spec/reek/smells/uncommunicative_module_name_spec.rb +5 -5
  98. data/spec/reek/smells/uncommunicative_parameter_name_spec.rb +4 -4
  99. data/spec/reek/smells/uncommunicative_variable_name_spec.rb +28 -21
  100. data/spec/reek/smells/unused_parameters_spec.rb +3 -5
  101. data/spec/reek/smells/utility_function_spec.rb +2 -1
  102. data/spec/reek/source/code_comment_spec.rb +7 -2
  103. data/spec/reek/source/reference_collector_spec.rb +0 -1
  104. data/spec/reek/source/sexp_extensions_spec.rb +0 -15
  105. data/spec/reek/source/source_code_spec.rb +13 -1
  106. data/spec/reek/spec/should_reek_only_of_spec.rb +22 -10
  107. data/spec/reek/spec/should_reek_spec.rb +6 -2
  108. data/spec/samples/minimal_smelly_and_masked/config.reek +7 -0
  109. data/spec/samples/minimal_smelly_and_masked/minimal_dirty.rb +4 -0
  110. data/spec/samples/simple_configuration.reek +5 -0
  111. data/spec/samples/standard_smelly/dirty.rb +8 -0
  112. data/spec/samples/standard_smelly/minimal_dirty.rb +4 -0
  113. data/spec/spec_helper.rb +20 -0
  114. data/tasks/develop.rake +1 -1
  115. data/tasks/rubocop.rake +5 -0
  116. metadata +41 -6
  117. data/lib/reek/config_file_exception.rb +0 -7
  118. data/lib/reek/smell_description.rb +0 -26
  119. data/lib/reek/source/config_file.rb +0 -88
  120. data/spec/reek/smell_description_spec.rb +0 -43
@@ -25,7 +25,7 @@ describe UncommunicativeParameterName do
25
25
  it "reports parameter's name" do
26
26
  src = "def #{host}help(x) basics(x) end"
27
27
  expect(src).to smell_of(UncommunicativeParameterName,
28
- UncommunicativeParameterName::PARAMETER_NAME_KEY => 'x')
28
+ name: 'x')
29
29
  end
30
30
 
31
31
  it 'does not report unused parameters' do
@@ -41,13 +41,13 @@ describe UncommunicativeParameterName do
41
41
  it 'reports names of the form "x2"' do
42
42
  src = "def #{host}help(x2) basics(x2) end"
43
43
  expect(src).to smell_of(UncommunicativeParameterName,
44
- UncommunicativeParameterName::PARAMETER_NAME_KEY => 'x2')
44
+ name: 'x2')
45
45
  end
46
46
 
47
47
  it 'reports long name ending in a number' do
48
48
  src = "def #{host}help(param2) basics(param2) end"
49
49
  expect(src).to smell_of(UncommunicativeParameterName,
50
- UncommunicativeParameterName::PARAMETER_NAME_KEY => 'param2')
50
+ name: 'param2')
51
51
  end
52
52
 
53
53
  it 'does not report unused anonymous parameter' do
@@ -78,7 +78,7 @@ describe UncommunicativeParameterName do
78
78
  it_should_behave_like 'common fields set correctly'
79
79
 
80
80
  it 'reports the correct values' do
81
- expect(@warning.smell[UncommunicativeParameterName::PARAMETER_NAME_KEY]).to eq('bad2')
81
+ expect(@warning.parameters[:name]).to eq('bad2')
82
82
  expect(@warning.lines).to eq([1])
83
83
  end
84
84
  end
@@ -28,41 +28,49 @@ describe UncommunicativeVariableName do
28
28
 
29
29
  context 'local variable name' do
30
30
  it 'does not report one-word variable name' do
31
- expect('def help(fred) simple = jim(45) end').not_to smell_of(UncommunicativeVariableName)
31
+ expect('def help(fred) simple = jim(45) end').
32
+ not_to smell_of(UncommunicativeVariableName)
32
33
  end
34
+
33
35
  it 'does not report single underscore as a variable name' do
34
36
  expect('def help(fred) _ = jim(45) end').not_to smell_of(UncommunicativeVariableName)
35
37
  end
38
+
36
39
  it 'reports one-letter variable name' do
37
40
  src = 'def simple(fred) x = jim(45) end'
38
41
  expect(src).to smell_of(UncommunicativeVariableName,
39
- UncommunicativeVariableName::VARIABLE_NAME_KEY => 'x')
42
+ name: 'x')
40
43
  end
44
+
41
45
  it 'reports name of the form "x2"' do
42
46
  src = 'def simple(fred) x2 = jim(45) end'
43
47
  expect(src).to smell_of(UncommunicativeVariableName,
44
- UncommunicativeVariableName::VARIABLE_NAME_KEY => 'x2')
48
+ name: 'x2')
45
49
  end
50
+
46
51
  it 'reports long name ending in a number' do
47
52
  @bad_var = 'var123'
48
53
  src = "def simple(fred) #{@bad_var} = jim(45) end"
49
54
  expect(src).to smell_of(UncommunicativeVariableName,
50
- UncommunicativeVariableName::VARIABLE_NAME_KEY => @bad_var)
55
+ name: @bad_var)
51
56
  end
57
+
52
58
  it 'reports variable name only once' do
53
59
  src = 'def simple(fred) x = jim(45); x = y end'
54
60
  ctx = CodeContext.new(nil, src.to_reek_source.syntax_tree)
55
61
  smells = @detector.examine_context(ctx)
56
62
  expect(smells.length).to eq(1)
57
- expect(smells[0].subclass).to eq(UncommunicativeVariableName::SMELL_SUBCLASS)
58
- expect(smells[0].smell[UncommunicativeVariableName::VARIABLE_NAME_KEY]).to eq('x')
63
+ expect(smells[0].smell_type).to eq(UncommunicativeVariableName.smell_type)
64
+ expect(smells[0].parameters[:name]).to eq('x')
59
65
  expect(smells[0].lines).to eq([1, 1])
60
66
  end
67
+
61
68
  it 'reports a bad name inside a block' do
62
69
  src = 'def clean(text) text.each { q2 = 3 } end'
63
70
  expect(src).to smell_of(UncommunicativeVariableName,
64
- UncommunicativeVariableName::VARIABLE_NAME_KEY => 'q2')
71
+ name: 'q2')
65
72
  end
73
+
66
74
  it 'reports variable name outside any method' do
67
75
  expect('class Simple; x = jim(45); end').to reek_of(:UncommunicativeVariableName, /x/)
68
76
  end
@@ -78,7 +86,7 @@ describe UncommunicativeVariableName do
78
86
  end
79
87
  EOS
80
88
  expect(src).to smell_of(UncommunicativeVariableName,
81
- UncommunicativeVariableName::VARIABLE_NAME_KEY => 'x')
89
+ name: 'x')
82
90
  end
83
91
 
84
92
  it 'reports all relevant block parameters' do
@@ -88,8 +96,8 @@ EOS
88
96
  end
89
97
  EOS
90
98
  expect(src).to smell_of(UncommunicativeVariableName,
91
- { UncommunicativeVariableName::VARIABLE_NAME_KEY => 'x' },
92
- UncommunicativeVariableName::VARIABLE_NAME_KEY => 'y')
99
+ { name: 'x' },
100
+ { name: 'y' })
93
101
  end
94
102
 
95
103
  it 'reports block parameters used outside of methods' do
@@ -99,7 +107,7 @@ EOS
99
107
  end
100
108
  EOS
101
109
  expect(src).to smell_of(UncommunicativeVariableName,
102
- UncommunicativeVariableName::VARIABLE_NAME_KEY => 'x')
110
+ name: 'x')
103
111
  end
104
112
 
105
113
  it 'reports splatted block parameters correctly' do
@@ -109,7 +117,7 @@ EOS
109
117
  end
110
118
  EOS
111
119
  expect(src).to smell_of(UncommunicativeVariableName,
112
- UncommunicativeVariableName::VARIABLE_NAME_KEY => 'y')
120
+ name: 'y')
113
121
  end
114
122
 
115
123
  it 'reports nested block parameters' do
@@ -119,8 +127,8 @@ EOS
119
127
  end
120
128
  EOS
121
129
  expect(src).to smell_of(UncommunicativeVariableName,
122
- { UncommunicativeVariableName::VARIABLE_NAME_KEY => 'x' },
123
- UncommunicativeVariableName::VARIABLE_NAME_KEY => 'y')
130
+ { name: 'x' },
131
+ { name: 'y' })
124
132
  end
125
133
 
126
134
  it 'reports splatted nested block parameters' do
@@ -130,8 +138,8 @@ EOS
130
138
  end
131
139
  EOS
132
140
  expect(src).to smell_of(UncommunicativeVariableName,
133
- { UncommunicativeVariableName::VARIABLE_NAME_KEY => 'x' },
134
- UncommunicativeVariableName::VARIABLE_NAME_KEY => 'y')
141
+ { name: 'x' },
142
+ { name: 'y' })
135
143
  end
136
144
 
137
145
  it 'reports deeply nested block parameters' do
@@ -141,11 +149,10 @@ EOS
141
149
  end
142
150
  EOS
143
151
  expect(src).to smell_of(UncommunicativeVariableName,
144
- { UncommunicativeVariableName::VARIABLE_NAME_KEY => 'x' },
145
- { UncommunicativeVariableName::VARIABLE_NAME_KEY => 'y' },
146
- UncommunicativeVariableName::VARIABLE_NAME_KEY => 'z')
152
+ { name: 'x' },
153
+ { name: 'y' },
154
+ { name: 'z' })
147
155
  end
148
-
149
156
  end
150
157
 
151
158
  context 'when a smell is reported' do
@@ -167,7 +174,7 @@ EOS
167
174
  it_should_behave_like 'common fields set correctly'
168
175
 
169
176
  it 'reports the correct values' do
170
- expect(@warning.smell['variable_name']).to eq('x2')
177
+ expect(@warning.parameters[:name]).to eq('x2')
171
178
  expect(@warning.lines).to eq([3, 5])
172
179
  end
173
180
  end
@@ -6,9 +6,7 @@ include Reek
6
6
  include Reek::Smells
7
7
 
8
8
  describe UnusedParameters do
9
-
10
9
  context 'for methods' do
11
-
12
10
  it 'reports nothing for no parameters' do
13
11
  expect('def simple; true end').not_to smell_of(UnusedParameters)
14
12
  end
@@ -20,14 +18,14 @@ describe UnusedParameters do
20
18
  it 'reports for 1 used and 2 unused parameter' do
21
19
  src = 'def simple(num,sum,denum); sum end'
22
20
  expect(src).to smell_of(UnusedParameters,
23
- { UnusedParameters::PARAMETER_KEY => 'num' },
24
- UnusedParameters::PARAMETER_KEY => 'denum')
21
+ { name: 'num' },
22
+ { name: 'denum' })
25
23
  end
26
24
 
27
25
  it 'reports for 3 used and 1 unused parameter' do
28
26
  src = 'def simple(num,sum,denum,quotient); num + denum + sum end'
29
27
  expect(src).to smell_of(UnusedParameters,
30
- UnusedParameters::PARAMETER_KEY => 'quotient')
28
+ name: 'quotient')
31
29
  end
32
30
 
33
31
  it 'reports nothing for used splatted parameter' do
@@ -59,7 +59,8 @@ describe UtilityFunction do
59
59
 
60
60
  context 'with two or more calls' do
61
61
  it 'reports two calls' do
62
- expect('def simple(arga) arga.to_s + arga.to_i end').to reek_of(:UtilityFunction, /simple/)
62
+ src = 'def simple(arga) arga.to_s + arga.to_i end'
63
+ expect(src).to reek_of(:UtilityFunction, /simple/)
63
64
  end
64
65
  it 'counts a local call in a param initializer' do
65
66
  expect('def simple(arga=local) arga.to_s end').not_to reek_of(:UtilityFunction)
@@ -45,7 +45,10 @@ describe CodeComment do
45
45
  expect(config['NestedIterators']['enabled']).to be_truthy
46
46
  end
47
47
  it 'parses multiple hashed options' do
48
- config = CodeComment.new("# :reek:Duplication: { enabled: false }\n:reek:nested_iterators: { enabled: true }").config
48
+ config = CodeComment.new('
49
+ # :reek:Duplication: { enabled: false }
50
+ :reek:nested_iterators: { enabled: true }
51
+ ').config
49
52
  expect(config).to include('Duplication', 'NestedIterators')
50
53
  expect(config['Duplication']).to include('enabled')
51
54
  expect(config['Duplication']['enabled']).to be_falsey
@@ -53,7 +56,9 @@ describe CodeComment do
53
56
  expect(config['NestedIterators']['enabled']).to be_truthy
54
57
  end
55
58
  it 'parses multiple hashed options on the same line' do
56
- config = CodeComment.new('# :reek:Duplication: { enabled: false } and :reek:nested_iterators: { enabled: true }').config
59
+ config = CodeComment.new('
60
+ #:reek:Duplication: { enabled: false } and :reek:nested_iterators: { enabled: true }
61
+ ').config
57
62
  expect(config).to include('Duplication', 'NestedIterators')
58
63
  expect(config['Duplication']).to include('enabled')
59
64
  expect(config['Duplication']['enabled']).to be_falsey
@@ -4,7 +4,6 @@ require 'reek/source/reference_collector'
4
4
  include Reek::Source
5
5
 
6
6
  describe ReferenceCollector do
7
-
8
7
  context 'counting refs to self' do
9
8
  def refs_to_self(src)
10
9
  ReferenceCollector.new(src.to_reek_source.syntax_tree).num_refs_to_self
@@ -24,7 +24,6 @@ describe SexpExtensions::DefNode do
24
24
  it 'includes no marker in its full name with empty outer scope' do
25
25
  expect(@node.full_name('')).to eq 'hello'
26
26
  end
27
-
28
27
  end
29
28
 
30
29
  context 'with 1 parameter' do
@@ -48,7 +47,6 @@ describe SexpExtensions::DefNode do
48
47
  it 'includes no marker in its full name with empty outer scope' do
49
48
  expect(@node.full_name('')).to eq 'hello'
50
49
  end
51
-
52
50
  end
53
51
 
54
52
  context 'with a block parameter' do
@@ -74,7 +72,6 @@ describe SexpExtensions::DefNode do
74
72
  it 'includes no marker in its full name with empty outer scope' do
75
73
  expect(@node.full_name('')).to eq 'hello'
76
74
  end
77
-
78
75
  end
79
76
 
80
77
  context 'with 1 defaulted parameter' do
@@ -99,7 +96,6 @@ describe SexpExtensions::DefNode do
99
96
  it 'includes no marker in its full name with empty outer scope' do
100
97
  expect(@node.full_name('')).to eq 'hello'
101
98
  end
102
-
103
99
  end
104
100
 
105
101
  context 'with a body with 2 statements' do
@@ -160,7 +156,6 @@ describe SexpExtensions::DefsNode do
160
156
  it 'includes no marker in its full name with empty outer scope' do
161
157
  expect(@node.full_name('')).to eq 'obj.hello'
162
158
  end
163
-
164
159
  end
165
160
 
166
161
  context 'with 1 parameter' do
@@ -184,7 +179,6 @@ describe SexpExtensions::DefsNode do
184
179
  it 'includes no marker in its full name with empty outer scope' do
185
180
  expect(@node.full_name('')).to eq 'obj.hello'
186
181
  end
187
-
188
182
  end
189
183
 
190
184
  context 'with a block' do
@@ -210,7 +204,6 @@ describe SexpExtensions::DefsNode do
210
204
  it 'includes no marker in its full name with empty outer scope' do
211
205
  expect(@node.full_name('')).to eq 'obj.hello'
212
206
  end
213
-
214
207
  end
215
208
 
216
209
  context 'with 1 defaulted parameter' do
@@ -235,7 +228,6 @@ describe SexpExtensions::DefsNode do
235
228
  it 'includes no marker in its full name with empty outer scope' do
236
229
  expect(@node.full_name('')).to eq 'obj.hello'
237
230
  end
238
-
239
231
  end
240
232
 
241
233
  context 'with a body with 2 statements' do
@@ -254,9 +246,7 @@ describe SexpExtensions::DefsNode do
254
246
  b = @node.body
255
247
  expect(b.class.included_modules.first).to eq SexpNode
256
248
  end
257
-
258
249
  end
259
-
260
250
  end
261
251
 
262
252
  describe SexpExtensions::SendNode do
@@ -268,7 +258,6 @@ describe SexpExtensions::SendNode do
268
258
  it 'has no argument names' do
269
259
  expect(@node.arg_names).to eq []
270
260
  end
271
-
272
261
  end
273
262
 
274
263
  context 'with 1 literal parameter' do
@@ -279,7 +268,6 @@ describe SexpExtensions::SendNode do
279
268
  it 'has 1 argument name' do
280
269
  expect(@node.arg_names).to eq [:param]
281
270
  end
282
-
283
271
  end
284
272
 
285
273
  context 'with 2 literal parameters' do
@@ -290,9 +278,7 @@ describe SexpExtensions::SendNode do
290
278
  it 'has 2 argument names' do
291
279
  expect(@node.arg_names).to eq [:x, :y]
292
280
  end
293
-
294
281
  end
295
-
296
282
  end
297
283
 
298
284
  describe SexpExtensions::BlockNode do
@@ -304,7 +290,6 @@ describe SexpExtensions::BlockNode do
304
290
  it 'has no parameter names' do
305
291
  expect(@node.parameter_names).to eq []
306
292
  end
307
-
308
293
  end
309
294
 
310
295
  context 'with 1 parameter' do
@@ -11,6 +11,18 @@ describe SourceCode do
11
11
  result = source_code.syntax_tree
12
12
  expect(result.comments).to eq "# this is\n# a comment"
13
13
  end
14
+
15
+ it 'cleanly processes empty source' do
16
+ source_code = SourceCode.new('', '(string)')
17
+ result = source_code.syntax_tree
18
+ expect(result).to be_nil
19
+ end
20
+
21
+ it 'cleanly processes empty source with comments' do
22
+ source_code = SourceCode.new("# this is\n# a comment\n", '(string)')
23
+ result = source_code.syntax_tree
24
+ expect(result).to be_nil
25
+ end
14
26
  end
15
27
 
16
28
  context 'when the parser fails' do
@@ -31,7 +43,7 @@ describe SourceCode do
31
43
  end
32
44
 
33
45
  it 'returns an empty syntax tree' do
34
- expect(src.syntax_tree).to eq(s(:empty))
46
+ expect(src.syntax_tree).to be_nil
35
47
  end
36
48
 
37
49
  it 'records the syntax error' do
@@ -6,9 +6,9 @@ include Reek::Spec
6
6
 
7
7
  describe ShouldReekOnlyOf do
8
8
  before :each do
9
- @expected_smell_class = :NestedIterators
9
+ @expected_smell_type = :NestedIterators
10
10
  @expected_context_name = 'SmellyClass#big_method'
11
- @matcher = ShouldReekOnlyOf.new(@expected_smell_class, [/#{@expected_context_name}/])
11
+ @matcher = ShouldReekOnlyOf.new(@expected_smell_type, [/#{@expected_context_name}/])
12
12
  @examiner = double('examiner').as_null_object
13
13
  expect(@examiner).to receive(:smells) { smells }
14
14
  @match = @matcher.matches_examiner?(@examiner)
@@ -27,7 +27,7 @@ describe ShouldReekOnlyOf do
27
27
  expect(@matcher.failure_message).to match(@source)
28
28
  end
29
29
  it 'reports the expected smell class' do
30
- expect(@matcher.failure_message).to match(@expected_smell_class.to_s)
30
+ expect(@matcher.failure_message).to match(@expected_smell_type.to_s)
31
31
  end
32
32
  end
33
33
  end
@@ -41,18 +41,23 @@ describe ShouldReekOnlyOf do
41
41
  end
42
42
 
43
43
  context 'with 1 non-matching smell' do
44
+ let(:control_couple_detector) { build(:smell_detector, smell_type: 'ControlParameter') }
45
+
44
46
  def smells
45
- [SmellWarning.new('ControlCouple', 'context', [1], 'any old message')]
47
+ [build(:smell_warning, smell_detector: control_couple_detector)]
46
48
  end
47
49
 
48
50
  it_should_behave_like 'no match'
49
51
  end
50
52
 
51
53
  context 'with 2 non-matching smells' do
54
+ let(:control_couple_detector) { build(:smell_detector, smell_type: 'ControlParameter') }
55
+ let(:feature_envy_detector) { build(:smell_detector, smell_type: 'FeatureEnvy') }
56
+
52
57
  def smells
53
58
  [
54
- SmellWarning.new('ControlCouple', 'context', [1], 'any old message'),
55
- SmellWarning.new('FeatureEnvy', 'context', [1], 'any old message')
59
+ build(:smell_warning, smell_detector: control_couple_detector),
60
+ build(:smell_warning, smell_detector: feature_envy_detector)
56
61
  ]
57
62
  end
58
63
 
@@ -60,10 +65,14 @@ describe ShouldReekOnlyOf do
60
65
  end
61
66
 
62
67
  context 'with 1 non-matching and 1 matching smell' do
68
+ let(:control_couple_detector) { build(:smell_detector, smell_type: 'ControlParameter') }
69
+
63
70
  def smells
71
+ detector = build(:smell_detector, smell_type: @expected_smell_type.to_s)
64
72
  [
65
- SmellWarning.new('ControlCouple', 'context', [1], 'any old message'),
66
- SmellWarning.new(@expected_smell_class.to_s, 'context', [1], "message mentioning #{@expected_context_name}")
73
+ build(:smell_warning, smell_detector: control_couple_detector),
74
+ build(:smell_warning, smell_detector: detector,
75
+ message: "message mentioning #{@expected_context_name}")
67
76
  ]
68
77
  end
69
78
 
@@ -72,13 +81,16 @@ describe ShouldReekOnlyOf do
72
81
 
73
82
  context 'with 1 matching smell' do
74
83
  def smells
75
- [SmellWarning.new(@expected_smell_class.to_s, nil, [1], "message mentioning #{@expected_context_name}")]
84
+ detector = build(:smell_detector, smell_type: @expected_smell_type.to_s)
85
+
86
+ [build(:smell_warning, smell_detector: detector,
87
+ message: "message mentioning #{@expected_context_name}")]
76
88
  end
77
89
  it 'matches' do
78
90
  expect(@match).to be_truthy
79
91
  end
80
92
  it 'reports the expected smell when no match was expected' do
81
- expect(@matcher.failure_message_when_negated).to match(@expected_smell_class.to_s)
93
+ expect(@matcher.failure_message_when_negated).to match(@expected_smell_type.to_s)
82
94
  end
83
95
  it 'reports the source when no match was expected' do
84
96
  source = 'the_path/to_a/source_file.rb'