reek 4.6.0 → 5.0.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (294) hide show
  1. checksums.yaml +4 -4
  2. data/.codeclimate.yml +17 -12
  3. data/.rubocop.yml +79 -26
  4. data/.simplecov +1 -0
  5. data/.travis.yml +3 -9
  6. data/.yardopts +1 -1
  7. data/CHANGELOG.md +76 -0
  8. data/CONTRIBUTING.md +1 -1
  9. data/Gemfile +5 -5
  10. data/README.md +138 -107
  11. data/Rakefile +16 -3
  12. data/bin/code_climate_reek +1 -0
  13. data/bin/reek +2 -3
  14. data/docs/API.md +2 -9
  15. data/docs/Basic-Smell-Options.md +51 -11
  16. data/docs/Code-Smells.md +1 -1
  17. data/docs/Command-Line-Options.md +14 -4
  18. data/docs/Duplicate-Method-Call.md +49 -1
  19. data/docs/Feature-Envy.md +44 -0
  20. data/docs/How-To-Write-New-Detectors.md +7 -7
  21. data/docs/Instance-Variable-Assumption.md +1 -1
  22. data/docs/{Prima-Donna-Method.md → Missing-Safe-Method.md} +11 -9
  23. data/docs/Rake-Task.md +1 -1
  24. data/docs/Reek-4-to-Reek-5-migration.md +193 -0
  25. data/docs/Reek-Driven-Development.md +1 -1
  26. data/docs/Uncommunicative-Method-Name.md +45 -6
  27. data/docs/Uncommunicative-Module-Name.md +49 -7
  28. data/docs/Uncommunicative-Parameter-Name.md +43 -5
  29. data/docs/Uncommunicative-Variable-Name.md +73 -2
  30. data/docs/Unused-Private-Method.md +3 -3
  31. data/docs/defaults.reek.yml +129 -0
  32. data/docs/yard_plugin.rb +1 -0
  33. data/features/command_line_interface/basic_usage.feature +2 -2
  34. data/features/command_line_interface/options.feature +46 -4
  35. data/features/command_line_interface/show_progress.feature +4 -4
  36. data/features/command_line_interface/smell_selection.feature +1 -1
  37. data/features/command_line_interface/smells_count.feature +6 -6
  38. data/features/command_line_interface/stdin.feature +31 -5
  39. data/features/configuration_files/accept_setting.feature +45 -28
  40. data/features/configuration_files/directory_specific_directives.feature +80 -75
  41. data/features/configuration_files/exclude_directives.feature +11 -10
  42. data/features/configuration_files/exclude_paths_directives.feature +4 -4
  43. data/features/configuration_files/masking_smells.feature +38 -9
  44. data/features/configuration_files/mix_accept_reject_setting.feature +31 -28
  45. data/features/configuration_files/reject_setting.feature +52 -41
  46. data/features/configuration_files/schema_validation.feature +59 -0
  47. data/features/configuration_files/unused_private_method.feature +18 -16
  48. data/features/configuration_loading.feature +53 -10
  49. data/features/configuration_via_source_comments/erroneous_source_comments.feature +3 -3
  50. data/features/configuration_via_source_comments/well_formed_source_comments.feature +2 -2
  51. data/features/locales.feature +32 -0
  52. data/features/rake_task/rake_task.feature +58 -18
  53. data/features/reports/codeclimate.feature +59 -0
  54. data/features/reports/json.feature +3 -3
  55. data/features/reports/reports.feature +34 -34
  56. data/features/reports/yaml.feature +3 -3
  57. data/features/rspec_matcher.feature +40 -0
  58. data/features/samples.feature +287 -287
  59. data/features/step_definitions/reek_steps.rb +14 -2
  60. data/features/step_definitions/sample_file_steps.rb +9 -4
  61. data/features/support/env.rb +2 -11
  62. data/features/todo_list.feature +26 -23
  63. data/lib/reek/ast/ast_node_class_map.rb +1 -0
  64. data/lib/reek/ast/builder.rb +16 -0
  65. data/lib/reek/ast/node.rb +50 -58
  66. data/lib/reek/ast/object_refs.rb +2 -1
  67. data/lib/reek/ast/reference_collector.rb +3 -4
  68. data/lib/reek/ast/sexp_extensions/arguments.rb +1 -0
  69. data/lib/reek/ast/sexp_extensions/attribute_assignments.rb +1 -0
  70. data/lib/reek/ast/sexp_extensions/begin.rb +17 -0
  71. data/lib/reek/ast/sexp_extensions/block.rb +1 -0
  72. data/lib/reek/ast/sexp_extensions/case.rb +2 -1
  73. data/lib/reek/ast/sexp_extensions/constant.rb +1 -0
  74. data/lib/reek/ast/sexp_extensions/if.rb +9 -1
  75. data/lib/reek/ast/sexp_extensions/lambda.rb +1 -0
  76. data/lib/reek/ast/sexp_extensions/literal.rb +1 -0
  77. data/lib/reek/ast/sexp_extensions/logical_operators.rb +2 -1
  78. data/lib/reek/ast/sexp_extensions/methods.rb +5 -6
  79. data/lib/reek/ast/sexp_extensions/module.rb +55 -8
  80. data/lib/reek/ast/sexp_extensions/nested_assignables.rb +1 -0
  81. data/lib/reek/ast/sexp_extensions/self.rb +1 -0
  82. data/lib/reek/ast/sexp_extensions/send.rb +1 -4
  83. data/lib/reek/ast/sexp_extensions/super.rb +1 -0
  84. data/lib/reek/ast/sexp_extensions/symbols.rb +1 -0
  85. data/lib/reek/ast/sexp_extensions/variables.rb +1 -0
  86. data/lib/reek/ast/sexp_extensions/when.rb +1 -0
  87. data/lib/reek/ast/sexp_extensions/yield.rb +1 -0
  88. data/lib/reek/ast/sexp_extensions.rb +2 -0
  89. data/lib/reek/cli/application.rb +5 -3
  90. data/lib/reek/cli/command/base_command.rb +1 -0
  91. data/lib/reek/cli/command/report_command.rb +2 -2
  92. data/lib/reek/cli/command/todo_list_command.rb +9 -8
  93. data/lib/reek/cli/options.rb +32 -16
  94. data/lib/reek/cli/silencer.rb +15 -3
  95. data/lib/reek/cli/status.rb +1 -0
  96. data/lib/reek/code_comment.rb +14 -16
  97. data/lib/reek/configuration/app_configuration.rb +34 -28
  98. data/lib/reek/configuration/configuration_converter.rb +110 -0
  99. data/lib/reek/configuration/configuration_file_finder.rb +17 -41
  100. data/lib/reek/configuration/configuration_validator.rb +13 -23
  101. data/lib/reek/configuration/default_directive.rb +18 -3
  102. data/lib/reek/configuration/directory_directives.rb +18 -11
  103. data/lib/reek/configuration/excluded_paths.rb +2 -1
  104. data/lib/reek/configuration/rake_task_converter.rb +29 -0
  105. data/lib/reek/configuration/schema.yml +210 -0
  106. data/lib/reek/configuration/schema_validator.rb +38 -0
  107. data/lib/reek/context/attribute_context.rb +4 -3
  108. data/lib/reek/context/class_context.rb +1 -0
  109. data/lib/reek/context/code_context.rb +49 -44
  110. data/lib/reek/context/ghost_context.rb +1 -2
  111. data/lib/reek/context/method_context.rb +26 -18
  112. data/lib/reek/context/module_context.rb +11 -11
  113. data/lib/reek/context/root_context.rb +1 -4
  114. data/lib/reek/context/send_context.rb +3 -2
  115. data/lib/reek/context/singleton_attribute_context.rb +1 -0
  116. data/lib/reek/context/singleton_method_context.rb +1 -0
  117. data/lib/reek/context/statement_counter.rb +1 -0
  118. data/lib/reek/context/visibility_tracker.rb +1 -0
  119. data/lib/reek/context_builder.rb +44 -44
  120. data/lib/reek/detector_repository.rb +12 -11
  121. data/lib/reek/documentation_link.rb +28 -0
  122. data/lib/reek/errors/bad_detector_configuration_key_in_comment_error.rb +15 -13
  123. data/lib/reek/errors/bad_detector_in_comment_error.rb +13 -11
  124. data/lib/reek/errors/base_error.rb +3 -0
  125. data/lib/reek/errors/config_file_error.rb +11 -0
  126. data/lib/reek/errors/encoding_error.rb +43 -0
  127. data/lib/reek/errors/garbage_detector_configuration_in_comment_error.rb +14 -12
  128. data/lib/reek/errors/incomprehensible_source_error.rb +23 -24
  129. data/lib/reek/errors/syntax_error.rb +41 -0
  130. data/lib/reek/examiner.rb +24 -22
  131. data/lib/reek/logging_error_handler.rb +8 -5
  132. data/lib/reek/rake/task.rb +8 -5
  133. data/lib/reek/report/base_report.rb +9 -12
  134. data/lib/reek/report/code_climate/code_climate_configuration.rb +2 -1
  135. data/lib/reek/report/code_climate/code_climate_configuration.yml +6 -6
  136. data/lib/reek/report/code_climate/code_climate_fingerprint.rb +1 -0
  137. data/lib/reek/report/code_climate/code_climate_formatter.rb +1 -0
  138. data/lib/reek/report/code_climate/code_climate_report.rb +1 -0
  139. data/lib/reek/report/code_climate.rb +1 -0
  140. data/lib/reek/report/documentation_link_warning_formatter.rb +17 -0
  141. data/lib/reek/report/heading_formatter.rb +54 -0
  142. data/lib/reek/report/html_report.rb +1 -0
  143. data/lib/reek/report/json_report.rb +2 -1
  144. data/lib/reek/report/location_formatter.rb +40 -0
  145. data/lib/reek/report/progress_formatter.rb +79 -0
  146. data/lib/reek/report/simple_warning_formatter.rb +34 -0
  147. data/lib/reek/report/text_report.rb +2 -2
  148. data/lib/reek/report/xml_report.rb +4 -3
  149. data/lib/reek/report/yaml_report.rb +2 -1
  150. data/lib/reek/report.rb +16 -10
  151. data/lib/reek/smell_configuration.rb +3 -2
  152. data/lib/reek/smell_detectors/attribute.rb +6 -11
  153. data/lib/reek/smell_detectors/base_detector.rb +31 -26
  154. data/lib/reek/smell_detectors/boolean_parameter.rb +4 -5
  155. data/lib/reek/smell_detectors/class_variable.rb +6 -14
  156. data/lib/reek/smell_detectors/control_parameter.rb +19 -33
  157. data/lib/reek/smell_detectors/data_clump.rb +16 -9
  158. data/lib/reek/smell_detectors/duplicate_method_call.rb +24 -17
  159. data/lib/reek/smell_detectors/feature_envy.rb +10 -7
  160. data/lib/reek/smell_detectors/instance_variable_assumption.rb +15 -23
  161. data/lib/reek/smell_detectors/irresponsible_module.rb +6 -12
  162. data/lib/reek/smell_detectors/long_parameter_list.rb +11 -7
  163. data/lib/reek/smell_detectors/long_yield_list.rb +11 -7
  164. data/lib/reek/smell_detectors/manual_dispatch.rb +5 -5
  165. data/lib/reek/smell_detectors/{prima_donna_method.rb → missing_safe_method.rb} +21 -20
  166. data/lib/reek/smell_detectors/module_initialize.rb +4 -5
  167. data/lib/reek/smell_detectors/nested_iterators.rb +17 -24
  168. data/lib/reek/smell_detectors/nil_check.rb +9 -15
  169. data/lib/reek/smell_detectors/repeated_conditional.rb +14 -11
  170. data/lib/reek/smell_detectors/subclassed_from_core_class.rb +8 -8
  171. data/lib/reek/smell_detectors/too_many_constants.rb +11 -9
  172. data/lib/reek/smell_detectors/too_many_instance_variables.rb +11 -6
  173. data/lib/reek/smell_detectors/too_many_methods.rb +12 -7
  174. data/lib/reek/smell_detectors/too_many_statements.rb +11 -6
  175. data/lib/reek/smell_detectors/uncommunicative_method_name.rb +11 -11
  176. data/lib/reek/smell_detectors/uncommunicative_module_name.rb +15 -18
  177. data/lib/reek/smell_detectors/uncommunicative_parameter_name.rb +18 -22
  178. data/lib/reek/smell_detectors/uncommunicative_variable_name.rb +27 -27
  179. data/lib/reek/smell_detectors/unused_parameters.rb +5 -6
  180. data/lib/reek/smell_detectors/unused_private_method.rb +14 -20
  181. data/lib/reek/smell_detectors/utility_function.rb +13 -16
  182. data/lib/reek/smell_detectors.rb +2 -1
  183. data/lib/reek/smell_warning.rb +16 -8
  184. data/lib/reek/source/source_code.rb +65 -46
  185. data/lib/reek/source/source_locator.rb +9 -8
  186. data/lib/reek/spec/should_reek.rb +3 -2
  187. data/lib/reek/spec/should_reek_of.rb +13 -26
  188. data/lib/reek/spec/should_reek_only_of.rb +5 -4
  189. data/lib/reek/spec/smell_matcher.rb +2 -1
  190. data/lib/reek/spec.rb +7 -6
  191. data/lib/reek/tree_dresser.rb +9 -8
  192. data/lib/reek/version.rb +2 -1
  193. data/lib/reek.rb +1 -0
  194. data/reek.gemspec +5 -6
  195. data/samples/checkstyle.xml +1 -1
  196. data/samples/configuration/accepts_rejects_and_excludes_for_detectors.reek.yml +29 -0
  197. data/samples/configuration/accepts_rejects_and_excludes_for_directory_directives.reek.yml +30 -0
  198. data/samples/configuration/full_configuration.reek +8 -4
  199. data/samples/configuration/full_mask.reek +5 -4
  200. data/samples/configuration/partial_mask.reek +3 -2
  201. data/samples/configuration/regular_configuration/.reek.yml +4 -0
  202. data/samples/paths.rb +5 -4
  203. data/samples/source_with_hidden_directories/.hidden/hidden.rb +1 -0
  204. data/samples/source_with_hidden_directories/not_hidden.rb +1 -0
  205. data/spec/factories/factories.rb +2 -13
  206. data/spec/reek/ast/node_spec.rb +103 -10
  207. data/spec/reek/ast/reference_collector_spec.rb +1 -1
  208. data/spec/reek/ast/sexp_extensions_spec.rb +15 -34
  209. data/spec/reek/cli/application_spec.rb +52 -42
  210. data/spec/reek/cli/command/todo_list_command_spec.rb +6 -4
  211. data/spec/reek/cli/silencer_spec.rb +28 -0
  212. data/spec/reek/code_comment_spec.rb +31 -38
  213. data/spec/reek/configuration/app_configuration_spec.rb +46 -33
  214. data/spec/reek/configuration/configuration_file_finder_spec.rb +133 -51
  215. data/spec/reek/configuration/default_directive_spec.rb +1 -1
  216. data/spec/reek/configuration/directory_directives_spec.rb +6 -7
  217. data/spec/reek/configuration/excluded_paths_spec.rb +6 -6
  218. data/spec/reek/configuration/rake_task_converter_spec.rb +33 -0
  219. data/spec/reek/configuration/schema_validator_spec.rb +165 -0
  220. data/spec/reek/context/code_context_spec.rb +70 -106
  221. data/spec/reek/context/ghost_context_spec.rb +9 -9
  222. data/spec/reek/context/method_context_spec.rb +2 -2
  223. data/spec/reek/context/module_context_spec.rb +3 -3
  224. data/spec/reek/context/root_context_spec.rb +1 -1
  225. data/spec/reek/context/statement_counter_spec.rb +1 -0
  226. data/spec/reek/context_builder_spec.rb +20 -0
  227. data/spec/reek/documentation_link_spec.rb +20 -0
  228. data/spec/reek/errors/base_error_spec.rb +13 -0
  229. data/spec/reek/examiner_spec.rb +137 -29
  230. data/spec/reek/rake/task_spec.rb +25 -2
  231. data/spec/reek/report/code_climate/code_climate_fingerprint_spec.rb +82 -78
  232. data/spec/reek/report/code_climate/code_climate_formatter_spec.rb +6 -6
  233. data/spec/reek/report/code_climate/code_climate_report_spec.rb +22 -22
  234. data/spec/reek/report/json_report_spec.rb +13 -46
  235. data/spec/reek/report/{formatter/location_formatter_spec.rb → location_formatter_spec.rb} +5 -5
  236. data/spec/reek/report/{formatter/progress_formatter_spec.rb → progress_formatter_spec.rb} +4 -4
  237. data/spec/reek/report/text_report_spec.rb +4 -4
  238. data/spec/reek/report/xml_report_spec.rb +3 -3
  239. data/spec/reek/report/yaml_report_spec.rb +17 -46
  240. data/spec/reek/report_spec.rb +3 -3
  241. data/spec/reek/smell_detectors/base_detector_spec.rb +4 -5
  242. data/spec/reek/smell_detectors/boolean_parameter_spec.rb +2 -2
  243. data/spec/reek/smell_detectors/class_variable_spec.rb +26 -32
  244. data/spec/reek/smell_detectors/control_parameter_spec.rb +34 -4
  245. data/spec/reek/smell_detectors/duplicate_method_call_spec.rb +3 -3
  246. data/spec/reek/smell_detectors/feature_envy_spec.rb +47 -2
  247. data/spec/reek/smell_detectors/irresponsible_module_spec.rb +59 -21
  248. data/spec/reek/smell_detectors/{prima_donna_method_spec.rb → missing_safe_method_spec.rb} +10 -10
  249. data/spec/reek/smell_detectors/module_initialize_spec.rb +14 -0
  250. data/spec/reek/smell_detectors/nested_iterators_spec.rb +1 -1
  251. data/spec/reek/smell_detectors/too_many_constants_spec.rb +3 -3
  252. data/spec/reek/smell_detectors/too_many_instance_variables_spec.rb +1 -1
  253. data/spec/reek/smell_detectors/uncommunicative_method_name_spec.rb +6 -6
  254. data/spec/reek/smell_detectors/uncommunicative_module_name_spec.rb +6 -4
  255. data/spec/reek/smell_detectors/uncommunicative_parameter_name_spec.rb +36 -15
  256. data/spec/reek/smell_detectors/uncommunicative_variable_name_spec.rb +9 -9
  257. data/spec/reek/smell_detectors/unused_parameters_spec.rb +3 -3
  258. data/spec/reek/smell_detectors/unused_private_method_spec.rb +21 -10
  259. data/spec/reek/smell_detectors/utility_function_spec.rb +57 -5
  260. data/spec/reek/smell_warning_spec.rb +12 -8
  261. data/spec/reek/source/source_code_spec.rb +27 -38
  262. data/spec/reek/source/source_locator_spec.rb +42 -12
  263. data/spec/reek/spec/should_reek_of_spec.rb +25 -30
  264. data/spec/reek/spec/should_reek_only_of_spec.rb +2 -2
  265. data/spec/reek/spec/should_reek_spec.rb +8 -8
  266. data/spec/reek/spec/smell_matcher_spec.rb +23 -23
  267. data/spec/reek/tree_dresser_spec.rb +12 -17
  268. data/spec/spec_helper.rb +7 -17
  269. data/tasks/configuration.rake +8 -5
  270. metadata +77 -40
  271. data/defaults.reek +0 -128
  272. data/features/configuration_files/warn_about_multiple_configuration_files.feature +0 -44
  273. data/lib/reek/errors/parse_error.rb +0 -19
  274. data/lib/reek/report/formatter/heading_formatter.rb +0 -51
  275. data/lib/reek/report/formatter/location_formatter.rb +0 -41
  276. data/lib/reek/report/formatter/progress_formatter.rb +0 -80
  277. data/lib/reek/report/formatter/simple_warning_formatter.rb +0 -35
  278. data/lib/reek/report/formatter/wiki_link_warning_formatter.rb +0 -35
  279. data/lib/reek/report/formatter.rb +0 -32
  280. data/samples/configuration/non_public_modifiers_mask.reek +0 -3
  281. data/samples/smelly_with_inline_mask.rb +0 -8
  282. data/samples/smelly_with_modifiers.rb +0 -12
  283. data/samples/source_with_hidden_directories/.hidden/uncommunicative_method_name.rb +0 -5
  284. data/samples/source_with_non_ruby_files/uncommunicative_parameter_name.rb +0 -6
  285. /data/{samples/configuration/more_than_one_configuration_file/regular.reek → .reek.yml} +0 -0
  286. /data/samples/{clean.rb → clean_source/clean.rb} +0 -0
  287. /data/samples/{exceptions.reek → configuration/home/home.reek.yml} +0 -0
  288. /data/samples/configuration/{more_than_one_configuration_file/todo.reek → regular_configuration/empty_sub_directory/.gitignore} +0 -0
  289. /data/samples/{configuration/single_configuration_file/.reek → no_config_file/.keep} +0 -0
  290. /data/samples/{inline.rb → smelly_source/inline.rb} +0 -0
  291. /data/samples/{optparse.rb → smelly_source/optparse.rb} +0 -0
  292. /data/samples/{redcloth.rb → smelly_source/redcloth.rb} +0 -0
  293. /data/samples/{smelly.rb → smelly_source/smelly.rb} +0 -0
  294. /data/samples/{source_with_hidden_directories/uncommunicative_parameter_name.rb → source_with_non_ruby_files/ruby.rb} +0 -0
