// Build the static API reference from the canonical Markdown, without runtime dependencies.
// Supports the headings, paragraphs, lists, links, rules, and fenced code used by this reference.
import { readFileSync, writeFileSync } from 'node:fs';
import { fileURLToPath } from 'node:url';
const source = new URL('../docs/API_Documentation.md', import.meta.url);
const output = new URL('../meshview/static/api.html', import.meta.url);
const markdown = readFileSync(source, 'utf8');
const themeStyles = readFileSync(new URL('../meshview/templates/theme-styles.html', import.meta.url), 'utf8');
const escape = text => text.replace(/[&<>"']/g, char => ({
'&':'&', '<':'<', '>':'>', '"':'"', "'":'''
}[char]));
const slug = text => text.toLowerCase().replace(/`/g, '').replace(/[^a-z0-9]+/g, '-').replace(/^-|-$/g, '');
function inline(text) {
const tokens = /`([^`]+)`|\[([^\]]+)\]\(([^)]+)\)|\*\*([^*]+)\*\*/g;
let html = '', cursor = 0;
for (const match of text.matchAll(tokens)) {
html += escape(text.slice(cursor, match.index));
if (match[1] !== undefined) html += `${escape(match[1])}`;
else if (match[2] !== undefined && /^(#|\/|https?:\/\/)/.test(match[3])) {
html += `${escape(match[2])}`;
} else if (match[4] !== undefined) html += `${escape(match[4])}`;
else html += escape(match[0]);
cursor = match.index + match[0].length;
}
return html + escape(text.slice(cursor));
}
const endpoints = [];
const blocks = [];
const lines = markdown.split('\n');
let sectionOpen = false;
for (let i = 0; i < lines.length;) {
const line = lines[i];
if (!line.trim()) { i++; continue; }
if (line.startsWith('```')) {
const language = line.slice(3).trim(); const code = []; i++;
while (i < lines.length && !lines[i].startsWith('```')) code.push(lines[i++]);
if (i === lines.length) throw new Error('Unclosed code fence');
if (language === 'json') JSON.parse(code.join('\n'));
blocks.push(`
${escape(code.join('\n'))}`);
i++; continue;
}
const heading = line.match(/^(#{1,3})\s+(.+)$/);
if (heading) {
if (sectionOpen) { blocks.push(''); sectionOpen = false; }
const level = heading[1].length; const text = heading[2];
if (level === 3 && text.startsWith('GET ')) {
const id = slug(text); endpoints.push({text:text.replace(/`/g, ''),id});
blocks.push(`${inline(paragraph.join(' '))}
`); } if (sectionOpen) blocks.push('