前言:
新手误区:
一个简单的cli:
bin:
将会把 package.json 里定义的 bin 文件软连接到全局 node_modules/bin,如果是非全局安装,会软链接到项目文件夹./node_modules/.bin/cli-test中的 cli-test 文件。
/*cli-test 的 package.json*/ "bin": { "cli-test": "./bin/cli-test" }
如果我们把cli安装在项目A node_modules中,通过设置项目中 package.json 的 scripts,运行 npm run cli,npm 就会在项目的 node_modules/.bin 寻找并运行 cli-test
/*项目A package.json*/ "scripts": { "cli": "cli-test" }
cli文件:
下面是 cli-test
#!/usr/bin/env node //do something
commander 的 nodecommander。
commander:
cli-test,代码如下:
#!/usr/bin/env node const program =require('commander'); program .usage('[option]', '--type required') .option('--type [typeName]', 'type: dev && build') .parse(process.argv); const {type} = program; if(type == 'dev'){ console.log('do something', type) }else if(type == 'build'){ console.log('do something', type) }else{ console.log('params error'); program.help(); }
require('commander')new一个内部的单例对象并返回,已经是一个实例,中打印出来。.--type的时候,根据 process.argv 之中的参数,获取到 --type,并把参数命和参数值存储在内部 commander 实例的属性之中,因此后面的代码就能从 program 之中取到 type不存在或者不是我们约定的值,最后我们打印参数错误,并执行help方法打印了 --help执行 cli-test的程序。(因为这里是本地的demo程序,所以直接使用node命令)
接着,我们执行正确的命令参数,如下
这样一个简单的demo就实现了,看起来也挺简单的,
再来一个例子:
-name,作为子命令文件
cli-test:
#!/usr/bin/env node const program =require('commander'); program .usage('<command> [option]', 'option --type required') .command('h5', 'to h5') .command('rn', 'to rn') .parse(process.argv);
cli-test-h5:
#!/usr/bin/env node const program =require('commander'); program .option('--type [typeName]', 'type: dev && build') .parse(process.argv); const {type} = program; if(type == 'dev'){ console.log('do something h5', type) }else if(type == 'build'){ console.log('do something h5', type) }else{ console.log('params error'); program.help(); }
cli-test-rn:
#!/usr/bin/env node const program =require('commander'); program .option('--type [typeName]', 'type: dev && build') .parse(process.argv); const {type} = program; if(type == 'dev'){ console.log('do something rn', type) }else if(type == 'build'){ console.log('do something rn', type) }else{ console.log('params error'); program.help(); }
先直接运行3个命令运行程序,看下结果,而后分别解释一下:
node ./bin/cli-test:
定义了.command子命令却没有相应执行参数,commander对象会直接打印-help,并process.exit退出进程
node ./bin/cli-test h5 --type dev:
h5node cli-test h5 --type dev的时候,cli-test,会在当前 commander 实例内部,new 一个 name Ϊ h5 的子 commander,存储在当前父实例的 commands 数组中执行,获取到参数中 h5 后,在 commands 里查找是否有 name Ϊ h5 的 commandercli-test-h5 文件并带入后面的 option 参数。 这样 commander 就帮助我们实现了多文件命令划分,我们可以把不同类型的执行代码放在不同的文件中。
node ./bin/cli-test h5 --type dev:
同上
小结
文件夹下的这3个 node实例,
最后
和 commander,一个 commander