前往小程序,Get更优阅读体验!
立即前往
首页
学习
活动
专区
工具
TVP
发布
社区首页 >专栏 >『手撕Vue-CLI』编译模板『下』

『手撕Vue-CLI』编译模板『下』

原创
作者头像
BNTang
修改2024-05-27 01:33:28
141
修改2024-05-27 01:33:28
举报

前言

经『手撕Vue-CLI』编译模板『上』已经将大概流程编写好了,接下来就是将模板中的变量替换成用户输入的内容。

让用户填写配置信息

vue-advanced-template 模板中,有一个 ask.js 文件,这个文件是用来获取用户输入的信息的,这个文件的内容已经给大家查看过了,所以这里就不再赘述。

直接编写实现代码:

代码语言:javascript
复制
.use(async (files, metal, done) => {
    // 获取元数据
    const args = require(askPath);
    // 执行询问
    const result = inquirer.prompt(args);
    // 将询问的结果挂载到 metal.metadata() 上,这样在下一个插件中就可以获取到询问的结果
    const data = await result;
    const meta = metal.metadata();
    Object.assign(meta, data);
    done();
})
.use(async (files, metal, done) => {
    // 从 metal.metadata() 获取到用户输入的数据
    const meta = metal.metadata();
    console.log(meta);
    done();
})

这里通过 inquirer.prompt(args) 获取到用户输入的数据,然后将这个数据挂载到 metal.metadata() 上,这样在下一个插件中就可以获取到用户输入的数据了。

替换模板中的变量

vue-advanced-template 模板中,有一个 package.json 文件,这个文件是用来替换模板中的变量的,这个文件的内容已经给大家查看过了,里面写的是 ejs 的语法,所以这里就不再赘述。

先根据 files 过滤出是否是模板文件,如果是模板文件,就将文件内容替换成用户输入的内容。

代码语言:javascript
复制
Reflect.ownKeys(files).forEach(async (file) => {
    // 判断是否是模板文件
    if (file.includes('js') || file.includes('json')) {
        console.log(files[file].contents.toString());
    }
});

这里通过 Reflect.ownKeys(files) 获取到所有的文件名,然后通过 file.includes('js') || file.includes('json') 判断是否是模板文件,如果是模板文件,就将文件内容打印出来,内容如下图所示:

接下来需要在判断一下当前文件的内容是否需要编译可以用是否包含 <% 来判断,如果包含 <% 就需要编译,否则就不需要编译。

代码语言:javascript
复制
Reflect.ownKeys(files).forEach(async (file) => {
    // 判断是否是模板文件
    if (file.includes('js') || file.includes('json')) {
        // 判断是否需要编译
        if (files[file].contents.toString().includes('<%')) {
            console.log(files[file].contents.toString());
        }
    }
});

到这里就可以拿到具体的文件了,那么问题来了如何替换呢?这里需要用到一个 consolidate 库,这个库是用来编译模板的,这里使用 consolidate.ejs.render 方法来编译模板。

先安装 consolidate 库,这里我不采用最新版本,因为我不使用 ES6 的语法,所以我安装 consolidate@0.15.1 版本。

代码语言:shell
复制
npm install consolidate@0.15.1

导入 consolidate.ejs.render 方法:

代码语言:javascript
复制
let {render} = require('consolidate').ejs;
render = promisify(render);

这里使用 promisify 方法将 render 方法转换成 Promise 方法,这样就可以使用 await 来等待编译结果了。

接下来的代码我就一步到位了,直接上代码:

代码语言:javascript
复制
Reflect.ownKeys(files).forEach(async (file) => {
    // 判断是否是模板文件
    if (file.includes('js') || file.includes('json')) {
        // 判断是否需要编译
        const fileContent = files[file].contents.toString();
        if (fileContent.includes('<%')) {
            const result = await consolidate.ejs.render(fileContent, meta);
            files[file].contents = Buffer.from(result);
        }
    }
});

这里通过 consolidate.ejs.render(fileContent, meta) 编译模板,然后将编译结果赋值给 files[file].contents,这样就完成了模板的编译。

测试

当我进行使用 nue-cli create 创建编译模板项目时,出现 Error: Cannot find module 'ejs' 错误,这是因为 consolidate 库需要依赖 ejs 库,所以需要安装 ejs 库。

代码语言:shell
复制
npm install ejs

然后再次使用 nue-cli create 创建编译模板项目,编译成功了,内容如下图所示:

我正在参与2024腾讯技术创作特训营最新征文,快来和我瓜分大奖!

原创声明:本文系作者授权腾讯云开发者社区发表,未经许可,不得转载。

如有侵权,请联系 cloudcommunity@tencent.com 删除。

原创声明:本文系作者授权腾讯云开发者社区发表,未经许可,不得转载。

如有侵权,请联系 cloudcommunity@tencent.com 删除。

评论
登录后参与评论
0 条评论
热度
最新
推荐阅读
目录
  • 前言
  • 让用户填写配置信息
  • 替换模板中的变量
  • 测试
领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档