import fs from 'fs' import path from 'path' import { camelize } from '@vue/shared' import glob from 'fast-glob' import { docRoot } from '../../../internal/build-utils/src' import type { Plugin } from 'vite' type Append = Record<'headers' | 'footers' | 'scriptSetups', string[]> let compPaths: string[] export function MarkdownTransform(): Plugin { return { name: 'antd-xv-md-transform', enforce: 'pre', async buildStart() { const pattern = `/component` compPaths = await glob(pattern, { cwd: docRoot, absolute: true, onlyDirectories: true, }) }, async transform(code, id) { if (!id.endsWith('.md')) return if (!id.includes('/component')) return const componentId = path.basename(id, '.md') const append: Append = { headers: [], footers: [], scriptSetups: getExampleImports(componentId), } code = transformVpScriptSetup(code, append) if (compPaths.some((compPath) => id.startsWith(compPath))) { code = transformComponentMarkdown(id, componentId, code, append) } return combineMarkdown( code, [combineScriptSetup(append.scriptSetups), ...append.headers], append.footers ) }, } } const combineScriptSetup = (codes: string[]) => `\n ` const combineMarkdown = ( code: string, headers: string[], footers: string[] ) => { const frontmatterEnds = code.indexOf('---\n\n') const firstHeader = code.search(/\n#{1,6}\s.+/) const sliceIndex = firstHeader < 0 ? frontmatterEnds < 0 ? 0 : frontmatterEnds + 4 : firstHeader if (headers.length > 0) code = code.slice(0, sliceIndex) + headers.join('\n') + code.slice(sliceIndex) code += footers.join('\n') return `${code}\n` } const vpScriptSetupRE = /([\s\S]*)<\/vp-script>/ const transformVpScriptSetup = (code: string, append: Append) => { const matches = code.match(vpScriptSetupRE) if (matches) code = code.replace(matches[0], '') const scriptSetup = matches?.[3] ?? '' if (scriptSetup) append.scriptSetups.push(scriptSetup) return code } const transformComponentMarkdown = ( id: string, componentId: string, code: string, append: Append ) => { return code } const getExampleImports = (componentId: string) => { const examplePath = path.resolve(docRoot, 'examples', componentId) if (!fs.existsSync(examplePath)) return [] const files = fs.readdirSync(examplePath) const imports: string[] = [] for (const item of files) { if (!/\.vue$/.test(item)) continue const file = item.replace(/\.vue$/, '') const name = camelize(`Ax-${componentId}-${file}`) imports.push( `import ${name} from '../examples/${componentId}/${file}.vue'`, `import ${name}Setup from '../examples-setup/${componentId}/${file}.vue'` ) } return imports }