Skip to content

WIP: Add support for the new Test Discovery API #590

New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Closed
wants to merge 9 commits into from
Closed
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
5 changes: 4 additions & 1 deletion Gemfile
Original file line number Diff line number Diff line change
Expand Up @@ -15,11 +15,14 @@ gem "rubocop-minitest", "~> 0.36.0", require: false
gem "rubocop-rake", "~> 0.6.0", require: false
gem "rubocop-sorbet", "~> 0.8", require: false
gem "sorbet-static-and-runtime", platforms: :ruby
gem "tapioca", "~> 0.13", require: false, platforms: :ruby
# gem "tapioca", "~> 0.13", require: false, platforms: :ruby
gem "tapioca", github: "Shopify/tapioca", branch: "at-rbs-rewriter"
gem "psych", "~> 5.1", require: false
gem "rails", "8.0.0"

platforms :mingw, :x64_mingw, :mswin, :jruby do
gem "tzinfo"
gem "tzinfo-data"
end

gem "ruby-lsp", github: "Shopify/ruby-lsp", branch: "main"
90 changes: 57 additions & 33 deletions Gemfile.lock
Original file line number Diff line number Diff line change
@@ -1,3 +1,31 @@
GIT
remote: https://github.com/Shopify/ruby-lsp.git
revision: 779679c26ba3830d29adbcec70476494fc194527
branch: main
specs:
ruby-lsp (0.23.12)
language_server-protocol (~> 3.17.0)
prism (>= 1.2, < 2.0)
rbs (>= 3, < 4)
sorbet-runtime (>= 0.5.10782)

GIT
remote: https://github.com/Shopify/tapioca.git
revision: 5995622a06e194a6308223d789d73f3cc9eae9c4
branch: at-rbs-rewriter
specs:
tapioca (0.16.11)
benchmark
bundler (>= 2.2.25)
netrc (>= 0.11.0)
parallel (>= 1.21.0)
rbi (>= 0.3.1)
ruby-next (~> 1.0)
sorbet-static-and-runtime (>= 0.5.11087)
spoom (>= 1.6.1)
thor (>= 1.2.0)
yard-sorbet

PATH
remote: .
specs:
Expand Down Expand Up @@ -90,6 +118,7 @@ GEM
debug (1.9.2)
irb (~> 1.10)
reline (>= 0.3.8)
diff-lcs (1.6.0)
drb (2.2.1)
erubi (1.13.1)
globalid (1.2.1)
Expand Down Expand Up @@ -134,14 +163,13 @@ GEM
racc (~> 1.4)
nokogiri (1.18.1-arm64-darwin)
racc (~> 1.4)
nokogiri (1.18.1-x64-mingw-ucrt)
racc (~> 1.4)
nokogiri (1.18.1-x86_64-darwin)
racc (~> 1.4)
nokogiri (1.18.1-x86_64-linux-gnu)
racc (~> 1.4)
nokogiri (1.18.1-x86_64-linux-musl)
racc (~> 1.4)
paco (0.2.3)
parallel (1.26.3)
parser (3.3.7.1)
ast (~> 2.4.1)
Expand Down Expand Up @@ -190,8 +218,9 @@ GEM
zeitwerk (~> 2.6)
rainbow (3.1.1)
rake (13.2.1)
rbi (0.2.3)
rbi (0.3.1)
prism (~> 1.0)
rbs (>= 3.4.4)
sorbet-runtime (>= 0.5.9204)
rbs (3.8.1)
logger
Expand All @@ -200,6 +229,7 @@ GEM
regexp_parser (2.10.0)
reline (0.5.11)
io-console (~> 0.5)
require-hooks (0.2.2)
rubocop (1.73.1)
json (~> 2.3)
language_server-protocol (~> 3.17.0.2)
Expand All @@ -222,24 +252,28 @@ GEM
rubocop (~> 1.51)
rubocop-sorbet (0.8.9)
rubocop (>= 1)
ruby-lsp (0.23.6)
language_server-protocol (~> 3.17.0)
prism (>= 1.2, < 2.0)
rbs (>= 3, < 4)
sorbet-runtime (>= 0.5.10782)
ruby-next (1.1.1)
paco (~> 0.2)
require-hooks (~> 0.2)
ruby-next-core (= 1.1.1)
ruby-next-parser (>= 3.4.0.2)
unparser (~> 0.6.0)
ruby-next-core (1.1.1)
ruby-next-parser (3.4.0.2)
parser (>= 3.0.3.1)
ruby-progressbar (1.13.0)
ruby2_keywords (0.0.5)
securerandom (0.3.1)
sorbet (0.5.11865)
sorbet-static (= 0.5.11865)
sorbet-runtime (0.5.11865)
sorbet-static (0.5.11865-aarch64-linux)
sorbet-static (0.5.11865-universal-darwin)
sorbet-static (0.5.11865-x86_64-linux)
sorbet-static-and-runtime (0.5.11865)
sorbet (= 0.5.11865)
sorbet-runtime (= 0.5.11865)
spoom (1.5.4)
sorbet (0.5.11915)
sorbet-static (= 0.5.11915)
sorbet-runtime (0.5.11915)
sorbet-static (0.5.11915-aarch64-linux)
sorbet-static (0.5.11915-universal-darwin)
sorbet-static (0.5.11915-x86_64-linux)
sorbet-static-and-runtime (0.5.11915)
sorbet (= 0.5.11915)
sorbet-runtime (= 0.5.11915)
spoom (1.6.1)
erubi (>= 1.10.0)
prism (>= 0.28.0)
rbi (>= 0.2.3)
Expand All @@ -248,30 +282,20 @@ GEM
sqlite3 (2.5.0-aarch64-linux-gnu)
sqlite3 (2.5.0-aarch64-linux-musl)
sqlite3 (2.5.0-arm64-darwin)
sqlite3 (2.5.0-x64-mingw-ucrt)
sqlite3 (2.5.0-x86_64-darwin)
sqlite3 (2.5.0-x86_64-linux-gnu)
sqlite3 (2.5.0-x86_64-linux-musl)
stringio (3.1.2)
tapioca (0.16.8)
benchmark
bundler (>= 2.2.25)
netrc (>= 0.11.0)
parallel (>= 1.21.0)
rbi (~> 0.2)
sorbet-static-and-runtime (>= 0.5.11087)
spoom (>= 1.2.0)
thor (>= 1.2.0)
yard-sorbet
thor (1.3.2)
timeout (0.4.2)
tzinfo (2.0.6)
concurrent-ruby (~> 1.0)
tzinfo-data (1.2025.1)
tzinfo (>= 1.0.0)
unicode-display_width (3.1.4)
unicode-emoji (~> 4.0, >= 4.0.4)
unicode-emoji (4.0.4)
unparser (0.6.15)
diff-lcs (~> 1.3)
parser (>= 3.3.0)
uri (1.0.1)
useragent (0.16.10)
websocket-driver (0.7.6)
Expand All @@ -289,7 +313,6 @@ PLATFORMS
aarch64-linux-musl
arm64-darwin
universal-darwin
x64-mingw-ucrt
x86_64-darwin
x86_64-linux
x86_64-linux-gnu
Expand All @@ -305,10 +328,11 @@ DEPENDENCIES
rubocop-rake (~> 0.6.0)
rubocop-shopify (~> 2.15)
rubocop-sorbet (~> 0.8)
ruby-lsp!
ruby-lsp-rails!
sorbet-static-and-runtime
sqlite3
tapioca (~> 0.13)
tapioca!
tzinfo
tzinfo-data

