const fs = require("fs");
const babylon = require("babylon");
const traverse = require("babel-traverse").default;
const {
transformFromAst
} = require('babel-core');
module.exports = {
// 通过 babylon 将源码生成AST:可以将 ES6 语法转换成 ES5 的语法·
getAST: (path) => {
const source = fs.readFileSync(path, "utf-8");
return babylon.parse(source, {
sourceType: "module",
});
},
//获取依赖文件
getDependencies: (ast) => {
const getDependencies = [];
traverse(ast, {
ImportDeclaration: ({
node
}) => {
getDependencies.push(node.source.value);
},
});
return getDependencies;
},
//将AST重新生成源码
transform: (ast) => {
const {
code
} = transformFromAst(ast, null, {
presets: ['env'],
});
return code;
},
};
webpack内部机制:
动手实现:
emitFiles() {
const outputPath = path.join(this.output.path, this.output.filename);
let modules = '';
this.modules.map((_module) => {
modules += `'${ _module.filename }': function (require, module, exports) { ${ _module.transformCode } },`
});
const bundle = `
(function(modules) {
function require(fileName) {
//获取文件对应的源码
const fn = modules[fileName];
const module = { exports : {} };
fn(require, module, module.exports);
return module.exports;
}
require('${this.entry}');
})({${modules}})
`;
fs.writeFileSync(outputPath, bundle, 'utf-8');
}
输出: