rubbycop 0.49.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 (499) hide show
  1. checksums.yaml +7 -0
  2. data/LICENSE.txt +21 -0
  3. data/README.md +211 -0
  4. data/assets/logo.png +0 -0
  5. data/assets/output.html.erb +261 -0
  6. data/bin/rubbycop +17 -0
  7. data/config/default.yml +1548 -0
  8. data/config/disabled.yml +119 -0
  9. data/config/enabled.yml +1734 -0
  10. data/lib/rubbycop.rb +510 -0
  11. data/lib/rubbycop/ast/builder.rb +64 -0
  12. data/lib/rubbycop/ast/node.rb +610 -0
  13. data/lib/rubbycop/ast/node/and_node.rb +37 -0
  14. data/lib/rubbycop/ast/node/array_node.rb +48 -0
  15. data/lib/rubbycop/ast/node/case_node.rb +64 -0
  16. data/lib/rubbycop/ast/node/ensure_node.rb +25 -0
  17. data/lib/rubbycop/ast/node/for_node.rb +53 -0
  18. data/lib/rubbycop/ast/node/hash_node.rb +109 -0
  19. data/lib/rubbycop/ast/node/if_node.rb +138 -0
  20. data/lib/rubbycop/ast/node/keyword_splat_node.rb +45 -0
  21. data/lib/rubbycop/ast/node/mixin/binary_operator_node.rb +23 -0
  22. data/lib/rubbycop/ast/node/mixin/conditional_node.rb +45 -0
  23. data/lib/rubbycop/ast/node/mixin/hash_element_node.rb +125 -0
  24. data/lib/rubbycop/ast/node/mixin/modifier_node.rb +17 -0
  25. data/lib/rubbycop/ast/node/mixin/predicate_operator_node.rb +35 -0
  26. data/lib/rubbycop/ast/node/or_node.rb +37 -0
  27. data/lib/rubbycop/ast/node/pair_node.rb +64 -0
  28. data/lib/rubbycop/ast/node/resbody_node.rb +25 -0
  29. data/lib/rubbycop/ast/node/send_node.rb +209 -0
  30. data/lib/rubbycop/ast/node/until_node.rb +43 -0
  31. data/lib/rubbycop/ast/node/when_node.rb +61 -0
  32. data/lib/rubbycop/ast/node/while_node.rb +43 -0
  33. data/lib/rubbycop/ast/sexp.rb +16 -0
  34. data/lib/rubbycop/ast/traversal.rb +171 -0
  35. data/lib/rubbycop/cached_data.rb +63 -0
  36. data/lib/rubbycop/cli.rb +199 -0
  37. data/lib/rubbycop/comment_config.rb +155 -0
  38. data/lib/rubbycop/config.rb +444 -0
  39. data/lib/rubbycop/config_loader.rb +244 -0
  40. data/lib/rubbycop/config_loader_resolver.rb +43 -0
  41. data/lib/rubbycop/config_store.rb +48 -0
  42. data/lib/rubbycop/cop/autocorrect_logic.rb +26 -0
  43. data/lib/rubbycop/cop/badge.rb +73 -0
  44. data/lib/rubbycop/cop/bundler/duplicated_gem.rb +69 -0
  45. data/lib/rubbycop/cop/bundler/ordered_gems.rb +113 -0
  46. data/lib/rubbycop/cop/commissioner.rb +118 -0
  47. data/lib/rubbycop/cop/cop.rb +222 -0
  48. data/lib/rubbycop/cop/corrector.rb +135 -0
  49. data/lib/rubbycop/cop/force.rb +41 -0
  50. data/lib/rubbycop/cop/ignored_node.rb +38 -0
  51. data/lib/rubbycop/cop/layout/access_modifier_indentation.rb +109 -0
  52. data/lib/rubbycop/cop/layout/align_array.rb +35 -0
  53. data/lib/rubbycop/cop/layout/align_hash.rb +235 -0
  54. data/lib/rubbycop/cop/layout/align_parameters.rb +97 -0
  55. data/lib/rubbycop/cop/layout/block_end_newline.rb +56 -0
  56. data/lib/rubbycop/cop/layout/case_indentation.rb +163 -0
  57. data/lib/rubbycop/cop/layout/closing_parenthesis_indentation.rb +88 -0
  58. data/lib/rubbycop/cop/layout/comment_indentation.rb +71 -0
  59. data/lib/rubbycop/cop/layout/dot_position.rb +84 -0
  60. data/lib/rubbycop/cop/layout/else_alignment.rb +105 -0
  61. data/lib/rubbycop/cop/layout/empty_line_after_magic_comment.rb +63 -0
  62. data/lib/rubbycop/cop/layout/empty_line_between_defs.rb +143 -0
  63. data/lib/rubbycop/cop/layout/empty_lines.rb +60 -0
  64. data/lib/rubbycop/cop/layout/empty_lines_around_access_modifier.rb +90 -0
  65. data/lib/rubbycop/cop/layout/empty_lines_around_begin_body.rb +42 -0
  66. data/lib/rubbycop/cop/layout/empty_lines_around_block_body.rb +41 -0
  67. data/lib/rubbycop/cop/layout/empty_lines_around_class_body.rb +39 -0
  68. data/lib/rubbycop/cop/layout/empty_lines_around_exception_handling_keywords.rb +127 -0
  69. data/lib/rubbycop/cop/layout/empty_lines_around_method_body.rb +41 -0
  70. data/lib/rubbycop/cop/layout/empty_lines_around_module_body.rb +44 -0
  71. data/lib/rubbycop/cop/layout/end_of_line.rb +52 -0
  72. data/lib/rubbycop/cop/layout/extra_spacing.rb +237 -0
  73. data/lib/rubbycop/cop/layout/first_array_element_line_break.rb +41 -0
  74. data/lib/rubbycop/cop/layout/first_hash_element_line_break.rb +33 -0
  75. data/lib/rubbycop/cop/layout/first_method_argument_line_break.rb +49 -0
  76. data/lib/rubbycop/cop/layout/first_method_parameter_line_break.rb +42 -0
  77. data/lib/rubbycop/cop/layout/first_parameter_indentation.rb +109 -0
  78. data/lib/rubbycop/cop/layout/indent_array.rb +114 -0
  79. data/lib/rubbycop/cop/layout/indent_assignment.rb +42 -0
  80. data/lib/rubbycop/cop/layout/indent_hash.rb +134 -0
  81. data/lib/rubbycop/cop/layout/indent_heredoc.rb +173 -0
  82. data/lib/rubbycop/cop/layout/indentation_consistency.rb +51 -0
  83. data/lib/rubbycop/cop/layout/indentation_width.rb +303 -0
  84. data/lib/rubbycop/cop/layout/initial_indentation.rb +42 -0
  85. data/lib/rubbycop/cop/layout/leading_comment_space.rb +43 -0
  86. data/lib/rubbycop/cop/layout/multiline_array_brace_layout.rb +81 -0
  87. data/lib/rubbycop/cop/layout/multiline_assignment_layout.rb +88 -0
  88. data/lib/rubbycop/cop/layout/multiline_block_layout.rb +134 -0
  89. data/lib/rubbycop/cop/layout/multiline_hash_brace_layout.rb +81 -0
  90. data/lib/rubbycop/cop/layout/multiline_method_call_brace_layout.rb +97 -0
  91. data/lib/rubbycop/cop/layout/multiline_method_call_indentation.rb +215 -0
  92. data/lib/rubbycop/cop/layout/multiline_method_definition_brace_layout.rb +82 -0
  93. data/lib/rubbycop/cop/layout/multiline_operation_indentation.rb +89 -0
  94. data/lib/rubbycop/cop/layout/rescue_ensure_alignment.rb +86 -0
  95. data/lib/rubbycop/cop/layout/space_after_colon.rb +40 -0
  96. data/lib/rubbycop/cop/layout/space_after_comma.rb +21 -0
  97. data/lib/rubbycop/cop/layout/space_after_method_name.rb +37 -0
  98. data/lib/rubbycop/cop/layout/space_after_not.rb +38 -0
  99. data/lib/rubbycop/cop/layout/space_after_semicolon.rb +21 -0
  100. data/lib/rubbycop/cop/layout/space_around_block_parameters.rb +109 -0
  101. data/lib/rubbycop/cop/layout/space_around_equals_in_parameter_default.rb +68 -0
  102. data/lib/rubbycop/cop/layout/space_around_keyword.rb +224 -0
  103. data/lib/rubbycop/cop/layout/space_around_operators.rb +142 -0
  104. data/lib/rubbycop/cop/layout/space_before_block_braces.rb +54 -0
  105. data/lib/rubbycop/cop/layout/space_before_comma.rb +16 -0
  106. data/lib/rubbycop/cop/layout/space_before_comment.rb +27 -0
  107. data/lib/rubbycop/cop/layout/space_before_first_arg.rb +64 -0
  108. data/lib/rubbycop/cop/layout/space_before_semicolon.rb +16 -0
  109. data/lib/rubbycop/cop/layout/space_in_lambda_literal.rb +87 -0
  110. data/lib/rubbycop/cop/layout/space_inside_array_percent_literal.rb +53 -0
  111. data/lib/rubbycop/cop/layout/space_inside_block_braces.rb +158 -0
  112. data/lib/rubbycop/cop/layout/space_inside_brackets.rb +20 -0
  113. data/lib/rubbycop/cop/layout/space_inside_hash_literal_braces.rb +150 -0
  114. data/lib/rubbycop/cop/layout/space_inside_parens.rb +16 -0
  115. data/lib/rubbycop/cop/layout/space_inside_percent_literal_delimiters.rb +64 -0
  116. data/lib/rubbycop/cop/layout/space_inside_range_literal.rb +63 -0
  117. data/lib/rubbycop/cop/layout/space_inside_string_interpolation.rb +65 -0
  118. data/lib/rubbycop/cop/layout/tab.rb +57 -0
  119. data/lib/rubbycop/cop/layout/trailing_blank_lines.rb +78 -0
  120. data/lib/rubbycop/cop/layout/trailing_whitespace.rb +28 -0
  121. data/lib/rubbycop/cop/lint/ambiguous_block_association.rb +66 -0
  122. data/lib/rubbycop/cop/lint/ambiguous_operator.rb +55 -0
  123. data/lib/rubbycop/cop/lint/ambiguous_regexp_literal.rb +43 -0
  124. data/lib/rubbycop/cop/lint/assignment_in_condition.rb +80 -0
  125. data/lib/rubbycop/cop/lint/block_alignment.rb +229 -0
  126. data/lib/rubbycop/cop/lint/circular_argument_reference.rb +83 -0
  127. data/lib/rubbycop/cop/lint/condition_position.rb +52 -0
  128. data/lib/rubbycop/cop/lint/debugger.rb +72 -0
  129. data/lib/rubbycop/cop/lint/def_end_alignment.rb +78 -0
  130. data/lib/rubbycop/cop/lint/deprecated_class_methods.rb +90 -0
  131. data/lib/rubbycop/cop/lint/duplicate_case_condition.rb +53 -0
  132. data/lib/rubbycop/cop/lint/duplicate_methods.rb +151 -0
  133. data/lib/rubbycop/cop/lint/duplicated_key.rb +38 -0
  134. data/lib/rubbycop/cop/lint/each_with_object_argument.rb +39 -0
  135. data/lib/rubbycop/cop/lint/else_layout.rb +65 -0
  136. data/lib/rubbycop/cop/lint/empty_ensure.rb +60 -0
  137. data/lib/rubbycop/cop/lint/empty_expression.rb +42 -0
  138. data/lib/rubbycop/cop/lint/empty_interpolation.rb +36 -0
  139. data/lib/rubbycop/cop/lint/empty_when.rb +38 -0
  140. data/lib/rubbycop/cop/lint/end_alignment.rb +157 -0
  141. data/lib/rubbycop/cop/lint/end_in_method.rb +40 -0
  142. data/lib/rubbycop/cop/lint/ensure_return.rb +43 -0
  143. data/lib/rubbycop/cop/lint/float_out_of_range.rb +35 -0
  144. data/lib/rubbycop/cop/lint/format_parameter_mismatch.rb +182 -0
  145. data/lib/rubbycop/cop/lint/handle_exceptions.rb +56 -0
  146. data/lib/rubbycop/cop/lint/implicit_string_concatenation.rb +95 -0
  147. data/lib/rubbycop/cop/lint/ineffective_access_modifier.rb +143 -0
  148. data/lib/rubbycop/cop/lint/inherit_exception.rb +83 -0
  149. data/lib/rubbycop/cop/lint/invalid_character_literal.rb +41 -0
  150. data/lib/rubbycop/cop/lint/literal_in_condition.rb +127 -0
  151. data/lib/rubbycop/cop/lint/literal_in_interpolation.rb +76 -0
  152. data/lib/rubbycop/cop/lint/loop.rb +63 -0
  153. data/lib/rubbycop/cop/lint/multiple_compare.rb +48 -0
  154. data/lib/rubbycop/cop/lint/nested_method_definition.rb +105 -0
  155. data/lib/rubbycop/cop/lint/next_without_accumulator.rb +50 -0
  156. data/lib/rubbycop/cop/lint/non_local_exit_from_iterator.rb +85 -0
  157. data/lib/rubbycop/cop/lint/parentheses_as_grouped_expression.rb +60 -0
  158. data/lib/rubbycop/cop/lint/percent_string_array.rb +84 -0
  159. data/lib/rubbycop/cop/lint/percent_symbol_array.rb +66 -0
  160. data/lib/rubbycop/cop/lint/rand_one.rb +39 -0
  161. data/lib/rubbycop/cop/lint/require_parentheses.rb +61 -0
  162. data/lib/rubbycop/cop/lint/rescue_exception.rb +45 -0
  163. data/lib/rubbycop/cop/lint/safe_navigation_chain.rb +70 -0
  164. data/lib/rubbycop/cop/lint/shadowed_exception.rb +132 -0
  165. data/lib/rubbycop/cop/lint/shadowing_outer_local_variable.rb +53 -0
  166. data/lib/rubbycop/cop/lint/string_conversion_in_interpolation.rb +58 -0
  167. data/lib/rubbycop/cop/lint/syntax.rb +55 -0
  168. data/lib/rubbycop/cop/lint/underscore_prefixed_variable_name.rb +62 -0
  169. data/lib/rubbycop/cop/lint/unified_integer.rb +42 -0
  170. data/lib/rubbycop/cop/lint/unneeded_disable.rb +231 -0
  171. data/lib/rubbycop/cop/lint/unneeded_splat_expansion.rb +141 -0
  172. data/lib/rubbycop/cop/lint/unreachable_code.rb +52 -0
  173. data/lib/rubbycop/cop/lint/unused_block_argument.rb +145 -0
  174. data/lib/rubbycop/cop/lint/unused_method_argument.rb +61 -0
  175. data/lib/rubbycop/cop/lint/useless_access_modifier.rb +229 -0
  176. data/lib/rubbycop/cop/lint/useless_assignment.rb +132 -0
  177. data/lib/rubbycop/cop/lint/useless_comparison.rb +28 -0
  178. data/lib/rubbycop/cop/lint/useless_else_without_rescue.rb +46 -0
  179. data/lib/rubbycop/cop/lint/useless_setter_call.rb +162 -0
  180. data/lib/rubbycop/cop/lint/void.rb +108 -0
  181. data/lib/rubbycop/cop/message_annotator.rb +116 -0
  182. data/lib/rubbycop/cop/metrics/abc_size.rb +39 -0
  183. data/lib/rubbycop/cop/metrics/block_length.rb +32 -0
  184. data/lib/rubbycop/cop/metrics/block_nesting.rb +64 -0
  185. data/lib/rubbycop/cop/metrics/class_length.rb +24 -0
  186. data/lib/rubbycop/cop/metrics/cyclomatic_complexity.rb +31 -0
  187. data/lib/rubbycop/cop/metrics/line_length.rb +168 -0
  188. data/lib/rubbycop/cop/metrics/method_length.rb +27 -0
  189. data/lib/rubbycop/cop/metrics/module_length.rb +24 -0
  190. data/lib/rubbycop/cop/metrics/parameter_lists.rb +45 -0
  191. data/lib/rubbycop/cop/metrics/perceived_complexity.rb +61 -0
  192. data/lib/rubbycop/cop/mixin/access_modifier_node.rb +41 -0
  193. data/lib/rubbycop/cop/mixin/annotation_comment.rb +36 -0
  194. data/lib/rubbycop/cop/mixin/array_hash_indentation.rb +82 -0
  195. data/lib/rubbycop/cop/mixin/array_min_size.rb +59 -0
  196. data/lib/rubbycop/cop/mixin/array_syntax.rb +15 -0
  197. data/lib/rubbycop/cop/mixin/autocorrect_alignment.rb +149 -0
  198. data/lib/rubbycop/cop/mixin/check_assignment.rb +40 -0
  199. data/lib/rubbycop/cop/mixin/classish_length.rb +36 -0
  200. data/lib/rubbycop/cop/mixin/code_length.rb +32 -0
  201. data/lib/rubbycop/cop/mixin/configurable_enforced_style.rb +97 -0
  202. data/lib/rubbycop/cop/mixin/configurable_formatting.rb +48 -0
  203. data/lib/rubbycop/cop/mixin/configurable_max.rb +19 -0
  204. data/lib/rubbycop/cop/mixin/configurable_naming.rb +16 -0
  205. data/lib/rubbycop/cop/mixin/configurable_numbering.rb +17 -0
  206. data/lib/rubbycop/cop/mixin/def_node.rb +27 -0
  207. data/lib/rubbycop/cop/mixin/documentation_comment.rb +46 -0
  208. data/lib/rubbycop/cop/mixin/duplication.rb +46 -0
  209. data/lib/rubbycop/cop/mixin/empty_lines_around_body.rb +161 -0
  210. data/lib/rubbycop/cop/mixin/end_keyword_alignment.rb +85 -0
  211. data/lib/rubbycop/cop/mixin/enforce_superclass.rb +36 -0
  212. data/lib/rubbycop/cop/mixin/first_element_line_break.rb +41 -0
  213. data/lib/rubbycop/cop/mixin/frozen_string_literal.rb +37 -0
  214. data/lib/rubbycop/cop/mixin/hash_alignment.rb +116 -0
  215. data/lib/rubbycop/cop/mixin/ignored_pattern.rb +27 -0
  216. data/lib/rubbycop/cop/mixin/integer_node.rb +12 -0
  217. data/lib/rubbycop/cop/mixin/match_range.rb +22 -0
  218. data/lib/rubbycop/cop/mixin/method_complexity.rb +30 -0
  219. data/lib/rubbycop/cop/mixin/method_preference.rb +30 -0
  220. data/lib/rubbycop/cop/mixin/min_body_length.rb +19 -0
  221. data/lib/rubbycop/cop/mixin/multiline_expression_indentation.rb +183 -0
  222. data/lib/rubbycop/cop/mixin/multiline_literal_brace_layout.rb +152 -0
  223. data/lib/rubbycop/cop/mixin/negative_conditional.rb +43 -0
  224. data/lib/rubbycop/cop/mixin/on_method_def.rb +44 -0
  225. data/lib/rubbycop/cop/mixin/on_normal_if_unless.rb +14 -0
  226. data/lib/rubbycop/cop/mixin/parentheses.rb +22 -0
  227. data/lib/rubbycop/cop/mixin/parser_diagnostic.rb +34 -0
  228. data/lib/rubbycop/cop/mixin/percent_literal.rb +100 -0
  229. data/lib/rubbycop/cop/mixin/preceding_following_alignment.rb +89 -0
  230. data/lib/rubbycop/cop/mixin/rescue_node.rb +21 -0
  231. data/lib/rubbycop/cop/mixin/safe_assignment.rb +20 -0
  232. data/lib/rubbycop/cop/mixin/safe_mode.rb +22 -0
  233. data/lib/rubbycop/cop/mixin/space_after_punctuation.rb +55 -0
  234. data/lib/rubbycop/cop/mixin/space_before_punctuation.rb +48 -0
  235. data/lib/rubbycop/cop/mixin/space_inside.rb +76 -0
  236. data/lib/rubbycop/cop/mixin/statement_modifier.rb +69 -0
  237. data/lib/rubbycop/cop/mixin/string_help.rb +33 -0
  238. data/lib/rubbycop/cop/mixin/string_literals_help.rb +33 -0
  239. data/lib/rubbycop/cop/mixin/surrounding_space.rb +40 -0
  240. data/lib/rubbycop/cop/mixin/target_rails_version.rb +16 -0
  241. data/lib/rubbycop/cop/mixin/target_ruby_version.rb +16 -0
  242. data/lib/rubbycop/cop/mixin/too_many_lines.rb +39 -0
  243. data/lib/rubbycop/cop/mixin/trailing_comma.rb +161 -0
  244. data/lib/rubbycop/cop/mixin/unused_argument.rb +42 -0
  245. data/lib/rubbycop/cop/offense.rb +188 -0
  246. data/lib/rubbycop/cop/performance/caller.rb +41 -0
  247. data/lib/rubbycop/cop/performance/case_when_splat.rb +176 -0
  248. data/lib/rubbycop/cop/performance/casecmp.rb +107 -0
  249. data/lib/rubbycop/cop/performance/compare_with_block.rb +107 -0
  250. data/lib/rubbycop/cop/performance/count.rb +98 -0
  251. data/lib/rubbycop/cop/performance/detect.rb +107 -0
  252. data/lib/rubbycop/cop/performance/double_start_end_with.rb +102 -0
  253. data/lib/rubbycop/cop/performance/end_with.rb +55 -0
  254. data/lib/rubbycop/cop/performance/fixed_size.rb +56 -0
  255. data/lib/rubbycop/cop/performance/flat_map.rb +73 -0
  256. data/lib/rubbycop/cop/performance/hash_each_methods.rb +84 -0
  257. data/lib/rubbycop/cop/performance/lstrip_rstrip.rb +41 -0
  258. data/lib/rubbycop/cop/performance/range_include.rb +41 -0
  259. data/lib/rubbycop/cop/performance/redundant_block_call.rb +93 -0
  260. data/lib/rubbycop/cop/performance/redundant_match.rb +55 -0
  261. data/lib/rubbycop/cop/performance/redundant_merge.rb +149 -0
  262. data/lib/rubbycop/cop/performance/redundant_sort_by.rb +45 -0
  263. data/lib/rubbycop/cop/performance/regexp_match.rb +215 -0
  264. data/lib/rubbycop/cop/performance/reverse_each.rb +40 -0
  265. data/lib/rubbycop/cop/performance/sample.rb +140 -0
  266. data/lib/rubbycop/cop/performance/size.rb +71 -0
  267. data/lib/rubbycop/cop/performance/start_with.rb +58 -0
  268. data/lib/rubbycop/cop/performance/string_replacement.rb +170 -0
  269. data/lib/rubbycop/cop/performance/times_map.rb +61 -0
  270. data/lib/rubbycop/cop/rails/action_filter.rb +96 -0
  271. data/lib/rubbycop/cop/rails/active_support_aliases.rb +68 -0
  272. data/lib/rubbycop/cop/rails/application_job.rb +32 -0
  273. data/lib/rubbycop/cop/rails/application_record.rb +32 -0
  274. data/lib/rubbycop/cop/rails/blank.rb +138 -0
  275. data/lib/rubbycop/cop/rails/date.rb +127 -0
  276. data/lib/rubbycop/cop/rails/delegate.rb +106 -0
  277. data/lib/rubbycop/cop/rails/delegate_allow_blank.rb +51 -0
  278. data/lib/rubbycop/cop/rails/dynamic_find_by.rb +81 -0
  279. data/lib/rubbycop/cop/rails/enum_uniqueness.rb +43 -0
  280. data/lib/rubbycop/cop/rails/exit.rb +61 -0
  281. data/lib/rubbycop/cop/rails/file_path.rb +75 -0
  282. data/lib/rubbycop/cop/rails/find_by.rb +51 -0
  283. data/lib/rubbycop/cop/rails/find_each.rb +47 -0
  284. data/lib/rubbycop/cop/rails/has_and_belongs_to_many.rb +18 -0
  285. data/lib/rubbycop/cop/rails/http_positional_arguments.rb +106 -0
  286. data/lib/rubbycop/cop/rails/not_null_column.rb +67 -0
  287. data/lib/rubbycop/cop/rails/output.rb +23 -0
  288. data/lib/rubbycop/cop/rails/output_safety.rb +58 -0
  289. data/lib/rubbycop/cop/rails/pluralization_grammar.rb +106 -0
  290. data/lib/rubbycop/cop/rails/present.rb +143 -0
  291. data/lib/rubbycop/cop/rails/read_write_attribute.rb +65 -0
  292. data/lib/rubbycop/cop/rails/relative_date_constant.rb +88 -0
  293. data/lib/rubbycop/cop/rails/request_referer.rb +56 -0
  294. data/lib/rubbycop/cop/rails/reversible_migration.rb +216 -0
  295. data/lib/rubbycop/cop/rails/safe_navigation.rb +91 -0
  296. data/lib/rubbycop/cop/rails/save_bang.rb +160 -0
  297. data/lib/rubbycop/cop/rails/scope_args.rb +29 -0
  298. data/lib/rubbycop/cop/rails/skips_model_validations.rb +63 -0
  299. data/lib/rubbycop/cop/rails/time_zone.rb +197 -0
  300. data/lib/rubbycop/cop/rails/uniq_before_pluck.rb +93 -0
  301. data/lib/rubbycop/cop/rails/validation.rb +64 -0
  302. data/lib/rubbycop/cop/registry.rb +171 -0
  303. data/lib/rubbycop/cop/security/eval.rb +30 -0
  304. data/lib/rubbycop/cop/security/json_load.rb +44 -0
  305. data/lib/rubbycop/cop/security/marshal_load.rb +37 -0
  306. data/lib/rubbycop/cop/security/yaml_load.rb +37 -0
  307. data/lib/rubbycop/cop/severity.rb +76 -0
  308. data/lib/rubbycop/cop/style/accessor_method_name.rb +45 -0
  309. data/lib/rubbycop/cop/style/alias.rb +119 -0
  310. data/lib/rubbycop/cop/style/and_or.rb +125 -0
  311. data/lib/rubbycop/cop/style/array_join.rb +30 -0
  312. data/lib/rubbycop/cop/style/ascii_comments.rb +38 -0
  313. data/lib/rubbycop/cop/style/ascii_identifiers.rb +36 -0
  314. data/lib/rubbycop/cop/style/attr.rb +50 -0
  315. data/lib/rubbycop/cop/style/auto_resource_cleanup.rb +42 -0
  316. data/lib/rubbycop/cop/style/bare_percent_literals.rb +57 -0
  317. data/lib/rubbycop/cop/style/begin_block.rb +16 -0
  318. data/lib/rubbycop/cop/style/block_comments.rb +46 -0
  319. data/lib/rubbycop/cop/style/block_delimiters.rb +228 -0
  320. data/lib/rubbycop/cop/style/braces_around_hash_parameters.rb +138 -0
  321. data/lib/rubbycop/cop/style/case_equality.rb +18 -0
  322. data/lib/rubbycop/cop/style/character_literal.rb +43 -0
  323. data/lib/rubbycop/cop/style/class_and_module_camel_case.rb +29 -0
  324. data/lib/rubbycop/cop/style/class_and_module_children.rb +69 -0
  325. data/lib/rubbycop/cop/style/class_check.rb +40 -0
  326. data/lib/rubbycop/cop/style/class_methods.rb +67 -0
  327. data/lib/rubbycop/cop/style/class_vars.rb +23 -0
  328. data/lib/rubbycop/cop/style/collection_methods.rb +51 -0
  329. data/lib/rubbycop/cop/style/colon_method_call.rb +33 -0
  330. data/lib/rubbycop/cop/style/command_literal.rb +119 -0
  331. data/lib/rubbycop/cop/style/comment_annotation.rb +62 -0
  332. data/lib/rubbycop/cop/style/conditional_assignment.rb +691 -0
  333. data/lib/rubbycop/cop/style/constant_name.rb +29 -0
  334. data/lib/rubbycop/cop/style/copyright.rb +89 -0
  335. data/lib/rubbycop/cop/style/def_with_parentheses.rb +31 -0
  336. data/lib/rubbycop/cop/style/documentation.rb +79 -0
  337. data/lib/rubbycop/cop/style/documentation_method.rb +80 -0
  338. data/lib/rubbycop/cop/style/double_negation.rb +35 -0
  339. data/lib/rubbycop/cop/style/each_for_simple_loop.rb +57 -0
  340. data/lib/rubbycop/cop/style/each_with_object.rb +91 -0
  341. data/lib/rubbycop/cop/style/empty_case_condition.rb +84 -0
  342. data/lib/rubbycop/cop/style/empty_else.rb +138 -0
  343. data/lib/rubbycop/cop/style/empty_literal.rb +108 -0
  344. data/lib/rubbycop/cop/style/empty_method.rb +102 -0
  345. data/lib/rubbycop/cop/style/encoding.rb +92 -0
  346. data/lib/rubbycop/cop/style/end_block.rb +17 -0
  347. data/lib/rubbycop/cop/style/even_odd.rb +56 -0
  348. data/lib/rubbycop/cop/style/file_name.rb +183 -0
  349. data/lib/rubbycop/cop/style/flip_flop.rb +20 -0
  350. data/lib/rubbycop/cop/style/for.rb +50 -0
  351. data/lib/rubbycop/cop/style/format_string.rb +46 -0
  352. data/lib/rubbycop/cop/style/format_string_token.rb +141 -0
  353. data/lib/rubbycop/cop/style/frozen_string_literal_comment.rb +96 -0
  354. data/lib/rubbycop/cop/style/global_vars.rb +70 -0
  355. data/lib/rubbycop/cop/style/guard_clause.rb +90 -0
  356. data/lib/rubbycop/cop/style/hash_syntax.rb +214 -0
  357. data/lib/rubbycop/cop/style/identical_conditional_branches.rb +130 -0
  358. data/lib/rubbycop/cop/style/if_inside_else.rb +45 -0
  359. data/lib/rubbycop/cop/style/if_unless_modifier.rb +80 -0
  360. data/lib/rubbycop/cop/style/if_unless_modifier_of_if_unless.rb +38 -0
  361. data/lib/rubbycop/cop/style/if_with_semicolon.rb +20 -0
  362. data/lib/rubbycop/cop/style/implicit_runtime_error.rb +31 -0
  363. data/lib/rubbycop/cop/style/infinite_loop.rb +91 -0
  364. data/lib/rubbycop/cop/style/inline_comment.rb +32 -0
  365. data/lib/rubbycop/cop/style/inverse_methods.rb +130 -0
  366. data/lib/rubbycop/cop/style/lambda.rb +209 -0
  367. data/lib/rubbycop/cop/style/lambda_call.rb +66 -0
  368. data/lib/rubbycop/cop/style/line_end_concatenation.rb +115 -0
  369. data/lib/rubbycop/cop/style/method_call_with_args_parentheses.rb +107 -0
  370. data/lib/rubbycop/cop/style/method_call_without_args_parentheses.rb +75 -0
  371. data/lib/rubbycop/cop/style/method_called_on_do_end_block.rb +44 -0
  372. data/lib/rubbycop/cop/style/method_def_parentheses.rb +83 -0
  373. data/lib/rubbycop/cop/style/method_missing.rb +81 -0
  374. data/lib/rubbycop/cop/style/method_name.rb +28 -0
  375. data/lib/rubbycop/cop/style/missing_else.rb +100 -0
  376. data/lib/rubbycop/cop/style/mixin_grouping.rb +135 -0
  377. data/lib/rubbycop/cop/style/module_function.rb +64 -0
  378. data/lib/rubbycop/cop/style/multiline_block_chain.rb +42 -0
  379. data/lib/rubbycop/cop/style/multiline_if_modifier.rb +63 -0
  380. data/lib/rubbycop/cop/style/multiline_if_then.rb +47 -0
  381. data/lib/rubbycop/cop/style/multiline_memoization.rb +77 -0
  382. data/lib/rubbycop/cop/style/multiline_ternary_operator.rb +19 -0
  383. data/lib/rubbycop/cop/style/mutable_constant.rb +68 -0
  384. data/lib/rubbycop/cop/style/negated_if.rb +103 -0
  385. data/lib/rubbycop/cop/style/negated_while.rb +32 -0
  386. data/lib/rubbycop/cop/style/nested_modifier.rb +87 -0
  387. data/lib/rubbycop/cop/style/nested_parenthesized_calls.rb +61 -0
  388. data/lib/rubbycop/cop/style/nested_ternary_operator.rb +21 -0
  389. data/lib/rubbycop/cop/style/next.rb +225 -0
  390. data/lib/rubbycop/cop/style/nil_comparison.rb +35 -0
  391. data/lib/rubbycop/cop/style/non_nil_check.rb +121 -0
  392. data/lib/rubbycop/cop/style/not.rb +69 -0
  393. data/lib/rubbycop/cop/style/numeric_literal_prefix.rb +97 -0
  394. data/lib/rubbycop/cop/style/numeric_literals.rb +101 -0
  395. data/lib/rubbycop/cop/style/numeric_predicate.rb +140 -0
  396. data/lib/rubbycop/cop/style/one_line_conditional.rb +75 -0
  397. data/lib/rubbycop/cop/style/op_method.rb +41 -0
  398. data/lib/rubbycop/cop/style/option_hash.rb +58 -0
  399. data/lib/rubbycop/cop/style/optional_arguments.rb +62 -0
  400. data/lib/rubbycop/cop/style/parallel_assignment.rb +287 -0
  401. data/lib/rubbycop/cop/style/parentheses_around_condition.rb +56 -0
  402. data/lib/rubbycop/cop/style/percent_literal_delimiters.rb +100 -0
  403. data/lib/rubbycop/cop/style/percent_q_literals.rb +52 -0
  404. data/lib/rubbycop/cop/style/perl_backrefs.rb +31 -0
  405. data/lib/rubbycop/cop/style/predicate_name.rb +67 -0
  406. data/lib/rubbycop/cop/style/preferred_hash_methods.rb +78 -0
  407. data/lib/rubbycop/cop/style/proc.rb +26 -0
  408. data/lib/rubbycop/cop/style/raise_args.rb +140 -0
  409. data/lib/rubbycop/cop/style/redundant_begin.rb +47 -0
  410. data/lib/rubbycop/cop/style/redundant_exception.rb +55 -0
  411. data/lib/rubbycop/cop/style/redundant_freeze.rb +45 -0
  412. data/lib/rubbycop/cop/style/redundant_parentheses.rb +199 -0
  413. data/lib/rubbycop/cop/style/redundant_return.rb +121 -0
  414. data/lib/rubbycop/cop/style/redundant_self.rb +144 -0
  415. data/lib/rubbycop/cop/style/regexp_literal.rb +114 -0
  416. data/lib/rubbycop/cop/style/rescue_modifier.rb +37 -0
  417. data/lib/rubbycop/cop/style/safe_navigation.rb +145 -0
  418. data/lib/rubbycop/cop/style/self_assignment.rb +93 -0
  419. data/lib/rubbycop/cop/style/semicolon.rb +70 -0
  420. data/lib/rubbycop/cop/style/send.rb +21 -0
  421. data/lib/rubbycop/cop/style/signal_exception.rb +109 -0
  422. data/lib/rubbycop/cop/style/single_line_block_params.rb +68 -0
  423. data/lib/rubbycop/cop/style/single_line_methods.rb +77 -0
  424. data/lib/rubbycop/cop/style/special_global_vars.rb +156 -0
  425. data/lib/rubbycop/cop/style/stabby_lambda_parentheses.rb +113 -0
  426. data/lib/rubbycop/cop/style/string_literals.rb +102 -0
  427. data/lib/rubbycop/cop/style/string_literals_in_interpolation.rb +30 -0
  428. data/lib/rubbycop/cop/style/string_methods.rb +34 -0
  429. data/lib/rubbycop/cop/style/struct_inheritance.rb +32 -0
  430. data/lib/rubbycop/cop/style/symbol_array.rb +109 -0
  431. data/lib/rubbycop/cop/style/symbol_literal.rb +32 -0
  432. data/lib/rubbycop/cop/style/symbol_proc.rb +143 -0
  433. data/lib/rubbycop/cop/style/ternary_parentheses.rb +200 -0
  434. data/lib/rubbycop/cop/style/trailing_comma_in_arguments.rb +64 -0
  435. data/lib/rubbycop/cop/style/trailing_comma_in_literal.rb +56 -0
  436. data/lib/rubbycop/cop/style/trailing_underscore_variable.rb +113 -0
  437. data/lib/rubbycop/cop/style/trivial_accessors.rb +176 -0
  438. data/lib/rubbycop/cop/style/unless_else.rb +39 -0
  439. data/lib/rubbycop/cop/style/unneeded_capital_w.rb +41 -0
  440. data/lib/rubbycop/cop/style/unneeded_interpolation.rb +98 -0
  441. data/lib/rubbycop/cop/style/unneeded_percent_q.rb +96 -0
  442. data/lib/rubbycop/cop/style/variable_interpolation.rb +44 -0
  443. data/lib/rubbycop/cop/style/variable_name.rb +39 -0
  444. data/lib/rubbycop/cop/style/variable_number.rb +78 -0
  445. data/lib/rubbycop/cop/style/when_then.rb +24 -0
  446. data/lib/rubbycop/cop/style/while_until_do.rb +36 -0
  447. data/lib/rubbycop/cop/style/while_until_modifier.rb +41 -0
  448. data/lib/rubbycop/cop/style/word_array.rb +114 -0
  449. data/lib/rubbycop/cop/style/zero_length_predicate.rb +90 -0
  450. data/lib/rubbycop/cop/team.rb +193 -0
  451. data/lib/rubbycop/cop/util.rb +309 -0
  452. data/lib/rubbycop/cop/variable_force.rb +458 -0
  453. data/lib/rubbycop/cop/variable_force/assignment.rb +90 -0
  454. data/lib/rubbycop/cop/variable_force/branch.rb +318 -0
  455. data/lib/rubbycop/cop/variable_force/branchable.rb +21 -0
  456. data/lib/rubbycop/cop/variable_force/reference.rb +49 -0
  457. data/lib/rubbycop/cop/variable_force/scope.rb +107 -0
  458. data/lib/rubbycop/cop/variable_force/variable.rb +103 -0
  459. data/lib/rubbycop/cop/variable_force/variable_table.rb +128 -0
  460. data/lib/rubbycop/error.rb +11 -0
  461. data/lib/rubbycop/formatter/base_formatter.rb +123 -0
  462. data/lib/rubbycop/formatter/clang_style_formatter.rb +54 -0
  463. data/lib/rubbycop/formatter/colorizable.rb +41 -0
  464. data/lib/rubbycop/formatter/disabled_config_formatter.rb +181 -0
  465. data/lib/rubbycop/formatter/disabled_lines_formatter.rb +57 -0
  466. data/lib/rubbycop/formatter/emacs_style_formatter.rb +24 -0
  467. data/lib/rubbycop/formatter/file_list_formatter.rb +19 -0
  468. data/lib/rubbycop/formatter/formatter_set.rb +102 -0
  469. data/lib/rubbycop/formatter/fuubar_style_formatter.rb +80 -0
  470. data/lib/rubbycop/formatter/html_formatter.rb +134 -0
  471. data/lib/rubbycop/formatter/json_formatter.rb +74 -0
  472. data/lib/rubbycop/formatter/offense_count_formatter.rb +55 -0
  473. data/lib/rubbycop/formatter/progress_formatter.rb +63 -0
  474. data/lib/rubbycop/formatter/simple_text_formatter.rb +136 -0
  475. data/lib/rubbycop/formatter/text_util.rb +20 -0
  476. data/lib/rubbycop/formatter/worst_offenders_formatter.rb +60 -0
  477. data/lib/rubbycop/magic_comment.rb +210 -0
  478. data/lib/rubbycop/name_similarity.rb +21 -0
  479. data/lib/rubbycop/node_pattern.rb +543 -0
  480. data/lib/rubbycop/options.rb +355 -0
  481. data/lib/rubbycop/path_util.rb +36 -0
  482. data/lib/rubbycop/platform.rb +11 -0
  483. data/lib/rubbycop/processed_source.rb +151 -0
  484. data/lib/rubbycop/rake_task.rb +86 -0
  485. data/lib/rubbycop/remote_config.rb +78 -0
  486. data/lib/rubbycop/result_cache.rb +176 -0
  487. data/lib/rubbycop/rspec/cop_helper.rb +98 -0
  488. data/lib/rubbycop/rspec/host_environment_simulation_helper.rb +32 -0
  489. data/lib/rubbycop/rspec/shared_contexts.rb +98 -0
  490. data/lib/rubbycop/rspec/shared_examples.rb +92 -0
  491. data/lib/rubbycop/rspec/support.rb +8 -0
  492. data/lib/rubbycop/runner.rb +338 -0
  493. data/lib/rubbycop/string_interpreter.rb +57 -0
  494. data/lib/rubbycop/string_util.rb +156 -0
  495. data/lib/rubbycop/target_finder.rb +201 -0
  496. data/lib/rubbycop/token.rb +25 -0
  497. data/lib/rubbycop/version.rb +19 -0
  498. data/lib/rubbycop/warning.rb +11 -0
  499. metadata +663 -0