@@ -7,14 +7,37 @@ RSpec.describe Reek::Rake::Task do
7
7
  task = described_class.new
8
8
  expect(task.source_files).to eq FileList['lib/**/*.rb']
9
9
  end
10
+
11
+ it 'is set to ENV["REEK_SRC"]' do
12
+ begin
13
+ ENV['REEK_SRC'] = '*.rb'
14
+ task = described_class.new
15
+ expect(task.source_files).to eq FileList['*.rb']
16
+ ensure
17
+ ENV['REEK_SRC'] = nil
18
+ end
19
+ end
10
20
  end
11
21
 
12
22
  describe '#source_files=' do
13
23
  it 'sets source_files to a FileList when passed a string' do
14
- task = described_class.new
15
- task.source_files = '*.rb'
24
+ task = described_class.new do |it|
25
+ it.source_files = '*.rb'
26
+ end
16
27
  expect(task.source_files).to eq FileList['*.rb']
17
28
  end
29
+
30
+ it 'has no effect when ENV["REEK_SRC"] is set' do
31
+ begin
32
+ ENV['REEK_SRC'] = '*.rb'
33
+ task = described_class.new do |it|
34
+ it.source_files = 'lib/*.rb'
35
+ end
36
+ expect(task.source_files).to eq FileList['*.rb']
37
+ ensure
38
+ ENV['REEK_SRC'] = nil
39
+ end
40
+ end
18
41
  end
