Skip to content

Engine: Honor # herb:debug disable on an output tag - #2860

Open
jonasporto wants to merge 1 commit into
marcoroth:mainfrom
jonasporto:engine-debug-disable-output-tag
Open

jonasporto wants to merge 1 commit into
marcoroth:mainfrom
jonasporto:engine-debug-disable-output-tag

Conversation

@jonasporto

Copy link
Copy Markdown

Touches marcoroth/reactionview#103.

# herb:debug disable is only read on a block's opening tag (include_debug_disable_comment? runs against @erb_block_stack in in_excluded_context?), so a single output tag has no way to opt out of the debug span. Where that span lands in a place the HTML parser does not allow a <span>, the element it wraps is dropped or moved:

  • A partial whose root element comes out of a helper, sent in a Turbo Stream. <%= tag.td "Ada", id: "cell_1" %> arrives as <template><span style="display: contents;"><td id="cell_1">Ada</td></span></template>; inside <template> the parser switches to "in body" at the <span> and ignores the <td> start tag, so only the text is left and the next stream that targets cell_1 finds nothing. <tr> and the other table-structure tags behave the same (reproduction in the issue).
  • A layout whose <head> content comes from a partial. The partial's own AST has no <head> ancestor, so <%= stylesheet_link_tag … %> is wrapped and the browser closes <head> at the <span> (the issue's report).

With this change the comment is honoured on an output tag too, with the same whitespace rules as on a block:

<%= tag.td "Ada", id: "cell_1" # herb:debug disable %>

compiles to _buf << (tag.td "Ada", id: "cell_1").to_s; with no span, and the other output tags in the same template keep theirs. The engine already drops a trailing comment from the compiled Ruby, so nothing changes at runtime.

This is an opt-out, not a detection: at compile time the visitor cannot know that a partial will be sent inside a <template> or rendered into <head>, and the span is only wrong there. If you would rather skip the span automatically for the helpers whose output is a table-structure element (tag.td, tag.tr, content_tag(:td, …), the list in the HTML table model), that fits beside complex_rails_helper? and I can add it. The head case has no finite helper list (the report's template uses vite_stylesheet_tag), so the comment seems the right tool there.

Tests: three in test/engine/debug_mode_test.rb with snapshots, placed after the last top-level test so the existing snapshot numbers do not move. Against main they fail with the span around the helper's output. Checked against v0.11.1 and main at 5d75561 (debug_visitor.rb is identical in both). bin/integration locally (macOS, Ruby 4.0.7): 5256 Ruby tests (0 failures, 0 errors, 59 skips), 135 C checks, 0 leaks, bin/lint, bin/tidy, RuboCop with no offenses.

@github-actions github-actions Bot added ruby Ruby source for the gem and its libraries engine Herb engine and Rails template compilation rubygem The herb RubyGem and its packaging labels Oct 29, 2026

This branch has not been deployed

No deployments
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

engine Herb engine and Rails template compilation ruby Ruby source for the gem and its libraries rubygem The herb RubyGem and its packaging

Projects

None yet

Development

Successfully merging this pull request may close these issues.

1 participant