@@ -0,0 +1,355 @@
1
+ # frozen_string_literal: true
2
+
3
+ require 'optparse'
4
+ require 'shellwords'
5
+
6
+ module RubbyCop
7
+ # This class handles command line options.
8
+ class Options
9
+ EXITING_OPTIONS = %i[version verbose_version show_cops].freeze
10
+ DEFAULT_MAXIMUM_EXCLUSION_ITEMS = 15
11
+
12
+ def initialize
13
+ @options = {}
14
+ @validator = OptionsValidator.new(@options)
15
+ end
16
+
17
+ def parse(command_line_args)
18
+ args = args_from_file.concat(args_from_env).concat(command_line_args)
19
+ define_options(args).parse!(args)
20
+ # The --no-color CLI option sets `color: false` so we don't want the
21
+ # `no_color` key, which is created automatically.
22
+ @options.delete(:no_color)
23
+
24
+ @validator.validate_compatibility
25
+
26
+ if @options[:stdin]
27
+ # The parser has put the file name given after --stdin into
28
+ # @options[:stdin]. The args array should be empty.
29
+ if args.any?
30
+ raise ArgumentError, '-s/--stdin requires exactly one path.'
31
+ end
32
+ # We want the STDIN contents in @options[:stdin] and the file name in
33
+ # args to simplify the rest of the processing.
34
+ args = [@options[:stdin]]
35
+ @options[:stdin] = $stdin.binmode.read
36
+ end
37
+
38
+ [@options, args]
39
+ end
40
+
41
+ private
42
+
43
+ def args_from_file
44
+ if File.exist?('.rubbycop') && !File.directory?('.rubbycop')
45
+ IO.readlines('.rubbycop').map(&:strip)
46
+ else
47
+ []
48
+ end
49
+ end
50
+
51
+ def args_from_env
52
+ Shellwords.split(ENV.fetch('RUBOCOP_OPTS', ''))
53
+ end
54
+
55
+ def define_options(args)
56
+ OptionParser.new do |opts|
57
+ opts.banner = 'Usage: rubbycop [options] [file1, file2, ...]'
58
+
59
+ add_list_options(opts)
60
+ add_only_options(opts)
61
+ add_configuration_options(opts, args)
62
+ add_formatting_options(opts)
63
+
64
+ option(opts, '-r', '--require FILE') { |f| require f }
65
+
66
+ add_severity_option(opts)
67
+ add_flags_with_optional_args(opts)
68
+ add_boolean_flags(opts)
69
+
70
+ option(opts, '-s', '--stdin FILE')
71
+ end
72
+ end
73
+
74
+ def add_only_options(opts)
75
+ add_cop_selection_csv_option('except', opts)
76
+ add_cop_selection_csv_option('only', opts)
77
+ option(opts, '--only-guide-cops')
78
+ end
79
+
80
+ def add_cop_selection_csv_option(option, opts)
81
+ option(opts, "--#{option} [COP1,COP2,...]") do |list|
82
+ @options[:"#{option}"] =
83
+ if list.empty?
84
+ ['']
85
+ else
86
+ list.split(',').map do |c|
87
+ Cop::Cop.qualified_cop_name(c, "--#{option} option")
88
+ end
89
+ end
90
+ end
91
+ end
92
+
93
+ def add_configuration_options(opts, args)
94
+ option(opts, '-c', '--config FILE')
95
+
96
+ option(opts, '--auto-gen-config')
97
+
98
+ option(opts, '--exclude-limit COUNT') do
99
+ @validator.validate_exclude_limit_option(args)
100
+ end
101
+
102
+ option(opts, '--force-exclusion')
103
+
104
+ option(opts, '--force-default-config')
105
+
106
+ option(opts, '--no-offense-counts') do
107
+ @options[:no_offense_counts] = true
108
+ end
109
+ end
110
+
111
+ def add_formatting_options(opts)
112
+ option(opts, '-f', '--format FORMATTER') do |key|
113
+ @options[:formatters] ||= []
114
+ @options[:formatters] << [key]
115
+ end
116
+
117
+ option(opts, '-o', '--out FILE') do |path|
118
+ if @options[:formatters]
119
+ @options[:formatters].last << path
120
+ else
121
+ @options[:output_path] = path
122
+ end
123
+ end
124
+ end
125
+
126
+ def add_severity_option(opts)
127
+ table = RubbyCop::Cop::Severity::CODE_TABLE.merge(A: :autocorrect)
128
+ option(opts, '--fail-level SEVERITY',
129
+ RubbyCop::Cop::Severity::NAMES + [:autocorrect],
130
+ table) do |severity|
131
+ @options[:fail_level] = severity
132
+ end
133
+ end
134
+
135
+ def add_flags_with_optional_args(opts)
136
+ option(opts, '--show-cops [COP1,COP2,...]') do |list|
137
+ @options[:show_cops] = list.nil? ? [] : list.split(',')
138
+ end
139
+ end
140
+
141
+ def add_boolean_flags(opts) # rubbycop:disable Metrics/MethodLength
142
+ option(opts, '-F', '--fail-fast')
143
+ option(opts, '-C', '--cache FLAG')
144
+ option(opts, '-d', '--debug')
145
+ option(opts, '-D', '--display-cop-names')
146
+ option(opts, '-E', '--extra-details')
147
+ option(opts, '-S', '--display-style-guide')
148
+ option(opts, '-R', '--rails')
149
+ option(opts, '-l', '--lint') do
150
+ @options[:only] ||= []
151
+ @options[:only] << 'Lint'
152
+ end
153
+ option(opts, '-a', '--auto-correct')
154
+
155
+ option(opts, '--[no-]color') { |c| @options[:color] = c }
156
+
157
+ option(opts, '-v', '--version')
158
+ option(opts, '-V', '--verbose-version')
159
+ option(opts, '-P', '--parallel')
160
+ end
161
+
162
+ def add_list_options(opts)
163
+ option(opts, '-L', '--list-target-files')
164
+ end
165
+
166
+ # Sets a value in the @options hash, based on the given long option and its
167
+ # value, in addition to calling the block if a block is given.
168
+ def option(opts, *args)
169
+ long_opt_symbol = long_opt_symbol(args)
170
+ args += Array(OptionsHelp::TEXT[long_opt_symbol])
171
+ opts.on(*args) do |arg|
172
+ @options[long_opt_symbol] = arg
173
+ yield arg if block_given?
174
+ end
175
+ end
176
+
177
+ # Finds the option in `args` starting with -- and converts it to a symbol,
178
+ # e.g. [..., '--auto-correct', ...] to :auto_correct.
179
+ def long_opt_symbol(args)
180
+ long_opt = args.find { |arg| arg.start_with?('--') }
181
+ long_opt[2..-1].sub(/ .*/, '').tr('-', '_').gsub(/[\[\]]/, '').to_sym
182
+ end
183
+ end
184
+
185
+ # Validates option arguments and the options' compatibility with each other.
186
+ class OptionsValidator
187
+ # Cop name validation must be done later than option parsing, so it's not
188
+ # called from within Options.
189
+ def self.validate_cop_list(names)
190
+ return unless names
191
+
192
+ departments = Cop::Cop.registry.departments.map(&:to_s)
193
+
194
+ names.each do |name|
195
+ next if Cop::Cop.registry.names.include?(name)
196
+ next if departments.include?(name)
197
+ next if %w[Syntax Lint/Syntax].include?(name)
198
+
199
+ raise ArgumentError, "Unrecognized cop or department: #{name}."
200
+ end
201
+ end
202
+
203
+ def initialize(options)
204
+ @options = options
205
+ end
206
+
207
+ def validate_compatibility # rubbycop:disable Metrics/MethodLength
208
+ if only_includes_unneeded_disable?
209
+ raise ArgumentError, 'Lint/UnneededDisable can not be used with --only.'
210
+ end
211
+ if except_syntax?
212
+ raise ArgumentError, 'Syntax checking can not be turned off.'
213
+ end
214
+ unless boolean_or_empty_cache?
215
+ raise ArgumentError, '-C/--cache argument must be true or false'
216
+ end
217
+ if no_offense_counts_without_auto_gen_config?
218
+ raise ArgumentError, '--no-offense-counts can only be used together ' \
219
+ 'with --auto-gen-config.'
220
+ end
221
+ validate_parallel
222
+
223
+ return if incompatible_options.size <= 1
224
+ raise ArgumentError, 'Incompatible cli options: ' \
225
+ "#{incompatible_options.inspect}"
226
+ end
227
+
228
+ def validate_parallel
229
+ return unless @options.key?(:parallel)
230
+
231
+ if @options[:cache] == 'false'
232
+ raise ArgumentError, '-P/--parallel uses caching to speed up ' \
233
+ 'execution, so combining with --cache false is ' \
234
+ 'not allowed.'
235
+ end
236
+
237
+ combos = {
238
+ auto_gen_config: '-P/--parallel uses caching to speed up execution, ' \
239
+ 'while --auto-gen-config needs a non-cached run, ' \
240
+ 'so they cannot be combined.',
241
+ fail_fast: '-P/--parallel can not be combined with -F/--fail-fast.',
242
+ auto_correct: '-P/--parallel can not be combined with --auto-correct.'
243
+ }
244
+
245
+ combos.each { |key, msg| raise ArgumentError, msg if @options.key?(key) }
246
+ end
247
+
248
+ def only_includes_unneeded_disable?
249
+ @options.key?(:only) &&
250
+ (@options[:only] & %w[Lint/UnneededDisable UnneededDisable]).any?
251
+ end
252
+
253
+ def except_syntax?
254
+ @options.key?(:except) &&
255
+ (@options[:except] & %w[Lint/Syntax Syntax]).any?
256
+ end
257
+
258
+ def boolean_or_empty_cache?
259
+ !@options.key?(:cache) || %w[true false].include?(@options[:cache])
260
+ end
261
+
262
+ def no_offense_counts_without_auto_gen_config?
263
+ @options.key?(:no_offense_counts) && !@options.key?(:auto_gen_config)
264
+ end
265
+
266
+ def incompatible_options
267
+ @incompatible_options ||= @options.keys & Options::EXITING_OPTIONS
268
+ end
269
+
270
+ def validate_exclude_limit_option(args)
271
+ if @options[:exclude_limit] !~ /^\d+$/
272
+ # Emulate OptionParser's behavior to make failures consistent regardless
273
+ # of option order.
274
+ raise OptionParser::MissingArgument
275
+ end
276
+
277
+ # --exclude-limit is valid if there's a parsed or yet unparsed
278
+ # --auto-gen-config.
279
+ return if @options[:auto_gen_config] || args.include?('--auto-gen-config')
280
+
281
+ raise ArgumentError,
282
+ '--exclude-limit can only be used with --auto-gen-config.'
283
+ end
284
+ end
285
+
286
+ # This module contains help texts for command line options.
287
+ module OptionsHelp
288
+ MAX_EXCL = RubbyCop::Options::DEFAULT_MAXIMUM_EXCLUSION_ITEMS.to_s
289
+ TEXT = {
290
+ only: 'Run only the given cop(s).',
291
+ only_guide_cops: ['Run only cops for rules that link to a',
292
+ 'style guide.'],
293
+ except: 'Disable the given cop(s).',
294
+ require: 'Require Ruby file.',
295
+ config: 'Specify configuration file.',
296
+ auto_gen_config: ['Generate a configuration file acting as a',
297
+ 'TODO list.'],
298
+ no_offense_counts: ['Do not include offense counts in configuration',
299
+ 'file generated by --auto-gen-config.'],
300
+ exclude_limit: ['Used together with --auto-gen-config to',
301
+ 'set the limit for how many Exclude',
302
+ "properties to generate. Default is #{MAX_EXCL}."],
303
+ force_exclusion: ['Force excluding files specified in the',
304
+ 'configuration `Exclude` even if they are',
305
+ 'explicitly passed as arguments.'],
306
+ force_default_config: ['Use default configuration even if configuration',
307
+ 'files are present in the directory tree.'],
308
+ format: ['Choose an output formatter. This option',
309
+ 'can be specified multiple times to enable',
310
+ 'multiple formatters at the same time.',
311
+ ' [p]rogress (default)',
312
+ ' [s]imple',
313
+ ' [c]lang',
314
+ ' [d]isabled cops via inline comments',
315
+ ' [fu]ubar',
316
+ ' [e]macs',
317
+ ' [j]son',
318
+ ' [h]tml',
319
+ ' [fi]les',
320
+ ' [o]ffenses',
321
+ ' [w]orst',
322
+ ' custom formatter class name'],
323
+ out: ['Write output to a file instead of STDOUT.',
324
+ 'This option applies to the previously',
325
+ 'specified --format, or the default format',
326
+ 'if no format is specified.'],
327
+ fail_level: ['Minimum severity (A/R/C/W/E/F) for exit',
328
+ 'with error code.'],
329
+ show_cops: ['Shows the given cops, or all cops by',
330
+ 'default, and their configurations for the',
331
+ 'current directory.'],
332
+ fail_fast: ['Inspect files in order of modification',
333
+ 'time and stop after the first file',
334
+ 'containing offenses.'],
335
+ cache: ["Use result caching (FLAG=true) or don't",
336
+ '(FLAG=false), default determined by',
337
+ 'configuration parameter AllCops: UseCache.'],
338
+ debug: 'Display debug info.',
339
+ display_cop_names: 'Display cop names in offense messages.',
340
+ display_style_guide: 'Display style guide URLs in offense messages.',
341
+ extra_details: 'Display extra details in offense messages.',
342
+ rails: 'Run extra Rails cops.',
343
+ lint: 'Run only lint cops.',
344
+ list_target_files: 'List all files RubbyCop will inspect.',
345
+ auto_correct: 'Auto-correct offenses.',
346
+ no_color: 'Force color output on or off.',
347
+ version: 'Display version.',
348
+ verbose_version: 'Display verbose version.',
349
+ parallel: ['Use available CPUs to execute inspection in',
350
+ 'parallel.'],
351
+ stdin: ['Pipe source from STDIN, using FILE in offense',
352
+ 'reports. This is useful for editor integration.']
353
+ }.freeze
354
+ end
355
+ end
@@ -0,0 +1,36 @@
1
+ # frozen_string_literal: true
2
+
3
+ module RubbyCop
4
+ # Common methods and behaviors for dealing with paths.
5
+ module PathUtil
6
+ module_function
7
+
8
+ def relative_path(path, base_dir = Dir.pwd)
9
+ # Optimization for the common case where path begins with the base
10
+ # dir. Just cut off the first part.
11
+ return path[(base_dir.length + 1)..-1] if path.start_with?(base_dir)
12
+
13
+ path_name = Pathname.new(File.expand_path(path))
14
+ path_name.relative_path_from(Pathname.new(base_dir)).to_s
15
+ end
16
+
17
+ def match_path?(pattern, path)
18
+ case pattern
19
+ when String
20
+ File.fnmatch?(pattern, path, File::FNM_PATHNAME)
21
+ when Regexp
22
+ begin
23
+ path =~ pattern
24
+ rescue ArgumentError => e
25
+ return false if e.message.start_with?('invalid byte sequence')
26
+ raise e
27
+ end
28
+ end
29
+ end
30
+
31
+ # Returns true for an absolute Unix or Windows path.
32
+ def absolute?(path)
33
+ path =~ %r{\A([A-Z]:)?/}
34
+ end
35
+ end
36
+ end
@@ -0,0 +1,11 @@
1
+ # frozen_string_literal: true
2
+
3
+ module RubbyCop
4
+ # This module provides information on the platform that RubbyCop is being run
5
+ # on.
6
+ module Platform
7
+ def self.windows?
8
+ RUBY_PLATFORM =~ /cygwin|mswin|mingw|bccwin|wince|emx/
9
+ end
10
+ end
11
+ end
@@ -0,0 +1,151 @@
1
+ # frozen_string_literal: true
2
+
3
+ require 'digest/md5'
4
+
5
+ module RubbyCop
6
+ # ProcessedSource contains objects which are generated by Parser
7
+ # and other information such as disabled lines for cops.
8
+ # It also provides a convenient way to access source lines.
9
+ class ProcessedSource
10
+ STRING_SOURCE_NAME = '(string)'.freeze
11
+
12
+ attr_reader :path, :buffer, :ast, :comments, :tokens, :diagnostics,
13
+ :parser_error, :raw_source, :ruby_version
14
+
15
+ def self.from_file(path, ruby_version)
16
+ file = File.read(path, mode: 'rb')
17
+ new(file, ruby_version, path)
18
+ rescue Errno::ENOENT
19
+ raise RubbyCop::Error, "No such file or directory: #{path}"
20
+ end
21
+
22
+ def initialize(source, ruby_version, path = nil)
23
+ # Defaults source encoding to UTF-8, regardless of the encoding it has
24
+ # been read with, which could be non-utf8 depending on the default
25
+ # external encoding.
26
+ unless source.encoding == Encoding::UTF_8
27
+ source.force_encoding(Encoding::UTF_8)
28
+ end
29
+
30
+ @raw_source = source
31
+ @path = path
32
+ @diagnostics = []
33
+ @ruby_version = ruby_version
34
+ @parser_error = nil
35
+
36
+ parse(source, ruby_version)
37
+ end
38
+
39
+ def comment_config
40
+ @comment_config ||= CommentConfig.new(self)
41
+ end
42
+
43
+ def disabled_line_ranges
44
+ comment_config.cop_disabled_line_ranges
45
+ end
46
+
47
+ def ast_with_comments
48
+ return if !ast || !comments
49
+ @ast_with_comments ||= Parser::Source::Comment.associate(ast, comments)
50
+ end
51
+
52
+ # Returns the source lines, line break characters removed, excluding a
53
+ # possible __END__ and everything that comes after.
54
+ def lines
55
+ @lines ||= begin
56
+ all_lines = @buffer.source_lines
57
+ last_token_line = tokens.any? ? tokens.last.pos.line : all_lines.size
58
+ result = []
59
+ all_lines.each_with_index do |line, ix|
60
+ break if ix >= last_token_line && line == '__END__'
61
+ result << line
62
+ end
63
+ result
64
+ end
65
+ end
66
+
67
+ def [](*args)
68
+ lines[*args]
69
+ end
70
+
71
+ def valid_syntax?
72
+ return false if @parser_error
73
+ @diagnostics.none? { |d| %i[error fatal].include?(d.level) }
74
+ end
75
+
76
+ # Raw source checksum for tracking infinite loops.
77
+ def checksum
78
+ Digest::MD5.hexdigest(@raw_source)
79
+ end
80
+
81
+ private
82
+
83
+ def parse(source, ruby_version)
84
+ buffer_name = @path || STRING_SOURCE_NAME
85
+ @buffer = Parser::Source::Buffer.new(buffer_name, 1)
86
+
87
+ begin
88
+ @buffer.source = source
89
+ rescue EncodingError => error
90
+ @parser_error = error
91
+ return
92
+ end
93
+
94
+ @ast, @comments, @tokens = tokenize(create_parser(ruby_version))
95
+ end
96
+
97
+ def tokenize(parser)
98
+ begin
99
+ ast, comments, tokens = parser.tokenize(@buffer)
100
+ ast.complete! if ast
101
+ rescue Parser::SyntaxError # rubbycop:disable Lint/HandleExceptions
102
+ # All errors are in diagnostics. No need to handle exception.
103
+ end
104
+
105
+ tokens = tokens.map { |t| Token.from_parser_token(t) } if tokens
106
+
107
+ [ast, comments, tokens]
108
+ end
109
+
110
+ def parser_class(ruby_version) # rubbycop:disable Metrics/MethodLength
111
+ case ruby_version
112
+ when 1.9
113
+ require 'parser/ruby19'
114
+ Parser::Ruby19
115
+ when 2.0
116
+ require 'parser/ruby20'
117
+ Parser::Ruby20
118
+ when 2.1
119
+ require 'parser/ruby21'
120
+ Parser::Ruby21
121
+ when 2.2
122
+ require 'parser/ruby22'
123
+ Parser::Ruby22
124
+ when 2.3
125
+ require 'parser/ruby23'
126
+ Parser::Ruby23
127
+ when 2.4
128
+ require 'parser/ruby24'
129
+ Parser::Ruby24
130
+ else
131
+ raise ArgumentError, "Unknown Ruby version: #{ruby_version.inspect}"
132
+ end
133
+ end
134
+
135
+ def create_parser(ruby_version)
136
+ builder = RubbyCop::AST::Builder.new
137
+
138
+ parser_class(ruby_version).new(builder).tap do |parser|
139
+ # On JRuby and Rubinius, there's a risk that we hang in tokenize() if we
140
+ # don't set the all errors as fatal flag. The problem is caused by a bug
141
+ # in Racc that is discussed in issue #93 of the whitequark/parser
142
+ # project on GitHub.
143
+ parser.diagnostics.all_errors_are_fatal = (RUBY_ENGINE != 'ruby')
144
+ parser.diagnostics.ignore_warnings = false
145
+ parser.diagnostics.consumer = lambda do |diagnostic|
146
+ @diagnostics << diagnostic
147
+ end
148
+ end
149
+ end
150
+ end
151
+ end