Skip to content

Commit 0a1381b

Browse files
committed
CallTargetNode and IndexTargetNode
1 parent 6c703f8 commit 0a1381b

3 files changed

Lines changed: 24 additions & 13 deletions

File tree

lib/repl_type_completor.rb

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -91,8 +91,8 @@ def analyze_code(code, binding = Object::TOPLEVEL_BINDING)
9191
else
9292
[:symbol, name] unless name.empty?
9393
end
94-
when Prism::CallNode
95-
return if target_node.opening
94+
when Prism::CallNode, Prism::CallTargetNode
95+
return if target_node.is_a?(Prism::CallNode) && target_node.opening
9696

9797
name = target_node.message.to_s
9898
return [:lvar_or_method, name, calculate_scope.call] if target_node.receiver.nil?

lib/repl_type_completor/type_analyzer.rb

Lines changed: 14 additions & 11 deletions
Original file line numberDiff line numberDiff line change
@@ -582,8 +582,8 @@ def evaluate_rescue_node(node, scope)
582582
case node.reference
583583
when Prism::LocalVariableTargetNode, Prism::InstanceVariableTargetNode, Prism::ClassVariableTargetNode, Prism::GlobalVariableTargetNode, Prism::ConstantTargetNode
584584
s[node.reference.name.to_s] = error_type
585-
when Prism::CallNode
586-
evaluate node.reference, s
585+
when Prism::CallTargetNode, Prism::IndexTargetNode
586+
evaluate_multi_write_receiver node.reference, s, nil
587587
end
588588
end
589589
node.statements ? evaluate(node.statements, s) : Types::NIL
@@ -1034,16 +1034,15 @@ def evaluate_write(node, value, scope, evaluated_receivers)
10341034
case node
10351035
when Prism::MultiTargetNode
10361036
evaluate_multi_write node, value, scope, evaluated_receivers
1037-
when Prism::CallNode
1038-
evaluated_receivers&.[](node.receiver) || evaluate(node.receiver, scope) if node.receiver
1037+
when Prism::CallTargetNode, Prism::IndexTargetNode
1038+
evaluated_receivers&.[](node.receiver) || evaluate_multi_write_receiver(node, scope, nil)
10391039
when Prism::SplatNode
10401040
evaluate_write node.expression, Types.array_of(value), scope, evaluated_receivers if node.expression
10411041
when Prism::LocalVariableTargetNode, Prism::GlobalVariableTargetNode, Prism::InstanceVariableTargetNode, Prism::ClassVariableTargetNode, Prism::ConstantTargetNode
10421042
scope[node.name.to_s] = value
10431043
when Prism::ConstantPathTargetNode
10441044
receiver = evaluated_receivers&.[](node.parent) || evaluate(node.parent, scope) if node.parent
10451045
const_path_write receiver, node.child.name.to_s, value, scope
1046-
value
10471046
end
10481047
end
10491048

@@ -1066,20 +1065,24 @@ def evaluate_multi_write_receiver(node, scope, evaluated_receivers)
10661065
when Prism::MultiWriteNode, Prism::MultiTargetNode
10671066
targets = [*node.lefts, *node.rest, *node.rights]
10681067
targets.each { evaluate_multi_write_receiver _1, scope, evaluated_receivers }
1069-
when Prism::CallNode
1070-
if node.receiver
1071-
receiver = evaluate(node.receiver, scope)
1072-
evaluated_receivers[node.receiver] = receiver if evaluated_receivers
1073-
end
1068+
when Prism::CallTargetNode, Prism::CallNode
1069+
receiver = evaluate(node.receiver, scope)
1070+
evaluated_receivers[node.receiver] = receiver if evaluated_receivers
1071+
receiver
1072+
when Prism::IndexTargetNode
1073+
receiver = evaluate(node.receiver, scope)
1074+
evaluated_receivers[node.receiver] = receiver if evaluated_receivers
10741075
if node.arguments
10751076
node.arguments.arguments&.each do |arg|
10761077
if arg.is_a? Prism::SplatNode
1077-
evaluate arg.expression, scope
1078+
evaluate arg.expression, scope if arg.expression
10781079
else
10791080
evaluate arg, scope
10801081
end
10811082
end
10821083
end
1084+
evaluate node.block.expression, scope if node.block&.expression
1085+
receiver
10831086
when Prism::SplatNode
10841087
evaluate_multi_write_receiver node.expression, scope, evaluated_receivers if node.expression
10851088
end

test/repl_type_completor/test_type_analyze.rb

Lines changed: 8 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -333,8 +333,15 @@ def test_massign
333333
assert_call('a, ((b=1).c, d) = 1; b.', include: Integer)
334334
assert_call('a, b[c=1] = 1; c.', include: Integer)
335335
assert_call('a, b[*(c=1)] = 1; c.', include: Integer)
336+
assert_call('a, b[**(c=1)] = 1; c.', include: Integer)
337+
assert_call('a, b[&(c=1)] = 1; c.', include: Integer)
338+
assert_call('a, b[] = 1; a.', include: Integer)
339+
assert_call('def f(*); a, b[*] = 1; a.', include: Integer)
340+
assert_call('def f(&); a, b[&] = 1; a.', include: Integer)
341+
assert_call('def f(**); a, b[**] = 1; a.', include: Integer)
336342
# incomplete massign
337343
assert_analyze_type('a,b', :lvar_or_method, 'b')
344+
assert_call('(a=1).b, a.a', include: Integer)
338345
assert_call('(a=1).b, a.', include: Integer)
339346
assert_call('a=1; *a.', include: Integer)
340347
end
@@ -575,6 +582,7 @@ def test_for
575582
assert_call('for *,(*) in [1,2,3]; 1.', include: Integer)
576583
assert_call('for *i in [1,2,3]; i.sample.', include: Integer)
577584
assert_call('for (a=1).b in [1,2,3]; a.', include: Integer)
585+
assert_call('for a[b=1] in [1,2,3]; b.', include: Integer)
578586
assert_call('for Array::B in [1,2,3]; Array::B.', include: Integer)
579587
assert_call('for A in [1,2,3]; A.', include: Integer)
580588
assert_call('for $a in [1,2,3]; $a.', include: Integer)

0 commit comments

Comments
 (0)