19
42
 
20
43
  # SMELL: Testing a private method
@@ -5,40 +5,42 @@ RSpec.describe Reek::Report::CodeClimateFingerprint do
5
5
  describe '#compute' do
6
6
  let(:computed) { described_class.new(warning).compute }
7
7
 
8
- shared_examples_for 'computes a fingerprint with no parameters' do
8
+ context 'when fingerprinting a warning with no parameters' do
9
9
  let(:expected_fingerprint) { 'e68badd29db51c92363a7c6a2438d722' }
10
10
  let(:warning) do
11
- FactoryGirl.build(:smell_warning,
12
- smell_detector: Reek::SmellDetectors::UtilityFunction.new,
13
- context: 'alfa',
14
- message: "doesn't depend on instance state (maybe move it to another class?)",
15
- lines: lines,
16
- source: 'a/ruby/source/file.rb')
11
+ build(:smell_warning,
12
+ smell_detector: Reek::SmellDetectors::UtilityFunction.new,
13
+ context: 'alfa',
14
+ message: "doesn't depend on instance state (maybe move it to another class?)",
15
+ lines: lines,
16
+ source: 'a/ruby/source/file.rb')
17
17
  end
18
18
 
19
- it 'computes the fingerprint' do
20
- expect(computed).to eq expected_fingerprint
19
+ context 'with code at a specific location' do
20
+ let(:lines) { [1] }
21
+
22
+ it 'computes the fingerprint' do
23
+ expect(computed).to eq expected_fingerprint
24
+ end
21
25
  end
