@ai-markdown/core 3.4.2 → 3.5.1

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
@@ -1,5 +1,134 @@
1
1
  import { Element } from "hast";
2
2
  import { CodeLanguage } from "@ai-markdown/code-language-detector";
3
+ /** Engine spellings, independent of the UI package. */
4
+ export declare enum CodeLanguageFormat {
5
+ HighlightJs = "highlight-js",
6
+ Shiki = "shiki",
7
+ Pierre = "pierre"
8
+ }
9
+ type CodeLanguageResolver = CodeLanguageFormat | ((language: string) => string);
10
+ export declare function resolveCodeHighlightLanguage(language: string, format?: CodeLanguageResolver): string;
11
+ export declare function resolveCodeHighlightInterval(value: number | undefined, fallback?: number): number;
12
+ interface CodeHighlightToken {
13
+ text: string;
14
+ color?: string;
15
+ backgroundColor?: string;
16
+ /** Shiki-compatible bit flags: italic=1, bold=2, underline=4. */
17
+ fontStyle?: number;
18
+ }
19
+ /** HTML must come from a trusted highlighter which escapes source text. Never return raw source as HTML. */
20
+ type CodeHighlightResult = {
21
+ html: string;
22
+ } | {
23
+ tokens: readonly CodeHighlightToken[];
24
+ };
25
+ interface CodeHighlightRequest {
26
+ code: string;
27
+ language: string;
28
+ colorScheme: 'light' | 'dark';
29
+ /** Enable incremental work while the document is streaming. */
30
+ streaming?: boolean;
31
+ }
32
+ /** Mutable engine state owned by one mounted code block, updated only on commit. */
33
+ interface CodeHighlightBackend {
34
+ highlight(request: CodeHighlightRequest): CodeHighlightResult | undefined;
35
+ dispose(): void;
36
+ }
37
+ /** Inject engines from the application; core imports no highlighting runtime. */
38
+ interface CodeHighlightAdapter {
39
+ languageFormat: CodeLanguageResolver;
40
+ /** Optional incremental backend. Never created during rendering or SSR. */
41
+ createSession?(): CodeHighlightBackend;
42
+ supports?(language: string): boolean;
43
+ isReady?(request: CodeHighlightRequest): boolean;
44
+ /** Called only after the framework commits. May load an engine, theme or language. */
45
+ prepare?(request: CodeHighlightRequest): void | Promise<void>;
46
+ /** Synchronous after preparation. Return undefined to display plain source. */
47
+ highlight(request: CodeHighlightRequest): CodeHighlightResult | undefined;
48
+ }
49
+ interface CodeHighlightInput {
50
+ adapter?: CodeHighlightAdapter;
51
+ code: string;
52
+ /** Unconverted fence language or detector result. */
53
+ language: string;
54
+ colorScheme: 'light' | 'dark';
55
+ /** Enable incremental work while the document is streaming. */
56
+ streaming?: boolean;
57
+ generation: number;
58
+ active?: boolean;
59
+ }
60
+ interface CodeHighlightSnapshot {
61
+ language: string;
62
+ status: 'plain' | 'loading' | 'ready' | 'error';
63
+ result?: CodeHighlightResult;
64
+ error?: unknown;
65
+ }
66
+ /** Per-block cache and async preparation. A late preparation never publishes an old code result. */
67
+ export declare function createCodeHighlightSession(onChange: () => void): {
68
+ read(input: CodeHighlightInput): CodeHighlightSnapshot;
69
+ commit(input: CodeHighlightInput): void;
70
+ retry(): void;
71
+ dispose(): void;
72
+ };
73
+ type MermaidConfig = {
74
+ theme?: string;
75
+ securityLevel?: string;
76
+ darkMode?: boolean;
77
+ suppressErrorRendering?: boolean;
78
+ maxTextSize?: number;
79
+ themeVariables?: unknown;
80
+ };
81
+ /** The part of the mermaid module this file touches. Structural so tests can
82
+ * pass a stub; `mermaidAPI` is deprecated in mermaid's types but present at
83
+ * runtime in mermaid 11, and it is the only place `getSiteConfig` /
84
+ * `getConfig` live (the default export has neither). */
85
+ type MermaidInitTarget = {
86
+ initialize(config: MermaidConfig): void;
87
+ mermaidAPI?: {
88
+ getSiteConfig?: () => MermaidConfig;
89
+ getConfig?: () => MermaidConfig;
90
+ };
91
+ };
92
+ /**
93
+ * The effective `maxTextSize`. `mermaid.render` does not reject oversized
94
+ * input: it swaps in a placeholder diagram ("Maximum text size in diagram
95
+ * exceeded") and resolves normally, and `mermaid.parse` has no size gate at
96
+ * all, so the whole text is parsed first. The renderer checks this before
97
+ * parsing and reports the size as an error instead. The key is in mermaid's
98
+ * `secure` list, so a `%%{init}%%` directive cannot raise it and the site
99
+ * config is the value that applies.
100
+ */
101
+ export declare const getMermaidMaxTextSize: (mermaid: MermaidInitTarget) => number;
102
+ /**
103
+ * mermaid's config is a module-level singleton shared with the host
104
+ * application when the bundler dedupes the package, and a host that enables
105
+ * `click` interactions calls `mermaid.initialize({ securityLevel: 'loose' })`
106
+ * — the officially documented way. Under `loose` mermaid skips DOMPurify
107
+ * and its output goes into this component's `innerHTML` verbatim: an
108
+ * LLM-authored diagram string could then run script in the page origin.
109
+ * So a theme cache alone is not enough of a guard: before every render the
110
+ * current `securityLevel` is read back (a config copy, still far cheaper
111
+ * than `initialize`'s merge + theme variables + diagram registration) and an
112
+ * unsafe value forces a re-initialize
113
+ * (2026-08-19 review r2 P2-11; the v2.4.2 "documented premise" made this
114
+ * the host's problem — it is ours, the innerHTML is ours).
115
+ *
116
+ * In mermaid 11 `initialize` goes through `setSiteConfig`, which REPLACES
117
+ * the site config with defaults + the keys passed in. Calling it with only
118
+ * our keys wiped the host's `theme`, `fontFamily`, `flowchart` options and
119
+ * so on, and turned a host `sandbox` into `strict` (3.0.2 review). So:
120
+ * - the current site config is read back and passed through with our
121
+ * overrides on top, so host keys survive;
122
+ * - `sandbox` is accepted as is; only `loose` / `antiscript` / unset become
123
+ * `strict`;
124
+ * - a theme the host chose is kept (with its `themeVariables`); the color
125
+ * scheme switch only applies to the theme when the host has not chosen
126
+ * one, or when the current theme is one we wrote;
127
+ * - when nothing needs to change, `initialize` is not called at all, so a
128
+ * host on `strict`/`sandbox` and this component stop overwriting each
129
+ * other on every render.
130
+ */
131
+ export declare const ensureMermaidInitialized: (mermaid: MermaidInitTarget, isDark: boolean) => void;
3
132
  /** Shared image semantics; no DOM or framework dependency. */
