前端工程化之脚手架工具

脚手架工具

常用脚手架工具

  • React项目create-react-app
  • Vue项目vue-cli
  • Angular项目angular-cli
  • Yeoman通用型脚手架工具
  • Plop创建一个组件/模块所需要的文件(类似于Yeoman的sub-generator)

脚手架工具的工作原理

脚手架的重要原理就是解析命令行输入的参数(主要解析command 和 options),根据参数来运行node.js代码。解析命令行参数常用的npm包有yargs和commander。

使用node.js来开发一个小型脚手架。

  • 创建sample-scaffolding文件夹,使用npm init初始化
  • 在package.json中添加”bin“: "cli.js"用于指定该脚手架的命令行入口文件为cli.js。关于Node命令行参考阮一峰老师的文章
    • "bin": { "sample-scaffolding": "cli.js" }表示sample-scaffolding是在终端输入的命令,该命令的真实入口文件是当前目录下的cli.js。"bin"字段用来指示命令名与可执行脚本文件的映射关系。当一个npm包的package.json中包含了bin字段时,在安装该包以后,会在项目的node_modules的.bin文件夹下自动生成一个软连接,指向bin字段的可执行脚本(全局安装的情况下,是在全局的node_modules目录下)。
  • 创建模板:在项目根路径下创建templates文件夹来存储模板文件,如这里创建了templates/index.html和templates/style.css。
  • cli.js的内容:
    • Node CLI应用入口文件必须要有#!/usr/bin/env node文件头,用于指定使用node解释器来执行该脚本文件,其中user/bin/env用来在不同主机和系统下找到node可执行文件的位置。
    • 如果是Linux或者MacOS系统,则需要修改文件的权限为755(文件拥有者可读可写可执行)chmod 755 cli.js
    • 业务代码
      • 获取命令行参数可以使用process.argv,使用yargs包可以更加方便简洁npm install yargs
      • 通过命令行交互询问用户问题,安装npm install inquirer
      • 根据用户回答的结果生成文件,需要安装模板引擎npm install ejs来解析模板文件
// cli.js
const inquirer = require('inquirer');
const ejs = require('ejs');

inquirer.propmt([
  {
    type: 'input',
    name: 'name',
    message: 'Project name?'
  }
])
.then(answers => {
  // 根据用户回答的结果answers结合模板文件,生成新文件
  // 模板目录
  const tmplDir = path.join(__dirname, 'templates');
  // 目标目录, 这里是程序执行的当前路径
  const destDir = process.cwd();
  // 将模板下的模板文件全部输出到目标目录
  fs.readdir(tmplDir, (err, files) => {
    if(err) {
      throw err;
    }
    files.forEach(file => {
      // 通过模板引擎渲染模板文件,将结果写入新的文件中。
      ejs.renderFile(path.join(tmplDir, file), answers, (err, result) => {
        if(err) throw err;
        // 将结果写入文件
        fs.writeFileSync(path.join(destDir, file), result);
      })
    })
  })
})
  • 使用npm link全局注册
  • 在命令行中使用sample-scaffolding命令执行

Yeoman

基本使用
  • 全局安装yeoman:npm install yo -g
  • 全局安装generator:安装项目对应的generator包,让yeoman运行generator包来创建项目基本结构。yeoman + generator包 = 脚手架工具。比如安装generator-node来创建一个node项目:npm install generator-node -g
  • 运行脚手架工具:yo node,注意要去掉前缀generator
sub-generator

在已有项目中再创建一些项目文件(结构),就是在generator创建的项目中继续generator一些文件,就是sub-generator。

  • 使用方式(以上面的node项目为例):yo node: cli
  • 语法:yo <generator-name>: <sub-generator-name>
  • 注意:并非所有的generator包都包含sub-generator(根据generator文档查看),有的时候需要我们自己去定义sub-generator
npm安装二进制文件时的镜像配置

有时候npm安装二进制包时,通过对应包的镜像配置来加速下载。
npm安装二进制包的镜像配置

创建自定义generator
  • Generator本质上就是一个NPM模块
  • Generator包含两个组成部分
    • 组装指令
    • 模板文件
  • Generator需要特定的文件结构
    在这里插入图片描述
    • app/index.js为生成器组装指令文件
  • sub-generator则在该Generator目录内与app目录同级,例如这里的component目录
    在这里插入图片描述
  • generator的名称要求是有generator-前缀generator-<name>,否则yeoman是无法找到的。
