FIG-001 · MASTHEAD
// compare / svelte-markdown vs vs-svelte-streamdown

vssvelte streamdown.

Two Svelte 5 Renderers Built for AI Streaming

FIG-001
SHEET 01 / 07
FIG-002 / OVERVIEW

at a glance.

Compare svelte-streamdown and @humanspeak/svelte-markdown: two Svelte 5 markdown renderers for streaming AI output, with different approaches to styling, caching, HTML, MDX, and rich content.

FIG-003 / FEATURE MATRIX

side-by-side.

Every surface that matters, compared without spin.

feature@humanspeak/svelte-markdownSvelte Streamdown
Svelte 5 Compatibility yesyes
TypeScript Support yesyes
Streaming API Svelte Markdown can consume transport deltas directly. With Svelte Streamdown, the application maintains and repeatedly supplies the accumulated content string.Reactive source or direct writeChunk() ingestionReactive complete-content prop
Out-of-Order Chunk Delivery Svelte Markdown accepts writeChunk({ value, offset }) and assembles websocket-style chunks even when they arrive out of order. Svelte Streamdown accepts a complete content string, so callers must order and assemble chunks before updating the prop.Native offset-addressed chunk assemblyno
Mid-Stream Corrections Offset-addressed writes support retransmission, transcription correction, and edits to previously received output without requiring callers to reconstruct the complete document first.Offset writes can replace earlier rangesCaller rebuilds the content string
Stream Lifecycle Isolation Svelte Markdown provides synchronous resetStream() and declarative streamId boundaries to prevent content from one response carrying into the next.resetStream() + streamIdCaller-managed content state
Incomplete Markdown Both projects are designed to keep partial AI output renderable while new content arrives.yesyes
Streaming HTML Output Svelte Markdown explicitly tracks incomplete raw HTML tails; Svelte Streamdown documents graceful handling for incomplete markdown and MDX blocks.Partial blocks reconcile when </tag> arrivesIncomplete blocks handled
Repeated Document Cache Svelte Streamdown caches block splitting and uses Svelte reactivity to reuse unchanged mounted blocks, but does not provide a reusable LRU for completed documents that are revisited or remounted.Built-in configurable LRU + TTLno
Append-Only Stream Reuse Both avoid needlessly parsing stable content. Svelte Markdown additionally coalesces bursts of incoming updates at the animation-frame boundary.Tail-window parser + frame coalescingCached block splitting + reactive block reuse
Measured Streaming Performance Measured against svelte-streamdown 4.2.0 on 2026-09-22 in production Chromium 151: append-only cumulative-prop updates with animation, controls and highlighting off; two suites, each with one warmup and five measured iterations per renderer/scenario. Streamdown / Svelte Markdown median completion-time ratios: 4.47–5.03 for 10 KB tiny chunks (10,059 bytes, 16-character chunks); 4.79–5.65 for 50 KB small chunks (50,153 bytes, 64-character chunks); 7.13–9.09 for 200 KB medium chunks (200,237 bytes, 256-character chunks). KB sizes are minimum targets. With one 512-character update per frame over 50,153 bytes, both sustained about 60 updates/s (ours 60.274–60.315; Streamdown 60.438–60.629), with Streamdown slightly lower elapsed medians. These observations apply to these workloads, not pure parsing or imperative chunk ingestion. Reproduce with pnpm perf:stream-compare.Lower measured burst medians; ~60 frame-paced updates/sHigher measured burst medians; ~60 frame-paced updates/s
Measured DOM Footprint (50 KB) Freshly measured against svelte-streamdown 4.2.0 on 2026-09-22 in production Chromium 151 using the actual 50,153-byte corpus (50 KB minimum target), append-only cumulative-prop updates, and animation, controls and highlighting off. Two suites, each with one warmup and five measured iterations per renderer/scenario: counts were stable across all 20 measured runs per renderer combining 64-character burst chunks and 512-character frame-paced chunks. Svelte Markdown used about 19% fewer descendant elements (2,821 versus 3,480); these counts measure elements, not all DOM nodes or memory. Matching semantic content was verified; table/list whitespace and code wrappers differ.2,821 descendant elements3,480 descendant elements
Custom Renderers 24 markdown + 83 HTML snippet overridesTyped snippets + theme system
HTML Tag Control 83 tags with allow/deny helpersskipHtml + allowed element controls
URL Safety Defaults The default ["*"] permits HTTP/HTTPS URLs across origins and mailto:/tel: links; it blocks javascript:, data:, and vbscript:. Prefix lists can restrict destinations further.Protocol allowlist + attribute sanitizationConfigurable prefixes + default protocol allowlist
Streaming Animations noWord, character, or block animations
MDX-Style Components noyes
Inline Citations noPopover + list/carousel views
Built-in Styling Unstyled by defaultTailwind typography + themes
Math (KaTeX) Opt-in first-class extensionOpt-in component
Diagrams (Mermaid) Opt-in first-class extensionOpt-in interactive component
Code Highlighting Opt-in Shiki extensionOpt-in @tanstack/highlight component + copy button
Marked Extensions Full extension objectsCustom tokenizers
Advanced Tables GFM tablesGFM + row/column spans, footers, multiple headers
FIG-004 / STRENGTHS