4
133
  type ImageActionIconName = 'rotateLeft' | 'rotateRight' | 'zoomIn' | 'zoomOut' | 'close' | 'prev' | 'next' | 'flipX' | 'flipY';
5
134
  type ImageIconName = 'placeholder' | 'error' | 'preview' | 'gallery' | ImageActionIconName;
@@ -88,6 +217,145 @@ interface TableLabels extends Record<TableExportReason, string> {
88
217
  scrollRegion: string;
89
218
  }
90
219
  export declare const defaultTableLabels: Readonly<TableLabels>;
220
+ interface DiagramEngine extends MermaidInitTarget {
221
+ kind?: 'mermaid';
222
+ /** Resolves truthy for a source that parses; rejects, or resolves falsy, for one that does not. */
223
+ parse(code: string): Promise<unknown>;
224
+ render(id: string, code: string): Promise<{
225
+ svg: string;
226
+ diagramType?: string;
227
+ bindFunctions?(element: object): void;
228
+ }>;
229
+ }
230
+ /** A stateless SVG renderer. Output must be safe to insert into the document. */
231
+ interface SvgDiagramEngine {
232
+ /** Identifies the built-in CSS palette, not a capability registry. */
233
+ palette?: 'pele' | 'ondine';
234
+ kind: 'svg';
235
+ maxTextSize?: number;
236
+ render(id: string, code: string, dark: boolean): Promise<{
237
+ svg: string;
238
+ diagramType?: string;
239
+ bindFunctions?(element: object): void | (() => void);
240
+ }>;
241
+ }
242
+ type DiagramEngineLoader = () => Promise<DiagramEngine | SvgDiagramEngine>;
243
+ /**
244
+ * What the host shows. One value instead of separate flags whose combinations
245
+ * had to be kept coherent by hand:
246
+ * - `source`: nothing has rendered in this generation (warm-up, server render).
247
+ * - `diagram`: the last successful render.
248
+ * - `error`: only a failed corrective pass after a stream, or a static failure
249
+ * with no diagram up, enters this state.
250
+ */
251
+ type DiagramView = {
252
+ kind: 'source';
253
+ } | {
254
+ kind: 'diagram';
255
+ svg: string;
256
+ chartType: string;
257
+ palette?: 'pele' | 'ondine';
258
+ dark?: boolean;
259
+ onBindError?: (error: unknown) => void;
260
+ bind?: (element: object) => void | (() => void);
261
+ } | DiagramError;
262
+ /**
263
+ * Why a diagram did not render, as data: the host owns the words.
264
+ * - `tooLarge`: the source is longer than the engine's `maxTextSize`.
265
+ * - `parse` and `render`: the engine refused the source or failed to draw it.
266
+ * `message` is the engine's own text, which is diagnostic and not
267
+ * translated, or empty when it gave none.
268
+ */
269
+ type DiagramError = {
270
+ kind: 'error';
271
+ reason: 'tooLarge';
272
+ length: number;
273
+ limit: number;
274
+ } | {
275
+ kind: 'error';
276
+ reason: 'parse' | 'render';
277
+ message: string;
278
+ };
279
+ /** The text for an error view: the engine's own message when there is one, else the label for the reason. */
280
+ export declare function diagramErrorText(error: DiagramError, labels: Pick<DiagramLabels, 'tooLarge' | 'renderFailed'>): string;
281
+ interface DiagramState {
282
+ view: DiagramView;
283
+ /** The engine module could not be loaded and the automatic retries are spent. `retry()` starts over. */
284
+ loadFailed: boolean;
285
+ }
286
+ interface DiagramRequest {
287
+ code: string;
288
+ dark: boolean;
289
+ /** Document streaming state. Its edges mark the start and the end of a generation. */
290
+ streaming: boolean;
291
+ /** False while the host shows something else, such as the source. No attempt runs. */
292
+ active: boolean;
293
+ /** Minimum time between attempts while streaming. Zero attempts every update. */
294
+ interval: number;
295
+ }
296
+ /**
297
+ * The render state machine for one diagram. The host passes every change of
298
+ * its inputs to `update` and draws what `publish` receives.
299
+ *
300
+ * ## While `streaming` is true
301
+ *
302
+ * The source is usually a truncated prefix, so a parse failure is expected:
303
+ * - Before the first success the view stays `source`, never `error`.
304
+ * - After a success the last diagram stays up; each attempt replaces it only
305
+ * when it succeeds.
306
+ * - Attempts are throttled by `interval` with the same trailing throttle as
307
+ * code display: appends inside an interval replace one pending frame without
308
+ * moving its deadline. A rewrite, a non-streaming update and the end of the
309
+ * stream pass through at once.
310
+ * - When streaming ends, one corrective pass runs on the final source. Its
311
+ * failure is published even over a diagram, because that diagram no longer
312
+ * matches the source. Only that one pass may do so.
313
+ * - When streaming starts, a new generation begins on the same instance (a
314
+ * regenerated answer keeps its block position). Everything from the previous
315
+ * generation is dropped and the view returns to `source`.
316
+ *
317
+ * ## While `streaming` stays false
318
+ *
319
+ * A failure is published only while no diagram is up. Once one is, a later
320
+ * failure (a theme change, an incomplete source from a host that does not pass
321
+ * `streaming`) keeps it.
322
+ *
323
+ * ## Always
324
+ *
325
+ * - An attempt whose source and theme match the diagram on screen is skipped.
326
+ * - A source above the engine's `maxTextSize` is an error, not a render.
327
+ * - A failed engine download is not a diagram error. It keeps the view, keeps a
328
+ * pending corrective pass, and is retried a bounded number of times.
329
+ * - An attempt that has been superseded publishes nothing.
330
+ */
331
+ export declare function createDiagramController(load: DiagramEngineLoader, publish: (state: DiagramState) => void, fallback?: DiagramEngineLoader): {
332
+ update(next: DiagramRequest): void;
333
+ /** Attempts again on unchanged inputs, with a fresh download budget. */
334
+ retry(): void;
335
+ dispose(): void;
336
+ };
337
+ interface CodeBlockOptions {
338
+ /** Legacy callbacks default to highlight.js names. Adapters own their language format. */
339
+ languageFormat?: CodeLanguageResolver;
340
+ /** Takes precedence over the legacy framework highlight callback. Keep adapter identity stable. */
341
+ highlighter?: CodeHighlightAdapter;
342
+ defaultExpanded?: boolean;
343
+ autoDetectUnknownLanguage?: boolean;
344
+ formatJson?: boolean;
345
+ expandNestedJson?: boolean;
346
+ highlightIntervalMs?: number;
347
+ mermaidIntervalMs?: number;
348
+ /** Optional renderer loader. Omit to use Mermaid. Keep its identity stable. */
349
+ mermaidEngine?: DiagramEngineLoader | false;
350
+ /** Standard entry only: fall back to Mermaid for a known unavailable type. Default true. */
351
+ mermaidFallback?: boolean;
352
+ /** Text of the code block, as overrides of the English defaults. A function is called on every render. */
353
+ labels?: LabelsOption<CodeBlockLabels>;
354
+ }
355
+ /** Common behavior defaults. UI integrations may override these defaults, not their resolution rules. */
356
+ type CodeBlockPolicy = Required<Pick<CodeBlockOptions, 'defaultExpanded' | 'autoDetectUnknownLanguage' | 'formatJson' | 'expandNestedJson' | 'highlightIntervalMs'>>;
357
+ export declare const defaultCodeBlockPolicy: Readonly<CodeBlockPolicy>;
358
+ export declare function resolveCodeBlockPolicy(overrides?: Partial<CodeBlockPolicy>, inherited?: Partial<CodeBlockPolicy>, defaults?: Partial<CodeBlockPolicy>): CodeBlockPolicy;
91
359
  interface CodeSource {
92
360
  code: string;
93
361
  language: string;
@@ -221,165 +489,6 @@ export declare const mermaidRenderQueue: {
221
489
  enqueue(owner: object, run: () => Promise<void>): Promise<void>;
222
490
  cancel(owner: object): void;
223
491
  };
224
- type MermaidConfig = {
225
- theme?: string;
226
- securityLevel?: string;
227
- darkMode?: boolean;
228
- suppressErrorRendering?: boolean;
229
- maxTextSize?: number;
230
- themeVariables?: unknown;
231
- };
232
- /** The part of the mermaid module this file touches. Structural so tests can
233
- * pass a stub; `mermaidAPI` is deprecated in mermaid's types but present at
234
- * runtime in mermaid 11, and it is the only place `getSiteConfig` /
235
- * `getConfig` live (the default export has neither). */
236
- type MermaidInitTarget = {
237
- initialize(config: MermaidConfig): void;
238
- mermaidAPI?: {
239
- getSiteConfig?: () => MermaidConfig;
240
- getConfig?: () => MermaidConfig;
241
- };
242
- };
243
- /**
244
- * The effective `maxTextSize`. `mermaid.render` does not reject oversized
245
- * input: it swaps in a placeholder diagram ("Maximum text size in diagram
246
- * exceeded") and resolves normally, and `mermaid.parse` has no size gate at
247
- * all, so the whole text is parsed first. The renderer checks this before
248
- * parsing and reports the size as an error instead. The key is in mermaid's
249
- * `secure` list, so a `%%{init}%%` directive cannot raise it and the site
250
- * config is the value that applies.
251
- */
252
- export declare const getMermaidMaxTextSize: (mermaid: MermaidInitTarget) => number;
253
- /**
254
- * mermaid's config is a module-level singleton shared with the host
255
- * application when the bundler dedupes the package, and a host that enables
256
- * `click` interactions calls `mermaid.initialize({ securityLevel: 'loose' })`
257
- * — the officially documented way. Under `loose` mermaid skips DOMPurify
258
- * and its output goes into this component's `innerHTML` verbatim: an
259
- * LLM-authored diagram string could then run script in the page origin.
260
- * So a theme cache alone is not enough of a guard: before every render the
261
- * current `securityLevel` is read back (a config copy, still far cheaper
262
- * than `initialize`'s merge + theme variables + diagram registration) and an
263
- * unsafe value forces a re-initialize
264
- * (2026-08-19 review r2 P2-11; the v2.4.2 "documented premise" made this
265
- * the host's problem — it is ours, the innerHTML is ours).
266
- *
267
- * In mermaid 11 `initialize` goes through `setSiteConfig`, which REPLACES
268
- * the site config with defaults + the keys passed in. Calling it with only
269
- * our keys wiped the host's `theme`, `fontFamily`, `flowchart` options and
270
- * so on, and turned a host `sandbox` into `strict` (3.0.2 review). So:
271
- * - the current site config is read back and passed through with our
272
- * overrides on top, so host keys survive;
273
- * - `sandbox` is accepted as is; only `loose` / `antiscript` / unset become
274
- * `strict`;
275
- * - a theme the host chose is kept (with its `themeVariables`); the color
276
- * scheme switch only applies to the theme when the host has not chosen
277
- * one, or when the current theme is one we wrote;
278
- * - when nothing needs to change, `initialize` is not called at all, so a
279
- * host on `strict`/`sandbox` and this component stop overwriting each
280
- * other on every render.
281
- */
282
- export declare const ensureMermaidInitialized: (mermaid: MermaidInitTarget, isDark: boolean) => void;
283
- interface DiagramEngine extends MermaidInitTarget {
284
- /** Resolves truthy for a source that parses; rejects, or resolves falsy, for one that does not. */
285
- parse(code: string): Promise<unknown>;
286
- render(id: string, code: string): Promise<{
287
- svg: string;
288
- diagramType?: string;
289
- bindFunctions?(element: object): void;
290
- }>;
291
- }
292
- /**
293
- * What the host shows. One value instead of separate flags whose combinations
294
- * had to be kept coherent by hand:
295
- * - `source`: nothing has rendered in this generation (warm-up, server render).
296
- * - `diagram`: the last successful render.
297
- * - `error`: only a failed corrective pass after a stream, or a static failure
298
- * with no diagram up, enters this state.
299
- */
300
- type DiagramView = {
301
- kind: 'source';
302
- } | {
303
- kind: 'diagram';
304
- svg: string;
305
- chartType: string;
306
- bind?: (element: object) => void;
307
- } | DiagramError;
308
- /**
309
- * Why a diagram did not render, as data: the host owns the words.
310
- * - `tooLarge`: the source is longer than the engine's `maxTextSize`.
311
- * - `parse` and `render`: the engine refused the source or failed to draw it.
312
- * `message` is the engine's own text, which is diagnostic and not
313
- * translated, or empty when it gave none.
314
- */
315
- type DiagramError = {
316
- kind: 'error';
317
- reason: 'tooLarge';
318
- length: number;
319
- limit: number;
320
- } | {
321
- kind: 'error';
322
- reason: 'parse' | 'render';
323
- message: string;
324
- };
325
- /** The text for an error view: the engine's own message when there is one, else the label for the reason. */
326
- export declare function diagramErrorText(error: DiagramError, labels: Pick<DiagramLabels, 'tooLarge' | 'renderFailed'>): string;
327
- interface DiagramState {
328
- view: DiagramView;
329
- /** The engine module could not be loaded and the automatic retries are spent. `retry()` starts over. */
330
- loadFailed: boolean;
331
- }
332
- interface DiagramRequest {
333
- code: string;
334
- dark: boolean;
335
- /** Document streaming state. Its edges mark the start and the end of a generation. */
336
- streaming: boolean;
337
- /** False while the host shows something else, such as the source. No attempt runs. */
338
- active: boolean;
339
- /** Minimum time between attempts while streaming. Zero attempts every update. */
340
- interval: number;
341
- }
342
- /**
343
- * The render state machine for one diagram. The host passes every change of
344
- * its inputs to `update` and draws what `publish` receives.
345
- *
346
- * ## While `streaming` is true
347
- *
348
- * The source is usually a truncated prefix, so a parse failure is expected:
349
- * - Before the first success the view stays `source`, never `error`.
350
- * - After a success the last diagram stays up; each attempt replaces it only
351
- * when it succeeds.
352
- * - Attempts are throttled by `interval` with the same trailing throttle as
353
- * code display: appends inside an interval replace one pending frame without
354
- * moving its deadline. A rewrite, a non-streaming update and the end of the
355
- * stream pass through at once.
356
- * - When streaming ends, one corrective pass runs on the final source. Its
357
- * failure is published even over a diagram, because that diagram no longer
358
- * matches the source. Only that one pass may do so.
359
- * - When streaming starts, a new generation begins on the same instance (a
360
- * regenerated answer keeps its block position). Everything from the previous
361
- * generation is dropped and the view returns to `source`.
362
- *
363
- * ## While `streaming` stays false
364
- *
365
- * A failure is published only while no diagram is up. Once one is, a later
366
- * failure (a theme change, an incomplete source from a host that does not pass
367
- * `streaming`) keeps it.
368
- *
369
- * ## Always
370
- *
371
- * - An attempt whose source and theme match the diagram on screen is skipped.
372
- * - A source above the engine's `maxTextSize` is an error, not a render.
373
- * - A failed engine download is not a diagram error. It keeps the view, keeps a
374
- * pending corrective pass, and is retried a bounded number of times.
375
- * - An attempt that has been superseded publishes nothing.
376
- */
377
- export declare function createDiagramController(load: () => Promise<DiagramEngine>, publish: (state: DiagramState) => void): {
378
- update(next: DiagramRequest): void;
379
- /** Attempts again on unchanged inputs, with a fresh download budget. */
380
- retry(): void;
381
- dispose(): void;
382
- };
383
492
  /**
384
493
  * Stops the page behind a preview from scrolling. `scrollbarWidth` is the
385
494
  * width of the scrollbar that hiding the overflow removes
@@ -592,6 +701,106 @@ export declare function createImagePreviewController(host: ImagePreviewHost, pub
592
701
  /** Stops every timer and subscription. The controller can be opened again afterwards. */
593
702
  dispose(): void;
594
703
  };
