From 796e5edadcc5a4e3d3a5a50e045c0cf4079361dd Mon Sep 17 00:00:00 2001 From: Soutaro Matsumoto Date: Thu, 17 Mar 2022 21:35:57 +0900 Subject: [PATCH 1/5] Pass `--log-output` option to workers --- lib/steep/server/worker_process.rb | 10 +++++++--- 1 file changed, 7 insertions(+), 3 deletions(-) diff --git a/lib/steep/server/worker_process.rb b/lib/steep/server/worker_process.rb index c264ece39..e37870db9 100644 --- a/lib/steep/server/worker_process.rb +++ b/lib/steep/server/worker_process.rb @@ -19,12 +19,16 @@ def initialize(reader:, writer:, stderr:, wait_thread:, name:, index: nil) end def self.spawn_worker(type, name:, steepfile:, options: [], delay_shutdown: false, index: nil) - log_level = %w(debug info warn error fatal unknown)[Steep.logger.level] + args = ["--name=#{name}", "--steepfile=#{steepfile}"] + args << (%w(debug info warn error fatal unknown)[Steep.logger.level].yield_self {|log_level| "--log-level=#{log_level}" }) + if Steep.log_output.is_a?(String) + args << "--log-output=#{Steep.log_output}" + end command = case type when :interaction - ["steep", "worker", "--interaction", "--name=#{name}", "--log-level=#{log_level}", "--steepfile=#{steepfile}", *options] + ["steep", "worker", "--interaction", *args, *options] when :typecheck - ["steep", "worker", "--typecheck", "--name=#{name}", "--log-level=#{log_level}", "--steepfile=#{steepfile}", *options] + ["steep", "worker", "--typecheck", *args, *options] else raise "Unknown type: #{type}" end From 2beb8efaceb5c8a4cf046ba5c3f4c263825be0ef Mon Sep 17 00:00:00 2001 From: Soutaro Matsumoto Date: Thu, 17 Mar 2022 21:36:23 +0900 Subject: [PATCH 2/5] Delete percentage from LSP progress message --- lib/steep/server/master.rb | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/lib/steep/server/master.rb b/lib/steep/server/master.rb index d8166080f..368c120c2 100644 --- a/lib/steep/server/master.rb +++ b/lib/steep/server/master.rb @@ -739,7 +739,7 @@ def on_type_check_update(guid:, path:) { kind: "end" } else progress_string = ("▮"*(percentage/5)) + ("▯"*(20 - percentage/5)) - { kind: "report", percentage: percentage, message: "#{progress_string} (#{percentage}%)" } + { kind: "report", percentage: percentage, message: "#{progress_string}" } end job_queue << SendMessageJob.to_client( From e37777dde331c4819c3e7eb958c542716643686c Mon Sep 17 00:00:00 2001 From: Soutaro Matsumoto Date: Thu, 17 Mar 2022 21:44:46 +0900 Subject: [PATCH 3/5] Strip HTML comment from markdown source --- lib/steep/server/interaction_worker.rb | 2 +- test/interaction_worker_test.rb | 39 ++++++++++++++++++++++++++ 2 files changed, 40 insertions(+), 1 deletion(-) diff --git a/lib/steep/server/interaction_worker.rb b/lib/steep/server/interaction_worker.rb index 8255dfbb9..38fb5acc0 100644 --- a/lib/steep/server/interaction_worker.rb +++ b/lib/steep/server/interaction_worker.rb @@ -89,7 +89,7 @@ def process_hover(job) end LSP::Interface::Hover.new( - contents: { kind: "markdown", value: format_hover(content) }, + contents: { kind: "markdown", value: format_hover(content)&.gsub(/)-->/, "") }, range: range ) end diff --git a/test/interaction_worker_test.rb b/test/interaction_worker_test.rb index 8220c9c52..b5c189f87 100644 --- a/test/interaction_worker_test.rb +++ b/test/interaction_worker_test.rb @@ -296,6 +296,45 @@ class ::Foo[T] < ::Parent[T] end end + def test_handle_class_hover_strip_html_comment + in_tmpdir do + project = Project.new(steepfile_path: current_dir + "Steepfile") + Project::DSL.parse(project, < [ContentChange.string(< +# This is comment content +class Foo[T] end + +type hello = Foo[String] +RBS + } + ) {} + + response = worker.process_hover(InteractionWorker::HoverJob.new(path: Pathname("sig/hello.rbs"), line: 5, column: 15)) + + response = response.attributes + expected_value = " +This is comment content + + +```rbs +class ::Foo[T] +``` +" + assert_equal({ kind: "markdown", value: expected_value }, response[:contents]) + end + end + def test_handle_hover_invalid in_tmpdir do project = Project.new(steepfile_path: current_dir + "Steepfile") From 730cbc9362c98a9bc5ff6fc797d480e9825d0ce9 Mon Sep 17 00:00:00 2001 From: Soutaro Matsumoto Date: Fri, 18 Mar 2022 09:37:19 +0900 Subject: [PATCH 4/5] Let GotoService filters results with respect to PathAssignment --- lib/steep/server/type_check_worker.rb | 2 +- lib/steep/services/goto_service.rb | 17 ++++++-- test/goto_service_test.rb | 63 ++++++++++++++++++++++----- 3 files changed, 66 insertions(+), 16 deletions(-) diff --git a/lib/steep/server/type_check_worker.rb b/lib/steep/server/type_check_worker.rb index 694220223..0ba242aec 100644 --- a/lib/steep/server/type_check_worker.rb +++ b/lib/steep/server/type_check_worker.rb @@ -268,7 +268,7 @@ def goto(job) line = job.params[:position][:line] + 1 column = job.params[:position][:character] - goto_service = Services::GotoService.new(type_check: service) + goto_service = Services::GotoService.new(type_check: service, assignment: assignment) locations = case when job.definition? diff --git a/lib/steep/services/goto_service.rb b/lib/steep/services/goto_service.rb index f8c44685d..5a2adb820 100644 --- a/lib/steep/services/goto_service.rb +++ b/lib/steep/services/goto_service.rb @@ -21,10 +21,11 @@ def from_rbs? end TypeNameQuery = Struct.new(:name, keyword_init: true) - attr_reader :type_check + attr_reader :type_check, :assignment - def initialize(type_check:) + def initialize(type_check:, assignment:) @type_check = type_check + @assignment = assignment end def project @@ -78,7 +79,17 @@ def definition(path:, line:, column:) end end - locations.uniq + # Drop un-assigned paths here. + # The path assignment makes sense only for `.rbs` files, because un-assigned `.rb` files are already skipped since they are not type checked. + # + locations.uniq.select do |loc| + case loc + when RBS::Location + assignment =~ loc.name + else + true + end + end end def test_ast_location(loc, line:, column:) diff --git a/test/goto_service_test.rb b/test/goto_service_test.rb index 458fde67b..65d68ba81 100644 --- a/test/goto_service_test.rb +++ b/test/goto_service_test.rb @@ -12,6 +12,10 @@ def dir @dir ||= Pathname(Dir.mktmpdir) end + def assignment + Services::PathAssignment.all + end + def project @project ||= Project.new(steepfile_path: dir + "Steepfile").tap do |project| Project::DSL.parse(project, < String RBS end - service = Services::GotoService.new(type_check: type_check) + service = Services::GotoService.new(type_check: type_check, assignment: assignment) service.query_at(path: dir + "sig/customer.rbs", line: 2, column: 16).tap do |qs| assert_equal 1, qs.size @@ -276,7 +280,7 @@ def self?.baz: () -> void RUBY end - service = Services::GotoService.new(type_check: type_check) + service = Services::GotoService.new(type_check: type_check, assignment: assignment) service.query_at(path: dir + "lib/main.rb", line: 1, column: 16).tap do |qs| assert_equal 1, qs.size @@ -326,7 +330,7 @@ module ::Customer2 type_check.source_files.each_key do |path| type_check.typecheck_source(path: path) {} end - service = Services::GotoService.new(type_check: type_check) + service = Services::GotoService.new(type_check: type_check, assignment: assignment) service.constant_definition_in_ruby(TypeName("::Customer"), locations: []).tap do |locs| assert_equal 1, locs.size @@ -420,7 +424,7 @@ def self.find type_check.source_files.each_key do |path| type_check.typecheck_source(path: path) {} end - service = Services::GotoService.new(type_check: type_check) + service = Services::GotoService.new(type_check: type_check, assignment: assignment) service.method_locations(MethodName("::Customer#foo"), locations: [], in_ruby: true, in_rbs: true).tap do |locs| assert_equal 2, locs.size @@ -493,7 +497,7 @@ class Customer RBS end - service = Services::GotoService.new(type_check: type_check) + service = Services::GotoService.new(type_check: type_check, assignment: assignment) service.type_name_locations(TypeName("::Customer")).tap do |locs| assert_equal 2, locs.size @@ -554,7 +558,7 @@ def self.new: (Integer) -> Baz RBS end - service = Services::GotoService.new(type_check: type_check) + service = Services::GotoService.new(type_check: type_check, assignment: assignment) service.definition(path: dir + "lib/test.rb", line: 1, column: 6).tap do |locs| assert_any!(locs) do |loc| @@ -612,7 +616,7 @@ def self.new(i) RBS end - service = Services::GotoService.new(type_check: type_check) + service = Services::GotoService.new(type_check: type_check, assignment: assignment) service.implementation(path: dir + "lib/test.rb", line: 12, column: 6).tap do |locs| assert_any!(locs, size: 1) do |loc| @@ -639,7 +643,7 @@ def test_method_block RBS end - service = Services::GotoService.new(type_check: type_check) + service = Services::GotoService.new(type_check: type_check, assignment: assignment) service.definition(path: dir + "lib/test.rb", line: 1, column: 4).tap do |locs| assert_any!(locs, size: 1) do |loc| @@ -647,4 +651,39 @@ def test_method_block end end end + + def test_goto_definition_wrt_assignment + type_check = type_check_service do |changes| + changes[Pathname("sig/a.rbs")] = [ContentChange.string(< Date: Thu, 17 Mar 2022 22:30:56 +0900 Subject: [PATCH 5/5] Fix completion insertion --- lib/steep/server/interaction_worker.rb | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/lib/steep/server/interaction_worker.rb b/lib/steep/server/interaction_worker.rb index 38fb5acc0..a5bbf1ed5 100644 --- a/lib/steep/server/interaction_worker.rb +++ b/lib/steep/server/interaction_worker.rb @@ -271,7 +271,7 @@ def format_completion_item_for_rbs(sig_service, type_name, context, job, prefix) ), end: LanguageServer::Protocol::Interface::Position.new( line: job.line - 1, - character: job.column - prefix.size + character: job.column ) )