The expected message bakes the receiver's `#inspect` into a heredoc before the
block raises, so a moving GC that relocates the receiver in between makes the
two addresses disagree. That is why these tests fail intermittently under MMTk.
`GC.compact` reproduces the same failure with the default GC.
Co-Authored-By: Claude Opus 5 <noreply@anthropic.com>
ErrorHighlight.spot defaults point_type to :args for ArgumentError. When an
ArgumentError originates from argument binding (e.g. a missing required
keyword), its first backtrace location maps to a def/lambda/block node. The
spotter had no implementation for the :args point type on those nodes and did
`raise NotImplementedError`.
This is a regression from 0.7.0 (and in Ruby 4.0 compared to Ruby 3.4).
ErrorHighlight.spot only rescues SyntaxError/SystemCallError/ArgumentError, and
NotImplementedError is not a StandardError, so it escaped through
CoreExt#generate_snippet -> Exception#detailed_message / #full_message and
replaced the original exception. This is normally hidden because the VM's
"missing keyword" message matches the keyword regex in generate_snippet and
takes the safe :name branch, but it surfaces as soon as the ArgumentError is
re-raised/wrapped with a custom message that falls into the :args else branch.
Return nil (the documented "no spot" result) for these cases instead, matching
the graceful-degradation behavior of the surrounding feature. The fix is
applied consistently across both compilers:
- prism: def_node / lambda_node / block_node
- parse.y: DEFN / DEFS (raised NotImplementedError) and LAMBDA / ITER
(silently returned a spot for :args, inconsistent with prism)
All of these branches were introduced together by the experimental "wrong
number of arguments" snippet feature and are only intended for point_type
:name, so returning nil for any other point_type keeps the two parsers in sync.
https://github.com/ruby/error_highlight/commit/ca126db2db
Previously calling a singleton method with invalid arguments would give:
RuntimeError: Incompatible locations
This is because `join` wants the operator to come before the location
https://github.com/ruby/error_highlight/commit/44920551dd
This is an experimental implementation for
https://bugs.ruby-lang.org/issues/21543.
```
test.rb:2:in 'Object#foo': wrong number of arguments (given 1, expected 2) (ArgumentError)
caller: test.rb:6
| foo(1)
^^^
callee: test.rb:2
| def foo(x, y)
^^^
from test.rb:6:in 'Object#bar'
from test.rb:10:in 'Object#baz'
from test.rb:13:in '<main>'
```
https://github.com/ruby/error_highlight/commit/21e974e1c4
Previously, RubyVM::AST.of opened a wrong file if the iseq's file path is spoofed.
```
module Dummy
binding.irb
end
```
```
$ ruby test.rb
From: test.rb @ line 2 :
1: module Dummy
=> 2: binding.irb
3: end
irb(Dummy):001:0> foo
/home/mame/work/ruby/local/lib/ruby/3.1.0/error_highlight/base.rb:412:in `spot_colon2': undefined method `last_lineno' for nil:NilClass (NoMethodError)
if nd_parent.last_lineno == @node.last_lineno
^^^^^^^^^^^^
```
Found by @kateinoigakukun
This issue is already fixed in the interpreter side.
This change just adds a test for the case.
https://github.com/ruby/error_highlight/commit/f3626b9032
Now the formatter configuration is per Ractor. DefaultFormatter is used
if not set.
DefaultFormatter#message_for is now a class method to allow sub-Ractors
to call the method.
https://github.com/ruby/error_highlight/commit/9fbaa8ab7c
Now, the highlight line is created by replacing non-tab characters with
spaces, and keeping all hard tabs as-is. This means the highlight line
has the completely same indentation as the code snippet line.
Fixes#7https://github.com/ruby/error_highlight/commit/38f20fa542