惯性聚合 高效追踪和阅读你感兴趣的博客、新闻、科技资讯
阅读原文 在惯性聚合中打开

推荐订阅源

博客园_首页
I
InfoQ
The Register - Security
The Register - Security
L
LangChain Blog
H
Help Net Security
The GitHub Blog
The GitHub Blog
S
Schneier on Security
博客园 - 【当耐特】
W
WeLiveSecurity
Attack and Defense Labs
Attack and Defense Labs
IT之家
IT之家
CTFtime.org: upcoming CTF events
CTFtime.org: upcoming CTF events
Google DeepMind News
Google DeepMind News
The Cloudflare Blog
H
Heimdal Security Blog
让小产品的独立变现更简单 - ezindie.com
让小产品的独立变现更简单 - ezindie.com
Y
Y Combinator Blog
雷峰网
雷峰网
N
Netflix TechBlog - Medium
Security Archives - TechRepublic
Security Archives - TechRepublic
cs.AI updates on arXiv.org
cs.AI updates on arXiv.org
Cyber Security Advisories - MS-ISAC
Cyber Security Advisories - MS-ISAC
L
Lohrmann on Cybersecurity
OSCHINA 社区最新新闻
OSCHINA 社区最新新闻
T
The Exploit Database - CXSecurity.com
P
Privacy & Cybersecurity Law Blog
G
GRAHAM CLULEY
Exploit-DB.com RSS Feed
Exploit-DB.com RSS Feed
V
Visual Studio Blog
博客园 - 聂微东
PCI Perspectives
PCI Perspectives
Last Week in AI
Last Week in AI
A
Arctic Wolf
宝玉的分享
宝玉的分享
T
The Blog of Author Tim Ferriss
S
Secure Thoughts
T
Threat Research - Cisco Blogs
GbyAI
GbyAI
云风的 BLOG
云风的 BLOG
D
Darknet – Hacking Tools, Hacker News & Cyber Security
S
SegmentFault 最新的问题
SecWiki News
SecWiki News
月光博客
月光博客
大猫的无限游戏
大猫的无限游戏
Schneier on Security
Schneier on Security
P
Proofpoint News Feed
博客园 - Franky
奇客Solidot–传递最新科技情报
奇客Solidot–传递最新科技情报
AI
AI
Engineering at Meta
Engineering at Meta

TanStack Blog

We Removed React Server Components from TanStack.com | TanStack Blog We Stopped Using RSC on TanStack.com | TanStack Blog Inside TanStack Table V9 Reactivity | TanStack Blog Run Any Coding Agent in a Sandbox, With One chat() Call | TanStack Blog TanStack Start and TanStack AI Win 2026 Open Source Awards | TanStack Blog How an Underrated Refactor Saved 90% Memory Usage | TanStack Blog TypeScript Performance in TanStack Table V9 | TanStack Blog TanStack AI Beta: The Switzerland of AI Tooling Grows Up | TanStack Blog TanStack Table V9: Taking Form | TanStack Blog TanStack AI: Your MCP, your way | TanStack Blog TanStack Start Adds First-Class Rsbuild Support | TanStack Blog Introducing Experimental Workflows and Orchestrators in TanStack AI | TanStack Blog Chat UIs Are Lists Until They Aren't | TanStack Blog Structured Output That Remembers Across Turns | TanStack Blog TanStack Virtual just got a lot faster, and finally handles iOS | TanStack Blog TanStack AI now fully speaks AG-UI | TanStack Blog Stop Waiting on JSON: Stream Structured Output with One Schema | TanStack Blog Hardening TanStack After the npm Compromise | TanStack Blog Postmortem: TanStack npm supply-chain compromise | TanStack Blog Who Owns the Tree? RSC as a Protocol, Not an Architecture | TanStack Blog TanStack AI Just Learned to Compose Music | TanStack Blog Your AI Tool Calls Should Fail at Compile Time, Not in Production | TanStack Blog One Flag, Every Chunk: Debug Logging Lands in TanStack AI | TanStack Blog How We Test TanStack AI Across 7 Providers on Every PR | TanStack Blog React Server Components Your Way | TanStack Blog Code Mode: Let Your AI Write Programs, Not Just Call Tools | TanStack Blog Solid 2.0 Beta Support in TanStack Router, Start, and Query | TanStack Blog TanStack Router's New Reactive Core: A Signal Graph | TanStack Blog TanStack DB 0.6 Now Includes Persistence, Offline Support, and Hierarchical Data | TanStack Blog We Removed 3rd Party Ads from TanStack.com | TanStack Blog 5x SSR Throughput: Profiling SSR Hot Paths in TanStack Start | TanStack Blog Lazy Tool Discovery: Scaling AI Tool Systems Without Drowning in Tokens | TanStack Blog TanStack AI Just Got Middleware — And It Changes Everything | TanStack Blog Talk to Your AI: Realtime Voice Chat in TanStack AI | TanStack Blog Generation Hooks: Type-Safe AI Beyond Chat | TanStack Blog TanStack + OpenRouter Partnership | TanStack Blog Introducing TanStack Intent: Ship Agent Skills with your npm Packages | TanStack Blog TanStack AI: Why We Split the Adapters | TanStack Blog The ai() Function That Almost Was | TanStack Blog TanStack AI Alpha 2: Every Modality, Better APIs, Smaller Bundles | TanStack Blog TanStack AI Alpha: Your AI, Your Way | TanStack Blog How We Track Billions of Downloads: The NPM Stats API Deep Dive | TanStack Blog The State of TanStack, Two Years of Full-Time OSS | TanStack Blog How we accidentally made route matching more performant by aiming for correctness | TanStack Blog TanStack DB 0.5 . Query-Driven Sync | TanStack Blog Directives and the Platform Boundary | TanStack Blog TanStack Start v1 Release Candidate | TanStack Blog Stop Re-Rendering. TanStack DB, the Embedded Client Database for TanStack Query | TanStack Blog Search Params Are State | TanStack Blog The Power in Pragmatism | TanStack Blog TanStack + Netlify Partnership | TanStack Blog Announcing TanStack Form v1 | TanStack Blog Why choose TanStack Start and Router? | TanStack Blog Why TanStack Start is Ditching Adapters | TanStack Blog A milestone for TypeScript Performance in TanStack Router | TanStack Blog Announcing TanStack Query v5 | TanStack Blog Announcing TanStack Query v4 | TanStack Blog TanStack Table + Ag-Grid Partnership | TanStack Blog
Introducing TanStack Markdown and TanStack Highlight | TanStack Blog
Tanner Linsley · 2026-07-24 · via TanStack Blog