where each shines.

▣ svelte markdown 20
  • +Svelte 5 runes-native — built for runes, not retrofitted
  • +TypeScript-first with full type safety
  • +Built-in token caching (50-200x faster re-renders on repeated content)
  • +LLM streaming with imperative writeChunk() / resetStream() API
  • +24 markdown renderers + 83 HTML tag renderers — every override is a Svelte snippet
  • +First-class extensions: KaTeX math, Mermaid diagrams, GitHub alerts, footnotes
  • +Opt-in Shiki syntax highlighting (streaming-compatible, tree-shaken from core)
  • +Built-in XSS protection — protocol allowlist, event-handler stripping, attribute sanitization
  • +Allow/deny utilities (allowHtmlOnly, excludeRenderersOnly, etc.) for fine-grained control
  • +Drop-in component — works anywhere in your Svelte app
  • +Direct transport-delta ingestion without maintaining a second reactive accumulator
  • +Native out-of-order chunk assembly with offset-addressed writes
  • +Mid-stream replacement writes for corrections and retransmission
  • +Explicit resetStream() and streamId lifecycle boundaries
  • +Lower median completion times than svelte-streamdown 4.2.0 in each measured burst workload (10/50/200 KB minimum targets; 2026-09-22)
  • +About 19% fewer descendant elements than svelte-streamdown 4.2.0 on the freshly measured 50,153-byte corpus (2026-09-22; animation, controls and highlighting off)
  • +Configurable LRU cache also accelerates repeated non-streaming documents
  • +Broad raw HTML support with per-tag renderers and allow/deny helpers
  • +Default URL and attribute sanitizers with customizable hooks
  • +Unstyled core integrates without requiring Tailwind
▢ svelte streamdown 5
  • +Purpose-built streaming animations at word, character, and block level
  • +MDX-style custom Svelte components inside runtime markdown
  • +Interactive citations with popover, list, and carousel presentations
  • +Opinionated typography and granular Tailwind theme system out of the box
  • +Rich built-ins including interactive Mermaid controls, code copy buttons, and advanced tables
FIG-005 / LIMITATIONS

where each falls short.

▣ svelte markdown 5
  • −Smaller community (newer project)
  • −Runtime-only (no build-time optimization)
  • −No built-in token reveal animations or citation UI
  • −No MDX-style component syntax inside markdown
  • −Requires application styling by design
▢ svelte streamdown 6
  • −No imperative chunk-ingestion API — callers update the complete content string
  • −No native offset-addressed assembly for out-of-order chunks or earlier-range corrections
  • −Stream resets and response isolation are managed in caller-owned content state
  • −No reusable LRU cache for switching among previously rendered documents
  • −Opinionated styling requires Tailwind setup or theme overrides
  • −A newer, single-maintainer port that tracks the upstream React project
FIG-006 / VERDICT

the honest call.

Choose Svelte Streamdown when you want a batteries-included AI response UI with animated reveals, citations, MDX-style components, interactive diagrams, and Tailwind styling. Choose @humanspeak/svelte-markdown when you want a lower-level, unstyled renderer with direct and out-of-order chunk ingestion, explicit stream lifecycle controls, frame-coalesced updates, reusable document caching, broad raw-HTML customization, and configurable URL and attribute sanitization. Both are credible Svelte 5 choices for incomplete streaming markdown; the deciding factor is whether you want an opinionated presentation layer or a composable rendering primitive.

FIG-007 / MORE

read more.

Every head-to-head, with the same matrix + pros / cons + verdict format.

SET / JETBRAINS MONO + INTER
HUMANSPEAK · 2026
MIT LICENCE
try
svelte markdown → install in 30 seconds
SHEET 07 / 07
END OF DOCUMENT
↩ ALL COMPARISONS