Add tests that column information can be translated

This commit is contained in:
Aaron Patterson 2022-10-09 14:51:26 -07:00
parent 1d39573a9f
commit cd48642561
No known key found for this signature in database
GPG Key ID: 953170BCB4FFAFC6
4 changed files with 33 additions and 1 deletions

@ -157,6 +157,8 @@ class Error < ActionViewError # :nodoc:
# Override to prevent #cause resetting during re-raise.
attr_reader :cause
attr_reader :template
def initialize(template)
super($!.message)
@cause = $!

@ -1,6 +1,7 @@
# frozen_string_literal: true
require "strscan"
require "active_support/core_ext/string"
module ActionView
class Template
@ -39,7 +40,7 @@ def handles_encoding?
# source location inside the template.
def translate_location(spot, backtrace_location, source)
# Tokenize the source line
tokens = ERB::Util.tokenize(source.lines[backtrace_location.lineno - 1])
tokens = ::ERB::Util.tokenize(source.lines[backtrace_location.lineno - 1])
new_first_column = find_offset(spot[:snippet], tokens, spot[:first_column])
lineno_delta = spot[:first_lineno] - backtrace_location.lineno
spot[:first_lineno] -= lineno_delta

@ -0,0 +1,6 @@
<h1>Oh no!</h1>
This template has a runtime error
<b>
<%= method_that_does_not_exist %>
</b>
Yikes!

@ -210,6 +210,29 @@ def test_render_outside_path
end
end
def test_render_runtime_error
skip unless RubyVM.respond_to?(:keep_script_lines)
# We need to enable this setting so that when we eval the template
# the compiled source is kept around.
setting = RubyVM.keep_script_lines
RubyVM.keep_script_lines = true
ex = assert_raises(ActionView::Template::Error) {
@view.render(template: "test/runtime_error")
}
erb_btl = ex.backtrace_locations.first
# Get the spot information from ErrorHighlight
spot = erb_btl.spot(ex.cause)
translated_spot = ex.template.translate_location(erb_btl, spot)
assert_equal 6, translated_spot[:first_column]
ensure
if RubyVM.respond_to?(:keep_script_lines)
RubyVM.keep_script_lines = setting
end
end
def test_render_partial
assert_equal "only partial", @view.render(partial: "test/partial_only")
end