rubocop 0.12.0 → 0.13.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.
- data/CHANGELOG.md +40 -0
- data/README.md +49 -8
- data/config/default.yml +40 -0
- data/config/enabled.yml +37 -9
- data/lib/rubocop.rb +24 -10
- data/lib/rubocop/cli.rb +41 -106
- data/lib/rubocop/config.rb +3 -2
- data/lib/rubocop/cop/commissioner.rb +15 -5
- data/lib/rubocop/cop/cop.rb +47 -32
- data/lib/rubocop/cop/lint/assignment_in_condition.rb +2 -2
- data/lib/rubocop/cop/lint/block_alignment.rb +30 -9
- data/lib/rubocop/cop/lint/empty_ensure.rb +1 -1
- data/lib/rubocop/cop/lint/end_alignment.rb +4 -4
- data/lib/rubocop/cop/lint/end_in_method.rb +1 -1
- data/lib/rubocop/cop/lint/ensure_return.rb +1 -1
- data/lib/rubocop/cop/lint/eval.rb +1 -3
- data/lib/rubocop/cop/lint/handle_exceptions.rb +1 -1
- data/lib/rubocop/cop/lint/literal_in_condition.rb +6 -4
- data/lib/rubocop/cop/lint/loop.rb +1 -1
- data/lib/rubocop/cop/lint/parentheses_as_grouped_expression.rb +1 -1
- data/lib/rubocop/cop/lint/rescue_exception.rb +1 -1
- data/lib/rubocop/cop/lint/shadowing_outer_local_variable.rb +5 -8
- data/lib/rubocop/cop/lint/unreachable_code.rb +1 -1
- data/lib/rubocop/cop/lint/useless_assignment.rb +57 -60
- data/lib/rubocop/cop/lint/useless_comparison.rb +1 -1
- data/lib/rubocop/cop/lint/useless_setter_call.rb +85 -0
- data/lib/rubocop/cop/lint/void.rb +6 -8
- data/lib/rubocop/cop/rails/has_and_belongs_to_many.rb +1 -1
- data/lib/rubocop/cop/rails/read_attribute.rb +1 -1
- data/lib/rubocop/cop/rails/validation.rb +1 -1
- data/lib/rubocop/cop/style/access_control.rb +4 -6
- data/lib/rubocop/cop/style/alias.rb +1 -3
- data/lib/rubocop/cop/style/align_array.rb +47 -0
- data/lib/rubocop/cop/style/align_hash.rb +145 -0
- data/lib/rubocop/cop/style/align_parameters.rb +9 -3
- data/lib/rubocop/cop/style/and_or.rb +3 -4
- data/lib/rubocop/cop/style/ascii_comments.rb +1 -3
- data/lib/rubocop/cop/style/ascii_identifiers.rb +1 -1
- data/lib/rubocop/cop/style/attr.rb +1 -4
- data/lib/rubocop/cop/style/begin_block.rb +1 -1
- data/lib/rubocop/cop/style/block_comments.rb +1 -1
- data/lib/rubocop/cop/style/block_nesting.rb +2 -2
- data/lib/rubocop/cop/style/blocks.rb +14 -2
- data/lib/rubocop/cop/style/case_equality.rb +1 -3
- data/lib/rubocop/cop/style/case_indentation.rb +1 -1
- data/lib/rubocop/cop/style/character_literal.rb +1 -2
- data/lib/rubocop/cop/style/class_and_module_camel_case.rb +1 -1
- data/lib/rubocop/cop/style/class_methods.rb +1 -3
- data/lib/rubocop/cop/style/{avoid_class_vars.rb → class_vars.rb} +6 -2
- data/lib/rubocop/cop/style/collection_methods.rb +7 -9
- data/lib/rubocop/cop/style/colon_method_call.rb +1 -2
- data/lib/rubocop/cop/style/comment_annotation.rb +6 -6
- data/lib/rubocop/cop/style/constant_name.rb +1 -3
- data/lib/rubocop/cop/style/def_parentheses.rb +4 -12
- data/lib/rubocop/cop/style/documentation.rb +2 -2
- data/lib/rubocop/cop/style/dot_position.rb +2 -4
- data/lib/rubocop/cop/style/empty_line_between_defs.rb +21 -6
- data/lib/rubocop/cop/style/empty_lines.rb +1 -1
- data/lib/rubocop/cop/style/empty_literal.rb +3 -12
- data/lib/rubocop/cop/style/encoding.rb +6 -6
- data/lib/rubocop/cop/style/end_block.rb +1 -1
- data/lib/rubocop/cop/style/end_of_line.rb +5 -5
- data/lib/rubocop/cop/style/even_odd.rb +2 -2
- data/lib/rubocop/cop/style/favor_join.rb +1 -3
- data/lib/rubocop/cop/style/favor_modifier.rb +7 -3
- data/lib/rubocop/cop/style/favor_sprintf.rb +1 -1
- data/lib/rubocop/cop/style/favor_unless_over_negated_if.rb +1 -1
- data/lib/rubocop/cop/style/final_newline.rb +23 -0
- data/lib/rubocop/cop/style/{avoid_for.rb → for.rb} +2 -2
- data/lib/rubocop/cop/style/{avoid_global_vars.rb → global_vars.rb} +19 -6
- data/lib/rubocop/cop/style/hash_methods.rb +3 -5
- data/lib/rubocop/cop/style/hash_syntax.rb +4 -4
- data/lib/rubocop/cop/style/if_then_else.rb +1 -1
- data/lib/rubocop/cop/style/indentation_width.rb +4 -4
- data/lib/rubocop/cop/style/lambda.rb +2 -2
- data/lib/rubocop/cop/style/leading_comment_space.rb +1 -1
- data/lib/rubocop/cop/style/line_length.rb +7 -8
- data/lib/rubocop/cop/style/method_and_variable_snake_case.rb +1 -1
- data/lib/rubocop/cop/style/method_call_parentheses.rb +1 -4
- data/lib/rubocop/cop/style/method_length.rb +4 -4
- data/lib/rubocop/cop/style/module_function.rb +1 -3
- data/lib/rubocop/cop/style/multiline_block_chain.rb +44 -0
- data/lib/rubocop/cop/style/nil_comparison.rb +1 -3
- data/lib/rubocop/cop/style/not.rb +1 -1
- data/lib/rubocop/cop/style/numeric_literals.rb +26 -6
- data/lib/rubocop/cop/style/op_method.rb +2 -2
- data/lib/rubocop/cop/style/parameter_lists.rb +4 -4
- data/lib/rubocop/cop/style/parentheses_around_condition.rb +2 -2
- data/lib/rubocop/cop/style/perl_backrefs.rb +26 -0
- data/lib/rubocop/cop/style/proc.rb +1 -3
- data/lib/rubocop/cop/style/reduce_arguments.rb +7 -5
- data/lib/rubocop/cop/style/redundant_begin.rb +1 -1
- data/lib/rubocop/cop/style/redundant_return.rb +9 -2
- data/lib/rubocop/cop/style/redundant_self.rb +9 -2
- data/lib/rubocop/cop/style/regexp_literal.rb +7 -8
- data/lib/rubocop/cop/style/rescue_modifier.rb +1 -1
- data/lib/rubocop/cop/style/semicolon.rb +10 -10
- data/lib/rubocop/cop/style/signal_exception.rb +2 -4
- data/lib/rubocop/cop/style/single_line_methods.rb +2 -4
- data/lib/rubocop/cop/style/space_after_comma_etc.rb +1 -1
- data/lib/rubocop/cop/style/space_after_control_keyword.rb +1 -1
- data/lib/rubocop/cop/style/space_after_method_name.rb +1 -1
- data/lib/rubocop/cop/style/space_before_modifier_keyword.rb +34 -0
- data/lib/rubocop/cop/style/{avoid_perlisms.rb → special_global_vars.rb} +17 -8
- data/lib/rubocop/cop/style/string_literals.rb +1 -2
- data/lib/rubocop/cop/style/surrounding_space.rb +9 -8
- data/lib/rubocop/cop/style/symbol_array.rb +1 -1
- data/lib/rubocop/cop/style/symbol_name.rb +9 -2
- data/lib/rubocop/cop/style/tab.rb +5 -5
- data/lib/rubocop/cop/style/ternary_operator.rb +2 -6
- data/lib/rubocop/cop/style/trailing_blank_lines.rb +32 -0
- data/lib/rubocop/cop/style/trailing_whitespace.rb +5 -6
- data/lib/rubocop/cop/style/trivial_accessors.rb +5 -5
- data/lib/rubocop/cop/style/unless_else.rb +1 -1
- data/lib/rubocop/cop/style/variable_interpolation.rb +1 -3
- data/lib/rubocop/cop/style/when_then.rb +1 -4
- data/lib/rubocop/cop/style/while_until_do.rb +7 -5
- data/lib/rubocop/cop/style/word_array.rb +1 -1
- data/lib/rubocop/cop/team.rb +100 -0
- data/lib/rubocop/cop/variable_inspector.rb +323 -235
- data/lib/rubocop/cop/variable_inspector/assignment.rb +103 -0
- data/lib/rubocop/cop/variable_inspector/locatable.rb +162 -0
- data/lib/rubocop/cop/variable_inspector/reference.rb +31 -0
- data/lib/rubocop/cop/variable_inspector/scope.rb +70 -0
- data/lib/rubocop/cop/variable_inspector/variable.rb +87 -0
- data/lib/rubocop/cop/variable_inspector/variable_table.rb +129 -0
- data/lib/rubocop/formatter/json_formatter.rb +8 -8
- data/lib/rubocop/formatter/progress_formatter.rb +4 -4
- data/lib/rubocop/processed_source.rb +22 -1
- data/lib/rubocop/version.rb +1 -1
- data/rubocop.gemspec +1 -1
- data/spec/rubocop/cli_spec.rb +32 -30
- data/spec/rubocop/config_spec.rb +4 -6
- data/spec/rubocop/cop/commissioner_spec.rb +4 -5
- data/spec/rubocop/cop/cop_spec.rb +8 -26
- data/spec/rubocop/cop/lint/assignment_in_condition_spec.rb +5 -9
- data/spec/rubocop/cop/lint/block_alignment_spec.rb +105 -57
- data/spec/rubocop/cop/lint/empty_ensure_spec.rb +1 -1
- data/spec/rubocop/cop/lint/end_alignment_spec.rb +1 -1
- data/spec/rubocop/cop/lint/end_in_method_spec.rb +1 -1
- data/spec/rubocop/cop/lint/ensure_return_spec.rb +1 -1
- data/spec/rubocop/cop/lint/eval_spec.rb +3 -3
- data/spec/rubocop/cop/lint/handle_exceptions_spec.rb +2 -2
- data/spec/rubocop/cop/lint/literal_in_condition_spec.rb +1 -1
- data/spec/rubocop/cop/lint/loop_spec.rb +1 -1
- data/spec/rubocop/cop/lint/parentheses_as_grouped_expression_spec.rb +1 -1
- data/spec/rubocop/cop/lint/rescue_exception_spec.rb +5 -5
- data/spec/rubocop/cop/lint/unreachable_code_spec.rb +1 -1
- data/spec/rubocop/cop/lint/useless_assignment_spec.rb +1545 -108
- data/spec/rubocop/cop/lint/useless_comparison_spec.rb +1 -1
- data/spec/rubocop/cop/lint/useless_setter_call_spec.rb +101 -0
- data/spec/rubocop/cop/lint/void_spec.rb +1 -1
- data/spec/rubocop/cop/offence_spec.rb +4 -4
- data/spec/rubocop/cop/rails/has_and_belongs_to_many_spec.rb +1 -1
- data/spec/rubocop/cop/rails/read_attribute_spec.rb +1 -1
- data/spec/rubocop/cop/rails/validation_spec.rb +1 -1
- data/spec/rubocop/cop/style/access_control_spec.rb +20 -20
- data/spec/rubocop/cop/style/alias_spec.rb +3 -3
- data/spec/rubocop/cop/style/align_array_spec.rb +62 -0
- data/spec/rubocop/cop/style/align_hash_spec.rb +267 -0
- data/spec/rubocop/cop/style/align_parameters_spec.rb +2 -2
- data/spec/rubocop/cop/style/and_or_spec.rb +1 -1
- data/spec/rubocop/cop/style/ascii_comments_spec.rb +2 -2
- data/spec/rubocop/cop/style/ascii_identifiers_spec.rb +2 -2
- data/spec/rubocop/cop/style/attr_spec.rb +1 -1
- data/spec/rubocop/cop/style/begin_block_spec.rb +1 -1
- data/spec/rubocop/cop/style/block_comments_spec.rb +1 -1
- data/spec/rubocop/cop/style/block_nesting_spec.rb +3 -3
- data/spec/rubocop/cop/style/blocks_spec.rb +25 -1
- data/spec/rubocop/cop/style/case_equality_spec.rb +1 -1
- data/spec/rubocop/cop/style/case_indentation_spec.rb +5 -5
- data/spec/rubocop/cop/style/character_literal_spec.rb +1 -1
- data/spec/rubocop/cop/style/class_and_module_camel_case_spec.rb +1 -1
- data/spec/rubocop/cop/style/class_methods_spec.rb +1 -1
- data/spec/rubocop/cop/style/class_vars_spec.rb +25 -0
- data/spec/rubocop/cop/style/collection_methods_spec.rb +5 -6
- data/spec/rubocop/cop/style/colon_method_call_spec.rb +0 -3
- data/spec/rubocop/cop/style/comment_annotation_spec.rb +20 -18
- data/spec/rubocop/cop/style/constant_name_spec.rb +1 -1
- data/spec/rubocop/cop/style/def_with_parentheses_spec.rb +1 -1
- data/spec/rubocop/cop/style/def_without_parentheses_spec.rb +1 -1
- data/spec/rubocop/cop/style/documentation_spec.rb +1 -1
- data/spec/rubocop/cop/style/dot_position_spec.rb +5 -5
- data/spec/rubocop/cop/style/empty_line_between_defs_spec.rb +35 -4
- data/spec/rubocop/cop/style/empty_lines_spec.rb +1 -1
- data/spec/rubocop/cop/style/empty_literal_spec.rb +7 -7
- data/spec/rubocop/cop/style/encoding_spec.rb +11 -5
- data/spec/rubocop/cop/style/end_block_spec.rb +1 -1
- data/spec/rubocop/cop/style/end_of_line_spec.rb +4 -3
- data/spec/rubocop/cop/style/even_odd_spec.rb +1 -1
- data/spec/rubocop/cop/style/favor_join_spec.rb +2 -2
- data/spec/rubocop/cop/style/favor_modifier_spec.rb +13 -10
- data/spec/rubocop/cop/style/favor_sprintf_spec.rb +4 -4
- 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 +4 -4
- data/spec/rubocop/cop/style/final_newline_spec.rb +25 -0
- data/spec/rubocop/cop/style/{avoid_for_spec.rb → for_spec.rb} +8 -12
- data/spec/rubocop/cop/style/{avoid_global_vars_spec.rb → global_vars_spec.rb} +13 -3
- data/spec/rubocop/cop/style/hash_methods_spec.rb +1 -1
- data/spec/rubocop/cop/style/hash_syntax_spec.rb +20 -9
- data/spec/rubocop/cop/style/if_with_semicolon_spec.rb +3 -3
- data/spec/rubocop/cop/style/indentation_width_spec.rb +19 -19
- data/spec/rubocop/cop/style/lambda_spec.rb +6 -6
- data/spec/rubocop/cop/style/leading_comment_space_spec.rb +1 -1
- data/spec/rubocop/cop/style/line_length_spec.rb +3 -3
- data/spec/rubocop/cop/style/method_and_variable_snake_case_spec.rb +8 -9
- data/spec/rubocop/cop/style/method_call_parentheses_spec.rb +1 -1
- data/spec/rubocop/cop/style/method_length_spec.rb +18 -17
- data/spec/rubocop/cop/style/module_function_spec.rb +1 -1
- data/spec/rubocop/cop/style/multiline_block_chain_spec.rb +84 -0
- data/spec/rubocop/cop/style/multiline_if_then_spec.rb +2 -2
- data/spec/rubocop/cop/style/nil_comparison_spec.rb +1 -1
- data/spec/rubocop/cop/style/not_spec.rb +1 -1
- data/spec/rubocop/cop/style/numeric_literals_spec.rb +15 -25
- data/spec/rubocop/cop/style/one_line_conditional_spec.rb +2 -2
- data/spec/rubocop/cop/style/op_method_spec.rb +3 -3
- data/spec/rubocop/cop/style/parameter_lists_spec.rb +5 -5
- data/spec/rubocop/cop/style/parentheses_around_condition_spec.rb +4 -8
- data/spec/rubocop/cop/style/perl_backrefs_spec.rb +23 -0
- data/spec/rubocop/cop/style/proc_spec.rb +1 -1
- data/spec/rubocop/cop/style/reduce_arguments_spec.rb +18 -11
- data/spec/rubocop/cop/style/redundant_begin_spec.rb +1 -1
- data/spec/rubocop/cop/style/redundant_return_spec.rb +16 -1
- data/spec/rubocop/cop/style/redundant_self_spec.rb +6 -1
- data/spec/rubocop/cop/style/regexp_literal_spec.rb +19 -23
- data/spec/rubocop/cop/style/rescue_modifier_spec.rb +3 -3
- data/spec/rubocop/cop/style/semicolon_spec.rb +3 -3
- data/spec/rubocop/cop/style/signal_exception_spec.rb +1 -1
- data/spec/rubocop/cop/style/single_line_methods_spec.rb +22 -18
- data/spec/rubocop/cop/style/space_after_colon_spec.rb +4 -4
- data/spec/rubocop/cop/style/space_after_comma_spec.rb +4 -4
- data/spec/rubocop/cop/style/space_after_control_keyword_spec.rb +1 -1
- data/spec/rubocop/cop/style/space_after_method_name_spec.rb +1 -1
- data/spec/rubocop/cop/style/space_after_semicolon_spec.rb +3 -3
- data/spec/rubocop/cop/style/space_around_braces_spec.rb +13 -12
- data/spec/rubocop/cop/style/space_around_equals_in_default_parameter_spec.rb +3 -3
- data/spec/rubocop/cop/style/space_around_operators_spec.rb +25 -25
- data/spec/rubocop/cop/style/space_before_modifier_keyword_spec.rb +53 -0
- data/spec/rubocop/cop/style/space_inside_brackets_spec.rb +9 -9
- data/spec/rubocop/cop/style/space_inside_hash_literal_braces_spec.rb +47 -61
- data/spec/rubocop/cop/style/space_inside_parens_spec.rb +4 -4
- data/spec/rubocop/cop/style/special_global_vars_spec.rb +52 -0
- data/spec/rubocop/cop/style/string_literals_spec.rb +5 -5
- data/spec/rubocop/cop/style/symbol_array_spec.rb +1 -1
- data/spec/rubocop/cop/style/symbol_name_spec.rb +27 -18
- data/spec/rubocop/cop/style/tab_spec.rb +1 -1
- data/spec/rubocop/cop/style/ternary_operator_spec.rb +2 -2
- data/spec/rubocop/cop/style/trailing_blank_lines_spec.rb +24 -0
- data/spec/rubocop/cop/style/trailing_whitespace_spec.rb +7 -7
- data/spec/rubocop/cop/style/trivial_accessors_spec.rb +6 -14
- data/spec/rubocop/cop/style/unless_else_spec.rb +3 -3
- data/spec/rubocop/cop/style/variable_interpolation_spec.rb +5 -5
- data/spec/rubocop/cop/style/when_then_spec.rb +15 -15
- data/spec/rubocop/cop/style/while_until_do_spec.rb +3 -3
- data/spec/rubocop/cop/style/word_array_spec.rb +1 -1
- data/spec/rubocop/cop/team_spec.rb +158 -0
- data/spec/rubocop/cop/variable_inspector/assignment_spec.rb +217 -0
- data/spec/rubocop/cop/variable_inspector/locatable_spec.rb +740 -0
- data/spec/rubocop/cop/variable_inspector/scope_spec.rb +191 -0
- data/spec/rubocop/cop/variable_inspector/variable_spec.rb +79 -0
- data/spec/rubocop/cop/variable_inspector/variable_table_spec.rb +275 -0
- data/spec/rubocop/cop/variable_inspector_spec.rb +13 -533
- data/spec/rubocop/formatter/clang_style_formatter_spec.rb +4 -4
- data/spec/rubocop/formatter/disabled_config_formatter_spec.rb +1 -1
- data/spec/rubocop/formatter/emacs_style_formatter_spec.rb +3 -3
- data/spec/rubocop/formatter/file_list_formatter_spec.rb +3 -3
- data/spec/rubocop/formatter/progress_formatter_spec.rb +1 -1
- data/spec/spec_helper.rb +5 -1
- data/spec/support/ast_helper.rb +15 -0
- data/spec/support/shared_context.rb +18 -0
- data/spec/support/shared_examples.rb +1 -1
- metadata +95 -32
- checksums.yaml +0 -7
- data/lib/rubocop/cop/lint/unused_local_variable.rb +0 -32
- data/lib/rubocop/cop/style/avoid_perl_backrefs.rb +0 -19
- data/spec/rubocop/cop/lint/unused_local_variable_spec.rb +0 -588
- data/spec/rubocop/cop/style/avoid_class_vars_spec.rb +0 -27
- data/spec/rubocop/cop/style/avoid_perl_backrefs_spec.rb +0 -20
- data/spec/rubocop/cop/style/avoid_perlisms_spec.rb +0 -47
@@ -0,0 +1,191 @@
|
|
1
|
+
# encoding: utf-8
|
2
|
+
|
3
|
+
require 'spec_helper'
|
4
|
+
|
5
|
+
module Rubocop
|
6
|
+
module Cop
|
7
|
+
module VariableInspector
|
8
|
+
describe Scope do
|
9
|
+
include ASTHelper
|
10
|
+
include AST::Sexp
|
11
|
+
|
12
|
+
describe '.new' do
|
13
|
+
context 'when non scope node is passed' do
|
14
|
+
it 'raises error' do
|
15
|
+
node = s(:lvasgn)
|
16
|
+
expect { Scope.new(node) }.to raise_error(ArgumentError)
|
17
|
+
end
|
18
|
+
end
|
19
|
+
|
20
|
+
context 'when begin node is passed' do
|
21
|
+
it 'accepts that as pseudo scope for top level scope' do
|
22
|
+
node = s(:begin)
|
23
|
+
expect { Scope.new(node) }.not_to raise_error
|
24
|
+
end
|
25
|
+
end
|
26
|
+
end
|
27
|
+
|
28
|
+
let(:ast) do
|
29
|
+
processed_source = Rubocop::SourceParser.parse(source)
|
30
|
+
processed_source.ast
|
31
|
+
end
|
32
|
+
|
33
|
+
let(:scope_node_type) { :def }
|
34
|
+
|
35
|
+
let(:scope_node) do
|
36
|
+
found_node = scan_node(ast, include_origin_node: true) do |node|
|
37
|
+
break node if node.type == scope_node_type
|
38
|
+
end
|
39
|
+
fail 'No scope node found!' unless found_node
|
40
|
+
found_node
|
41
|
+
end
|
42
|
+
|
43
|
+
subject(:scope) { Scope.new(scope_node) }
|
44
|
+
|
45
|
+
describe '#ancestors_of_node' do
|
46
|
+
let(:source) do
|
47
|
+
<<-END
|
48
|
+
puts 1
|
49
|
+
|
50
|
+
class SomeClass
|
51
|
+
def some_method
|
52
|
+
foo = 1
|
53
|
+
|
54
|
+
if foo > 0
|
55
|
+
while foo < 10
|
56
|
+
this_is_target
|
57
|
+
foo += 1
|
58
|
+
end
|
59
|
+
else
|
60
|
+
do_something
|
61
|
+
end
|
62
|
+
end
|
63
|
+
end
|
64
|
+
END
|
65
|
+
end
|
66
|
+
|
67
|
+
let(:target_node) do
|
68
|
+
found_node = scan_node(ast) do |node|
|
69
|
+
next unless node.type == :send
|
70
|
+
_receiver_node, method_name = *node
|
71
|
+
break node if method_name == :this_is_target
|
72
|
+
end
|
73
|
+
fail 'No target node found!' unless found_node
|
74
|
+
found_node
|
75
|
+
end
|
76
|
+
|
77
|
+
it 'returns nodes in between the scope node and the passed node' do
|
78
|
+
ancestor_nodes = scope.ancestors_of_node(target_node)
|
79
|
+
ancestor_types = ancestor_nodes.map(&:type)
|
80
|
+
expect(ancestor_types).to eq([:begin, :if, :while, :begin])
|
81
|
+
end
|
82
|
+
end
|
83
|
+
|
84
|
+
describe '#body_node' do
|
85
|
+
shared_examples 'returns the body node' do
|
86
|
+
it 'returns the body node' do
|
87
|
+
expect(scope.body_node.children[1]).to eq(:this_is_target)
|
88
|
+
end
|
89
|
+
end
|
90
|
+
|
91
|
+
context 'when the scope is instance method' do
|
92
|
+
let(:source) do
|
93
|
+
<<-END
|
94
|
+
def some_method
|
95
|
+
this_is_target
|
96
|
+
end
|
97
|
+
END
|
98
|
+
end
|
99
|
+
|
100
|
+
let(:scope_node_type) { :def }
|
101
|
+
|
102
|
+
include_examples 'returns the body node'
|
103
|
+
end
|
104
|
+
|
105
|
+
context 'when the scope is singleton method' do
|
106
|
+
let(:source) do
|
107
|
+
<<-END
|
108
|
+
def self.some_method
|
109
|
+
this_is_target
|
110
|
+
end
|
111
|
+
END
|
112
|
+
end
|
113
|
+
|
114
|
+
let(:scope_node_type) { :defs }
|
115
|
+
|
116
|
+
include_examples 'returns the body node'
|
117
|
+
end
|
118
|
+
|
119
|
+
context 'when the scope is module' do
|
120
|
+
let(:source) do
|
121
|
+
<<-END
|
122
|
+
module SomeModule
|
123
|
+
this_is_target
|
124
|
+
end
|
125
|
+
END
|
126
|
+
end
|
127
|
+
|
128
|
+
let(:scope_node_type) { :module }
|
129
|
+
|
130
|
+
include_examples 'returns the body node'
|
131
|
+
end
|
132
|
+
|
133
|
+
context 'when the scope is class' do
|
134
|
+
let(:source) do
|
135
|
+
<<-END
|
136
|
+
class SomeClass
|
137
|
+
this_is_target
|
138
|
+
end
|
139
|
+
END
|
140
|
+
end
|
141
|
+
|
142
|
+
let(:scope_node_type) { :class }
|
143
|
+
|
144
|
+
include_examples 'returns the body node'
|
145
|
+
end
|
146
|
+
|
147
|
+
context 'when the scope is singleton class' do
|
148
|
+
let(:source) do
|
149
|
+
<<-END
|
150
|
+
class << self
|
151
|
+
this_is_target
|
152
|
+
end
|
153
|
+
END
|
154
|
+
end
|
155
|
+
|
156
|
+
let(:scope_node_type) { :sclass }
|
157
|
+
|
158
|
+
include_examples 'returns the body node'
|
159
|
+
end
|
160
|
+
|
161
|
+
context 'when the scope is block' do
|
162
|
+
let(:source) do
|
163
|
+
<<-END
|
164
|
+
1.times do
|
165
|
+
this_is_target
|
166
|
+
end
|
167
|
+
END
|
168
|
+
end
|
169
|
+
|
170
|
+
let(:scope_node_type) { :block }
|
171
|
+
|
172
|
+
include_examples 'returns the body node'
|
173
|
+
end
|
174
|
+
|
175
|
+
context 'when the scope is top level' do
|
176
|
+
let(:source) do
|
177
|
+
<<-END
|
178
|
+
foo = 1
|
179
|
+
this_is_target
|
180
|
+
END
|
181
|
+
end
|
182
|
+
|
183
|
+
let(:scope_node_type) { :begin }
|
184
|
+
|
185
|
+
include_examples 'returns the body node'
|
186
|
+
end
|
187
|
+
end
|
188
|
+
end
|
189
|
+
end
|
190
|
+
end
|
191
|
+
end
|
@@ -0,0 +1,79 @@
|
|
1
|
+
# encoding: utf-8
|
2
|
+
|
3
|
+
require 'spec_helper'
|
4
|
+
|
5
|
+
module Rubocop
|
6
|
+
module Cop
|
7
|
+
module VariableInspector
|
8
|
+
describe Variable do
|
9
|
+
include AST::Sexp
|
10
|
+
|
11
|
+
describe '.new' do
|
12
|
+
context 'when non variable declaration node is passed' do
|
13
|
+
it 'raises error' do
|
14
|
+
name = :foo
|
15
|
+
declaration_node = s(:def)
|
16
|
+
scope = Scope.new(s(:class))
|
17
|
+
expect { Variable.new(name, declaration_node, scope) }
|
18
|
+
.to raise_error(ArgumentError)
|
19
|
+
end
|
20
|
+
end
|
21
|
+
end
|
22
|
+
|
23
|
+
describe '#referenced?' do
|
24
|
+
let(:name) { :foo }
|
25
|
+
let(:declaration_node) { s(:arg, name) }
|
26
|
+
let(:scope) { double('scope') }
|
27
|
+
let(:variable) { Variable.new(name, declaration_node, scope) }
|
28
|
+
|
29
|
+
subject { variable.referenced? }
|
30
|
+
|
31
|
+
context 'when the variable is not yet assigned' do
|
32
|
+
it { should be_false }
|
33
|
+
end
|
34
|
+
|
35
|
+
context 'when the variable has an assignment' do
|
36
|
+
before do
|
37
|
+
variable.assign(s(:lvasgn, :foo))
|
38
|
+
end
|
39
|
+
|
40
|
+
context 'and the assignment is not yet referenced' do
|
41
|
+
it { should be_false }
|
42
|
+
end
|
43
|
+
|
44
|
+
context 'and the assignment is referenced' do
|
45
|
+
before do
|
46
|
+
variable.assignments.first.reference!
|
47
|
+
end
|
48
|
+
|
49
|
+
it { should be_true }
|
50
|
+
end
|
51
|
+
end
|
52
|
+
|
53
|
+
context 'when the variable has multiple assignments' do
|
54
|
+
before do
|
55
|
+
variable.assign(s(:lvasgn, :foo))
|
56
|
+
variable.assign(s(:lvasgn, :foo))
|
57
|
+
end
|
58
|
+
|
59
|
+
context 'and only once assignment is referenced' do
|
60
|
+
before do
|
61
|
+
variable.assignments[1].reference!
|
62
|
+
end
|
63
|
+
|
64
|
+
it { should be_true }
|
65
|
+
end
|
66
|
+
|
67
|
+
context 'and all assignments are referenced' do
|
68
|
+
before do
|
69
|
+
variable.assignments.each { |a| a.reference! }
|
70
|
+
end
|
71
|
+
|
72
|
+
it { should be_true }
|
73
|
+
end
|
74
|
+
end
|
75
|
+
end
|
76
|
+
end
|
77
|
+
end
|
78
|
+
end
|
79
|
+
end
|
@@ -0,0 +1,275 @@
|
|
1
|
+
# encoding: utf-8
|
2
|
+
|
3
|
+
require 'spec_helper'
|
4
|
+
|
5
|
+
module Rubocop
|
6
|
+
module Cop
|
7
|
+
module VariableInspector
|
8
|
+
describe VariableTable do
|
9
|
+
include AST::Sexp
|
10
|
+
|
11
|
+
subject(:variable_table) { VariableTable.new }
|
12
|
+
|
13
|
+
describe '#push_scope' do
|
14
|
+
it 'returns pushed scope object' do
|
15
|
+
node = s(:def)
|
16
|
+
scope = variable_table.push_scope(node)
|
17
|
+
expect(scope).to equal(variable_table.current_scope)
|
18
|
+
expect(scope.node).to equal(node)
|
19
|
+
end
|
20
|
+
end
|
21
|
+
|
22
|
+
describe '#pop_scope' do
|
23
|
+
before do
|
24
|
+
node = s(:def)
|
25
|
+
variable_table.push_scope(node)
|
26
|
+
end
|
27
|
+
|
28
|
+
it 'returns popped scope object' do
|
29
|
+
last_scope = variable_table.current_scope
|
30
|
+
popped_scope = variable_table.pop_scope
|
31
|
+
expect(popped_scope).to equal(last_scope)
|
32
|
+
end
|
33
|
+
end
|
34
|
+
|
35
|
+
describe '#current_scope_level' do
|
36
|
+
before do
|
37
|
+
variable_table.push_scope(s(:def))
|
38
|
+
end
|
39
|
+
|
40
|
+
it 'increases by pushing scope' do
|
41
|
+
last_scope_level = variable_table.current_scope_level
|
42
|
+
variable_table.push_scope(s(:def))
|
43
|
+
expect(variable_table.current_scope_level)
|
44
|
+
.to eq(last_scope_level + 1)
|
45
|
+
end
|
46
|
+
|
47
|
+
it 'decreases by popping scope' do
|
48
|
+
last_scope_level = variable_table.current_scope_level
|
49
|
+
variable_table.pop_scope
|
50
|
+
expect(variable_table.current_scope_level)
|
51
|
+
.to eq(last_scope_level - 1)
|
52
|
+
end
|
53
|
+
end
|
54
|
+
|
55
|
+
describe '#declare_variable' do
|
56
|
+
before do
|
57
|
+
2.times do
|
58
|
+
node = s(:def)
|
59
|
+
variable_table.push_scope(node)
|
60
|
+
end
|
61
|
+
end
|
62
|
+
|
63
|
+
it 'adds variable to current scope with its name as key' do
|
64
|
+
node = s(:lvasgn, :foo)
|
65
|
+
variable_table.declare_variable(:foo, node)
|
66
|
+
expect(variable_table.current_scope.variables)
|
67
|
+
.to have_key(:foo)
|
68
|
+
expect(variable_table.scope_stack[-2].variables)
|
69
|
+
.to be_empty
|
70
|
+
variable = variable_table.current_scope.variables[:foo]
|
71
|
+
expect(variable.declaration_node).to equal(node)
|
72
|
+
end
|
73
|
+
|
74
|
+
it 'returns the added variable' do
|
75
|
+
node = s(:lvasgn, :foo)
|
76
|
+
variable = variable_table.declare_variable(:foo, node)
|
77
|
+
expect(variable.declaration_node).to equal(node)
|
78
|
+
end
|
79
|
+
end
|
80
|
+
|
81
|
+
describe '#find_variable' do
|
82
|
+
before do
|
83
|
+
variable_table.push_scope(s(:class))
|
84
|
+
variable_table.declare_variable(:baz, s(:lvasgn, :baz))
|
85
|
+
|
86
|
+
variable_table.push_scope(s(:def))
|
87
|
+
variable_table.declare_variable(:bar, s(:lvasgn, :bar))
|
88
|
+
end
|
89
|
+
|
90
|
+
context 'when current scope is block' do
|
91
|
+
before do
|
92
|
+
variable_table.push_scope(s(:block))
|
93
|
+
end
|
94
|
+
|
95
|
+
context 'when a variable with the target name exists ' +
|
96
|
+
'in current scope' do
|
97
|
+
before do
|
98
|
+
variable_table.declare_variable(:foo, s(:lvasgn, :foo))
|
99
|
+
end
|
100
|
+
|
101
|
+
context 'and does not exist in outer scope' do
|
102
|
+
it 'returns the current scope variable' do
|
103
|
+
found_variable = variable_table.find_variable(:foo)
|
104
|
+
expect(found_variable.name).to eq(:foo)
|
105
|
+
end
|
106
|
+
end
|
107
|
+
|
108
|
+
context 'and also exists in outer scope' do
|
109
|
+
before do
|
110
|
+
variable_table.declare_variable(:bar, s(:lvasgn, :bar))
|
111
|
+
end
|
112
|
+
|
113
|
+
it 'returns the current scope variable' do
|
114
|
+
found_variable = variable_table.find_variable(:bar)
|
115
|
+
expect(found_variable.name).to equal(:bar)
|
116
|
+
expect(variable_table.current_scope.variables)
|
117
|
+
.to have_value(found_variable)
|
118
|
+
expect(variable_table.scope_stack[-2].variables)
|
119
|
+
.not_to have_value(found_variable)
|
120
|
+
end
|
121
|
+
end
|
122
|
+
end
|
123
|
+
|
124
|
+
context 'when a variable with the target name does not exist ' +
|
125
|
+
'in current scope' do
|
126
|
+
context 'but exists in the direct outer scope' do
|
127
|
+
it 'returns the direct outer scope variable' do
|
128
|
+
found_variable = variable_table.find_variable(:bar)
|
129
|
+
expect(found_variable.name).to equal(:bar)
|
130
|
+
end
|
131
|
+
end
|
132
|
+
|
133
|
+
context 'but exists in a indirect outer scope' do
|
134
|
+
context 'when the direct outer scope is block' do
|
135
|
+
before do
|
136
|
+
variable_table.pop_scope
|
137
|
+
variable_table.pop_scope
|
138
|
+
|
139
|
+
variable_table.push_scope(s(:block))
|
140
|
+
variable_table.push_scope(s(:block))
|
141
|
+
end
|
142
|
+
|
143
|
+
it 'returns the indirect outer scope variable' do
|
144
|
+
found_variable = variable_table.find_variable(:baz)
|
145
|
+
expect(found_variable.name).to equal(:baz)
|
146
|
+
end
|
147
|
+
end
|
148
|
+
|
149
|
+
context 'when the direct outer scope is not block' do
|
150
|
+
it 'returns nil' do
|
151
|
+
found_variable = variable_table.find_variable(:baz)
|
152
|
+
expect(found_variable).to be_nil
|
153
|
+
end
|
154
|
+
end
|
155
|
+
end
|
156
|
+
|
157
|
+
context 'and does not exist in all outer scopes' do
|
158
|
+
it 'returns nil' do
|
159
|
+
found_variable = variable_table.find_variable(:non)
|
160
|
+
expect(found_variable).to be_nil
|
161
|
+
end
|
162
|
+
end
|
163
|
+
end
|
164
|
+
end
|
165
|
+
|
166
|
+
context 'when current scope is not block' do
|
167
|
+
before do
|
168
|
+
variable_table.push_scope(s(:def))
|
169
|
+
end
|
170
|
+
|
171
|
+
context 'when a variable with the target name exists ' +
|
172
|
+
'in current scope' do
|
173
|
+
before do
|
174
|
+
variable_table.declare_variable(:foo, s(:lvasgn, :foo))
|
175
|
+
end
|
176
|
+
|
177
|
+
context 'and does not exist in outer scope' do
|
178
|
+
it 'returns the current scope variable' do
|
179
|
+
found_variable = variable_table.find_variable(:foo)
|
180
|
+
expect(found_variable.name).to eq(:foo)
|
181
|
+
end
|
182
|
+
end
|
183
|
+
|
184
|
+
context 'and also exists in outer scope' do
|
185
|
+
it 'returns the current scope variable' do
|
186
|
+
found_variable = variable_table.find_variable(:foo)
|
187
|
+
expect(found_variable.name).to equal(:foo)
|
188
|
+
expect(variable_table.current_scope.variables)
|
189
|
+
.to have_value(found_variable)
|
190
|
+
expect(variable_table.scope_stack[-2].variables)
|
191
|
+
.not_to have_value(found_variable)
|
192
|
+
end
|
193
|
+
end
|
194
|
+
end
|
195
|
+
|
196
|
+
context 'when a variable with the target name does not exist ' +
|
197
|
+
'in current scope' do
|
198
|
+
context 'but exists in the direct outer scope' do
|
199
|
+
it 'returns nil' do
|
200
|
+
found_variable = variable_table.find_variable(:bar)
|
201
|
+
expect(found_variable).to be_nil
|
202
|
+
end
|
203
|
+
end
|
204
|
+
|
205
|
+
context 'and does not exist in all outer scopes' do
|
206
|
+
it 'returns nil' do
|
207
|
+
found_variable = variable_table.find_variable(:non)
|
208
|
+
expect(found_variable).to be_nil
|
209
|
+
end
|
210
|
+
end
|
211
|
+
end
|
212
|
+
end
|
213
|
+
end
|
214
|
+
|
215
|
+
describe '#accessible_variables' do
|
216
|
+
let(:accessible_variable_names) do
|
217
|
+
variable_table.accessible_variables.map(&:name)
|
218
|
+
end
|
219
|
+
|
220
|
+
before do
|
221
|
+
variable_table.push_scope(s(:class))
|
222
|
+
end
|
223
|
+
|
224
|
+
context 'when there are no variables' do
|
225
|
+
it 'returns empty array' do
|
226
|
+
expect(variable_table.accessible_variables).to be_empty
|
227
|
+
end
|
228
|
+
end
|
229
|
+
|
230
|
+
context 'when the current scope has some variables' do
|
231
|
+
before do
|
232
|
+
variable_table.declare_variable(:foo, s(:lvasgn, :foo))
|
233
|
+
variable_table.declare_variable(:bar, s(:lvasgn, :bar))
|
234
|
+
end
|
235
|
+
|
236
|
+
it 'returns all the variables' do
|
237
|
+
expect(accessible_variable_names).to match_array([:foo, :bar])
|
238
|
+
end
|
239
|
+
end
|
240
|
+
|
241
|
+
context 'when the direct outer scope has some variables' do
|
242
|
+
before do
|
243
|
+
variable_table.declare_variable(:foo, s(:lvasgn, :foo))
|
244
|
+
end
|
245
|
+
|
246
|
+
context 'and the current scope is block' do
|
247
|
+
before do
|
248
|
+
variable_table.push_scope(s(:block))
|
249
|
+
variable_table.declare_variable(:bar, s(:lvasgn, :bar))
|
250
|
+
variable_table.declare_variable(:baz, s(:lvasgn, :baz))
|
251
|
+
end
|
252
|
+
|
253
|
+
it 'returns the current and direct outer scope variables' do
|
254
|
+
expect(accessible_variable_names)
|
255
|
+
.to match_array([:foo, :bar, :baz])
|
256
|
+
end
|
257
|
+
end
|
258
|
+
|
259
|
+
context 'and the current scope is not block' do
|
260
|
+
before do
|
261
|
+
variable_table.push_scope(s(:def))
|
262
|
+
variable_table.declare_variable(:bar, s(:lvasgn, :bar))
|
263
|
+
variable_table.declare_variable(:baz, s(:lvasgn, :baz))
|
264
|
+
end
|
265
|
+
|
266
|
+
it 'returns only the current scope variables' do
|
267
|
+
expect(accessible_variable_names).to match_array([:bar, :baz])
|
268
|
+
end
|
269
|
+
end
|
270
|
+
end
|
271
|
+
end
|
272
|
+
end
|
273
|
+
end
|
274
|
+
end
|
275
|
+
end
|