Expand Down
7 changes: 7 additions & 0 deletions lib/ruby_lsp/ruby_lsp_rails/addon.rb
Original file line number Diff line number Diff line change
Expand Up @@ -13,6 +13,7 @@
require_relative "code_lens"
require_relative "document_symbol"
require_relative "definition"
require_relative "discover_tests"
require_relative "completion"
require_relative "indexing_enhancement"

Expand Down Expand Up @@ -121,6 +122,12 @@ def create_completion_listener(response_builder, node_context, dispatcher, uri)
Completion.new(@rails_runner_client, response_builder, node_context, dispatcher, uri)
end

# @override
#: (ResponseBuilders::TestCollection response_builder, Prism::Dispatcher dispatcher, URI::Generic uri) -> void
def create_discover_tests_listener(response_builder, dispatcher, uri)
DiscoverTests.new(response_builder, dispatcher, uri)
end

#: (Array[{uri: String, type: Integer}] changes) -> void
def workspace_did_change_watched_files(changes)
if changes.any? { |c| c[:uri].end_with?("db/schema.rb") || c[:uri].end_with?("structure.sql") }
Expand Down
78 changes: 78 additions & 0 deletions lib/ruby_lsp/ruby_lsp_rails/discover_tests.rb
Original file line number Diff line number Diff line change
@@ -0,0 +1,78 @@
# typed: strict
# frozen_string_literal: true

module RubyLsp
module Rails
class DiscoverTests
include Requests::Support::Common

# @override
#: (ResponseBuilders::TestCollection response_builder, Prism::Dispatcher dispatcher, URI::Generic uri) -> void
def initialize(response_builder, dispatcher, uri)
@response_builder = response_builder
@nesting = T.let([], T::Array[String])
@uri = uri
dispatcher.register(
self,
:on_class_node_enter,
:on_class_node_leave,
:on_module_node_enter,
:on_module_node_leave,
:on_call_node_enter, # e.g. `test "..."`
)
end

#: (Prism::ClassNode node) -> void
def on_class_node_enter(node)
name = constant_name(node.constant_path)
return unless name

@nesting << name
end

#: (Prism::ClassNode node) -> void
def on_class_node_leave(node)
@nesting.pop
end

#: (Prism::ModuleNode node) -> void
def on_module_node_enter(node)
name = constant_name(node.constant_path)
return unless name

@nesting << name
end

#: (Prism::ModuleNode node) -> void
def on_module_node_leave(node)
@nesting.pop
end

#: (Prism::CallNode node) -> void
def on_call_node_enter(node)
return unless node.name == :test
return unless node.block

args = node.arguments&.arguments
return unless args

arg = args[0]
return unless arg.is_a?(Prism::StringNode)

name = arg.unescaped # right way to access?

current_group_name = RubyIndexer::Index.actual_nesting(@nesting, nil).join("::")

test_item = Requests::Support::TestItem.new(
"#{current_group_name}##{name}",
name,
@uri,
range_from_node(node),
tags: [:active_support_declarative],
)

@response_builder.add(test_item)
end
end
end
end
Loading
Loading