@intlayer/core
Version:
Includes core Intlayer functions like translation, dictionary, and utility functions shared across multiple packages.
74 lines (72 loc) • 2.13 kB
JavaScript
import { validateHTML } from "../html/validateHTML.mjs";
//#region src/transpiler/markdown/validateMarkdown.ts
/**
* Strips fenced code blocks and inline code from markdown content so that
* HTML-like syntax inside code is not mistakenly validated.
*/
const stripCode = (content) => {
const lines = content.split("\n");
const result = [];
let inCodeBlock = false;
let openFence = null;
for (const line of lines) {
const fence = line.match(/^[\s>]*(`{3,}|~{3,})/);
if (!inCodeBlock) if (fence) {
inCodeBlock = true;
openFence = fence[1];
result.push("");
} else result.push(line.replace(/`[^`\n]+`/g, (m) => " ".repeat(m.length)));
else {
if (fence && fence[1][0] === openFence[0] && fence[1].length >= openFence.length) {
inCodeBlock = false;
openFence = null;
}
result.push("");
}
}
return result.join("\n");
};
const validateCodeBlocks = (content) => {
const issues = [];
const lines = content.split("\n");
let inCodeBlock = false;
let openFence = null;
let openLineNumber = -1;
for (let i = 0; i < lines.length; i++) {
const fence = lines[i].match(/^[\s>]*(`{3,}|~{3,})/);
if (!inCodeBlock) {
if (fence) {
inCodeBlock = true;
openFence = fence[1];
openLineNumber = i + 1;
}
} else if (fence && fence[1][0] === openFence[0] && fence[1].length >= openFence.length) {
inCodeBlock = false;
openFence = null;
}
}
if (inCodeBlock) issues.push({
type: "error",
message: `Unclosed code block (opened at line ${openLineNumber})`
});
return issues;
};
/**
* Validates markdown content for structural correctness:
* - All fenced code blocks are properly closed
* - HTML tags are properly nested and closed
*
* HTML inside code blocks is excluded from HTML validation.
*/
const validateMarkdown = (content) => {
const codeIssues = validateCodeBlocks(content);
const htmlIssues = validateHTML(stripCode(content)).issues;
const issues = [...codeIssues, ...htmlIssues];
return {
valid: issues.filter((i) => i.type === "error").length === 0,
issues
};
};
//#endregion
export { validateMarkdown };
//# sourceMappingURL=validateMarkdown.mjs.map