704
+ /** Structural subset; generic options preserve the installed engine's own parameter types. */
705
+ interface SvgRendererModule<Options extends object = {
706
+ idPrefix?: string;
707
+ limit?: number;
708
+ }> {
709
+ render(source: string, options?: Options): {
710
+ svg: string;
711
+ type?: string;
712
+ } | Promise<{
713
+ svg: string;
714
+ type?: string;
715
+ }>;
716
+ }
717
+ interface DiagramAdapterOptions<Options extends object> {
718
+ renderOptions?: Omit<Options, 'idPrefix'>;
719
+ }
720
+ export declare function createPeleLoader<Options extends object>(load: () => Promise<SvgRendererModule<Options>>, options?: DiagramAdapterOptions<Options>): DiagramEngineLoader;
721
+ export declare function createOndineLoader<Options extends object>(load: () => Promise<SvgRendererModule<Options>>, options?: DiagramAdapterOptions<Options>): DiagramEngineLoader;
722
+ interface PierreHighlightToken {
723
+ content: string;
724
+ offset: number;
725
+ color?: string;
726
+ bgColor?: string;
727
+ fontStyle?: number;
728
+ }
729
+ /** Only the synchronous, editable-document API is needed; core imports no WASM runtime. */
730
+ interface PierreLiveTokenizer {
731
+ readonly lineCount: number;
732
+ getLineLength(line: number): number;
733
+ getLineTokens(line: number): {
734
+ tokens: readonly PierreHighlightToken[];
735
+ };
736
+ applyEdits(edits: readonly {
737
+ range: {
738
+ start: {
739
+ line: number;
740
+ character: number;
741
+ };
742
+ end: {
743
+ line: number;
744
+ character: number;
745
+ };
746
+ };
747
+ newText: string;
748
+ }[]): {
749
+ lineChanges: readonly {
750
+ oldStartLine: number;
751
+ oldEndLine: number;
752
+ newStartLine: number;
753
+ newEndLine: number;
754
+ }[];
755
+ };
756
+ dispose(): void;
757
+ }
758
+ /** Structural interface: applications own the optional WASM engine and theme imports. */
759
+ interface PierreHighlightRuntime<Language extends string, Theme> {
760
+ isSupportedLanguage(language: string): boolean;
761
+ codeToTokens(code: string, options: {
762
+ lang: Language;
763
+ theme: NoInfer<Theme>;
764
+ }): {
765
+ tokens: readonly (readonly PierreHighlightToken[])[];
766
+ fg?: string;
767
+ };
768
+ LiveTokenizer?: new (options: {
769
+ code: string;
770
+ lang: Language;
771
+ theme: NoInfer<Theme>;
772
+ }) => PierreLiveTokenizer;
773
+ themes: {
774
+ light: Theme;
775
+ dark: Theme;
776
+ };
777
+ }
778
+ /** Lazy initialization is shared; mutable tokenizers belong to individual mounted blocks. */
779
+ export declare function createPierreHighlightAdapter<Language extends string, Theme>(options: {
780
+ load: () => Promise<PierreHighlightRuntime<Language, Theme>>;
781
+ /** Defaults to true. Disable to compare with full-frame tokenization. */
782
+ incremental?: boolean;
783
+ }): CodeHighlightAdapter;
784
+ /** Raised only for an identified diagram type unavailable in the selected engine. */
785
+ export declare class UnsupportedDiagramError extends Error {
786
+ readonly diagramType: string;
787
+ constructor(diagramType: string);
788
+ }
789
+ export declare const resolveDiagramInterval: (value: number | undefined) => number;
790
+ /** Shared per loader, not per component. Rejected imports are never retained. */
791
+ export declare function createCachedDiagramLoader(load: DiagramEngineLoader): DiagramEngineLoader;
792
+ export declare function preloadDiagramEngine(load: DiagramEngineLoader): Promise<void>;
793
+ interface DiagramInput {
794
+ code: string;
795
+ colorScheme: 'light' | 'dark';
796
+ streaming: boolean;
797
+ active: boolean;
798
+ resetKey: string;
799
+ intervalMs?: number;
800
+ load: DiagramEngineLoader;
801
+ /** Absent in engine-independent entry points. Only a classified unsupported type can use this. */
802
+ fallback?: DiagramEngineLoader;
803
+ }
595
804
  export interface CodeRendererInput {
596
805
  /** Raw accumulated source, including its trailing newline. */
597
806
  code: string;
@@ -604,14 +813,4 @@ export interface CodeRendererInput {
604
813
  /** Changes on source replacement or identity change; append preserves it. */
605
814
  resetKey: string;
606
815
  }
607
- export interface CodeBlockOptions {
608
- defaultExpanded?: boolean;
609
- autoDetectUnknownLanguage?: boolean;
610
- formatJson?: boolean;
611
- expandNestedJson?: boolean;
612
- highlightIntervalMs?: number;
613
- mermaidIntervalMs?: number;
614
- /** Text of the code block, as overrides of the English defaults. A function is called on every render. */
615
- labels?: LabelsOption<CodeBlockLabels>;
616
- }
617
- export type { CodeBlockInput, CodeBlockLabels, CodeBlockSnapshot, CodeFrame, CodeSource, DiagramEngine, DiagramError, DiagramLabels, DiagramRequest, DiagramState, DiagramView, ImageActionIconName, ImageGallery, ImageGalleryItem, ImageGeometry, ImageIconName, ImageLabels, ImageLoadStatus, ImagePointer, ImagePreviewAction, ImagePreviewHost, ImagePreviewOptions, ImagePreviewPhase, ImagePreviewState, ImageTransform, LabelsOption, MermaidInitTarget, TableExportReason, TableLabels, TableProjection };
816
+ export type { CodeBlockInput, CodeBlockLabels, CodeBlockOptions, CodeBlockPolicy, CodeBlockSnapshot, CodeFrame, CodeHighlightAdapter, CodeHighlightBackend, CodeHighlightInput, CodeHighlightRequest, CodeHighlightResult, CodeHighlightSnapshot, CodeHighlightToken, CodeLanguageResolver, CodeSource, DiagramAdapterOptions, DiagramEngine, DiagramEngineLoader, DiagramError, DiagramInput, DiagramLabels, DiagramRequest, DiagramState, DiagramView, ImageActionIconName, ImageGallery, ImageGalleryItem, ImageGeometry, ImageIconName, ImageLabels, ImageLoadStatus, ImagePointer, ImagePreviewAction, ImagePreviewHost, ImagePreviewOptions, ImagePreviewPhase, ImagePreviewState, ImageTransform, LabelsOption, MermaidInitTarget, PierreHighlightRuntime, PierreHighlightToken, PierreLiveTokenizer, SvgDiagramEngine, SvgRendererModule, TableExportReason, TableLabels, TableProjection };