创建generator
  • 新建文件夹作为自定义generator的项目根路径,文件夹命名为generator-<name>
  • 使用npm init初始化package.json文件,注意需要手动更改一些信息。
    在这里插入图片描述
  • 安装最新版的yeoman-generator作为依赖npm install yeoman-generator -S
  • 在项目文件夹中,创建generator/app/index.js文件,作为generator的核心入口。
    • index.js需要导出一个继承自Yeoman Generator的类型
    • Yeoman Generator会在工作时自动调用此类型中定义的一些生命周期方法
    • 在这些生命周期方法中,通过调用父类的API实现功能,如文件写入等
  • 完成generator后,在项目根路径使用npm link命令将generator包链接到本地的全局npm包所在地,这样就相当于使用了全局安装。
使用自定义generator
  • 新建文件夹作为项目根路径
  • 使用yo <name>来使用自定义的generator作为脚手架工具来生成项目结构。
使用模板文件来创建自定义generator
  • 在app/目录下创建一个templates/目录,用于存放模板文件
  • 模板文件使用的是EJS模板引擎的语法规范
  • 同时,在index.js中需要使用根据模板方式创建项目的API方法
接收用户输入的数据

有很多时候需要根据用户输入的信息,来决定如何生成项目的结构。比如模板文件中的动态数据、是否安装某项依赖等等

命令行询问

在index.js中,导出的类里添加prompting方法,yeoman在询问用户的阶段会自动调用此方法,在prompting方法中可以调用父类的prompt方法来发出对用户的命令行询问。

module.exports = class extends Generator {
  prompting() {
    // 返回一个Promise,yeoman可以使用异步流程
    // this.prompt()接收一个数组,数组元素为表示要提出的问题对象
    // 
    return this.prompt([
      // 以下这个示例表示的是请用户输入项目名称,默认是该项目所在文件夹名称
      {
        type: 'input', // 问题类型,这里表示使用用户输入的方式提交信息
        name: 'name', // 类似于web表单的name属性,也就是结果的键值对中的键
        message: 'your project name', // 该问题的描述
        default: this.appname // 该问题的默认值,我们这里使用了this.appname表示为项目生成的目录名称
      }
    ])
    // answers为当前问题的用户回答
    .then(answers => {
      // 将用户给与的回答挂载到answers属性上,以便于之后使用该信息。
      this.answers = answers;
    })
  }
}
创建自定义的Vue脚手架

Plop:小而美的脚手架工具

创建特定类型文件的脚手架工具,有点类似yeoman sub-generator。一般不独立使用,而是集成在项目中,自动化地创建同类型文件。

使用
  • 安装:npm install plop -D
  • 项目根目录下创建plopfile.js文件作为Plop的入口文件
    • 需要导出一个函数
    • 该函数接受一个Plop对象,用于创建生成器任务
  • 项目根目录下创建plop-templates目录,用于存放Plop生成文件时的模板文件
  • 模板文件遵循handlebars的模板语法
  • 在命令行中启动Plop:npx plop <task-name>,这里的<task-name>就是在plopfile.js中定义的生成器任务名字。启动的方式与gulp在命令行启动任务是一致的。
// plopfile.js
module.exports = plop => {
  // 创建生成器任务
  // setGenerator第一个参数为生成器名字,第二个参数为配置选项
  plop.setGenerator('component', {
    // 对于任务的一个描述
    description: 'create a component',
    // 对于该任务,在命令行中的交互问题
    prompts: [
      {
        type: 'input',
        name: 'name',
        message: 'component name',
        default: 'MyComponent'
      }
    ],
    // 完成命令行交互后生成器的动作,多个文件多个模板如下
    actions: [
      {
        type: 'add', // 表示添加新的文件
        // 表示添加文件的路径,可以使用{{}}的插值语法,下面的name就是命令行获得的name值
        path: 'src/components/{{name}}/{{name}}.js',
        // 指定模板文件的路径
        templateFile: 'plop-templates/component.hbs'
      }{
        type: 'add', // 表示添加新的文件
        // 表示添加文件的路径,可以使用{{}}的插值语法,下面的name就是命令行获得的name值
        path: 'src/components/{{name}}/{{name}}.css',
        // 指定模板文件的路径
        templateFile: 'plop-templates/component.css.hbs'
      },
      {
        type: 'add', // 表示添加新的文件
        // 表示添加文件的路径,可以使用{{}}的插值语法,下面的name就是命令行获得的name值
        path: 'src/components/{{name}}/{{name}}.test.j.s',
        // 指定模板文件的路径
        templateFile: 'plop-templates/component.test.hbs'
      }
    ]
  })
}
  • 1
    点赞
  • 1
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值