minimist 是一个node 模块,用来做命令行参数解析。
比如,解析
$ls -a avalue -b bvalue arg
效果简练,功能俊秀:
var d ="ls -a avalue -b bvalue arg".split(' ')
var opt = require('minimist')
var argv = opt(d);
expect(argv.a).to.equal("avalue")
expect(argv.b).to.equal("bvalue")
expect(argv._).to.deep.equal("ls arg".split(' '))
这里的-a,-b 都是一个string类型的参数,值分别为 avalue,bvalue 。具体的命令格式和参数类型,需要自己去看看此模块的readme。
对于 $ls -ar ” 的解析,也还得体:
var d ="ls -ar c".split(' ')
var argv = opt(d);
expect(argv.a).to.equal(true)
expect(argv.r).to.equal(true)
这里的-a,-r都是boolean类型的,有就是true,没有就是false。
可是,如果是 $ls -ar r
var d ="ls -ar r".split(' ')
var opt = require('minimist')
var argv = opt(d);
expect(argv.a).to.equal(true)
expect(argv.r).to.equal("r")
expect(argv._).to.deep.equal("ls".split(' '))
有些歧义出现。-a 自然无话可说,就是一个boolean参数。-r呢,到底是Boolean参数,还是一个值为r的string参数呢?
解决此问题也还简单。为了消除歧义,指定r为boolean类型即可。
var d ="ls -ar r".split(' ')
var opt = require('minimist')
var argv = opt(d);
var argv = opt(d,{boolean:["r"]});
console.log(argv)
expect(argv.a).to.equal(true)
expect(argv.r).to.equal(true)
expect(argv._).to.deep.equal("ls r".split(' '))
—————-干净的表象,自此堕入黑暗 ————-
我想要做一个cross shell,跨平台运行shell,在mac,windows上。作为此工作的一个sub project,我需要用到option parser。
有两个选项:minimist ,optimist 。optimist是我先知道的,但是此组件的作者自己用 minimist !他还说明了原因:
DEPRECATION NOTICE:I don't want to maintain this module anymore
since I just use minimist, the argument parsing engine,
directly instead nowadays.
于是我npm i minimist 。
回到本意,我要解析ls命令的简版,以便适配 shell.js 。语料为:
ls -fg c
结果是:
{
_: [ 'ls', 'b' ],
f: true,
g: 'c',
}
怎么办?原来必须指定fg为boolean。不说明的话,默认的行为虽然不是我现在希望的,但是它这样做也有特定的场景的
ls -o1 o1value -o2 o2value value
所以指定即可
var d ="ls b -fg c".split(' ')
var opt = require('minimist')
var argv = opt(d,{boolean:["f","g"]});
expect("f" in argv).to.equal(true)
expect("g" in argv).to.equal(true)
expect(argv._).to.deep.equal("ls b c".split(' '))
花了不少时间去修改了minimist 以便完成我的需求,完成代码后才发现还可以这样做 。果然还是需要细读文档;比读文档更重要的,是需要对unix command line的格式约定烂熟于心。这次的坑就在于我不那么清楚这个逻辑。