prism
prism copied to clipboard
Inconsistent line numbers for Method.source_location
In Ruby 3.4, the following code returns different results depending on which parser is used:
# test.rb
class Foo
define_method "foo" \
"bar" do
end
end
p Foo.instance_method(:foobar).source_location
With ruby --parser=parse.y test.rb I get ["test.rb", 2]
With ruby --parser=prism test.rb I get ["test.rb", 3]
I'm using ruby 3.4.0preview2 (2024-10-07 master 32c733f57b) +PRISM [arm64-darwin23]
Same behaviour on Ruby 3.4.1 as well:
❯ ruby -v --parser=prism test.rb
ruby 3.4.1 (2024-12-25 revision 48d4efcb85) +PRISM [arm64-darwin23]
["test.rb", 3]
❯ ruby -v --parser=parse.y test.rb
ruby 3.4.1 (2024-12-25 revision 48d4efcb85) [arm64-darwin23]
["test.rb", 2]
I think parse.y is wrong here, the block clearly starts on line 3. I will bring this up for discussion.
I discovered this in the context of fixing a bug in a test plugin which allows you to run tests by line number.
e.g. in code like this:
1 class FooTest < TestCase
2 test "really long" \
3 "test name" do
4 assert ...
5 end
6 end
I think it's reasonable for a developer to want to be able to run the test which starts on line 2.
Rails uses method.source_location and node.start_line to determine which line numbers correspond to test methods: https://github.com/kddnewton/rails/blob/main/railties/lib/rails/test_unit/test_parser.rb#L19