Release v0.50.295 — 3-PR batch (YAML/JSON/diff newlines + macOS scroll race + custom:* providers + glued-bold-lift raw pre)#1643
Merged
nesquena-hermes merged 9 commits intomasterfrom May 4, 2026
Conversation
Closes #1618 (reported by @Zixim) and corrects #1463's previous fix. Bug: YAML, JSON, and diff/patch fenced code blocks render flattened to a single line. Reporter noted the bug persisted v0.50.279 -> v0.50.291 -> v0.50.292 despite PR #1516's CSS-only "fix". Root cause: PR #484 (v0.50.237) added a JSON/YAML tree-viewer that routes those languages through <div class="code-tree-wrap">...<pre class="tree-raw-view"> instead of bare <pre>. Same release added the diff/patch coloring path that emits <pre class="diff-block">. The _pre_stash regex at static/ui.js:1914 matched only literal <pre> with no attributes: <pre>[\s\S]*?<\/pre> Both new shapes failed to match, fell through to the paragraph-wrap pass, and \n characters inside the code blocks got replaced with <br> tags inside <code>. By the time Prism ran, no newlines remained for the CSS rule (PR #1516, language-yaml .token { white-space: pre !important }) to preserve. Fix: relax the regex to accept any attribute on <pre>: <pre>[\s\S]*?<\/pre> -> <pre[^>]*>[\s\S]*?<\/pre> One regex character. Pulls JSON, YAML, and diff/patch blocks into the stash so paragraph-wrap can't mangle them. Bash, Python, Go, etc. were never affected because they emit bare <pre>. Tests: 9 new (2 source-string invariants + 7 behavioural via node-driver against the actual static/ui.js renderMd()). 6 of the 7 behavioural tests fail on master and pass with the fix; the 3 sanity checks (yml-alias, bash, mermaid) pass on both. Plus widened source-scan window in 3 pre-existing test_745 assertions from 400 to 1500 chars. The new comment block above the fixed regex pushed it past the previous scan window. Pure window-narrowness bug, not a behavior regression. 4245 -> 4254 passing.
…l list (#1619) #1360 — On macOS WKWebView, trackpad momentum scrolling fires scroll events that interleave with the _programmaticScroll setTimeout(0) guard. A mid-momentum scroll event either gets swallowed (_programmaticScroll still true) or falsely reports nearBottom (momentum hasn't settled), keeping _scrollPinned=true and snapping the viewport back down. Fix: rAF-debounce the scroll listener so the nearBottom check runs at the next paint frame when the browser's scroll position has settled. Added a hysteresis counter requiring 2 consecutive near-bottom samples before re-pinning, preventing accidental re-pin during deceleration. #1619 — When a custom:* provider (e.g. custom:relay via custom_providers) has models that overlap with auto-detected models from base_url /v1/models, the dedup logic at config.py:2263 skipped them all. The named custom group ended up empty, and the continue at line 2334 silently discarded the auto-detected models. Result: only the default model appeared. Fix 1 (config.py): When custom:* named group has 0 models after dedup, fall back to auto_detected_models_by_provider instead of dropping them. Fix 2 (routes.py): Extended /api/models/live fallback to handle custom:* slugs (not just bare "custom") for both custom_providers config lookup and base_url live fetch.
test_scroll_listener_hides_button_when_pinned checked 300 chars after
el.addEventListener('scroll', but the rAF-debounce fix moved the
scrollToBottomBtn logic into the requestAnimationFrame callback,
beyond the 300-char window. Extended to 600 to cover the full block.
#1641) Adopt the UI media from @Michaelyklam's parallel-discovery PR #1641 which shipped the same one-character regex relax fix for #1618. PR #1641 is being closed as superseded by #1642 (which carries nesquena APPROVED + 322 LOC test suite); preserving Michael's UI evidence here so the visual proof of the fix lives in-tree alongside the canonical PR. Co-authored-by: Michael Lam <[email protected]>
#1463) by @nesquena-hermes — APPROVED, with media from @Michaelyklam
Constituent PRs: #1637 by @Michaelyklam — protect raw pre from glued-bold lift (closes #1451) #1639 by @bergeouss — macOS auto-scroll race + custom:* provider list (closes #1360, #1619) #1642 by @nesquena-hermes — YAML/JSON/diff code block newlines (closes #1618, #1463) Opus advisor SHIP verdict on stage-295. One observation absorbed: - api/config.py:2533 dead-code comment per Opus (defensive belt-and-braces for #1619 fallback; load-bearing fix is in routes.py /api/models/live) PR #1641 (Michaelyklam parallel-discovery duplicate of #1642) closed as superseded; UI media adopted with co-author trailer. 4245 → 4255 tests passing (+10).
This was referenced May 4, 2026
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
Add this suggestion to a batch that can be applied as a single commit.This suggestion is invalid because no changes were made to the code.Suggestions cannot be applied while the pull request is closed.Suggestions cannot be applied while viewing a subset of changes.Only one suggestion per line can be applied in a batch.Add this suggestion to a batch that can be applied as a single commit.Applying suggestions on deleted lines is not supported.You must change the existing code in this line in order to create a valid suggestion.Outdated suggestions cannot be applied.This suggestion has been applied or marked resolved.Suggestions cannot be applied from pending reviews.Suggestions cannot be applied on multi-line comments.Suggestions cannot be applied while the pull request is queued to merge.Suggestion cannot be applied right now. Please check back later.
Release v0.50.295 — 3-PR batch (YAML/JSON/diff newlines + macOS scroll race + custom:* providers + glued-bold-lift raw pre)
3 PRs from 3 contributors. Closes 5 issues: #1360, #1451, #1463, #1618, #1619.
What ships
#1642 by @nesquena-hermes — YAML/JSON/diff code block newlines (closes #1618, #1463)
Reporter @Zixim flagged that YAML rendering had been flattened to a single line since v0.50.237 despite PR #1516's CSS-only "fix" in v0.50.279. Live-rendered both
```yaml ... ```and a control```yml ... ```block throughrenderMd()in the browser to verify — @Zixim was right, the bug was real on master. Root cause: PR #484 introduced<pre class="tree-raw-view">for JSON/YAML and<pre class="diff-block">for diff/patch, but the_pre_stashregex matched only literal<pre>(no attributes). One-character regex relax:<pre>→<pre[^>]*>.Parallel-discovery: @Michaelyklam independently filed PR #1641 with the same fix 4 minutes earlier; closed as superseded by #1642 (which carries APPROVED + 322 LOC test suite covering YAML+JSON+diff vs YAML-only). UI before/after PNGs from #1641 adopted with
Co-authored-bytrailer.#1639 by @bergeouss — macOS WKWebView auto-scroll race (closes #1360)
Trackpad scrolling up during streaming snapped viewport back to bottom.
_programmaticScrollsetTimeout(0) guard was racing with WKWebView momentum scrolling. rAF-debounce the scroll listener + 2-sample hysteresis counter requires two consecutive near-bottom samples before re-pinning.#1639 by @bergeouss — custom:* provider model list (closes #1619)
Custom:* providers were only showing the default model in the dropdown.
/api/models/liveonly handled barecustom, notcustom:*slugs. Plus defensive belt-and-braces inapi/config.pyfor dedup fallback.#1637 by @Michaelyklam — protect raw
<pre>from glued-bold lift (closes #1451)renderMd()was restoring raw<pre>blocks BEFORE the glued-bold-heading lift ran, so literal preformatted text containingPara text.**Heading**\n\nNextgot mangled by the lift. MoverawPreStashrestore to AFTER markdown rewrites, BEFORE HTML sanitization.Tests
4245 → 4255 passing (+10). 0 regressions. Full suite ~120s.
Pre-release verification
static/ui.jsoverlap between fix: protect raw pre from glued-bold lift #1637 (rawPreStash R-token), fix: macOS auto-scroll momentum race (#1360) + custom:* provider model list (#1619) #1639 (scroll listener), and fix(renderer): YAML/JSON/diff code blocks lose newlines (#1618 / #1463) #1642 (_pre_stash E-token) verified non-overlapping with separate token namespaces and correct ordering. fix: protect raw pre from glued-bold lift #1637's relocated restore (line 1668 → 1799) traced through every intermediate rewrite pass — placeholder has no syntactic chars matching any rewrite. fix(renderer): YAML/JSON/diff code blocks lose newlines (#1618 / #1463) #1642 nested-<pre>non-greedy verified identical to existingrawPreStashregex (no regression). One non-blockingapi/config.pydefensive-dead-code observation absorbed via comment.static/ui.jsclean.Authors