-
Notifications
You must be signed in to change notification settings - Fork 0
Expand file tree
/
Copy pathmarkdown-renderer.ts
More file actions
58 lines (45 loc) · 1.95 KB
/
Copy pathmarkdown-renderer.ts
File metadata and controls
58 lines (45 loc) · 1.95 KB
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
/**
* Markdown renderer for CLI output.
*
* Renders a small subset of markdown (headers, lists, inline code, code
* fences, links) into ANSI-colored output using chalk directly.
*
* Replaces the previous blessed-style tag renderer. The API signature
* (renderMarkdownToTags, RendererOptions) is preserved for backward
* compatibility even though the name "ToTags" is a misnomer — the output
* is actually chalk ANSI strings.
*/
import chalk from 'chalk';
export interface RendererOptions {
maxSize?: number; // characters
}
export function renderMarkdownToTags(input: string, opts?: RendererOptions): string {
const maxSize = opts?.maxSize ?? 100_000;
if (!input) return '';
if (input.length > maxSize) return input;
let out = String(input);
// Normalize line endings
out = out.replace(/\r\n?/g, '\n');
// Code fences: ```lang\n...``` -> header and indented code lines
out = out.replace(/```(?:([a-zA-Z0-9_+-]+)\n)?([\s\S]*?)```/g, (_m, lang, code) => {
const language = lang || 'code';
const lines = String(code).split('\n');
const renderedLines = lines.map(l => ` ${chalk.gray(l)}`).join('\n');
return `\n${chalk.cyan(chalk.bold(`--- ${language} ---`))}\n${renderedLines}\n`;
});
// Headers: # Header -> bold white
out = out.replace(/^#{1,6}\s*(.*)$/gm, (_m, txt) => {
const t = String(txt).trim();
return chalk.white(chalk.bold(t));
});
// Inline code: `code` -> magenta
out = out.replace(/`([^`]+)`/g, (_m, c) => chalk.magenta(c));
// Links: [text](url) -> underlined blue text (url shown after)
out = out.replace(/\[([^\]]+)\]\(([^)]+)\)/g, (_m, text, url) => `${chalk.blue(chalk.underline(text))} (${url})`);
// Unordered list markers: - or * -> bullet
out = out.replace(/^(\s*)[-*]\s+/gm, (_m, indent) => `${indent}• `);
// Ordered list: 1. -> keep as is but normalized spacing
out = out.replace(/^\s*\d+\.\s+/gm, (m) => m.replace(/\s+/g, ' '));
return out;
}
export default renderMarkdownToTags;