22
- end
23
26
 
24
- context 'with code at a specific location' do
25
- let(:lines) { [1] }
26
- it_behaves_like 'computes a fingerprint with no parameters'
27
- end
27
+ context 'with code at a different location' do
28
+ let(:lines) { [5] }
28
29
 
29
- context 'with code at a different location' do
30
- let(:lines) { [5] }
31
- it_behaves_like 'computes a fingerprint with no parameters'
30
+ it 'computes the same fingerprint' do
31
+ expect(computed).to eq expected_fingerprint
32
+ end
33
+ end
32
34
  end
33
35
 
34
36
  context 'when the fingerprint should not be computed' do
35
37
  let(:warning) do
36
- FactoryGirl.build(:smell_warning,
37
- smell_detector: Reek::SmellDetectors::ManualDispatch.new,
38
- context: 'Alfa#bravo',
39
- message: 'manually dispatches method call',
40
- lines: [4],
41
- source: 'a/ruby/source/file.rb')
38
+ build(:smell_warning,
39
+ smell_detector: Reek::SmellDetectors::ManualDispatch.new,
40
+ context: 'Alfa#bravo',
41
+ message: 'manually dispatches method call',
42
+ lines: [4],
43
+ source: 'a/ruby/source/file.rb')
42
44
  end
