Files
toco-react-template/template/script/GenerateMetaPlugin.js
2024-10-14 18:51:44 +08:00

71 lines
1.8 KiB
JavaScript

const fs = require('fs');
const path = require('path');
const glob = require('glob');
// 递归地构建嵌套结构
function buildNestedStructure(filePaths) {
const root = [];
filePaths.forEach((filePath) => {
const parts = filePath.split('/').slice(2, -1); // 去掉 'src/pages' 'meta.json'
let current = root;
parts.forEach((part, index) => {
const find = current.find((item) => item._path === part);
if (find) {
current = find;
} else {
current.push({
_path: part,
_children: [],
});
current = current[current.length - 1];
}
if (index === parts.length - 1) {
const content = fs.readFileSync(filePath, 'utf-8');
Object.assign(current, JSON.parse(content), {
_fullpath: parts.join('/'),
});
}
current = current._children;
});
});
return root;
}
// 自定义插件:用于生成 meta.js 文件
class GenerateMetaPlugin {
apply(compiler) {
compiler.hooks.emit.tapAsync(
'GenerateMetaPlugin',
(compilation, callback) => {
const metaFiles = glob.sync('src/pages/**/meta.json');
const metaInfo = buildNestedStructure(metaFiles);
const output = `export const metaInfo = ${JSON.stringify(metaInfo, null, 2)};`;
const outputPath = path.resolve(__dirname, '../src/meta.js');
if (fs.existsSync(outputPath)) {
const existingContent = fs.readFileSync(outputPath, 'utf8');
if (existingContent === output) {
// 文件已存在且内容相同,跳过文件生成
return callback();
}
}
fs.writeFileSync(outputPath, output, 'utf-8');
console.log('meta.js has been generated successfully!');
callback();
},
);
}
}
module.exports = GenerateMetaPlugin;