commander, tj编写的又一个nodejs库,主要用于为你的Nodejs程序提供命令行支持,本篇以nata-dfs为例讲解如何使用commander为项目编写命令行支持。

准备工作

  1. 安装commander模块,这里使用npminstall模块提升安装速度npminstall --save commmander

  2. 创建bin目录与你的命令行文件比如natadfsmkdir bin && touch natadfs

  3. 添加命令行文件执行权限chmod +x natadfs

  4. 打开natadfs添加命令行程序运行环境#!/usr/bin/env node

  5. 引入commander包与基本结构代码

1
2
3
var program = require('commander');
program
.parse(process.argv);

现在运行./natadfs -h就可以看到

1
2
3
4
5
Usage: natadfs [options]
Options:
-h, --help output usage information

-h为commander默认的选项

添加基本选项

version

我们希望能够显示工具的版本并与项目package.json中保持一致

1
2
3
4
5
var program = require('commander');
program
.version(require('../package.json').version)
.parse(process.argv);

现在使用./natadfs -h可以看到多出来一个-V, --version output the version number的选项,使用./natadfs -V可以看到当前的版本号与package.json中一致

option

配置参数选项

1
.option('-p, --apk-path <apk>', 'absolute apk path, if set we will parse the apk and install')

option有4个参数

  • 第一个参数中, -p 为short option, --apk-path 为对应的long option, 二者的分割符是|,。可以在程序里通过program.apkPath 的方式取到该option的值,以由-分隔的变量会转成骆驼形式,即apk-path -> apkPath
  • 第二个为option描述, 会在help信息里展示出来
  • 第三个参数为回调函数
  • 第四个参数为默认值

option 有两种类型

  • <lang> required参数, 使用时后边必须跟参数值, 否则程序会报错
  • [db] optional参数, 后面可以选择是否跟参数值

对于nata-dfs目前我们定义了部分选项,仅供参考

1
2
3
4
5
6
7
8
9
10
program
.version(require('../package.json').version)
.option('-p, --apk-path <apk>', 'absolute apk path, if set we will parse the apk and install')
.option('-n, --number <num>', `set limited actions number, default to 1000`, 1000)
.option('-p, --pkg <pkg>', 'specify the package name')
.option('-e, --entry <entry>', 'specify the starting activity entry')
.option('-d, --directory <directory>', 'specify the running directory, default to be <results> in the package')
.option('--device <device>', 'specify the runnging device id, default to run on all connected devices')
.option('--verbose', 'show more running information')
.parse(process.argv)

command

子命令,由于nata-dfs中没有用到,这里给出官方的示例

1
2
3
4
5
6
7
8
9
program
.command('setup [env]')
.description('run setup commands for all envs')
.option("-s, --setup_mode [mode]", "Which setup mode to use")
.action(function(env, options){
var mode = options.setup_mode || "normal";
env = env || 'all';
console.log('setup for %s env(s) with %s mode', env, mode);
});

运行主程序

定义完成后,我们需要拿到用户设定的值对程序进行设置,然后运行我们的主程序,一个简单的例子如下

1
2
3
4
5
6
7
8
function *run() {
if (program.entry) {
console.log(chalk.blue(`Using specified act ${program.pkg}`))
generator.entry(program.entry)
}
yield generator.run()
}
co(run)

我们简单的判断有没有定义entry,如果定义了就设置entry,然后运行主程序,全程序可以参考github

另外command可以做一些定制的工作,可以在官网查看

安装到全局

如果想在要在global安装你的软件包的时候把bin中的命令安装到全局使用,那么你需要在package.json中声明bin选项

1
2
3
"bin": {
"natadfs": "bin/natadfs"
},

然后使用npm install -g .安装到全局,然后你就能在命令行中使用natadfs命令了

或者也可以使用npm link将添加全局的符号引用