Skip to content

fix(options): dedent OPTION-group trailing content to col 0 (#2820) - #2858

Merged
jung-thomas merged 3 commits into
DEVfrom
worktree-fix-2820-option-rendering
Oct 20, 2026
Merged

jung-thomas merged 3 commits into
DEVfrom
worktree-fix-2820-option-rendering

Conversation

@jung-thomas

Copy link
Copy Markdown
Contributor

Fixes #2820 — raw markdown leaking into a code block when an [OPTION] group is followed by shared substep content (prose, image, > [!TIP] alerts). Live symptom: hana-clients-install step 3 showed a "SHELL" box full of literal markdown.

Root cause

A Hugo shortcode that emits a block-level <div> (os-options/os-panel) closes the surrounding tight numbered list regardless of source indentation — verified against production-pinned Hugo 0.147.7. Once the list closes, Goldmark measures the still-4-space-indented trailing content from column 0, where the ≥4-space rule turns it into a literal indented-code block.

Commit 19db8d027 (the third #2820 fix attempt) regressed this by deleting the "Bug B" tail-dedent, on the false premise that indenting the shortcode wrappers keeps the list open. The Hugo renders disprove that — the list always closes, so the dedent is mandatory. The three prior PRs (#2822, #2826, #2842) each chased the impossible goal of nesting the OPTION block inside the <li>; this PR accepts the honest structure (OPTION block is a sibling of the list) and fixes the actual leak.

Fix (two parts)

  1. Parser (scripts/parsers/options.ts): restore the tail-dedent — trailing substep content after an OPTION group is dedented to column 0 so it renders as sibling markdown. The author's own N. ordinal reopens the list as <ol start="N">, so numbering continues.
  2. CSS (sap-fundamental.src.css): split the trailing-figure rule so vertical rhythm is set with margin-top/bottom instead of the margin shorthand, which was resetting margin-left: 1.5rem to 0 and jamming the trailing image to the far-left column (a latent bug the parser fix exposes).

Verification

Before/after through the real production path (composeTutorial → renderHugoFrontmatter {{% tutorial-step %}} → Hugo):

tutorial BEFORE AFTER
hana-clients-install LEAK CLEAN
hana-clients-hdbsql LEAK CLEAN
hana-clients-jdbc LEAK CLEAN
hana-clients-golang LEAK CLEAN
  • New render-level regression test test/unit/option-tail-leak.test.ts reproduces the leak via the percent-shortcode path (the only path that reproduces it — rendering at page top level does not) and asserts the corrected contract.
  • Updated options-hugo.test.ts and option-figure-list-nesting.test.ts, which encoded the old (impossible "nest in <li>") behavior.
  • 290 parser/options/render tests pass.

Design doc: docs/superpowers/specs/2026-10-20-option-block-rendering-design.md.

release: v1.40.2 (DEV→main promotion)
Trailing substep content after an [OPTION] group (prose, images,
`> [!TIP]` alerts) was leaking as raw markdown inside a code block on
rendered tutorials (e.g. hana-clients-install step 3).

Root cause: a Hugo shortcode that emits a block-level <div>
(os-options/os-panel) closes the surrounding tight numbered list
regardless of source indentation (verified against production-pinned
Hugo 0.147.7). Once the list closes, Goldmark measures the still-4-space
-indented tail from column 0, where the >=4-space rule turns it into a
literal indented-code block. Commit 19db8d0 deleted the "Bug B"
tail-dedent on the false premise that indented wrappers keep the list
open — the Hugo renders disprove that; the list always closes, so the
dedent is mandatory.

Fix (two parts):
- Parser: restore the tail-dedent in convertOptionBlocks — trailing
  substep content is dedented to column 0 so it renders as sibling
  markdown; the author's `N.` ordinal reopens the list as <ol start="N">
  and numbering continues.
- CSS: split the trailing-figure rule so `margin-top/bottom` sets the
  rhythm without the `margin` shorthand clobbering `margin-left: 1.5rem`
  — a latent bug the parser fix exposes (the trailing image otherwise
  jams to the far-left column).

Verified before/after on the real production path (composeTutorial ->
renderHugoFrontmatter {{% tutorial-step %}} -> Hugo) across
hana-clients-install/-hdbsql/-jdbc/-golang: all leaked BEFORE, all CLEAN
AFTER. New render-level regression test test/unit/option-tail-leak.test.ts
reproduces the leak via the percent-shortcode path (the only path that
reproduces it) and asserts the corrected contract. Updated two tests
that encoded the old (impossible "nest in <li>") behavior.

Design: docs/superpowers/specs/2026-10-20-option-block-rendering-design.md
@jung-thomas
jung-thomas merged commit e0d941f into DEV Oct 20, 2026
5 checks passed
@jung-thomas
jung-thomas deleted the worktree-fix-2820-option-rendering branch October 20, 2026 15:44
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

1 participant