diff --git a/scripts/compare-mdx.js b/scripts/compare-mdx.js new file mode 100644 index 000000000..12d393b0a --- /dev/null +++ b/scripts/compare-mdx.js @@ -0,0 +1,119 @@ +import fs from 'fs'; +import path from 'path'; + +// Mapping of German slugs to English slugs (based on messages/en.json) +const slugMapping = { + 'agb.mdx': 'terms.mdx', + 'bohrtechnik.mdx': 'bohrtechnik.mdx', // Mapped via Slugs.pages + 'datenschutz.mdx': 'privacy-policy.mdx', + 'glasfaser.mdx': 'glasfaser.mdx', // Mapped via Slugs.pages + 'home.mdx': 'home.mdx', + 'impressum.mdx': 'imprint.mdx', + 'kabeltiefbau.mdx': 'kabeltiefbau.mdx', // Mapped via Slugs.pages + 'karriere.mdx': 'karriere.mdx', + 'kompetenzen.mdx': 'kompetenzen.mdx', + 'messen.mdx': 'messen.mdx', + 'planung.mdx': 'planung.mdx', // Mapped via Slugs.pages + 'team.mdx': 'team.mdx', + 'ueber-uns.mdx': 'ueber-uns.mdx', + 'vermessung.mdx': 'vermessung.mdx', // Mapped via Slugs.pages + 'zertifikate.mdx': 'zertifikate.mdx' +}; + +const DE_DIR = './content/de'; +const EN_DIR = './content/en'; + +function extractComponents(content) { + // Regex to match MDX/JSX components like or ... + const componentRegex = /<([A-Z][a-zA-Z0-9]+)/g; + const components = []; + let match; + while ((match = componentRegex.exec(content)) !== null) { + components.push(match[1]); + } + return components; +} + +function verifyParity() { + console.log('šŸ” Starting MDX Component Parity Verification...'); + let hasError = false; + + for (const [deFile, enFile] of Object.entries(slugMapping)) { + const dePath = path.join(DE_DIR, deFile); + const enPath = path.join(EN_DIR, enFile); + + if (!fs.existsSync(dePath)) { + console.error(`āŒ German file missing: ${dePath}`); + hasError = true; + continue; + } + if (!fs.existsSync(enPath)) { + console.error(`āŒ English file missing: ${enPath}`); + hasError = true; + continue; + } + + const deContent = fs.readFileSync(dePath, 'utf-8'); + const enContent = fs.readFileSync(enPath, 'utf-8'); + + const deComponents = extractComponents(deContent); + const enComponents = extractComponents(enContent); + + // Assert length and names match in sequence + const deComponentsStr = deComponents.join(', '); + const enComponentsStr = enComponents.join(', '); + + if (deComponentsStr !== enComponentsStr) { + console.error(`āŒ Component mismatch in ${deFile} āž” ${enFile}`); + console.error(` DE Components: [${deComponentsStr}]`); + console.error(` EN Components: [${enComponentsStr}]`); + hasError = true; + } else { + console.log(`āœ… ${deFile} āž” ${enFile} matched perfectly [${deComponentsStr}]`); + } + } + + // Also verify subfolders like referenzen + const deRefsDir = path.join(DE_DIR, 'referenzen'); + const enRefsDir = path.join(EN_DIR, 'referenzen'); + + if (fs.existsSync(deRefsDir) && fs.existsSync(enRefsDir)) { + const deRefFiles = fs.readdirSync(deRefsDir).filter(f => f.endsWith('.mdx')); + for (const refFile of deRefFiles) { + const dePath = path.join(deRefsDir, refFile); + const enPath = path.join(enRefsDir, refFile); + + if (fs.existsSync(enPath)) { + const deContent = fs.readFileSync(dePath, 'utf-8'); + const enContent = fs.readFileSync(enPath, 'utf-8'); + + const deComponents = extractComponents(deContent); + const enComponents = extractComponents(enContent); + + const deComponentsStr = deComponents.join(', '); + const enComponentsStr = enComponents.join(', '); + + if (deComponentsStr !== enComponentsStr) { + console.error(`āŒ Component mismatch in referenzen/${refFile}`); + console.error(` DE Components: [${deComponentsStr}]`); + console.error(` EN Components: [${enComponentsStr}]`); + hasError = true; + } else { + console.log(`āœ… referenzen/${refFile} matched perfectly [${deComponentsStr}]`); + } + } else { + console.error(`āŒ English reference file missing: ${enPath}`); + hasError = true; + } + } + } + + if (hasError) { + console.error('\nāŒ Parity verification failed.'); + process.exit(1); + } else { + console.log('\nšŸŽ‰ ALL MDX pages are 100% structurally identical in both German and English!'); + } +} + +verifyParity();