@topik/content 0.0.0-stage → 0.1.0-alpha.6

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.
@@ -0,0 +1,783 @@
1
+ import { Code, Node, Root, RootContent } from "mdast";
2
+ //#region src/expressions.d.ts
3
+ /** The deliberately small expression language accepted in authored conditionals. */
4
+ type Expression = {
5
+ type: "literal";
6
+ value: string | number | boolean | null;
7
+ } | {
8
+ type: "variable";
9
+ path: string[];
10
+ } | {
11
+ type: "call";
12
+ name: "equals" | "and" | "or" | "not";
13
+ args: Expression[];
14
+ };
15
+ //#endregion
16
+ //#region src/code-presentation.d.ts
17
+ /** Bounds are independent of ordinary, unpresented code admission. */
18
+ export declare const CODE_PRESENTATION_LIMITS: Readonly<{
19
+ metadataLength: 16384;
20
+ selectionIntervals: 1024;
21
+ rows: 20000;
22
+ decorativeOutput: 8000000;
23
+ }>;
24
+ type CodeLineRange = [number, number];
25
+ type CodeLineSelection = CodeLineRange[];
26
+ /** Only explicitly authored keys are stored. Selections are closed, merged intervals. */
27
+ interface CodePresentationOptions {
28
+ filename?: string;
29
+ title?: string;
30
+ lineNumbers?: boolean;
31
+ startLine?: number;
32
+ highlight?: CodeLineSelection;
33
+ focus?: CodeLineSelection;
34
+ collapse?: CodeLineSelection;
35
+ wrap?: boolean;
36
+ added?: CodeLineSelection;
37
+ removed?: CodeLineSelection;
38
+ }
39
+ interface CodePresentationEffectiveOptions extends CodePresentationOptions {
40
+ lineNumbers: boolean;
41
+ startLine: number;
42
+ wrap: boolean;
43
+ }
44
+ export declare function effectiveCodePresentationOptions(options: CodePresentationOptions): CodePresentationEffectiveOptions;
45
+ //#endregion
46
+ //#region src/model.d.ts
47
+ type Scalar = string | number | boolean;
48
+ /** Unevaluated text with an explicit distinction between literals and references. */
49
+ type TextTemplate = {
50
+ type: "topikTextTemplate";
51
+ segments: Array<{
52
+ type: "literal";
53
+ value: string;
54
+ } | {
55
+ type: "variable";
56
+ path: string[];
57
+ }>;
58
+ };
59
+ type AuthoredAttributeValue = Scalar | TextTemplate;
60
+ interface CodeTemplate extends Node {
61
+ type: "topikCodeTemplate";
62
+ lang?: string | null;
63
+ meta?: string | null;
64
+ template: TextTemplate;
65
+ }
66
+ /** Authoritative, unevaluated options for one fenced code payload. */
67
+ interface CodePresentation extends Node {
68
+ type: "topikCodePresentation";
69
+ children: [Code | CodeTemplate];
70
+ options: CodePresentationOptions;
71
+ /** Decoded opaque metadata, including its separating spaces/tabs. */
72
+ opaqueMetaSuffix: string;
73
+ }
74
+ interface Variable extends Node {
75
+ type: "topikVariable";
76
+ path: string[];
77
+ }
78
+ interface Branch extends Node {
79
+ type: "topikBranch";
80
+ condition: Expression | null;
81
+ children: Array<RootContent | Component | Conditional>;
82
+ }
83
+ interface Conditional extends Node {
84
+ type: "topikConditional";
85
+ children: Branch[];
86
+ }
87
+ interface Component extends Node {
88
+ type: "topikComponent";
89
+ name: string;
90
+ props: Record<string, AuthoredAttributeValue>;
91
+ children: Array<RootContent | Component>;
92
+ }
93
+ declare module "mdast" {
94
+ interface BlockContentMap {
95
+ topikComponent: Component;
96
+ topikConditional: Conditional;
97
+ topikCodeTemplate: CodeTemplate;
98
+ topikCodePresentation: CodePresentation;
99
+ }
100
+ interface PhrasingContentMap {
101
+ topikComponent: Component;
102
+ topikVariable: Variable;
103
+ }
104
+ interface RootContentMap {
105
+ topikComponent: Component;
106
+ topikConditional: Conditional;
107
+ topikVariable: Variable;
108
+ topikCodeTemplate: CodeTemplate;
109
+ topikCodePresentation: CodePresentation;
110
+ }
111
+ }
112
+ interface ContentDocument extends Omit<Root, "children"> {
113
+ children: Array<RootContent | Component>;
114
+ }
115
+ interface Diagnostic {
116
+ /** Stable machine-readable code for public compatibility adapters. */
117
+ id?: string;
118
+ /** Bounded code-presentation option name; never an authored value. */
119
+ option?: string;
120
+ type?: string;
121
+ message: string;
122
+ line?: number;
123
+ column?: number;
124
+ }
125
+ type ParseResult = {
126
+ ok: true;
127
+ document: ContentDocument;
128
+ source: string;
129
+ } | {
130
+ ok: false;
131
+ diagnostics: Diagnostic[];
132
+ source: string;
133
+ };
134
+ //#endregion
135
+ //#region src/extensions/native.d.ts
136
+ declare const nativeComponents: {
137
+ readonly codeBlock: {
138
+ readonly name: "codeBlock";
139
+ readonly render: "TopikCodeBlock";
140
+ readonly kind: "block";
141
+ readonly description: "A fenced code block with an optional language.";
142
+ readonly attributes: {
143
+ readonly language: {
144
+ readonly type: "string";
145
+ readonly description: "Code language identifier.";
146
+ };
147
+ };
148
+ };
149
+ readonly inlineCode: {
150
+ readonly name: "inlineCode";
151
+ readonly render: "TopikInlineCode";
152
+ readonly kind: "inline";
153
+ readonly description: "Inline code text.";
154
+ };
155
+ readonly image: {
156
+ readonly name: "image";
157
+ readonly render: "TopikImage";
158
+ readonly kind: "block";
159
+ readonly description: "Markdown image rendered through Topik asset resolution.";
160
+ readonly attributes: {
161
+ readonly src: {
162
+ readonly type: "string";
163
+ readonly required: true;
164
+ readonly description: "Image source URL.";
165
+ readonly assetReference: {
166
+ readonly slot: "image.src";
167
+ readonly role: "image";
168
+ };
169
+ };
170
+ readonly alt: {
171
+ readonly type: "string";
172
+ readonly description: "Accessible alternative text.";
173
+ };
174
+ readonly title: {
175
+ readonly type: "string";
176
+ readonly description: "Optional image title.";
177
+ };
178
+ };
179
+ };
180
+ readonly link: {
181
+ readonly name: "link";
182
+ readonly render: "TopikLink";
183
+ readonly kind: "inline";
184
+ readonly description: "Markdown link with optional application-level navigation interception.";
185
+ readonly attributes: {
186
+ readonly href: {
187
+ readonly type: "string";
188
+ readonly required: true;
189
+ readonly description: "Link target URL.";
190
+ readonly assetReference: {
191
+ readonly slot: "link.href";
192
+ readonly role: "download";
193
+ readonly conditional: "proven-download";
194
+ };
195
+ };
196
+ readonly title: {
197
+ readonly type: "string";
198
+ readonly description: "Optional link title.";
199
+ };
200
+ };
201
+ };
202
+ readonly mermaid: {
203
+ readonly name: "mermaid";
204
+ readonly render: "TopikMermaid";
205
+ readonly kind: "block";
206
+ readonly description: "Mermaid diagram rendered from a fenced mermaid code block.";
207
+ readonly attributes: {
208
+ readonly content: {
209
+ readonly type: "string";
210
+ readonly required: true;
211
+ readonly description: "Mermaid diagram source.";
212
+ };
213
+ };
214
+ };
215
+ readonly table: {
216
+ readonly name: "table";
217
+ readonly render: "TopikTable";
218
+ readonly kind: "block";
219
+ readonly description: "Markdown table.";
220
+ };
221
+ readonly tableRow: {
222
+ readonly name: "tableRow";
223
+ readonly render: "TopikTableRow";
224
+ readonly kind: "block";
225
+ readonly description: "A row inside a Markdown table.";
226
+ };
227
+ readonly tableCell: {
228
+ readonly name: "tableCell";
229
+ readonly render: "TopikTableCell";
230
+ readonly kind: "block";
231
+ readonly description: "A cell inside a Markdown table.";
232
+ };
233
+ readonly tableHeader: {
234
+ readonly name: "tableHeader";
235
+ readonly render: "TopikTableHeader";
236
+ readonly kind: "block";
237
+ readonly description: "A header cell inside a Markdown table.";
238
+ };
239
+ };
240
+ //#endregion
241
+ //#region src/registry.d.ts
242
+ export declare const TOPIK_CONTENT_SCHEMA_VERSION = "0.2.2";
243
+ export declare const CALLOUT_VARIANTS: readonly ["info", "tip", "warning", "danger"];
244
+ export declare const BADGE_VARIANTS: readonly ["neutral", "info", "success", "warning", "danger"];
245
+ export declare const QUIZ_QUESTION_TYPES: readonly ["single-choice", "multiple-choice"];
246
+ type TopikAssetReferenceRole = "image" | "image-light" | "image-dark" | "media" | "download";
247
+ interface TopikAssetReferenceDefinition {
248
+ slot: string;
249
+ role: TopikAssetReferenceRole;
250
+ conditional?: "proven-download";
251
+ }
252
+ type AttributeOptions<T extends Scalar> = {
253
+ required?: boolean;
254
+ default?: T;
255
+ description?: string;
256
+ asset?: boolean;
257
+ assetReference?: TopikAssetReferenceDefinition;
258
+ };
259
+ type AttributeDefinition = (AttributeOptions<string> & {
260
+ type: "string";
261
+ escapedWhitespace?: boolean;
262
+ /** Canonical text slots alone admit explicit authored templates. */
263
+ interpolation?: "text";
264
+ values?: never;
265
+ min?: never;
266
+ max?: never;
267
+ }) | (AttributeOptions<string> & {
268
+ type: "enum";
269
+ values: readonly string[];
270
+ min?: never;
271
+ max?: never;
272
+ }) | (AttributeOptions<number> & {
273
+ type: "number";
274
+ min?: number;
275
+ max?: number;
276
+ integer?: boolean;
277
+ values?: never;
278
+ }) | (AttributeOptions<boolean> & {
279
+ type: "boolean";
280
+ values?: never;
281
+ min?: never;
282
+ max?: never;
283
+ });
284
+ type ChildConstraint = "blocks" | "inline" | "none" | {
285
+ components: readonly string[];
286
+ min?: number;
287
+ } | {
288
+ nodes: readonly string[];
289
+ min?: number;
290
+ };
291
+ interface ValidationIssue {
292
+ id: string;
293
+ message: string;
294
+ /** Safe authored presentation option name, never a supplied value. */
295
+ option?: string;
296
+ }
297
+ /** Declarative schema accepted in application configuration. */
298
+ interface ComponentSchema {
299
+ kind: "block" | "inline";
300
+ render: string | boolean;
301
+ description?: string;
302
+ attributes: Record<string, AttributeDefinition>;
303
+ children: ChildConstraint;
304
+ /** Allows an empty block body to use a self-closing source tag. */
305
+ selfClosing?: boolean;
306
+ allowedParents?: readonly string[];
307
+ }
308
+ /** Runtime definitions additionally carry the canonical catalog's semantic rules. */
309
+ interface ComponentDefinition extends ComponentSchema {
310
+ /** Only for rules depending on sibling properties, such as quiz answers. */
311
+ validate?: (component: Component, effectiveProps: Record<string, AuthoredAttributeValue>) => ValidationIssue[];
312
+ }
313
+ type Registry = Record<string, ComponentDefinition>;
314
+ interface TopikComponentDefinition {
315
+ name: string;
316
+ kind: "block" | "inline";
317
+ render: string;
318
+ description: string;
319
+ attributes?: Record<string, AttributeDefinition>;
320
+ allowedChildren?: readonly string[];
321
+ requiredChildren?: readonly string[];
322
+ }
323
+ type TopikComponentAttributeDefinition = AttributeDefinition;
324
+ declare const authoredComponents: {
325
+ accordion: ComponentDefinition;
326
+ badge: ComponentDefinition;
327
+ callout: ComponentDefinition;
328
+ card: ComponentDefinition;
329
+ cardGrid: ComponentDefinition;
330
+ codeGroup: ComponentDefinition;
331
+ codeTab: {
332
+ kind: "block" | "inline";
333
+ render: string | boolean;
334
+ description?: string;
335
+ attributes: Record<string, AttributeDefinition>;
336
+ /** Allows an empty block body to use a self-closing source tag. */
337
+ selfClosing?: boolean;
338
+ allowedParents?: readonly string[];
339
+ /** Only for rules depending on sibling properties, such as quiz answers. */
340
+ validate?: (component: Component, effectiveProps: Record<string, AuthoredAttributeValue>) => ValidationIssue[];
341
+ children: {
342
+ nodes: string[];
343
+ min: number;
344
+ };
345
+ };
346
+ choice: ComponentDefinition;
347
+ explanation: ComponentDefinition;
348
+ figure: ComponentDefinition;
349
+ math: ComponentDefinition;
350
+ mathInline: ComponentDefinition;
351
+ question: ComponentDefinition;
352
+ quiz: ComponentDefinition;
353
+ step: ComponentDefinition;
354
+ steps: ComponentDefinition;
355
+ tab: ComponentDefinition;
356
+ tabs: ComponentDefinition;
357
+ underline: ComponentDefinition;
358
+ };
359
+ /** Canonical schemas are immutable; callers add custom names in a separate registry. */
360
+ export declare const components: Registry;
361
+ /** Legacy catalog metadata, derived from authored definitions plus native mdast nodes. */
362
+ export declare const topikComponents: Record<keyof typeof authoredComponents | keyof typeof nativeComponents, TopikComponentDefinition>;
363
+ type TopikComponentName = keyof typeof topikComponents;
364
+ /** Defaults are for reading/rendering; authored absence stays unchanged. */
365
+ export declare function getEffectiveProps(component: Pick<Component, "name" | "props">, registry?: Registry): Record<string, AuthoredAttributeValue>;
366
+ //#endregion
367
+ //#region src/validation.d.ts
368
+ export declare function validateDocument(document: ContentDocument, registry?: Registry): Diagnostic[];
369
+ //#endregion
370
+ //#region src/document-meaning.d.ts
371
+ /** Compare admitted authoring trees, retaining explicit heading IDs and every authored branch.
372
+ * Source positions, cosmetic spelling and derived metadata do not affect equality.
373
+ * This compares meaning; it does not validate arbitrary caller-constructed trees.
374
+ */
375
+ export declare function sameDocumentMeaning(left: ContentDocument, right: ContentDocument): boolean;
376
+ //#endregion
377
+ //#region src/parser.d.ts
378
+ export declare const FORMAT_VERSION = 1;
379
+ //#endregion
380
+ //#region src/writer.d.ts
381
+ export declare function writeDocument(document: ContentDocument, registry?: Registry, formatVersion?: number): string;
382
+ //#endregion
383
+ //#region src/markdown.d.ts
384
+ export declare function parseDocument(source: string, registry?: Registry, formatVersion?: number): ParseResult;
385
+ export declare function formatDocument(source: string, registry?: Registry): ParseResult & {
386
+ formatted?: string;
387
+ };
388
+ //#endregion
389
+ //#region src/assets.d.ts
390
+ /** Rewrite asset definitions once, preserving reference identity and unrelated navigation. */
391
+ export declare function rewriteAssets(document: ContentDocument, replace: (url: string) => string | undefined, registry?: Registry): ContentDocument;
392
+ //#endregion
393
+ //#region src/evaluate.d.ts
394
+ export declare class ContentEvaluationError extends Error {
395
+ constructor(message: string);
396
+ }
397
+ /** Resolve into a new, writable document; the authored branches remain untouched. */
398
+ export declare function evaluateDocument(document: ContentDocument, context: Record<string, unknown>, registry?: Registry): ContentDocument;
399
+ //#endregion
400
+ //#region src/limits.d.ts
401
+ /** Fixed admission limits, measured in UTF-16 code units and tree nodes. */
402
+ export declare const CONTENT_LIMITS: Readonly<{
403
+ sourceLength: 1000000;
404
+ /** Inline delimiter attempts; code-span attempts are weighted by delimiter run length. */
405
+ parserSteps: 4096;
406
+ treeDepth: 64;
407
+ treeNodes: 50000;
408
+ dataDepth: 160;
409
+ dataEntries: 500000;
410
+ dataStringLength: 1000000;
411
+ expressionLength: 16384;
412
+ expressionDepth: 32;
413
+ expressionNodes: 256;
414
+ /** Bounded escaped payload and row decorations, before reader allocation. */
415
+ presentationOutputLength: 8000000;
416
+ }>;
417
+ export declare class ContentLimitError extends Error {
418
+ readonly id = "topik-content-limit";
419
+ constructor(message: string);
420
+ }
421
+ //#endregion
422
+ //#region src/config.d.ts
423
+ interface TopikContentConfig {
424
+ /** Additional component schemas. Canonical Topik definitions cannot be replaced. */
425
+ components?: Record<string, ComponentSchema>;
426
+ /** Reader context used only by explicit evaluation or rendering. */
427
+ variables?: Record<string, unknown>;
428
+ }
429
+ interface ResolvedTopikContentConfig {
430
+ components: Registry;
431
+ variables: Record<string, unknown>;
432
+ }
433
+ /** Isolate schemas before validation; runtime variables are read without invoking accessors. */
434
+ export declare function mergeTopikContentConfig(extension?: TopikContentConfig): ResolvedTopikContentConfig;
435
+ //#endregion
436
+ //#region src/asset-reference-policy.d.ts
437
+ export declare const TOPIK_ASSET_REFERENCE_VERSION: "topik-asset-reference-v1";
438
+ /** Public grammar descriptor. Runtime admission uses an isolated boundary. */
439
+ export declare const TOPIK_GENERATED_ASSET_NAME_PATTERN: RegExp;
440
+ declare const topikGeneratedAssetNameBrand: unique symbol;
441
+ /** Compiler-generated name used by the compiled-content Asset reference protocol. */
442
+ type TopikGeneratedAssetName = string & {
443
+ readonly [topikGeneratedAssetNameBrand]: "TopikGeneratedAssetName";
444
+ };
445
+ export declare function isTopikGeneratedAssetName(value: unknown): value is TopikGeneratedAssetName;
446
+ export declare function parseTopikGeneratedAssetName(value: string): TopikGeneratedAssetName;
447
+ type TopikAssetReferenceValidation = {
448
+ valid: true;
449
+ kind: "asset";
450
+ name: TopikGeneratedAssetName;
451
+ } | {
452
+ valid: true;
453
+ kind: "local";
454
+ decodedPath: string;
455
+ } | {
456
+ valid: true;
457
+ kind: "external-https";
458
+ } | {
459
+ valid: false;
460
+ kind: "unsafe";
461
+ failureKind: "local" | "external";
462
+ };
463
+ /** Validate the URL-facing portion of topik-asset-reference-v1 without filesystem access. */
464
+ export declare function validateTopikAssetReference(reference: string): TopikAssetReferenceValidation;
465
+ //#endregion
466
+ //#region src/asset-references.d.ts
467
+ interface TopikAssetReferenceSlot {
468
+ node: "image" | "tag" | "link";
469
+ tag?: "figure";
470
+ attribute: "src" | "darkSrc" | "href";
471
+ slot: "image.src" | "figure.src" | "figure.darkSrc" | "link.href";
472
+ role: TopikAssetReferenceRole;
473
+ conditional?: "proven-download";
474
+ }
475
+ /**
476
+ * Closed registry for topik-asset-reference-v1. Extractors never infer a slot from an
477
+ * attribute name and never recursively inspect arbitrary strings.
478
+ */
479
+ export declare const topikAssetReferenceSlots: readonly [{
480
+ readonly node: "image";
481
+ readonly attribute: "src";
482
+ readonly slot: "image.src";
483
+ readonly role: "image";
484
+ }, {
485
+ readonly node: "tag";
486
+ readonly tag: "figure";
487
+ readonly attribute: "src";
488
+ readonly slot: "figure.src";
489
+ readonly role: "image-light";
490
+ }, {
491
+ readonly node: "tag";
492
+ readonly tag: "figure";
493
+ readonly attribute: "darkSrc";
494
+ readonly slot: "figure.darkSrc";
495
+ readonly role: "image-dark";
496
+ }, {
497
+ readonly node: "link";
498
+ readonly attribute: "href";
499
+ readonly slot: "link.href";
500
+ readonly role: "download";
501
+ readonly conditional: "proven-download";
502
+ }];
503
+ type TopikAssetOccurrenceKind = "asset" | "reserved-asset" | "local" | "external-https" | "unsafe";
504
+ interface TopikAssetOccurrenceSemantics {
505
+ alt?: string;
506
+ /** Authored text, detached from source nodes and never resolved by asset operations. */
507
+ altTemplate?: TextTemplate;
508
+ decorative?: boolean;
509
+ title?: string;
510
+ caption?: string;
511
+ captionTemplate?: TextTemplate;
512
+ lightDarkRole?: "light" | "dark";
513
+ linkLabel?: string;
514
+ }
515
+ interface TopikAssetOccurrence {
516
+ /** Stable normalized tree position, independent from other occurrences. */
517
+ position: string;
518
+ treePath: readonly number[];
519
+ slot: TopikAssetReferenceSlot["slot"];
520
+ role: TopikAssetReferenceRole;
521
+ /** Parser-produced destination used only to prove what the exact source bytes resolve to. */
522
+ parsedReference: string;
523
+ reference: string;
524
+ kind: TopikAssetOccurrenceKind;
525
+ semantics: TopikAssetOccurrenceSemantics;
526
+ }
527
+ interface ExtractTopikAssetOccurrencesOptions {
528
+ config?: TopikContentConfig;
529
+ /** Decoded regular-file paths. Enables unambiguous generic download-link occurrences. */
530
+ provenDownloadPaths?: ReadonlySet<string> | readonly string[];
531
+ /** Return generic-link candidates so a compiler can prove plain-mode downloads. */
532
+ includeGenericLinkCandidates?: boolean;
533
+ }
534
+ export declare function extractTopikAssetOccurrences(source: string, options?: ExtractTopikAssetOccurrencesOptions): TopikAssetOccurrence[];
535
+ /** Remove unsafe destinations from a preview tree, retaining readable descriptions. */
536
+ export declare function removeInvalidTopikAssetReferences(document: ContentDocument, source?: string, options?: {
537
+ config?: TopikContentConfig;
538
+ }): void;
539
+ //#endregion
540
+ //#region src/content.d.ts
541
+ type TopikContentNode = ContentDocument;
542
+ interface ParseTopikContentOptions {
543
+ /** @deprecated Compatibility-only; use validation/analysis options for diagnostic labels. */
544
+ file?: string;
545
+ /** @deprecated Compatibility-only; parsing always retains available source positions. */
546
+ location?: boolean;
547
+ config?: TopikContentConfig;
548
+ }
549
+ /** Parse the authoring tree. Use validateTopikContent at publication boundaries. */
550
+ export declare function parseTopikContent(source: string, options?: ParseTopikContentOptions): ContentDocument;
551
+ //#endregion
552
+ //#region src/diagnostics.d.ts
553
+ type TopikContentDiagnosticLevel = "debug" | "info" | "warning" | "error" | "critical";
554
+ interface ContentValidationIssue {
555
+ type: string;
556
+ lines: number[];
557
+ location?: {
558
+ file?: string;
559
+ };
560
+ error: {
561
+ id: string;
562
+ level: TopikContentDiagnosticLevel;
563
+ message: string;
564
+ };
565
+ }
566
+ interface TopikContentDiagnostic {
567
+ /** Stable diagnostic identifier. */
568
+ id: string;
569
+ /** Content node type that produced the diagnostic. */
570
+ type: string;
571
+ /** Diagnostic severity. */
572
+ level: TopikContentDiagnosticLevel;
573
+ /** Human-readable diagnostic message. */
574
+ message: string;
575
+ /** One-based source lines associated with the diagnostic, when available. */
576
+ lines: number[];
577
+ /** Optional sanitized source label. Absolute directories and URL secrets are removed. */
578
+ file?: string;
579
+ /** Authored template text slot, when available. */
580
+ attribute?: string;
581
+ /** Bounded authored variable path; context values are never included. */
582
+ variable?: string;
583
+ /** Supported code presentation option, with no authored/resolved values. */
584
+ option?: string;
585
+ /** One-based source column when available. */
586
+ column?: number;
587
+ }
588
+ /** Fixed public wording for link diagnostics; authored targets are never accepted as input. */
589
+ export declare function topikLinkDiagnosticMessage(id: string): string | undefined;
590
+ /** Re-apply fixed public messages and safe file labels when diagnostics cross package layers. */
591
+ export declare function sanitizeTopikContentDiagnostic(diagnostic: TopikContentDiagnostic): TopikContentDiagnostic;
592
+ export declare function toTopikContentDiagnostic(error: ContentValidationIssue): TopikContentDiagnostic;
593
+ /** Convert an untrusted diagnostic location to a browser-compatible safe label. */
594
+ export declare function sanitizeTopikDiagnosticFile(file: string | undefined): string | undefined;
595
+ //#endregion
596
+ //#region src/source.d.ts
597
+ interface ValidateTopikContentOptions {
598
+ file?: string;
599
+ config?: TopikContentConfig;
600
+ /** Accept compiler-produced references at a compiled-output boundary. */
601
+ allowCompiledAssetReferences?: boolean;
602
+ }
603
+ //#endregion
604
+ //#region src/validate.d.ts
605
+ interface ValidateTopikContentResult {
606
+ source: string;
607
+ valid: boolean;
608
+ errors: TopikContentDiagnostic[];
609
+ }
610
+ /** Source admission is the same boundary used by formatting and asset rewriting. */
611
+ export declare function validateTopikContent(source: string, options?: ValidateTopikContentOptions): ValidateTopikContentResult;
612
+ //#endregion
613
+ //#region src/format.d.ts
614
+ interface FormatTopikContentOptions extends ValidateTopikContentOptions {}
615
+ interface FormatTopikContentSuccess {
616
+ ok: true;
617
+ /** Exact caller-supplied source. */
618
+ source: string;
619
+ diagnostics: TopikContentDiagnostic[];
620
+ formatted: string;
621
+ }
622
+ interface FormatTopikContentFailure {
623
+ ok: false;
624
+ /** Exact caller-supplied source, unchanged and unformatted. */
625
+ source: string;
626
+ diagnostics: TopikContentDiagnostic[];
627
+ }
628
+ type FormatTopikContentResult = FormatTopikContentSuccess | FormatTopikContentFailure;
629
+ /** Validate source before formatting so unsupported input remains an exact opaque handoff. */
630
+ export declare function formatTopikContent(source: string, options?: FormatTopikContentOptions): FormatTopikContentResult;
631
+ //#endregion
632
+ //#region src/rewrite.d.ts
633
+ interface RewriteTopikAssetOccurrencesOptions extends ExtractTopikAssetOccurrencesOptions, ValidateTopikContentOptions {}
634
+ interface RewriteTopikAssetOccurrencesSuccess {
635
+ ok: true;
636
+ /** Exact caller-supplied source before rewriting. */
637
+ source: string;
638
+ diagnostics: TopikContentDiagnostic[];
639
+ /** Rewritten content. Replacements are validated, including compiler-generated Asset references. */
640
+ content: string;
641
+ }
642
+ interface RewriteTopikAssetOccurrencesFailure {
643
+ ok: false;
644
+ /** Exact caller-supplied source, unchanged and unformatted. */
645
+ source: string;
646
+ diagnostics: TopikContentDiagnostic[];
647
+ }
648
+ type RewriteTopikAssetOccurrencesResult = RewriteTopikAssetOccurrencesSuccess | RewriteTopikAssetOccurrencesFailure;
649
+ export declare function rewriteTopikAssetOccurrences(source: string, replace: (occurrence: TopikAssetOccurrence) => string | undefined, options?: RewriteTopikAssetOccurrencesOptions): RewriteTopikAssetOccurrencesResult;
650
+ //#endregion
651
+ //#region src/headings.d.ts
652
+ interface TopikHeading {
653
+ id: string;
654
+ level: number;
655
+ title: string;
656
+ }
657
+ export declare function assignTopikHeadingIds(document: ContentDocument): TopikHeading[];
658
+ //#endregion
659
+ //#region src/resource-references.d.ts
660
+ /** Version of the portable compiled-content resource reference contract. */
661
+ export declare const TOPIK_RESOURCE_REFERENCE_VERSION: 1;
662
+ interface TopikResourceReference {
663
+ /** Schema resource type; no repository or application namespace is implied. */
664
+ type: "WikiPage" | "Guide" | "CoursePage";
665
+ /** Schema resource name (at most 63 characters), independent of its public route. */
666
+ name: string;
667
+ /** URI query, including its leading '?' when present. */
668
+ search: string;
669
+ /** URI fragment, without a leading '#'. */
670
+ hash: string;
671
+ }
672
+ /** Parse an explicit resource identity without consulting routes or fetching a catalogue. */
673
+ export declare function parseTopikResourceReference(href: string): TopikResourceReference | null;
674
+ /** Serialize an identity as a canonical ref:// URI; this is not a browser-facing URL. */
675
+ export declare function serializeTopikResourceReference(reference: TopikResourceReference): string;
676
+ //#endregion
677
+ //#region src/navigation-rewrite.d.ts
678
+ interface TopikNavigationReference {
679
+ href: string;
680
+ kind: "link" | "card";
681
+ position: string;
682
+ }
683
+ type RewriteTopikNavigationResult = {
684
+ ok: true;
685
+ content: string;
686
+ changes: readonly (TopikNavigationReference & {
687
+ replacement: string;
688
+ })[];
689
+ diagnostics: TopikContentDiagnostic[];
690
+ } | {
691
+ ok: false;
692
+ source: string;
693
+ diagnostics: TopikContentDiagnostic[];
694
+ };
695
+ /** Rewrite actual navigation references, retaining definitions/scopes and every authored branch. */
696
+ export declare function rewriteTopikNavigationReferences(source: string, replace: (reference: TopikNavigationReference) => string | undefined, options?: ValidateTopikContentOptions): RewriteTopikNavigationResult;
697
+ //#endregion
698
+ //#region src/links.d.ts
699
+ type ValidationError = {
700
+ id: string;
701
+ level: "error";
702
+ message: string;
703
+ };
704
+ type TopikContentLinkKind = "card" | "link";
705
+ interface TopikContentLink {
706
+ file?: string;
707
+ href: string;
708
+ kind: TopikContentLinkKind;
709
+ lines: number[];
710
+ }
711
+ interface TopikAnalyzedHeading extends TopikHeading {
712
+ file?: string;
713
+ lines: number[];
714
+ }
715
+ interface AnalyzeTopikContentResult {
716
+ diagnostics: TopikContentDiagnostic[];
717
+ headings: TopikAnalyzedHeading[];
718
+ links: TopikContentLink[];
719
+ }
720
+ interface AnalyzeTopikContentOptions {
721
+ file?: string;
722
+ config?: TopikContentConfig;
723
+ }
724
+ export declare function analyzeTopikContent(source: string, options?: AnalyzeTopikContentOptions): AnalyzeTopikContentResult;
725
+ export declare function validateTopikHref(value: unknown): ValidationError[];
726
+ /** Admit only resolved hrefs at a boundary that can emit browser navigation. */
727
+ export declare function validateTopikBrowserHref(value: unknown): ValidationError[];
728
+ export declare function validateTopikNavigationHref(value: unknown): ValidationError[];
729
+ /** Remove invalid navigation attributes before a renderer can emit a browser-facing URL. */
730
+ export declare function removeInvalidTopikNavigationReferences(root: ContentDocument): void;
731
+ //#endregion
732
+ //#region src/render.d.ts
733
+ /** Framework-independent, serializable output. It contains no executable values. */
734
+ type RenderableTreeNode = ContentTag | string | number | boolean | null | RenderableTreeNode[];
735
+ export declare class ContentTag {
736
+ name: string;
737
+ attributes: Record<string, unknown>;
738
+ children: RenderableTreeNode[];
739
+ readonly type = "element";
740
+ constructor(name: string, attributes?: Record<string, unknown>, children?: RenderableTreeNode[]);
741
+ }
742
+ export declare function isContentTag(value: unknown): value is ContentTag;
743
+ /** Render a validated authored document through a separate evaluated document. */
744
+ export declare function transformTopikContent(document: ContentDocument, options?: TopikContentConfig): RenderableTreeNode;
745
+ //#endregion
746
+ //#region src/compiled.d.ts
747
+ interface CompiledTopikContent {
748
+ sourceFormat: "topik";
749
+ topikSchemaVersion: string;
750
+ formatVersion: number;
751
+ configHash: string;
752
+ renderableTree: RenderableTreeNode;
753
+ diagnostics: TopikContentDiagnostic[];
754
+ }
755
+ //#endregion
756
+ //#region src/compile.d.ts
757
+ interface CompileTopikContentOptions {
758
+ file?: string;
759
+ config?: TopikContentConfig;
760
+ onDiagnostic?: (diagnostic: TopikContentDiagnostic) => void;
761
+ }
762
+ interface CompileTopikContentSuccess {
763
+ ok: true;
764
+ /** Exact caller-supplied source. */
765
+ source: string;
766
+ diagnostics: TopikContentDiagnostic[];
767
+ tree: RenderableTreeNode;
768
+ }
769
+ interface CompileTopikContentFailure {
770
+ ok: false;
771
+ /** Exact caller-supplied source, unchanged and never transformed. */
772
+ source: string;
773
+ diagnostics: TopikContentDiagnostic[];
774
+ }
775
+ type CompileTopikContentResult = CompileTopikContentSuccess | CompileTopikContentFailure;
776
+ /** Admit source once, including compiled asset references, and produce a reader tree. */
777
+ export declare function compileTopikContent(source: string, options?: CompileTopikContentOptions): CompileTopikContentResult;
778
+ //#endregion
779
+ //#region src/index.d.ts
780
+ export type TopikComponentKind = "block" | "inline";
781
+ export type TopikAttributeType = "string" | "number" | "boolean" | "enum";
782
+ //#endregion
783
+ export type { AnalyzeTopikContentOptions, AnalyzeTopikContentResult, AttributeDefinition, AuthoredAttributeValue, Branch, ChildConstraint, CodeLineSelection, CodePresentation, CodePresentationEffectiveOptions, CodePresentationOptions, CodeTemplate, CompileTopikContentFailure, CompileTopikContentOptions, CompileTopikContentResult, CompileTopikContentSuccess, CompiledTopikContent, Component, ComponentDefinition, ComponentSchema, Conditional, ContentDocument, Diagnostic, Expression, ExtractTopikAssetOccurrencesOptions, FormatTopikContentFailure, FormatTopikContentOptions, FormatTopikContentResult, FormatTopikContentSuccess, ParseResult, ParseTopikContentOptions, Registry, RenderableTreeNode, ResolvedTopikContentConfig, RewriteTopikAssetOccurrencesFailure, RewriteTopikAssetOccurrencesOptions, RewriteTopikAssetOccurrencesResult, RewriteTopikAssetOccurrencesSuccess, RewriteTopikNavigationResult, Scalar, TextTemplate, TopikAnalyzedHeading, TopikAssetOccurrence, TopikAssetOccurrenceKind, TopikAssetOccurrenceSemantics, TopikAssetReferenceDefinition, TopikAssetReferenceRole, TopikAssetReferenceSlot, TopikAssetReferenceValidation, TopikComponentAttributeDefinition, TopikComponentDefinition, TopikComponentName, TopikContentConfig, TopikContentDiagnostic, TopikContentDiagnosticLevel, TopikContentLink, TopikContentLinkKind, TopikContentNode, TopikGeneratedAssetName, TopikHeading, TopikNavigationReference, TopikResourceReference, ValidateTopikContentOptions, ValidateTopikContentResult, Variable };