43
45
 
44
46
  it 'returns nil' do
@@ -46,77 +48,79 @@ RSpec.describe Reek::Report::CodeClimateFingerprint do
46
48
  end
47
49
  end
48
50
 
49
- shared_examples_for 'computes a fingerprint with identifying parameters' do
51
+ context 'when the smell warning has only identifying parameters' do
50
52
  let(:warning) do
51
- FactoryGirl.build(:smell_warning,
52
- smell_detector: Reek::SmellDetectors::ClassVariable.new,
53
- context: 'Alfa',
54
- message: "declares the class variable '@@#{name}'",
55
- lines: [4],
56
- parameters: { name: "@@#{name}" },
57
- source: 'a/ruby/source/file.rb')
53
+ build(:smell_warning,
54
+ smell_detector: Reek::SmellDetectors::ClassVariable.new,
55
+ context: 'Alfa',
56
+ message: "declares the class variable '@@#{name}'",
57
+ lines: [4],
58
+ parameters: { name: "@@#{name}" },
59
+ source: 'a/ruby/source/file.rb')
58
60
  end
59
61
 
60
- it 'computes the fingerprint' do
61
- expect(computed).to eq expected_fingerprint
62
- end
63
- end
64
-
65
- context 'when the name is one thing it has one fingerprint' do
66
- let(:name) { 'bravo' }
67
- let(:expected_fingerprint) { '9c3fd378178118a67e9509f87cae24f9' }
62
+ context 'when the name is one thing' do
63
+ let(:name) { 'bravo' }
64
+ let(:expected_fingerprint) { '9c3fd378178118a67e9509f87cae24f9' }
68
65
 
69
- it_behaves_like 'computes a fingerprint with identifying parameters'
70
- end
66
+ it 'computes the fingerprint' do
67
+ expect(computed).to eq expected_fingerprint
68
+ end
69
+ end
71
70
 
72
- context 'when the name is another thing it has another fingerprint' do
73
- let(:name) { 'echo' }
74
- let(:expected_fingerprint) { 'd2a6d2703ce04cca65e7300b7de4b89f' }
71
+ context 'when the name is another thing' do
72
+ let(:name) { 'echo' }
73
+ let(:expected_fingerprint) { 'd2a6d2703ce04cca65e7300b7de4b89f' }
75
74
 
76
- it_behaves_like 'computes a fingerprint with identifying parameters'
75
+ it 'computes another fingerprint' do
76
+ expect(computed).to eq expected_fingerprint
77
+ end
78
+ end
77
79
  end
78
80
 
79
- shared_examples_for 'computes a fingerprint with identifying and non-identifying parameters' do
81
+ context 'when the smell warning has identifying and non-identifying parameters' do
80
82
  let(:warning) do
81
- FactoryGirl.build(:smell_warning,
82
- smell_detector: Reek::SmellDetectors::DuplicateMethodCall.new,
83
- context: "Alfa##{name}",
84
- message: "calls '#{name}' #{count} times",
85
- lines: lines,
86
- parameters: { name: "@@#{name}", count: count },
87
- source: 'a/ruby/source/file.rb')
83
+ build(:smell_warning,
84
+ smell_detector: Reek::SmellDetectors::DuplicateMethodCall.new,
85
+ context: "Alfa##{name}",
86
+ message: "calls '#{name}' #{count} times",
87
+ lines: lines,
88
+ parameters: { name: "@@#{name}", count: count },
89
+ source: 'a/ruby/source/file.rb')
88
90
  end
89
91
 
90
- it 'computes the fingerprint' do
91
- expect(computed).to eq expected_fingerprint
92
- end
93
- end
92
+ context 'when the parameters are provided' do
93
+ let(:name) { 'bravo' }
94
+ let(:count) { 5 }
95
+ let(:lines) { [1, 7, 10, 13, 15] }
96
+ let(:expected_fingerprint) { '238733f4f51ba5473dcbe94a43ec5400' }
94
97
 
95
- context 'when the parameters are provided' do
96
- let(:name) { 'bravo' }
97
- let(:count) { 5 }
98
- let(:lines) { [1, 7, 10, 13, 15] }
99
- let(:expected_fingerprint) { '238733f4f51ba5473dcbe94a43ec5400' }
100
-
101
- it_behaves_like 'computes a fingerprint with identifying and non-identifying parameters'
102
- end
98
+ it 'computes the fingerprint' do
99
+ expect(computed).to eq expected_fingerprint
100
+ end
101
+ end
103
102
 
104
- context 'when the non-identifying parameters change, it computes the same fingerprint' do
105
- let(:name) { 'bravo' }
106
- let(:count) { 9 }
107
- let(:lines) { [1, 7, 10, 13, 15, 17, 19, 20, 25] }
108
- let(:expected_fingerprint) { '238733f4f51ba5473dcbe94a43ec5400' }
103
+ context 'when the non-identifying parameters change' do
104
+ let(:name) { 'bravo' }
105
+ let(:count) { 9 }
106
+ let(:lines) { [1, 7, 10, 13, 15, 17, 19, 20, 25] }
107
+ let(:expected_fingerprint) { '238733f4f51ba5473dcbe94a43ec5400' }
109
108
 
110
- it_behaves_like 'computes a fingerprint with identifying and non-identifying parameters'
111
- end
109
+ it 'computes the same fingerprint' do
110
+ expect(computed).to eq expected_fingerprint
111
+ end
112
+ end
112
113
 