by Tanner Linsley on Jul 24, 2026.

A braided river flows through dark mineral channels into a pale tropical sandbar

Our last post about removing React Server Components from tanstack.com ended with a pretty simple preference, I don't want to reach for an architecture to hide a dependency problem, I'd rather make the dependency small and let content be content.

TanStack Markdown and TanStack Highlight are the two libraries that made that decision possible, and we haven't properly introduced either of them yet.

We didn't set out to build two more TanStack libraries, we were trying to make one embarrassingly large part of tanstack.com small enough that we could stop designing the site around it. Earlier this year, a docs page was transferring about 1.1 MiB of script, with roughly 358 KiB tied to syntax highlighting alone. Shiki, its WASM and runtime pieces, themes, language chunks, and our Markdown pipeline had quietly turned reading a page into downloading a small publishing system.

RSC gave us a good way to keep that system on the server, and it worked, but the underlying cost was still there. We'd made an application architecture decision around hiding a dependency problem, and I couldn't stop asking why rendering the subset of Markdown and web code we actually use needed to be that expensive in the first place.

So we made the expensive part small.

Today we're releasing the first alphas of TanStack Markdown and TanStack Highlight, two deliberately narrow libraries built around the content contract we actually need for technical blogs, documentation, and streamed AI output. The last post was about the architecture we could remove, this one is about what we built to remove it.

Markdown and syntax highlighting tend to arrive as one tangled pipeline. A parser finds a code fence, a plugin loads a grammar engine, the grammar engine loads themes, the renderer turns the whole thing into framework-specific output, and pretty soon changing how a link works means understanding half of a compiler toolchain.

TanStack Markdown parses content into a public, serializable document tree. TanStack Highlight turns known source languages into escaped, semantic HTML. Neither package imports the other, and the boundary between them is a normal callback carrying code, language, and fence metadata.

That separation is doing a lot of work for us. A Markdown document can be parsed, cached, indexed, inspected, or rendered without loading a highlighter, and a highlighter can be used for a code example that has never been near Markdown. If you connect them, you choose the language set and theme contract explicitly.

Most Markdown APIs make the rendered output the product. TanStack Markdown treats the parsed document as the durable part.

The tree is plain objects and arrays, so it can cross a server boundary, sit in a cache, feed a search index, or render later through HTML, React, or Octane. Parsing doesn't trap the content inside a framework or an async plugin pipeline.

The parser is currently 4.9 KB gzipped, the HTML renderer and framework adapters are about 6.7 KB gzipped, and the package has zero runtime dependencies. React and Octane are optional peers behind their own entry points, while docs extensions, callouts, streaming behavior, and other transforms stay in separate imports.

That size comes from having an opinion about the job. TanStack Markdown supports the syntax we use across technical blogs and documentation, including headings, emphasis, lists, task lists, tables, footnotes, fenced code and metadata, links, images, references, and optional frontmatter. It does not promise every CommonMark edge case, arbitrary async plugin chains, automatic linkification, MDX evaluation, or a bundled sanitizer.

