rubocop 0.16.0 → 0.17.0
Sign up to get free protection for your applications and to get access to all the features.
Potentially problematic release.
This version of rubocop might be problematic. Click here for more details.
- checksums.yaml +4 -4
- data/.gitignore +1 -0
- data/.travis.yml +3 -1
- data/CHANGELOG.md +44 -0
- data/CONTRIBUTING.md +40 -8
- data/Gemfile +6 -0
- data/README.md +65 -20
- data/Rakefile +0 -1
- data/config/default.yml +15 -3
- data/config/enabled.yml +143 -109
- data/lib/rubocop.rb +45 -26
- data/lib/rubocop/cli.rb +26 -27
- data/lib/rubocop/config.rb +0 -1
- data/lib/rubocop/config_loader.rb +16 -23
- data/lib/rubocop/cop/commissioner.rb +2 -7
- data/lib/rubocop/cop/cop.rb +24 -51
- data/lib/rubocop/cop/ignored_node.rb +31 -0
- data/lib/rubocop/cop/lint/ambiguous_operator.rb +50 -0
- data/lib/rubocop/cop/lint/ambiguous_regexp_literal.rb +36 -0
- data/lib/rubocop/cop/lint/assignment_in_condition.rb +3 -11
- data/lib/rubocop/cop/lint/block_alignment.rb +6 -20
- data/lib/rubocop/cop/lint/condition_position.rb +52 -0
- data/lib/rubocop/cop/lint/else_layout.rb +57 -0
- data/lib/rubocop/cop/lint/end_alignment.rb +33 -8
- data/lib/rubocop/cop/lint/invalid_character_literal.rb +37 -0
- data/lib/rubocop/cop/lint/parentheses_as_grouped_expression.rb +2 -4
- data/lib/rubocop/cop/lint/syntax.rb +6 -12
- data/lib/rubocop/cop/lint/useless_else_without_rescue.rb +25 -0
- data/lib/rubocop/cop/mixin/array_syntax.rb +20 -0
- data/lib/rubocop/cop/mixin/autocorrect_alignment.rb +76 -0
- data/lib/rubocop/cop/mixin/check_assignment.rb +26 -0
- data/lib/rubocop/cop/{check_methods.rb → mixin/check_methods.rb} +0 -0
- data/lib/rubocop/cop/mixin/code_length.rb +33 -0
- data/lib/rubocop/cop/mixin/configurable_enforced_style.rb +53 -0
- data/lib/rubocop/cop/mixin/configurable_max.rb +19 -0
- data/lib/rubocop/cop/mixin/configurable_naming.rb +45 -0
- data/lib/rubocop/cop/{style → mixin}/if_node.rb +0 -0
- data/lib/rubocop/cop/mixin/if_then_else.rb +23 -0
- data/lib/rubocop/cop/mixin/negative_conditional.rb +24 -0
- data/lib/rubocop/cop/mixin/parser_diagnostic.rb +34 -0
- data/lib/rubocop/cop/mixin/safe_assignment.rb +19 -0
- data/lib/rubocop/cop/mixin/space_after_punctuation.rb +32 -0
- data/lib/rubocop/cop/mixin/space_inside.rb +31 -0
- data/lib/rubocop/cop/mixin/statement_modifier.rb +59 -0
- data/lib/rubocop/cop/mixin/string_help.rb +32 -0
- data/lib/rubocop/cop/mixin/surrounding_space.rb +42 -0
- data/lib/rubocop/cop/rails/default_scope.rb +3 -1
- data/lib/rubocop/cop/style/accessor_method_name.rb +4 -12
- data/lib/rubocop/cop/style/braces_around_hash_parameters.rb +16 -1
- data/lib/rubocop/cop/style/case_indentation.rb +33 -16
- data/lib/rubocop/cop/style/character_literal.rb +10 -0
- data/lib/rubocop/cop/style/dot_position.rb +23 -6
- data/lib/rubocop/cop/style/empty_lines_around_body.rb +5 -5
- data/lib/rubocop/cop/style/favor_unless_over_negated_if.rb +1 -32
- data/lib/rubocop/cop/style/favor_until_over_negated_while.rb +20 -0
- data/lib/rubocop/cop/style/hash_syntax.rb +5 -1
- data/lib/rubocop/cop/style/if_unless_modifier.rb +34 -0
- data/lib/rubocop/cop/style/if_with_semicolon.rb +1 -1
- data/lib/rubocop/cop/style/indentation_consistency.rb +51 -0
- data/lib/rubocop/cop/style/indentation_width.rb +0 -26
- data/lib/rubocop/cop/style/lambda_call.rb +12 -5
- data/lib/rubocop/cop/style/method_def_parentheses.rb +29 -11
- data/lib/rubocop/cop/style/multiline_if_then.rb +4 -9
- data/lib/rubocop/cop/style/multiline_ternary_operator.rb +22 -0
- data/lib/rubocop/cop/style/{ternary_operator.rb → nested_ternary_operator.rb} +0 -15
- data/lib/rubocop/cop/style/numeric_literals.rb +30 -2
- data/lib/rubocop/cop/style/one_line_conditional.rb +2 -1
- data/lib/rubocop/cop/style/parameter_lists.rb +7 -3
- data/lib/rubocop/cop/style/parentheses_around_condition.rb +9 -11
- data/lib/rubocop/cop/style/predicate_name.rb +4 -12
- data/lib/rubocop/cop/style/raise_args.rb +19 -11
- data/lib/rubocop/cop/style/regexp_literal.rb +19 -6
- data/lib/rubocop/cop/style/space_after_colon.rb +36 -0
- data/lib/rubocop/cop/style/space_after_comma.rb +16 -0
- data/lib/rubocop/cop/style/space_after_semicolon.rb +16 -0
- data/lib/rubocop/cop/style/space_around_block_braces.rb +38 -38
- data/lib/rubocop/cop/style/space_around_operators.rb +1 -2
- data/lib/rubocop/cop/style/space_inside_hash_literal_braces.rb +6 -2
- data/lib/rubocop/cop/style/string_literals.rb +5 -5
- data/lib/rubocop/cop/style/trailing_comma.rb +94 -0
- data/lib/rubocop/cop/style/unless_else.rb +2 -2
- data/lib/rubocop/cop/style/while_until_modifier.rb +32 -0
- data/lib/rubocop/cop/style/word_array.rb +9 -1
- data/lib/rubocop/cop/util.rb +14 -0
- data/lib/rubocop/cop/variable_inspector.rb +11 -6
- data/lib/rubocop/cop/variable_inspector/scope.rb +4 -3
- data/lib/rubocop/file_inspector.rb +22 -6
- data/lib/rubocop/formatter/clang_style_formatter.rb +1 -1
- data/lib/rubocop/formatter/colorizable.rb +37 -0
- data/lib/rubocop/formatter/disabled_config_formatter.rb +27 -6
- data/lib/rubocop/formatter/progress_formatter.rb +1 -1
- data/lib/rubocop/formatter/simple_text_formatter.rb +9 -5
- data/lib/rubocop/options.rb +19 -4
- data/lib/rubocop/target_finder.rb +4 -0
- data/lib/rubocop/version.rb +1 -1
- data/rubocop-todo.yml +10 -2
- data/rubocop.gemspec +3 -2
- data/spec/project_spec.rb +12 -7
- data/spec/rubocop/cli_spec.rb +262 -99
- data/spec/rubocop/config_loader_spec.rb +5 -5
- data/spec/rubocop/config_spec.rb +3 -3
- data/spec/rubocop/config_store_spec.rb +12 -11
- data/spec/rubocop/cop/commissioner_spec.rb +21 -5
- data/spec/rubocop/cop/cop_spec.rb +1 -1
- data/spec/rubocop/cop/lint/ambiguous_operator_spec.rb +113 -0
- data/spec/rubocop/cop/lint/ambiguous_regexp_literal_spec.rb +35 -0
- data/spec/rubocop/cop/lint/block_alignment_spec.rb +2 -2
- data/spec/rubocop/cop/lint/condition_position_spec.rb +49 -0
- data/spec/rubocop/cop/lint/else_layout_spec.rb +65 -0
- data/spec/rubocop/cop/lint/end_alignment_spec.rb +41 -1
- data/spec/rubocop/cop/lint/invalid_character_literal_spec.rb +33 -0
- data/spec/rubocop/cop/lint/parentheses_as_grouped_expression_spec.rb +3 -3
- data/spec/rubocop/cop/lint/shadowing_outer_local_variable_spec.rb +12 -12
- data/spec/rubocop/cop/lint/syntax_spec.rb +2 -2
- data/spec/rubocop/cop/lint/useless_assignment_spec.rb +72 -54
- data/spec/rubocop/cop/lint/useless_else_without_rescue_spec.rb +48 -0
- data/spec/rubocop/cop/offence_spec.rb +1 -1
- data/spec/rubocop/cop/rails/default_scope_spec.rb +6 -0
- data/spec/rubocop/cop/rails/output_spec.rb +2 -1
- data/spec/rubocop/cop/style/align_hash_spec.rb +9 -9
- data/spec/rubocop/cop/style/align_parameters_spec.rb +1 -1
- data/spec/rubocop/cop/style/braces_around_hash_parameters_spec.rb +5 -0
- data/spec/rubocop/cop/style/case_indentation_spec.rb +53 -2
- data/spec/rubocop/cop/style/class_and_module_camel_case_spec.rb +3 -3
- data/spec/rubocop/cop/style/documentation_spec.rb +0 -1
- data/spec/rubocop/cop/style/dot_position_spec.rb +18 -3
- data/spec/rubocop/cop/style/empty_line_between_defs_spec.rb +4 -4
- data/spec/rubocop/cop/style/empty_lines_around_body_spec.rb +13 -0
- data/spec/rubocop/cop/style/favor_unless_over_negated_if_spec.rb +1 -1
- data/spec/rubocop/cop/style/favor_until_over_negated_while_spec.rb +1 -1
- data/spec/rubocop/cop/style/hash_syntax_spec.rb +5 -0
- data/spec/rubocop/cop/style/{favor_modifier_spec.rb → if_unless_modifier_spec.rb} +4 -111
- data/spec/rubocop/cop/style/indentation_consistency_spec.rb +490 -0
- data/spec/rubocop/cop/style/indentation_width_spec.rb +19 -91
- data/spec/rubocop/cop/style/lambda_call_spec.rb +18 -0
- data/spec/rubocop/cop/style/method_called_on_do_end_block_spec.rb +2 -2
- data/spec/rubocop/cop/style/method_def_parentheses_spec.rb +35 -1
- data/spec/rubocop/cop/style/method_length_spec.rb +1 -0
- data/spec/rubocop/cop/style/method_name_spec.rb +27 -5
- data/spec/rubocop/cop/style/multiline_block_chain_spec.rb +4 -4
- data/spec/rubocop/cop/style/multiline_if_then_spec.rb +2 -2
- data/spec/rubocop/cop/style/multiline_ternary_operator_spec.rb +18 -0
- data/spec/rubocop/cop/style/{ternary_operator_spec.rb → nested_ternary_operator_spec.rb} +0 -15
- data/spec/rubocop/cop/style/numeric_literals_spec.rb +18 -1
- data/spec/rubocop/cop/style/one_line_conditional_spec.rb +2 -1
- data/spec/rubocop/cop/style/parameter_lists_spec.rb +1 -0
- data/spec/rubocop/cop/style/parentheses_around_condition_spec.rb +13 -4
- data/spec/rubocop/cop/style/raise_args_spec.rb +22 -0
- data/spec/rubocop/cop/style/redundant_self_spec.rb +4 -4
- data/spec/rubocop/cop/style/regexp_literal_spec.rb +4 -0
- data/spec/rubocop/cop/style/space_after_colon_spec.rb +12 -4
- data/spec/rubocop/cop/style/space_after_method_name_spec.rb +2 -2
- data/spec/rubocop/cop/style/space_around_block_braces_spec.rb +30 -1
- data/spec/rubocop/cop/style/{space_around_equals_in_default_parameter_spec.rb → space_around_equals_in_parameter_default_spec.rb} +0 -0
- data/spec/rubocop/cop/style/space_around_operators_spec.rb +2 -1
- data/spec/rubocop/cop/style/space_inside_hash_literal_braces_spec.rb +20 -3
- data/spec/rubocop/cop/style/string_literals_spec.rb +33 -0
- data/spec/rubocop/cop/style/trailing_comma_spec.rb +200 -0
- data/spec/rubocop/cop/style/variable_name_spec.rb +27 -3
- data/spec/rubocop/cop/style/while_until_modifier_spec.rb +75 -0
- data/spec/rubocop/cop/style/word_array_spec.rb +1 -0
- data/spec/rubocop/cop/team_spec.rb +1 -1
- data/spec/rubocop/cop/variable_inspector/scope_spec.rb +3 -4
- data/spec/rubocop/file_inspector_spec.rb +1 -1
- data/spec/rubocop/formatter/base_formatter_spec.rb +12 -11
- data/spec/rubocop/formatter/colorizable_spec.rb +107 -0
- data/spec/rubocop/formatter/disabled_config_formatter_spec.rb +2 -0
- data/spec/rubocop/formatter/formatter_set_spec.rb +1 -1
- data/spec/rubocop/formatter/json_formatter_spec.rb +4 -3
- data/spec/rubocop/formatter/progress_formatter_spec.rb +2 -2
- data/spec/rubocop/options_spec.rb +3 -1
- data/spec/rubocop/target_finder_spec.rb +13 -11
- data/spec/spec_helper.rb +5 -1
- data/spec/support/shared_examples.rb +2 -2
- data/spec/support/statement_modifier_helper.rb +41 -0
- metadata +88 -30
- data/lib/rubocop/cop/check_assignment.rb +0 -43
- data/lib/rubocop/cop/style/array_syntax.rb +0 -22
- data/lib/rubocop/cop/style/autocorrect_alignment.rb +0 -78
- data/lib/rubocop/cop/style/code_length.rb +0 -35
- data/lib/rubocop/cop/style/configurable_enforced_style.rb +0 -51
- data/lib/rubocop/cop/style/configurable_max.rb +0 -17
- data/lib/rubocop/cop/style/configurable_naming.rb +0 -41
- data/lib/rubocop/cop/style/favor_modifier.rb +0 -118
- data/lib/rubocop/cop/style/if_then_else.rb +0 -27
- data/lib/rubocop/cop/style/space_after_comma_etc.rb +0 -73
- data/lib/rubocop/cop/style/space_inside.rb +0 -33
- data/lib/rubocop/cop/style/string_help.rb +0 -30
- data/lib/rubocop/cop/style/surrounding_space.rb +0 -44
@@ -0,0 +1,31 @@
|
|
1
|
+
# encoding: utf-8
|
2
|
+
|
3
|
+
module Rubocop
|
4
|
+
module Cop
|
5
|
+
# Handles adding and checking ignored nodes.
|
6
|
+
module IgnoredNode
|
7
|
+
def ignore_node(node)
|
8
|
+
@ignored_nodes ||= []
|
9
|
+
@ignored_nodes << node
|
10
|
+
end
|
11
|
+
|
12
|
+
def part_of_ignored_node?(node)
|
13
|
+
return false unless @ignored_nodes
|
14
|
+
expression = node.loc.expression
|
15
|
+
@ignored_nodes.each do |ignored_node|
|
16
|
+
if ignored_node.loc.expression.begin_pos <= expression.begin_pos &&
|
17
|
+
ignored_node.loc.expression.end_pos >= expression.end_pos
|
18
|
+
return true
|
19
|
+
end
|
20
|
+
end
|
21
|
+
|
22
|
+
false
|
23
|
+
end
|
24
|
+
|
25
|
+
def ignored_node?(node)
|
26
|
+
# Same object found in array?
|
27
|
+
@ignored_nodes && @ignored_nodes.any? { |n| n.eql?(node) }
|
28
|
+
end
|
29
|
+
end
|
30
|
+
end
|
31
|
+
end
|
@@ -0,0 +1,50 @@
|
|
1
|
+
# encoding: utf-8
|
2
|
+
|
3
|
+
module Rubocop
|
4
|
+
module Cop
|
5
|
+
module Lint
|
6
|
+
# This cop checks for ambiguous operators in the first argument of a
|
7
|
+
# method invocation without parentheses.
|
8
|
+
#
|
9
|
+
# @example
|
10
|
+
# array = [1, 2, 3]
|
11
|
+
#
|
12
|
+
# # The `*` is interpreted as a splat operator but it could possibly be
|
13
|
+
# # a `*` method invocation (i.e. `do_something.*(array)`).
|
14
|
+
# do_something *array
|
15
|
+
#
|
16
|
+
# # With parentheses, there's no ambiguity.
|
17
|
+
# do_something(*array)
|
18
|
+
class AmbiguousOperator < Cop
|
19
|
+
include ParserDiagnostic
|
20
|
+
|
21
|
+
AMBIGUITIES = {
|
22
|
+
'+' => { actual: 'positive number', possible: 'addition' },
|
23
|
+
'-' => { actual: 'negative number', possible: 'subtraction' },
|
24
|
+
'*' => { actual: 'splat', possible: 'multiplication' },
|
25
|
+
'&' => { actual: 'block', possible: 'binary AND' },
|
26
|
+
'**' => { actual: 'keyword splat', possible: 'exponent' }
|
27
|
+
}.each do |key, hash|
|
28
|
+
hash[:operator] = key
|
29
|
+
end
|
30
|
+
|
31
|
+
MSG_FORMAT = 'Ambiguous %{actual} operator. Parenthesize the method ' +
|
32
|
+
"arguments if it's surely a %{actual} operator, or add " +
|
33
|
+
'a whitespace to the right of the %{operator} if it ' +
|
34
|
+
'should be a %{possible}.'
|
35
|
+
|
36
|
+
private
|
37
|
+
|
38
|
+
def relevant_diagnostic?(diagnostic)
|
39
|
+
diagnostic.reason == :ambiguous_prefix
|
40
|
+
end
|
41
|
+
|
42
|
+
def alternative_message(diagnostic)
|
43
|
+
operator = diagnostic.location.source
|
44
|
+
hash = AMBIGUITIES[operator]
|
45
|
+
format(MSG_FORMAT, hash)
|
46
|
+
end
|
47
|
+
end
|
48
|
+
end
|
49
|
+
end
|
50
|
+
end
|
@@ -0,0 +1,36 @@
|
|
1
|
+
# encoding: utf-8
|
2
|
+
|
3
|
+
module Rubocop
|
4
|
+
module Cop
|
5
|
+
module Lint
|
6
|
+
# This cop checks for ambiguous regexp literals in the first argument of
|
7
|
+
# a method invocation without parentheses.
|
8
|
+
#
|
9
|
+
# @example
|
10
|
+
# # This is interpreted as a method invocation with a regexp literal,
|
11
|
+
# # but it could possibly be `/` method invocations.
|
12
|
+
# # (i.e. `do_something./(pattern)./(i)`)
|
13
|
+
# do_something /pattern/i
|
14
|
+
#
|
15
|
+
# # With parentheses, there's no ambiguity.
|
16
|
+
# do_something(/pattern/i)
|
17
|
+
class AmbiguousRegexpLiteral < Cop
|
18
|
+
include ParserDiagnostic
|
19
|
+
|
20
|
+
MSG = 'Ambiguous regexp literal. Parenthesize the method arguments ' +
|
21
|
+
"if it's surely a regexp literal, or add a whitespace to the " +
|
22
|
+
'right of the / if it should be a division.'
|
23
|
+
|
24
|
+
private
|
25
|
+
|
26
|
+
def relevant_diagnostic?(diagnostic)
|
27
|
+
diagnostic.reason == :ambiguous_literal
|
28
|
+
end
|
29
|
+
|
30
|
+
def alternative_message(diagnostic)
|
31
|
+
MSG
|
32
|
+
end
|
33
|
+
end
|
34
|
+
end
|
35
|
+
end
|
36
|
+
end
|
@@ -6,7 +6,8 @@ module Rubocop
|
|
6
6
|
# This cop checks for assignments in the conditions of
|
7
7
|
# if/while/until.
|
8
8
|
class AssignmentInCondition < Cop
|
9
|
-
|
9
|
+
include SafeAssignment
|
10
|
+
|
10
11
|
MSG = 'Assignment in condition - you probably meant to use ==.'
|
11
12
|
|
12
13
|
def on_if(node)
|
@@ -29,7 +30,7 @@ module Rubocop
|
|
29
30
|
# assignments inside blocks are not what we're looking for
|
30
31
|
return if condition.type == :block
|
31
32
|
|
32
|
-
on_node([:begin, *
|
33
|
+
on_node([:begin, *EQUALS_ASGN_NODES], condition) do |asgn_node|
|
33
34
|
# skip safe assignment nodes if safe assignment is allowed
|
34
35
|
return if safe_assignment_allowed? && safe_assignment?(asgn_node)
|
35
36
|
|
@@ -39,15 +40,6 @@ module Rubocop
|
|
39
40
|
end
|
40
41
|
end
|
41
42
|
end
|
42
|
-
|
43
|
-
def safe_assignment?(node)
|
44
|
-
node.type == :begin && node.children.size == 1 &&
|
45
|
-
ASGN_NODES.include?(node.children[0].type)
|
46
|
-
end
|
47
|
-
|
48
|
-
def safe_assignment_allowed?
|
49
|
-
cop_config['AllowSafeAssignment']
|
50
|
-
end
|
51
43
|
end
|
52
44
|
end
|
53
45
|
end
|
@@ -12,6 +12,8 @@ module Rubocop
|
|
12
12
|
# i
|
13
13
|
# end
|
14
14
|
class BlockAlignment < Cop
|
15
|
+
include CheckAssignment
|
16
|
+
|
15
17
|
MSG = 'end at %d, %d is not aligned with %s at %d, %d%s'
|
16
18
|
|
17
19
|
def initialize(config = nil, options = nil)
|
@@ -36,40 +38,24 @@ module Rubocop
|
|
36
38
|
|
37
39
|
alias_method :on_or, :on_and
|
38
40
|
|
39
|
-
def on_lvasgn(node)
|
40
|
-
_, children = *node
|
41
|
-
process_block_assignment(node, children)
|
42
|
-
end
|
43
|
-
|
44
|
-
alias_method :on_ivasgn, :on_lvasgn
|
45
|
-
alias_method :on_cvasgn, :on_lvasgn
|
46
|
-
alias_method :on_gvasgn, :on_lvasgn
|
47
|
-
alias_method :on_and_asgn, :on_lvasgn
|
48
|
-
alias_method :on_or_asgn, :on_lvasgn
|
49
|
-
|
50
|
-
def on_casgn(node)
|
51
|
-
_, _, children = *node
|
52
|
-
process_block_assignment(node, children)
|
53
|
-
end
|
54
|
-
|
55
41
|
def on_op_asgn(node)
|
56
42
|
variable, _op, args = *node
|
57
|
-
|
43
|
+
check_assignment(variable, args)
|
58
44
|
end
|
59
45
|
|
60
46
|
def on_send(node)
|
61
47
|
_receiver, _method, *args = *node
|
62
|
-
|
48
|
+
check_assignment(node, args.last)
|
63
49
|
end
|
64
50
|
|
65
51
|
def on_masgn(node)
|
66
52
|
variables, args = *node
|
67
|
-
|
53
|
+
check_assignment(variables, args)
|
68
54
|
end
|
69
55
|
|
70
56
|
private
|
71
57
|
|
72
|
-
def
|
58
|
+
def check_assignment(begin_node, other_node)
|
73
59
|
return unless other_node
|
74
60
|
|
75
61
|
block_node = find_block_node(other_node)
|
@@ -0,0 +1,52 @@
|
|
1
|
+
# encoding: utf-8
|
2
|
+
|
3
|
+
module Rubocop
|
4
|
+
module Cop
|
5
|
+
module Lint
|
6
|
+
# This cop checks for conditions that are not on the same line as
|
7
|
+
# if/while/until.
|
8
|
+
#
|
9
|
+
# @example
|
10
|
+
#
|
11
|
+
# if
|
12
|
+
# some_condition
|
13
|
+
# do_something
|
14
|
+
# end
|
15
|
+
class ConditionPosition < Cop
|
16
|
+
def on_if(node)
|
17
|
+
return if node.loc.respond_to?(:question)
|
18
|
+
|
19
|
+
check(node)
|
20
|
+
end
|
21
|
+
|
22
|
+
def on_while(node)
|
23
|
+
check(node)
|
24
|
+
end
|
25
|
+
|
26
|
+
def on_until(node)
|
27
|
+
check(node)
|
28
|
+
end
|
29
|
+
|
30
|
+
private
|
31
|
+
|
32
|
+
def check(node)
|
33
|
+
condition, = *node
|
34
|
+
|
35
|
+
if on_different_line?(node.loc.keyword.line,
|
36
|
+
condition.loc.expression.line)
|
37
|
+
add_offence(condition, :expression,
|
38
|
+
message(node.loc.keyword.source))
|
39
|
+
end
|
40
|
+
end
|
41
|
+
|
42
|
+
def message(keyword)
|
43
|
+
"Place the condition on the same line as #{keyword}."
|
44
|
+
end
|
45
|
+
|
46
|
+
def on_different_line?(keyword_line, cond_line)
|
47
|
+
keyword_line != cond_line
|
48
|
+
end
|
49
|
+
end
|
50
|
+
end
|
51
|
+
end
|
52
|
+
end
|
@@ -0,0 +1,57 @@
|
|
1
|
+
# encoding: utf-8
|
2
|
+
|
3
|
+
module Rubocop
|
4
|
+
module Cop
|
5
|
+
module Lint
|
6
|
+
# This cop checks for odd else block layout - like
|
7
|
+
# having an expression on the same line as the else keyword,
|
8
|
+
# which is usually a mistake.
|
9
|
+
#
|
10
|
+
# @example
|
11
|
+
#
|
12
|
+
# if something
|
13
|
+
# ...
|
14
|
+
# else do_this
|
15
|
+
# do_that
|
16
|
+
# end
|
17
|
+
class ElseLayout < Cop
|
18
|
+
def on_if(node)
|
19
|
+
# ignore ternary ops
|
20
|
+
return if node.loc.respond_to?(:question)
|
21
|
+
# ignore modifier ops & elsif nodes
|
22
|
+
return unless node.loc.end
|
23
|
+
|
24
|
+
check(node)
|
25
|
+
end
|
26
|
+
|
27
|
+
private
|
28
|
+
|
29
|
+
def check(node)
|
30
|
+
return unless node
|
31
|
+
|
32
|
+
if node.loc.respond_to?(:else) &&
|
33
|
+
node.loc.else &&
|
34
|
+
node.loc.else.is?('else')
|
35
|
+
_cond, _if_branch, else_branch = *node
|
36
|
+
|
37
|
+
return unless else_branch && else_branch.type == :begin
|
38
|
+
|
39
|
+
first_else_expr = else_branch.children.first
|
40
|
+
|
41
|
+
if first_else_expr.loc.expression.line == node.loc.else.line
|
42
|
+
add_offence(first_else_expr, :expression, message)
|
43
|
+
end
|
44
|
+
elsif node.loc.respond_to?(:keyword) &&
|
45
|
+
%w(if elsif).include?(node.loc.keyword.source)
|
46
|
+
_cond, _if_branch, else_branch = *node
|
47
|
+
check(else_branch)
|
48
|
+
end
|
49
|
+
end
|
50
|
+
|
51
|
+
def message
|
52
|
+
'Odd else layout detected. Perhaps you meant to use elsif instead?'
|
53
|
+
end
|
54
|
+
end
|
55
|
+
end
|
56
|
+
end
|
57
|
+
end
|
@@ -18,6 +18,7 @@ module Rubocop
|
|
18
18
|
class EndAlignment < Cop
|
19
19
|
include CheckMethods
|
20
20
|
include CheckAssignment
|
21
|
+
include ConfigurableEnforcedStyle
|
21
22
|
|
22
23
|
MSG = 'end at %d, %d is not aligned with %s at %d, %d'
|
23
24
|
|
@@ -41,8 +42,32 @@ module Rubocop
|
|
41
42
|
check(node)
|
42
43
|
end
|
43
44
|
|
45
|
+
def on_send(node)
|
46
|
+
receiver, method_name, *args = *node
|
47
|
+
if visibility_and_def_on_same_line?(receiver, method_name, args)
|
48
|
+
expr = node.loc.expression
|
49
|
+
method_def = args.first
|
50
|
+
range = Parser::Source::Range.new(expr.source_buffer,
|
51
|
+
expr.begin_pos,
|
52
|
+
method_def.loc.keyword.end_pos)
|
53
|
+
check_offset(method_def, range.source,
|
54
|
+
method_def.loc.keyword.begin_pos - expr.begin_pos)
|
55
|
+
ignore_node(method_def) # Don't check the same `end` again.
|
56
|
+
end
|
57
|
+
end
|
58
|
+
|
44
59
|
private
|
45
60
|
|
61
|
+
# Returns true for constructs such as
|
62
|
+
# private def my_method
|
63
|
+
# which are allowed in Ruby 2.1 and later.
|
64
|
+
def visibility_and_def_on_same_line?(receiver, method_name, args)
|
65
|
+
!receiver &&
|
66
|
+
[:public, :protected, :private,
|
67
|
+
:module_function].include?(method_name) &&
|
68
|
+
args.size == 1 && [:def, :defs].include?(args.first.type)
|
69
|
+
end
|
70
|
+
|
46
71
|
def check_assignment(node, rhs)
|
47
72
|
# If there are method calls chained to the right hand side of the
|
48
73
|
# assignment, we let rhs be the receiver of those method calls before
|
@@ -55,7 +80,7 @@ module Rubocop
|
|
55
80
|
when :if, :while, :until
|
56
81
|
return if rhs.loc.respond_to?(:question) # ternary
|
57
82
|
|
58
|
-
offset = if
|
83
|
+
offset = if style == :variable
|
59
84
|
rhs.loc.keyword.column - node.loc.expression.column
|
60
85
|
else
|
61
86
|
0
|
@@ -85,16 +110,16 @@ module Rubocop
|
|
85
110
|
kw_loc.column != end_loc.column + offset
|
86
111
|
add_offence(nil, end_loc,
|
87
112
|
sprintf(MSG, end_loc.line, end_loc.column,
|
88
|
-
alignment_base, kw_loc.line, kw_loc.column))
|
113
|
+
alignment_base, kw_loc.line, kw_loc.column)) do
|
114
|
+
opposite_style_detected
|
115
|
+
end
|
116
|
+
else
|
117
|
+
correct_style_detected
|
89
118
|
end
|
90
119
|
end
|
91
120
|
|
92
|
-
def
|
93
|
-
|
94
|
-
case a
|
95
|
-
when 'keyword', 'variable' then a.to_sym
|
96
|
-
else fail "Unknown AlignWith: #{a}"
|
97
|
-
end
|
121
|
+
def parameter_name
|
122
|
+
'AlignWith'
|
98
123
|
end
|
99
124
|
end
|
100
125
|
end
|
@@ -0,0 +1,37 @@
|
|
1
|
+
# encoding: utf-8
|
2
|
+
|
3
|
+
module Rubocop
|
4
|
+
module Cop
|
5
|
+
module Lint
|
6
|
+
# This cop checks for invalid character literals with a non-escaped
|
7
|
+
# whitespace character (e.g. `? `).
|
8
|
+
# However, currently it's unclear whether there's a way to emit this
|
9
|
+
# warning without syntax errors.
|
10
|
+
#
|
11
|
+
# $ ruby -w
|
12
|
+
# p(? )
|
13
|
+
# -:1: warning: invalid character syntax; use ?\s
|
14
|
+
# -:1: syntax error, unexpected '?', expecting ')'
|
15
|
+
# p(? )
|
16
|
+
# ^
|
17
|
+
#
|
18
|
+
# @example
|
19
|
+
# p(? )
|
20
|
+
class InvalidCharacterLiteral < Cop
|
21
|
+
include ParserDiagnostic
|
22
|
+
|
23
|
+
private
|
24
|
+
|
25
|
+
def relevant_diagnostic?(diagnostic)
|
26
|
+
diagnostic.reason == :invalid_escape_use
|
27
|
+
end
|
28
|
+
|
29
|
+
def alternative_message(diagnostic)
|
30
|
+
diagnostic.message
|
31
|
+
.capitalize
|
32
|
+
.gsub('character syntax', 'character literal')
|
33
|
+
end
|
34
|
+
end
|
35
|
+
end
|
36
|
+
end
|
37
|
+
end
|
@@ -14,10 +14,8 @@ module Rubocop
|
|
14
14
|
|
15
15
|
def on_send(node)
|
16
16
|
_receiver, method_name, args = *node
|
17
|
-
if
|
18
|
-
|
19
|
-
return
|
20
|
-
end
|
17
|
+
return if operator?(method_name) || method_name.to_s.end_with?('=')
|
18
|
+
|
21
19
|
if args && args.loc.expression.source.start_with?('(')
|
22
20
|
space_length = spaces_before_left_parenthesis(node)
|
23
21
|
if space_length > 0
|
@@ -3,11 +3,11 @@
|
|
3
3
|
module Rubocop
|
4
4
|
module Cop
|
5
5
|
module Lint
|
6
|
-
# This
|
7
|
-
# into RuboCop's offences.
|
8
|
-
|
9
|
-
|
10
|
-
|
6
|
+
# This is actually not a cop and inspects nothing. It just provides
|
7
|
+
# methods to repack Parser's diagnostics into RuboCop's offences.
|
8
|
+
module Syntax
|
9
|
+
COP_NAME = 'Syntax'.freeze
|
10
|
+
|
11
11
|
def self.offences_from_diagnostics(diagnostics)
|
12
12
|
diagnostics.map do |diagnostic|
|
13
13
|
offence_from_diagnostic(diagnostic)
|
@@ -19,15 +19,9 @@ module Rubocop
|
|
19
19
|
diagnostic.level,
|
20
20
|
diagnostic.location,
|
21
21
|
diagnostic.message,
|
22
|
-
|
22
|
+
COP_NAME
|
23
23
|
)
|
24
24
|
end
|
25
|
-
|
26
|
-
def investigate(processed_source)
|
27
|
-
processed_source.diagnostics.each do |d|
|
28
|
-
add_offence(nil, d.location, d.message, d.level)
|
29
|
-
end
|
30
|
-
end
|
31
25
|
end
|
32
26
|
end
|
33
27
|
end
|