113
- context 'but when the identifying parameters change, it computes a different fingerprint' do
114
- let(:name) { 'echo' }
115
- let(:count) { 5 }
116
- let(:lines) { [1, 7, 10, 13, 15] }
117
- let(:expected_fingerprint) { 'e0c35e9223cc19bdb9a04fb3e60573e1' }
114
+ context 'when the identifying parameters change' do
115
+ let(:name) { 'echo' }
116
+ let(:count) { 5 }
117
+ let(:lines) { [1, 7, 10, 13, 15] }
118
+ let(:expected_fingerprint) { 'e0c35e9223cc19bdb9a04fb3e60573e1' }
118
119
 
119
- it_behaves_like 'computes a fingerprint with identifying and non-identifying parameters'
120
+ it 'computes a different fingerprint' do
121
+ expect(computed).to eq expected_fingerprint
122
+ end
123
+ end
120
124
  end
121
125
  end
122
126
  end
@@ -4,12 +4,12 @@ require_lib 'reek/report/code_climate/code_climate_formatter'
4
4
  RSpec.describe Reek::Report::CodeClimateFormatter do
5
5
  describe '#render' do
6
6
  let(:warning) do
7
- FactoryGirl.build(:smell_warning,
8
- smell_detector: Reek::SmellDetectors::UtilityFunction.new,
9
- context: 'context foo',
10
- message: 'message bar',
11
- lines: [1, 2],
12
- source: 'a/ruby/source/file.rb')
7
+ build(:smell_warning,
8
+ smell_detector: Reek::SmellDetectors::UtilityFunction.new,
9
+ context: 'context foo',
10
+ message: 'message bar',
11
+ lines: [1, 2],
12
+ source: 'a/ruby/source/file.rb')
13
13
  end
14
14
  let(:rendered) { described_class.new(warning).render }
15
15
  let(:json) { JSON.parse rendered.chop }
@@ -26,28 +26,28 @@ RSpec.describe Reek::Report::CodeClimateReport do
26
26
  let(:source) { 'def simple(a) a[3] end' }
27
27
 
28
28
  it 'prints smells as json' do
