forked from AssemblyScript/assemblyscript
-
Notifications
You must be signed in to change notification settings - Fork 0
Expand file tree
/
Copy pathoptions.js
More file actions
135 lines (126 loc) · 4.56 KB
/
options.js
File metadata and controls
135 lines (126 loc) · 4.56 KB
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
/**
* @fileoverview Command line options utility.
* @license Apache-2.0
*/
const colorsUtil = require("./colors");
// type | meaning
// -----|---------------
// b | boolean
// i | integer
// f | float
// s | string
// I | integer array
// F | float array
// S | string array
/** Parses the specified command line arguments according to the given configuration. */
function parse(argv, config) {
var options = {};
var unknown = [];
var arguments = [];
var trailing = [];
// make an alias map and initialize defaults
var aliases = {};
Object.keys(config).forEach(key => {
if (key.startsWith(" ")) return;
var option = config[key];
if (option.alias != null) {
if (typeof option.alias === "string") aliases[option.alias] = key;
else if (Array.isArray(option.alias)) option.alias.forEach(alias => aliases[alias] = key);
}
if (option.default != null) options[key] = option.default;
});
// iterate over argv
for (var i = 0, k = (argv = argv.slice()).length; i < k; ++i) {
let arg = argv[i];
if (arg == "--") { ++i; break; }
let match = /^(?:(\-\w)(?:=(.*))?|(\-\-\w{2,})(?:=(.*))?)$/.exec(arg), option, key;
if (match) {
if (config[arg]) option = config[key = arg]; // exact
else if (match[1] != null) { // alias
option = config[key = aliases[match[1].substring(1)]];
if (option && match[2] != null) argv[i--] = match[2];
} else if (match[3] != null) { // full
option = config[key = match[3].substring(2)];
if (option && match[4] != null) argv[i--] = match[4];
}
} else {
if (arg.charCodeAt(0) == 45) option = config[key = arg]; // exact
else { arguments.push(arg); continue; } // argument
}
if (option) {
if (option.type == null || option.type === "b") options[key] = true; // flag
else {
if (i + 1 < argv.length && argv[i + 1].charCodeAt(0) != 45) { // present
switch (option.type) {
case "i": options[key] = parseInt(argv[++i], 10); break;
case "I": options[key] = (options[key] || []).concat(parseInt(argv[++i], 10)); break;
case "f": options[key] = parseFloat(argv[++i]); break;
case "F": options[key] = (options[key] || []).concat(parseFloat(argv[++i])); break;
case "s": options[key] = String(argv[++i]); break;
case "S": options[key] = (options[key] || []).concat(argv[++i].split(",")); break;
default: unknown.push(arg); --i;
}
} else { // omitted
switch (option.type) {
case "i":
case "f": options[key] = option.default || 0; break;
case "s": options[key] = option.default || ""; break;
case "I":
case "F":
case "S": options[key] = options.default || []; break;
default: unknown.push(arg);
}
}
}
if (option.value) Object.keys(option.value).forEach(k => options[k] = option.value[k]);
} else unknown.push(arg);
}
while (i < k) trailing.push(argv[i++]); // trailing
return { options, unknown, arguments, trailing };
}
exports.parse = parse;
/** Generates the help text for the specified configuration. */
function help(config, options) {
if (!options) options = {};
var indent = options.indent || 2;
var padding = options.padding || 24;
var eol = options.eol || "\n";
var sbCategories = {};
var sbOther = [];
Object.keys(config).forEach(key => {
var option = config[key];
if (option.description == null) return;
var text = "";
while (text.length < indent) text += " ";
text += "--" + key;
if (option.alias) text += ", -" + option.alias;
while (text.length < padding) text += " ";
var sb;
if (!options.noCategories && option.category) {
if (!(sb = sbCategories[option.category])) {
sbCategories[option.category] = sb = [];
}
} else {
sb = sbOther;
}
if (Array.isArray(option.description)) {
sb.push(text + option.description[0] + option.description.slice(1).map(line => {
for (let i = 0; i < padding; ++i) line = " " + line;
return eol + line;
}).join(""));
} else sb.push(text + option.description);
});
var sb = [];
var hasCategories = false;
Object.keys(sbCategories).forEach(category => {
hasCategories = true;
sb.push(eol + " " + colorsUtil.gray(category) + eol);
sb.push(sbCategories[category].join(eol));
});
if (hasCategories) {
sb.push(eol + " " + colorsUtil.gray("Other") + eol);
}
sb.push(sbOther.join(eol));
return sb.join(eol);
}
exports.help = help;