From 06fc55aaca8fc501e78df7f0928c89e50ec0ba40 Mon Sep 17 00:00:00 2001 From: Vinicius Stock Date: Mon, 18 Nov 2024 09:56:08 -0500 Subject: [PATCH] Check target precision for call node in hover and definition --- lib/ruby_lsp/requests/definition.rb | 2 ++ lib/ruby_lsp/requests/hover.rb | 2 ++ test/requests/definition_expectations_test.rb | 34 +++++++++++++++++++ test/requests/hover_expectations_test.rb | 34 +++++++++++++++++++ 4 files changed, 72 insertions(+) diff --git a/lib/ruby_lsp/requests/definition.rb b/lib/ruby_lsp/requests/definition.rb index 8305f0ec6..e4817e3db 100644 --- a/lib/ruby_lsp/requests/definition.rb +++ b/lib/ruby_lsp/requests/definition.rb @@ -118,6 +118,8 @@ def position_outside_target?(position, target) Prism::InstanceVariableWriteNode !covers_position?(target.name_loc, position) + when Prism::CallNode + !covers_position?(target.message_loc, position) else false end diff --git a/lib/ruby_lsp/requests/hover.rb b/lib/ruby_lsp/requests/hover.rb index 06fe522f9..55c5ea8ba 100644 --- a/lib/ruby_lsp/requests/hover.rb +++ b/lib/ruby_lsp/requests/hover.rb @@ -103,6 +103,8 @@ def position_outside_target?(position, target) Prism::GlobalVariableOrWriteNode, Prism::GlobalVariableWriteNode !covers_position?(target.name_loc, position) + when Prism::CallNode + !covers_position?(target.message_loc, position) else false end diff --git a/test/requests/definition_expectations_test.rb b/test/requests/definition_expectations_test.rb index b74090c7b..d24d178c5 100644 --- a/test/requests/definition_expectations_test.rb +++ b/test/requests/definition_expectations_test.rb @@ -1097,6 +1097,40 @@ def baz end end + def test_definition_call_node_precision + source = <<~RUBY + class Foo + def message + "hello!" + end + end + + class Bar + def with_foo(foo) + @foo_message = foo.message + end + end + RUBY + + with_server(source) do |server, uri| + # On the `foo` receiver, we should not show any results + server.process_message( + id: 1, + method: "textDocument/definition", + params: { textDocument: { uri: uri }, position: { character: 19, line: 8 } }, + ) + assert_empty(server.pop_response.response) + + # On `message`, we should + server.process_message( + id: 2, + method: "textDocument/definition", + params: { textDocument: { uri: uri }, position: { character: 23, line: 8 } }, + ) + refute_empty(server.pop_response.response) + end + end + private def create_definition_addon diff --git a/test/requests/hover_expectations_test.rb b/test/requests/hover_expectations_test.rb index 6b08c8d24..b43ae8709 100644 --- a/test/requests/hover_expectations_test.rb +++ b/test/requests/hover_expectations_test.rb @@ -820,6 +820,40 @@ def foo end end + def test_hover_call_node_precision + source = <<~RUBY + class Foo + def message + "hello!" + end + end + + class Bar + def with_foo(foo) + @foo_message = foo.message + end + end + RUBY + + with_server(source) do |server, uri| + # On the `foo` receiver, we should not show any results + server.process_message( + id: 1, + method: "textDocument/hover", + params: { textDocument: { uri: uri }, position: { character: 19, line: 8 } }, + ) + assert_nil(server.pop_response.response) + + # On `message`, we should + server.process_message( + id: 2, + method: "textDocument/hover", + params: { textDocument: { uri: uri }, position: { character: 23, line: 8 } }, + ) + refute_nil(server.pop_response.response) + end + end + private def create_hover_addon