1 | 'use strict';
|
2 |
|
3 | Object.defineProperty(exports, "__esModule", {
|
4 | value: true
|
5 | });
|
6 | exports.RequiredFlagError = undefined;
|
7 |
|
8 | require('cli-engine-config');
|
9 |
|
10 | class Parse {
|
11 | constructor(input) {
|
12 | this.input = input;
|
13 | input.args = input.args || [];
|
14 | input.flags = input.flags || {};
|
15 | }
|
16 |
|
17 | async parse(output = {}) {
|
18 | let argv = output.argv || [];
|
19 | output.flags = output.flags || {};
|
20 | output.argv = [];
|
21 | output.args = {};
|
22 |
|
23 | let parseFlag = arg => {
|
24 | let long = arg.startsWith('--');
|
25 | let name = long ? findLongFlag(arg) : findShortFlag(arg);
|
26 | if (!name) {
|
27 | const i = arg.indexOf('=');
|
28 | if (i !== -1) {
|
29 | let sliced = arg.slice(i + 1);
|
30 | argv.unshift(sliced);
|
31 |
|
32 | let equalsParsed = parseFlag(arg.slice(0, i));
|
33 | if (!equalsParsed) {
|
34 | argv.shift();
|
35 | }
|
36 | return equalsParsed;
|
37 | }
|
38 | return false;
|
39 | }
|
40 | let flag = this.input.flags[name];
|
41 | let cur = output.flags[name];
|
42 | if (flag.parse) {
|
43 |
|
44 | if (cur) throw new Error(`Flag --${name} already provided`);
|
45 | let input;
|
46 | if (long || arg.length < 3) input = argv.shift();else input = arg.slice(arg[2] === '=' ? 3 : 2);
|
47 | if (!input) throw new Error(`Flag --${name} expects a value`);
|
48 | output.flags[name] = input;
|
49 | } else {
|
50 | if (!cur) output.flags[name] = true;
|
51 |
|
52 | if (!long && arg.length > 2) argv.unshift(`-${arg.slice(2)}`);
|
53 | }
|
54 | return true;
|
55 | };
|
56 |
|
57 | let findLongFlag = arg => {
|
58 | let name = arg.slice(2);
|
59 | if (this.input.flags[name]) return name;
|
60 | };
|
61 |
|
62 | let findShortFlag = arg => {
|
63 | for (let k of Object.keys(this.input.flags)) {
|
64 | if (this.input.flags[k].char === arg[1]) return k;
|
65 | }
|
66 | };
|
67 |
|
68 | let parsingFlags = true;
|
69 | let maxArgs = this.input.args.length;
|
70 | let minArgs = this.input.args.filter(a => a.required !== false && !a.optional).length;
|
71 | while (argv.length) {
|
72 | let arg = argv.shift();
|
73 | if (parsingFlags && arg.startsWith('-')) {
|
74 |
|
75 | if (arg === '--') {
|
76 | parsingFlags = false;
|
77 | continue;
|
78 | }
|
79 | if (parseFlag(arg)) continue;
|
80 |
|
81 | }
|
82 |
|
83 | let argDefinition = this.input.args[output.argv.length];
|
84 | if (argDefinition) output.args[argDefinition.name] = arg;
|
85 | output.argv.push(arg);
|
86 | }
|
87 |
|
88 | if (!this.input.variableArgs && output.argv.length > maxArgs) throw new Error(`Unexpected argument ${output.argv[maxArgs]}`);
|
89 | if (output.argv.length < minArgs) throw new Error(new Error(`Missing required argument ${this.input.args[output.argv.length].name}`));
|
90 |
|
91 | for (let name of Object.keys(this.input.flags)) {
|
92 | const flag = this.input.flags[name];
|
93 | if (flag.parse) {
|
94 | output.flags[name] = await flag.parse(output.flags[name], this.input.cmd, name);
|
95 | flag.required = flag.required || flag.optional === false;
|
96 | if (flag.required && !output.flags[name]) throw new RequiredFlagError(name);
|
97 | }
|
98 | }
|
99 |
|
100 | return output;
|
101 | }
|
102 | }
|
103 |
|
104 | exports.default = Parse;
|
105 | class RequiredFlagError extends Error {
|
106 | constructor(name) {
|
107 | super(`Missing required flag --${name}`);
|
108 | }
|
109 | }
|
110 | exports.RequiredFlagError = RequiredFlagError; |
\ | No newline at end of file |