clef-parse
Version:
Simple, lightweight argv parser. Powers the cleffa and clefairy packages
152 lines (151 loc) • 5.37 kB
JavaScript
;
var __importDefault = (this && this.__importDefault) || function (mod) {
return (mod && mod.__esModule) ? mod : { "default": mod };
};
Object.defineProperty(exports, "__esModule", { value: true });
exports.parseArgv = exports.Path = void 0;
const path_1 = __importDefault(require("path"));
const nice_path_1 = require("nice-path");
Object.defineProperty(exports, "Path", { enumerable: true, get: function () { return nice_path_1.Path; } });
const convert_case_1 = require("./convert-case");
function bestGuess(nextValue) {
if (nextValue === "true" || nextValue === "false") {
return Boolean;
}
else if (nextValue == null || nextValue.startsWith("-")) {
return Boolean;
}
else if (nextValue === String(Number(nextValue))) {
return Number;
}
else {
return String;
}
}
function hintToString(hint) {
switch (hint) {
case String: {
return "string";
}
case Boolean: {
return "boolean";
}
case Number: {
return "number";
}
case nice_path_1.Path: {
return "path";
}
default: {
throw new Error("Invalid hint: " + hint);
}
}
}
function parseArgv(argv = process.argv.slice(2), hints = {}, { isAbsolute = path_1.default.isAbsolute, resolvePath = path_1.default.resolve, getCwd = process.cwd, } = {}) {
const options = {};
const positionalArgs = [];
const metadata = {
keys: {},
hints: {},
guesses: {},
};
let isAfterDoubleDash = false;
while (argv.length > 0) {
let item = argv.shift();
if (item == null)
break;
if (item === "--") {
isAfterDoubleDash = true;
continue;
}
if (item.startsWith("-")) {
if (isAfterDoubleDash) {
positionalArgs.push(item);
}
else {
let propertyName;
let rightHandValue;
let valueComesFromNextArg;
if (/=/.test(item)) {
let equalsOffset = item.indexOf("=");
const before = item.slice(0, equalsOffset);
const after = item.slice(equalsOffset + 1);
propertyName = (0, convert_case_1.convertToCamelCase)(before);
metadata.keys[before] = propertyName;
rightHandValue = after;
valueComesFromNextArg = false;
}
else {
propertyName = (0, convert_case_1.convertToCamelCase)(item);
metadata.keys[item] = propertyName;
rightHandValue = argv[0];
valueComesFromNextArg = true;
}
let propertyValue;
let propertyHint = hints[propertyName];
if (propertyHint == null) {
propertyHint = bestGuess(rightHandValue);
metadata.guesses[propertyName] = hintToString(propertyHint);
}
else {
metadata.hints[propertyName] = hintToString(propertyHint);
}
switch (propertyHint) {
case Boolean: {
if (rightHandValue === "false") {
if (valueComesFromNextArg) {
argv.shift();
}
propertyValue = false;
}
else {
if (rightHandValue === "true") {
if (valueComesFromNextArg) {
argv.shift();
}
}
propertyValue = true;
}
break;
}
case Number: {
if (valueComesFromNextArg) {
argv.shift();
}
propertyValue = Number(rightHandValue);
break;
}
case String: {
if (valueComesFromNextArg) {
argv.shift();
}
propertyValue = rightHandValue;
break;
}
case nice_path_1.Path: {
if (valueComesFromNextArg) {
argv.shift();
}
propertyValue = isAbsolute(rightHandValue)
? new nice_path_1.Path(rightHandValue)
: new nice_path_1.Path(resolvePath(getCwd(), rightHandValue));
break;
}
default: {
throw new Error(`Invalid option hint: ${propertyHint}`);
}
}
options[propertyName] = propertyValue;
}
}
else {
positionalArgs.push(item);
}
}
return {
options,
positionalArgs,
metadata,
};
}
exports.parseArgv = parseArgv;