29
- expected = <<-EOS.delete("\n")
30
- {\"type\":\"issue\",
31
- \"check_name\":\"UncommunicativeParameterName\",
32
- \"description\":\"simple has the parameter name 'a'\",
33
- \"categories\":[\"Complexity\"],
34
- \"location\":{\"path\":\"string\",\"lines\":{\"begin\":1,\"end\":1}},
35
- \"remediation_points\":150000,
36
- \"content\":{\"body\":\"An `Uncommunicative Parameter Name` is a parameter name that
37
- doesn't communicate its intent well enough.\\n\\nPoor names make it hard for the reader
38
- to build a mental picture of what's going on in the code. They can also be
39
- mis-interpreted; and they hurt the flow of reading, because the reader must slow down
40
- to interpret the names.\\n\"},
41
- \"fingerprint\":\"09970037d92b5a628bf682a3e2bb126d\"}\u0000
42
- {\"type\":\"issue\",
43
- \"check_name\":\"UtilityFunction\",
44
- \"description\":\"simple doesn't depend on instance state (maybe move it to another class?)\",
45
- \"categories\":[\"Complexity\"],
46
- \"location\":{\"path\":\"string\",\"lines\":{\"begin\":1,\"end\":1}},
47
- \"remediation_points\":250000,
48
- \"content\":{\"body\":\"A _Utility Function_ is any instance method that has no
49
- dependency on the state of the instance.\\n\"},
50
- \"fingerprint\":\"db456db7cb344bb5a98b8fc54a2f382e\"}\u0000
29
+ expected = <<-EOS.strip_heredoc.delete("\n")
30
+ {\"type\":\"issue\",
31
+ \"check_name\":\"UncommunicativeParameterName\",
32
+ \"description\":\"simple has the parameter name 'a'\",
33
+ \"categories\":[\"Complexity\"],
34
+ \"location\":{\"path\":\"string\",\"lines\":{\"begin\":1,\"end\":1}},
35
+ \"remediation_points\":150000,
36
+ \"content\":{\"body\":\"An `Uncommunicative Parameter Name` is a parameter name that
37
+ doesn't communicate its intent well enough.\\n\\nPoor names make it hard for the reader
38
+ to build a mental picture of what's going on in the code. They can also be
39
+ mis-interpreted; and they hurt the flow of reading, because the reader must slow down
40
+ to interpret the names.\\n\"},
41
+ \"fingerprint\":\"09970037d92b5a628bf682a3e2bb126d\"}\u0000
42
+ {\"type\":\"issue\",
43
+ \"check_name\":\"UtilityFunction\",
44
+ \"description\":\"simple doesn't depend on instance state (maybe move it to another class?)\",
45
+ \"categories\":[\"Complexity\"],
46
+ \"location\":{\"path\":\"string\",\"lines\":{\"begin\":1,\"end\":1}},
47
+ \"remediation_points\":250000,
48
+ \"content\":{\"body\":\"A _Utility Function_ is any instance method that has no
49
+ dependency on the state of the instance.\\n\"},
50
+ \"fingerprint\":\"db456db7cb344bb5a98b8fc54a2f382e\"}\u0000
51
51
  EOS
52
52
 
53
53
  expect { instance.show }.to output(expected).to_stdout
@@ -1,7 +1,6 @@
1
1
  require_relative '../../spec_helper'
2
2
  require_lib 'reek/examiner'
3
3
  require_lib 'reek/report/json_report'
4
- require_lib 'reek/report/formatter'
5
4
 
6
5
  require 'json'
7
6
  require 'stringio'
@@ -34,58 +33,26 @@ RSpec.describe Reek::Report::JSONReport do
34
33
  expected = JSON.parse <<-EOS
35
34
  [
36
35
  {
37
- "context": "simple",
38
- "lines": [1],
39
- "message": "has the parameter name 'a'",
40
- "smell_type": "UncommunicativeParameterName",
41
- "source": "string",
42
- "name": "a"
36
+ "context": "simple",
37
+ "lines": [1],
38
+ "message": "has the parameter name 'a'",
39
+ "smell_type": "UncommunicativeParameterName",
40
+ "source": "string",
41
+ "name": "a",
42
+ "documentation_link": "https://github.com/troessner/reek/blob/v#{Reek::Version::STRING}/docs/Uncommunicative-Parameter-Name.md"
43
43
  },
44
44
  {
45
- "context": "simple",
46
- "lines": [1],
47
- "message": "doesn't depend on instance state (maybe move it to another class?)",
48
- "smell_type": "UtilityFunction",
49
- "source": "string"
45
+ "context": "simple",
46
+ "lines": [1],
47
+ "message": "doesn't depend on instance state (maybe move it to another class?)",
48
+ "smell_type": "UtilityFunction",
49
+ "source": "string",
50
+ "documentation_link": "https://github.com/troessner/reek/blob/v#{Reek::Version::STRING}/docs/Utility-Function.md"
50
51
  }
51
52
  ]
52
53
  EOS
53
54
 
54
55
  expect(result).to eq expected
55
56
  end
56
-
57
- context 'with link formatter' do
58
- let(:options) { { warning_formatter: Reek::Report::Formatter::WikiLinkWarningFormatter.new } }
59
-
60
- it 'prints documentation links' do
61
- out = StringIO.new
62
- instance.show(out)
63
- out.rewind
64
- result = JSON.parse(out.read)
65
- expected = JSON.parse <<-EOS
66
- [
67
- {
68
- "context": "simple",
69
- "lines": [1],
70
- "message": "has the parameter name 'a'",
71
- "smell_type": "UncommunicativeParameterName",
72
- "source": "string",
73
- "name": "a",
74
- "wiki_link": "https://github.com/troessner/reek/blob/master/docs/Uncommunicative-Parameter-Name.md"
75
- },
76
- {
77
- "context": "simple",
78
- "lines": [1],
79
- "message": "doesn't depend on instance state (maybe move it to another class?)",
80
- "smell_type": "UtilityFunction",
81
- "source": "string",
82
- "wiki_link": "https://github.com/troessner/reek/blob/master/docs/Utility-Function.md"
83
- }
84
- ]
85
- EOS
86
-
87
- expect(result).to eq expected
88
- end
89
- end
90
57
  end
91
58
  end
@@ -1,7 +1,7 @@
1
- require_relative '../../../spec_helper'
2
- require_lib 'reek/report/formatter'
1
+ require_relative '../../spec_helper'
2
+ require_lib 'reek/report/location_formatter'
3
3
 
4
- RSpec.describe Reek::Report::Formatter::BlankLocationFormatter do
4
+ RSpec.describe Reek::Report::BlankLocationFormatter do
5
5
  let(:warning) { build(:smell_warning, lines: [11, 9, 250, 100]) }
6
6
 
7
7
  describe '.format' do
@@ -11,7 +11,7 @@ RSpec.describe Reek::Report::Formatter::BlankLocationFormatter do
11
11
  end
12
12
  end
13
13
 
14
- RSpec.describe Reek::Report::Formatter::DefaultLocationFormatter do
14
+ RSpec.describe Reek::Report::DefaultLocationFormatter do
15
15
  let(:warning) { build(:smell_warning, lines: [11, 9, 250, 100]) }
16
16
 
17
17
  describe '.format' do
@@ -21,7 +21,7 @@ RSpec.describe Reek::Report::Formatter::DefaultLocationFormatter do
21
21
  end
22
22
  end
23
23
 
24
- RSpec.describe Reek::Report::Formatter::SingleLineLocationFormatter do
24
+ RSpec.describe Reek::Report::SingleLineLocationFormatter do
25
25
  let(:warning) { build(:smell_warning, lines: [11, 9, 250, 100]) }
26
26
 
27
27
  describe '.format' do
@@ -1,7 +1,7 @@
1
- require_relative '../../../spec_helper'
2
- require_lib 'reek/report/formatter/progress_formatter'
1
+ require_relative '../../spec_helper'
2
+ require_lib 'reek/report/progress_formatter'
3
3
 
4
- RSpec.describe Reek::Report::Formatter::ProgressFormatter::Dots do
4
+ RSpec.describe Reek::Report::ProgressFormatter::Dots do
5
5
  let(:sources_count) { 23 }
6
6
  let(:formatter) { described_class.new(sources_count) }
7
7
 
@@ -37,7 +37,7 @@ RSpec.describe Reek::Report::Formatter::ProgressFormatter::Dots do
37
37
  end
38
38
  end
39
39
 
40
- RSpec.describe Reek::Report::Formatter::ProgressFormatter::Quiet do
40
+ RSpec.describe Reek::Report::ProgressFormatter::Quiet do
41
41
  let(:sources_count) { 23 }
42
42
  let(:formatter) { described_class.new(sources_count) }
43
43
 
@@ -1,15 +1,15 @@
1
1
  require_relative '../../spec_helper'
2
2
  require_lib 'reek/examiner'
3
3
  require_lib 'reek/report/text_report'
4
- require_lib 'reek/report/formatter'
4
+ require_lib 'reek/report/heading_formatter'
5
+ require_lib 'reek/report/simple_warning_formatter'
5
6
  require 'rainbow'
6
7
 
7
8
  RSpec.describe Reek::Report::TextReport do
8
9
  let(:report_options) do
9
10
  {
10
- warning_formatter: Reek::Report::Formatter::SimpleWarningFormatter.new,
11
- report_formatter: Reek::Report::Formatter,
12
- heading_formatter: Reek::Report::Formatter::QuietHeadingFormatter
11
+ warning_formatter: Reek::Report::SimpleWarningFormatter.new,
12
+ heading_formatter: Reek::Report::QuietHeadingFormatter
13
13
  }
14
14
  end
15
15
  let(:instance) { described_class.new report_options }
@@ -5,7 +5,7 @@ require_lib 'reek/report/xml_report'
5
5
  RSpec.describe Reek::Report::XMLReport do
6
6
  let(:xml_report) { described_class.new }
7
7
 
8
- context 'empty source' do
8
+ context 'with an empty source' do
9
9
  it 'prints empty checkstyle XML' do
10
10
  xml_report.add_examiner Reek::Examiner.new('')
11
11
  xml = "<?xml version='1.0'?>\n<checkstyle/>\n"
@@ -13,10 +13,10 @@ RSpec.describe Reek::Report::XMLReport do
13
13
  end
14
14
  end
15
15
 
16
- context 'source with voliations' do
16
+ context 'with a source with violations' do
17
17
  it 'prints non-empty checkstyle XML' do
18
18
  xml_report.add_examiner Reek::Examiner.new(SMELLY_FILE)
19
- xml = SAMPLES_PATH.join('checkstyle.xml').read
19
+ xml = SAMPLES_DIR.join('checkstyle.xml').read
20
20
  xml = xml.gsub(SMELLY_FILE.to_s, SMELLY_FILE.expand_path.to_s)
21
21
  expect { xml_report.show }.to output(xml).to_stdout
22
22
  end
@@ -1,7 +1,6 @@
1
1
  require_relative '../../spec_helper'
2
2
  require_lib 'reek/examiner'
3
3
  require_lib 'reek/report/yaml_report'
4
- require_lib 'reek/report/formatter'
5
4
 
6
5
  require 'yaml'
7
6
  require 'stringio'
@@ -31,54 +30,26 @@ RSpec.describe Reek::Report::YAMLReport do
31
30
  instance.show(out)
32
31
  out.rewind
33
32
  result = YAML.safe_load(out.read)
34
- expected = YAML.safe_load <<-EOS
35
- ---
36
- - context: "simple"
37
- lines:
38
- - 1
39
- message: "has the parameter name 'a'"
40
- smell_type: "UncommunicativeParameterName"
41
- source: "string"
42
- name: "a"
43
- - context: "simple"
44
- lines:
45
- - 1
46
- message: "doesn't depend on instance state (maybe move it to another class?)"
47
- smell_type: "UtilityFunction"
48
- source: "string"
33
+ expected = YAML.safe_load <<-EOS.strip_heredoc
34
+ ---
35
+ - context: "simple"
36
+ lines:
37
+ - 1
38
+ message: "has the parameter name 'a'"
39
+ smell_type: "UncommunicativeParameterName"
40
+ source: "string"
41
+ name: "a"
42
+ documentation_link: "https://github.com/troessner/reek/blob/v#{Reek::Version::STRING}/docs/Uncommunicative-Parameter-Name.md"
43
+ - context: "simple"
44
+ lines:
45
+ - 1
46
+ message: "doesn't depend on instance state (maybe move it to another class?)"
47
+ smell_type: "UtilityFunction"
48
+ source: "string"
49
+ documentation_link: "https://github.com/troessner/reek/blob/v#{Reek::Version::STRING}/docs/Utility-Function.md"
49
50
  EOS
50
51
 
51
52
  expect(result).to eq expected
52
53
  end
53
- context 'with link formatter' do
54
- let(:options) { { warning_formatter: Reek::Report::Formatter::WikiLinkWarningFormatter.new } }
55
-
56
- it 'prints documentation links' do
57
- out = StringIO.new
58
- instance.show(out)
59
- out.rewind
60
- result = YAML.safe_load(out.read)
61
- expected = YAML.safe_load <<-EOS
62
- ---
63
- - context: "simple"
64
- lines:
65
- - 1
66
- message: "has the parameter name 'a'"
67
- smell_type: "UncommunicativeParameterName"
68
- source: "string"
69
- name: "a"
70
- wiki_link: "https://github.com/troessner/reek/blob/master/docs/Uncommunicative-Parameter-Name.md"
71
- - context: "simple"
72
- lines:
73
- - 1
74
- message: "doesn't depend on instance state (maybe move it to another class?)"
75
- smell_type: "UtilityFunction"
76
- source: "string"
77
- wiki_link: "https://github.com/troessner/reek/blob/master/docs/Utility-Function.md"
78
- EOS
79
-
80
- expect(result).to eq expected
81
- end
82
- end
83
54
  end
84
55
  end
@@ -10,19 +10,19 @@ RSpec.describe Reek::Report do
10
10
 
11
11
  describe '.location_formatter' do
12
12
  it 'returns the correct class' do
13
- expect(described_class.location_formatter(:plain)).to eq Reek::Report::Formatter::BlankLocationFormatter
13
+ expect(described_class.location_formatter(:plain)).to eq Reek::Report::BlankLocationFormatter
14
14
  end
15
15
  end
16
16
 
17
17
  describe '.heading_formatter' do
18
18
  it 'returns the correct class' do
19
- expect(described_class.heading_formatter(:quiet)).to eq Reek::Report::Formatter::QuietHeadingFormatter
19
+ expect(described_class.heading_formatter(:quiet)).to eq Reek::Report::QuietHeadingFormatter
20
20
  end
21
21
  end
22
22
 
23
23
  describe '.warning_formatter_class' do
24
24
  it 'returns the correct class' do
25
- expect(described_class.warning_formatter_class(:simple)).to eq Reek::Report::Formatter::SimpleWarningFormatter
25
+ expect(described_class.warning_formatter_class(:simple)).to eq Reek::Report::SimpleWarningFormatter
26
26
  end
27
27
  end
28
28
  end
@@ -21,16 +21,15 @@ RSpec.describe Reek::SmellDetectors::BaseDetector do
21
21
  context 'with default exclusions present' do
22
22
  let(:subclass) { Reek::SmellDetectors::TooManyStatements }
23
23
 
24
- before do
25
- expect(subclass.default_config['exclude']).to eq ['initialize']
26
- end
27
-
28
24
  it 'includes default exclusions' do
29
25
  detector = subclass.new
30
26
  smell = create(:smell_warning, smell_detector: detector, context: 'Foo#bar')
31
27
  result = subclass.todo_configuration_for([smell])
32
28
 
33
- expect(result).to eq('TooManyStatements' => { 'exclude' => ['initialize', 'Foo#bar'] })
29
+ aggregate_failures do
30
+ expect(subclass.default_config['exclude']).to eq ['initialize']
31
+ expect(result).to eq('TooManyStatements' => { 'exclude' => ['initialize', 'Foo#bar'] })
32
+ end
34
33
  end
35
34
  end
36
35
  end
@@ -27,7 +27,7 @@ RSpec.describe Reek::SmellDetectors::BooleanParameter do
27
27
  and reek_of(:BooleanParameter, lines: [1], context: 'alfa', parameter: 'charlie')
28
28
  end
29
29
 
30
- context 'in a method' do
30
+ context 'when examining an instance method' do
31
31
  it 'reports a parameter defaulted to false' do
32
32
  src = 'def alfa(bravo = false) end'
33
33
  expect(src).to reek_of(:BooleanParameter)
@@ -70,7 +70,7 @@ RSpec.describe Reek::SmellDetectors::BooleanParameter do
70
70
  end
71
71
  end
72
72
 
73
- context 'in a singleton method' do
73
+ context 'when examining a singleton method' do
74
74
  it 'reports a parameter defaulted to true' do
75
75
  src = 'def self.alfa(bravo = true) end'
76
76
  expect(src).to reek_of(:BooleanParameter)