diff --git a/.github/workflows/jruby.yml b/.github/workflows/jruby.yml index 651e33236..10dfe8b5f 100644 --- a/.github/workflows/jruby.yml +++ b/.github/workflows/jruby.yml @@ -10,9 +10,13 @@ on: - "include/**" - "src/**" - "wasm/**" - - "lib/rbs/wasm/**" - - "lib/rbs.rb" + - "lib/**" + - "sig/**" + - "core/**" + - "stdlib/**" + - "test/**" - "Rakefile" + - "rbs.gemspec" permissions: contents: read @@ -58,8 +62,6 @@ jobs: ruby-version: jruby bundler: none - name: Install runtime and test gems - run: gem install prism test-unit --no-document - - name: Run RBS's parser on JRuby - run: | - jruby -Ilib -Itest test/rbs/wasm/jruby_parser_test.rb - jruby -Ilib -Itest test/rbs/parser_test.rb + run: gem install prism rake rake-compiler test-unit rdoc rspec minitest json-schema pry --no-document + - name: Run the test suite on JRuby + run: jruby -S rake test diff --git a/Rakefile b/Rakefile index 9b46e77b3..c5b2aacac 100644 --- a/Rakefile +++ b/Rakefile @@ -33,7 +33,14 @@ test_config = lambda do |t| end end -Rake::TestTask.new(test: :compile, &test_config) +if RUBY_ENGINE == "jruby" + # JRuby runs the parser in WebAssembly instead of the C extension, so there is + # nothing to compile. The wasm runtime must be assembled first with + # `rake wasm:jruby_setup` (which needs CRuby + the WASI SDK). + Rake::TestTask.new(:test, &test_config) +else + Rake::TestTask.new(test: :compile, &test_config) +end multitask :default => [:test, :stdlib_test, :typecheck_test, :rubocop, :validate, :test_doc] diff --git a/lib/rbs.rb b/lib/rbs.rb index e59fd95e4..b9503d6b8 100644 --- a/lib/rbs.rb +++ b/lib/rbs.rb @@ -4,7 +4,11 @@ require "set" require "json" -require "pathname" unless defined?(Pathname) +# Always require pathname: `Pathname()` (Kernel#Pathname) is only defined once +# pathname is loaded. Guarding on `defined?(Pathname)` is wrong because another +# library (e.g. Bundler) can define the Pathname constant without that method, +# which left RBS::EnvironmentLoader's `Pathname(...)` undefined on JRuby. +require "pathname" require "pp" require "logger" require "tsort" diff --git a/lib/rbs/wasm/location.rb b/lib/rbs/wasm/location.rb index 6f89d6927..bafcd501a 100644 --- a/lib/rbs/wasm/location.rb +++ b/lib/rbs/wasm/location.rb @@ -55,7 +55,7 @@ def [](name) return range && Location.new(@buffer, range[0], range[1]) end - nil + raise "Unknown child name given: #{name}" end end end diff --git a/rbs.gemspec b/rbs.gemspec index dcc0935e2..870d99f03 100644 --- a/rbs.gemspec +++ b/rbs.gemspec @@ -36,11 +36,17 @@ Gem::Specification.new do |spec| end end - # JRuby cannot load the MRI C extension. The `java` platform gem ships the - # prebuilt WebAssembly parser and the Chicory jars instead (assembled by - # `rake wasm:jruby_setup`), and RBS loads the WebAssembly-backed parser. - if ENV["RBS_PLATFORM"] == "java" || (defined?(RUBY_ENGINE) && RUBY_ENGINE == "jruby") - spec.platform = "java" + # JRuby cannot load the MRI C extension. On JRuby (and in the `java` platform + # gem, built with RBS_PLATFORM=java) RBS runs the WebAssembly-backed parser, so + # ship the prebuilt parser and the Chicory jars (assembled by + # `rake wasm:jruby_setup`) and skip the C extension. + building_java_gem = ENV["RBS_PLATFORM"] == "java" + on_jruby = defined?(RUBY_ENGINE) && RUBY_ENGINE == "jruby" + + if building_java_gem || on_jruby + # Only stamp the platform when building the release gem; leave it unset for + # local development on JRuby so it still matches a `ruby` platform lockfile. + spec.platform = "java" if building_java_gem spec.files += Dir.chdir(File.expand_path('..', __FILE__)) do Dir.glob("lib/rbs/wasm/rbs_parser.wasm") + Dir.glob("lib/rbs/wasm/jars/*.jar") end diff --git a/test/rbs/ast/ruby/comment_block_test.rb b/test/rbs/ast/ruby/comment_block_test.rb index 92de581c6..66d4b51b7 100644 --- a/test/rbs/ast/ruby/comment_block_test.rb +++ b/test/rbs/ast/ruby/comment_block_test.rb @@ -61,6 +61,7 @@ def test__buffer__multi_line_prefix_header_line def test_build omit_on_truffle_ruby! "`Prism::Location#start_line_slice` returns `nil` on TruffleRuby's prism" + omit_on_jruby! "`Prism::Location#start_line_slice` returns `nil` on JRuby's prism" buffer, comments = parse_comments(<<~RUBY) # Comment1 @@ -191,6 +192,7 @@ def test_each_paragraph_colon def test_trailing_annotation omit_on_truffle_ruby! "`Prism::Location#start_line_slice` returns `nil` on TruffleRuby's prism" + omit_on_jruby! "`Prism::Location#start_line_slice` returns `nil` on JRuby's prism" buffer, comments = parse_comments(<<~RUBY) foo #: String @@ -223,6 +225,7 @@ def test_trailing_annotation def test_trailing_annotation_type_application omit_on_truffle_ruby! "`Prism::Location#start_line_slice` returns `nil` on TruffleRuby's prism" + omit_on_jruby! "`Prism::Location#start_line_slice` returns `nil` on JRuby's prism" buffer, comments = parse_comments(<<~RUBY) foo #[String] diff --git a/test/rbs/cli_test.rb b/test/rbs/cli_test.rb index a1245d396..3c70ffa20 100644 --- a/test/rbs/cli_test.rb +++ b/test/rbs/cli_test.rb @@ -892,6 +892,7 @@ def test_parse_method_type def test_prototype_no_parser omit_on_truffle_ruby! "`rbs prototype` requires `RubyVM::AbstractSyntaxTree`, which is not available on TruffleRuby" + omit_on_jruby! "`rbs prototype` requires `RubyVM::AbstractSyntaxTree`, which is not available on JRuby" Dir.mktmpdir do |dir| with_cli do |cli| @@ -910,6 +911,7 @@ def cli.has_parser? def test_prototype_batch omit_on_truffle_ruby! "`rbs prototype` requires `RubyVM::AbstractSyntaxTree`, which is not available on TruffleRuby" + omit_on_jruby! "`rbs prototype` requires `RubyVM::AbstractSyntaxTree`, which is not available on JRuby" Dir.mktmpdir do |dir| dir = Pathname(dir) @@ -973,6 +975,7 @@ module C def test_prototype_batch_outer omit_on_truffle_ruby! "`rbs prototype` requires `RubyVM::AbstractSyntaxTree`, which is not available on TruffleRuby" + omit_on_jruby! "`rbs prototype` requires `RubyVM::AbstractSyntaxTree`, which is not available on JRuby" Dir.mktmpdir do |dir| dir = Pathname(dir) @@ -1001,6 +1004,7 @@ module A def test_prototype_batch_syntax_error omit_on_truffle_ruby! "`rbs prototype` requires `RubyVM::AbstractSyntaxTree`, which is not available on TruffleRuby" + omit_on_jruby! "`rbs prototype` requires `RubyVM::AbstractSyntaxTree`, which is not available on JRuby" Dir.mktmpdir do |dir| dir = Pathname(dir) @@ -1051,6 +1055,7 @@ def test_prototype__runtime__todo def test_test omit_on_truffle_ruby! "`rbs test` relies on `TracePoint` `:end` event, which is not supported on TruffleRuby" + omit_on_jruby! "`rbs test` relies on `TracePoint` `:end` event, which is not supported on JRuby" Dir.mktmpdir do |dir| dir = Pathname(dir) @@ -1078,6 +1083,8 @@ def foo: () -> void end def test_collection_install + omit_on_jruby! "`rbs collection install` runs `bundle install`, which builds native gem extensions that do not compile on JRuby" + Dir.mktmpdir do |dir| Dir.chdir(dir) do dir = Pathname(dir) @@ -1144,6 +1151,8 @@ def test_collection_install_frozen end def test_collection_update + omit_on_jruby! "`rbs collection update` runs `bundle install`, which builds native gem extensions that do not compile on JRuby" + Dir.mktmpdir do |dir| Dir.chdir(dir) do dir = Pathname(dir) @@ -1167,6 +1176,8 @@ def test_collection_update end def test_collection_install_gemspec + omit_on_jruby! "`rbs collection install` runs `bundle install`, which builds native gem extensions that do not compile on JRuby" + Dir.mktmpdir do |dir| Dir.chdir(dir) do dir = Pathname(dir) diff --git a/test/rbs/node_usage_test.rb b/test/rbs/node_usage_test.rb index a071ecfab..7f20677af 100644 --- a/test/rbs/node_usage_test.rb +++ b/test/rbs/node_usage_test.rb @@ -9,6 +9,7 @@ def parse(string) def test_conditional omit_on_truffle_ruby! "`RubyVM::AbstractSyntaxTree` is not available on TruffleRuby" + omit_on_jruby! "`RubyVM::AbstractSyntaxTree` is not available on JRuby" NodeUsage.new(parse(<<~RB)) def block diff --git a/test/rbs/rb_prototype_test.rb b/test/rbs/rb_prototype_test.rb index 4e490692a..d628bec0d 100644 --- a/test/rbs/rb_prototype_test.rb +++ b/test/rbs/rb_prototype_test.rb @@ -2,6 +2,7 @@ class RBS::RbPrototypeTest < Test::Unit::TestCase omit_on_truffle_ruby! "`RubyVM::AbstractSyntaxTree` is not available on TruffleRuby" + omit_on_jruby! "`RubyVM::AbstractSyntaxTree` is not available on JRuby" RB = RBS::Prototype::RB diff --git a/test/rbs/rbi_prototype_test.rb b/test/rbs/rbi_prototype_test.rb index dda875958..c8bed6dec 100644 --- a/test/rbs/rbi_prototype_test.rb +++ b/test/rbs/rbi_prototype_test.rb @@ -2,6 +2,7 @@ class RBS::RbiPrototypeTest < Test::Unit::TestCase omit_on_truffle_ruby! "`RubyVM::AbstractSyntaxTree` is not available on TruffleRuby" + omit_on_jruby! "`RubyVM::AbstractSyntaxTree` is not available on JRuby" RBI = RBS::Prototype::RBI diff --git a/test/rbs/runtime_prototype_test.rb b/test/rbs/runtime_prototype_test.rb index 11cd2a127..24efac0cd 100644 --- a/test/rbs/runtime_prototype_test.rb +++ b/test/rbs/runtime_prototype_test.rb @@ -2,6 +2,7 @@ class RBS::RuntimePrototypeTest < Test::Unit::TestCase omit_on_truffle_ruby! "`RubyVM::AbstractSyntaxTree` is not available on TruffleRuby" + omit_on_jruby! "`RubyVM::AbstractSyntaxTree` is not available on JRuby" Runtime = RBS::Prototype::Runtime DefinitionBuilder = RBS::DefinitionBuilder diff --git a/test/rbs/test/runtime_test_test.rb b/test/rbs/test/runtime_test_test.rb index 9528e7444..ad8b969c3 100644 --- a/test/rbs/test/runtime_test_test.rb +++ b/test/rbs/test/runtime_test_test.rb @@ -6,6 +6,7 @@ class RBS::Test::RuntimeTestTest < Test::Unit::TestCase omit_on_truffle_ruby! "`rbs test` relies on `TracePoint` `:end` event, which is not supported on TruffleRuby" + omit_on_jruby! "`rbs test` relies on `TracePoint` `:end` event, which is not supported on JRuby" include TestHelper diff --git a/test/rbs/test/type_check_test.rb b/test/rbs/test/type_check_test.rb index fc3bd09b0..a8e2824ad 100644 --- a/test/rbs/test/type_check_test.rb +++ b/test/rbs/test/type_check_test.rb @@ -11,6 +11,7 @@ class RBS::Test::TypeCheckTest < Test::Unit::TestCase def test_type_check omit_on_truffle_ruby! "Type checking a block-less `loop` Enumerator behaves differently on TruffleRuby" + omit_on_jruby! "Type checking a block-less `loop` Enumerator behaves differently on JRuby" SignatureManager.new do |manager| manager.files[Pathname("foo.rbs")] = <