/** * Incremental parsing engine for streaming markdown. * * The win for AI chat output: as the source string grows token-by-token, we * never re-parse or re-render finalized content, and completed blocks keep a * stable identity so the reconciler never remounts (no flicker / reflow). * * Core invariant: for an append-only stream, only the **last** top-level block * can still change — appended text always extends the final block. So when a * parse of the live tail yields N blocks, the first N−1 are finalized: they are * cached by reference and never rebuilt, and the source cursor advances to the * start of the last block. Each subsequent chunk re-parses only that trailing * block region (≈ O(last block), not O(document)). * * Keys are the absolute block index (`b-`), so a block keeps the same key * when it transitions from live → finalized: the reconciler patches in place * rather than remounting. */ import type { BlockNode } from '../ast.js'; import type { ParserInlineExtension } from './extensions.js'; export interface IncrementalEngine { /** Parse `src`, reusing finalized blocks from prior calls where possible. */ parse(src: string): BlockNode[]; /** Drop all cached state (e.g. when the source is replaced, not appended). */ reset(): void; } export interface IncrementalEngineOptions { /** * Inline extensions threaded into every parse. Captured at construction — * extensions are configuration, not data: to change the set, create a new * engine. Each `match` must be pure, or finalized-block reuse breaks. */ extensions?: readonly ParserInlineExtension[]; } export declare function createIncrementalEngine(options?: IncrementalEngineOptions): IncrementalEngine;