Skip to content

fix(core): guard MarkdownRenderable.getStyle against undefined syntaxStyle#606

Merged
kommander merged 1 commit intoanomalyco:mainfrom
cevr:fix/markdown-getStyle-guard
Feb 2, 2026
Merged

fix(core): guard MarkdownRenderable.getStyle against undefined syntaxStyle#606
kommander merged 1 commit intoanomalyco:mainfrom
cevr:fix/markdown-getStyle-guard

Conversation

@cevr
Copy link
Contributor

@cevr cevr commented Feb 1, 2026

Summary

  • Guards MarkdownRenderable.getStyle() against _syntaxStyle being undefined when the Solid reconciler sets content before syntaxStyle

Problem

The @opentui/solid reconciler creates elements with new Element(ctx, { id }) — only { id } is passed in constructor options. Props are then applied via setters in JSX declaration order.

When a consumer writes:

<markdown content={props.content} syntaxStyle={props.syntaxStyle()} ... />

The content setter fires first, triggering updateBlocks()createChunk()getStyle(), which accesses this._syntaxStyle — still undefined because the syntaxStyle setter hasn't run yet.

This crashes with:

TypeError: undefined is not an object (evaluating 'this._syntaxStyle.getStyle')

Note

There's an existing branch fix(solid)-prop-initialization-before-insert that attempts to fix this at the Solid/babel level. This PR takes a complementary approach — defensive guard in MarkdownRenderable itself, so the component is resilient regardless of prop order.

Fix

  • Early-return undefined from getStyle() when _syntaxStyle is uninitialized
  • Blocks render unstyled initially; once syntaxStyle setter runs, _styleDirty triggers rerenderBlocks() on the next render cycle with correct styles

Test plan

  • Verified fix resolves the crash in gent TUI (streaming markdown with <markdown content={...} syntaxStyle={...} />)
  • TypeScript compiles clean (no new errors in Markdown.ts)
  • Visual: markdown renders with correct syntax highlighting after initial unstyled frame

🤖 Generated with Claude Code

@cevr cevr force-pushed the fix/markdown-getStyle-guard branch from 17728ea to d0d7534 Compare February 1, 2026 01:17
…Style

The Solid reconciler creates elements with `new Element(ctx, { id })` —
only `id` is passed in constructor options. Props are applied via setters
in JSX declaration order. When `content` is set before `syntaxStyle`,
the content setter triggers `updateBlocks()` → `createChunk()` →
`getStyle()` which accesses `this._syntaxStyle` — still undefined.

This crashes with: `TypeError: undefined is not an object
(evaluating 'this._syntaxStyle.getStyle')`

The guard returns undefined when `_syntaxStyle` hasn't been initialized
yet, producing unstyled text. Once `syntaxStyle` is set via its setter,
`_styleDirty` triggers `rerenderBlocks()` on the next render cycle,
applying correct styles.

Co-Authored-By: Claude Opus 4.5 <noreply@anthropic.com>
@cevr cevr force-pushed the fix/markdown-getStyle-guard branch from d0d7534 to 3aea717 Compare February 1, 2026 01:18
@pkg-pr-new
Copy link

pkg-pr-new bot commented Feb 1, 2026

@opentui/core

npm i https://pkg.pr.new/anomalyco/opentui/@opentui/core@606

@opentui/react

npm i https://pkg.pr.new/anomalyco/opentui/@opentui/react@606

@opentui/solid

npm i https://pkg.pr.new/anomalyco/opentui/@opentui/solid@606

@opentui/core-darwin-arm64

npm i https://pkg.pr.new/anomalyco/opentui/@opentui/core-darwin-arm64@606

@opentui/core-darwin-x64

npm i https://pkg.pr.new/anomalyco/opentui/@opentui/core-darwin-x64@606

@opentui/core-linux-arm64

npm i https://pkg.pr.new/anomalyco/opentui/@opentui/core-linux-arm64@606

@opentui/core-linux-x64

npm i https://pkg.pr.new/anomalyco/opentui/@opentui/core-linux-x64@606

@opentui/core-win32-arm64

npm i https://pkg.pr.new/anomalyco/opentui/@opentui/core-win32-arm64@606

@opentui/core-win32-x64

npm i https://pkg.pr.new/anomalyco/opentui/@opentui/core-win32-x64@606

commit: 3aea717

@kommander kommander merged commit 72cd249 into anomalyco:main Feb 2, 2026
6 checks passed
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.

2 participants