Raw HTML is escaped by default and executable URL protocols are removed, but this is still a rendering primitive, not a complete policy for untrusted content. Applications still own outbound link behavior, remote images, and what happens if they explicitly enable raw HTML.

Stream the text, not parser state

AI output made another Markdown tradeoff feel more complicated than it needed to be. A lot of streaming renderers maintain incremental parser state as tokens arrive, which means the state has to survive updates, recover from partial syntax, and eventually agree with the completed document.

TanStack Markdown's optional streaming extension takes the accumulated response and reparses it synchronously on every UI update. Completed blocks stay deterministic, unfinished trailing headings, quotes, and list items don't leave empty placeholders behind, and there isn't any parser state to coordinate or throw away.

The extension adds about 0.2 KB gzipped to the React path. For unusually long responses, you should still batch tiny transport tokens into sensible paint intervals, but the parser itself doesn't need a second streaming architecture.

Syntax highlighting for a webpage is a much smaller job than syntax highlighting for an editor.

An editor needs incremental parsing, huge language coverage, TextMate compatibility, semantic tokens, extension ecosystems, and enough state to update one character without touching the rest of the file. A docs page usually knows the language before rendering and needs compact, deterministic HTML that looks the same on the server and in the browser.

TanStack Highlight is built for that second job. Its empty core is 1.7 KB gzipped, core plus TSX is 3.9 KB, our nine-language docs set is 5.8 KB, and the build containing all 25 shipped languages is about 8 KB.

There isn't an initialization promise, automatic language detection, or a hidden all-language registry. You import the languages your site uses, create the highlighter once, and share it between SSR and the browser. Unknown languages fall back to escaped plaintext instead of guessing.

Web languages also have a habit of containing other web languages, so the scanners can delegate embedded regions when you've registered the matching language. HTML can highlight a <script> or <style> body, Vue and Svelte can hand their script regions to TypeScript, and Markdown can highlight fenced code without making those nested grammars mandatory.

Our old setup generated a surprising amount of markup because token colors and theme decisions were baked into the output. Dark mode could mean another highlighted tree, another set of inline styles, or both.

TanStack Highlight emits one <pre><code> tree with stable th-* semantic classes and no inline colors. Themes are isolated imports that generate CSS variables, so changing from light to dark is a CSS operation and the source never needs another highlighting pass.

The renderer also understands the things documentation code blocks need around the tokens. Fence metadata and programmatic decorations can mark line highlights, insertions, deletions, focus, errors, warnings, exact character ranges, titles, and line numbers without introducing a transformer framework.

Coding agents made it practical for us to explore purpose-built parsers and scanners much faster than we could've justified a few years ago, but "AI wrote a smaller Markdown parser" isn't the bet here. Small software doesn't get to hand correctness to a giant dependency, which means the corpus, fixtures, size budgets, and output contracts become part of the product.

TanStack Highlight's committed corpus currently samples 333 fixtures from 2,940 TanStack documentation files. Release checks cover token fidelity, deterministic HTML, package exports, bundle profiles, focused parser regressions, and a roughly 10,000-block throughput budget. Markdown tracks its supported CommonMark examples explicitly, checks renderer parity, and audits real TanStack and external content corpora.

The first tanstack.com migrations found edge cases in tight lists and image handling almost immediately. That's exactly what alpha software should surface, and every fix has to leave behind a focused regression test instead of another clever branch nobody can explain six months later.

The cost of going tiny is owning the contract. We want that cost in the repositories where everyone can inspect it.

Both packages now power tanstack.com's docs and blog, and they were small enough to change an architecture decision we had already made.

Our RSC content pipeline existed largely to keep the old Markdown and highlighting stack out of the browser. Once the replacement renderer was about 27 KiB transferred on the production routes we measured, regular SSR plus raw content data became the better trade for this site. We removed the content-specific RSC path, kept the original performance win, and made subsequent navigations smaller because the browser can reuse the renderer instead of receiving another serialized component tree.

The RSC post has the measurements and caveats behind that decision. For this announcement, the important part is that these aren't tiny libraries built around a benchmark toy, they're already carrying the messiest content corpus we own.

Both libraries are available now:

The Markdown docs cover the supported syntax profile, renderers, extensions, security boundary, and AI streaming setup. The Highlight docs cover language registration, themes, annotations, Markdown adapters, and the output contract.

If you need every CommonMark edge case, hundreds of languages, TextMate fidelity, MDX evaluation, or an open-ended compiler ecosystem, these probably aren't replacements for the tools you already use. If you're rendering known technical content into webpages and the publishing stack has started to outweigh the page, try them, measure them against your own corpus, and bring us the cases our tests don't know yet.