1# Commander.js 2 3[![Build Status](https://github.com/tj/commander.js/workflows/build/badge.svg)](https://github.com/tj/commander.js/actions?query=workflow%3A%22build%22) 4[![NPM Version](http://img.shields.io/npm/v/commander.svg?style=flat)](https://www.npmjs.org/package/commander) 5[![NPM Downloads](https://img.shields.io/npm/dm/commander.svg?style=flat)](https://npmcharts.com/compare/commander?minimal=true) 6[![Install Size](https://packagephobia.now.sh/badge?p=commander)](https://packagephobia.now.sh/result?p=commander) 7 8The complete solution for [node.js](http://nodejs.org) command-line interfaces. 9 10Read this in other languages: English | [简体中文](./Readme_zh-CN.md) 11 12- [Commander.js](#commanderjs) 13 - [Installation](#installation) 14 - [Quick Start](#quick-start) 15 - [Declaring _program_ variable](#declaring-program-variable) 16 - [Options](#options) 17 - [Common option types, boolean and value](#common-option-types-boolean-and-value) 18 - [Default option value](#default-option-value) 19 - [Other option types, negatable boolean and boolean|value](#other-option-types-negatable-boolean-and-booleanvalue) 20 - [Required option](#required-option) 21 - [Variadic option](#variadic-option) 22 - [Version option](#version-option) 23 - [More configuration](#more-configuration) 24 - [Custom option processing](#custom-option-processing) 25 - [Commands](#commands) 26 - [Command-arguments](#command-arguments) 27 - [More configuration](#more-configuration-1) 28 - [Custom argument processing](#custom-argument-processing) 29 - [Action handler](#action-handler) 30 - [Stand-alone executable (sub)commands](#stand-alone-executable-subcommands) 31 - [Life cycle hooks](#life-cycle-hooks) 32 - [Automated help](#automated-help) 33 - [Custom help](#custom-help) 34 - [Display help after errors](#display-help-after-errors) 35 - [Display help from code](#display-help-from-code) 36 - [.name](#name) 37 - [.usage](#usage) 38 - [.description and .summary](#description-and-summary) 39 - [.helpOption(flags, description)](#helpoptionflags-description) 40 - [.addHelpCommand()](#addhelpcommand) 41 - [More configuration](#more-configuration-2) 42 - [Custom event listeners](#custom-event-listeners) 43 - [Bits and pieces](#bits-and-pieces) 44 - [.parse() and .parseAsync()](#parse-and-parseasync) 45 - [Parsing Configuration](#parsing-configuration) 46 - [Legacy options as properties](#legacy-options-as-properties) 47 - [TypeScript](#typescript) 48 - [createCommand()](#createcommand) 49 - [Node options such as `--harmony`](#node-options-such-as---harmony) 50 - [Debugging stand-alone executable subcommands](#debugging-stand-alone-executable-subcommands) 51 - [Display error](#display-error) 52 - [Override exit and output handling](#override-exit-and-output-handling) 53 - [Additional documentation](#additional-documentation) 54 - [Support](#support) 55 - [Commander for enterprise](#commander-for-enterprise) 56 57For information about terms used in this document see: [terminology](./docs/terminology.md) 58 59## Installation 60 61```sh 62npm install commander 63``` 64 65## Quick Start 66 67You write code to describe your command line interface. 68Commander looks after parsing the arguments into options and command-arguments, 69displays usage errors for problems, and implements a help system. 70 71Commander is strict and displays an error for unrecognised options. 72The two most used option types are a boolean option, and an option which takes its value from the following argument. 73 74Example file: [split.js](./examples/split.js) 75 76```js 77const { program } = require('commander'); 78 79program 80 .option('--first') 81 .option('-s, --separator <char>'); 82 83program.parse(); 84 85const options = program.opts(); 86const limit = options.first ? 1 : undefined; 87console.log(program.args[0].split(options.separator, limit)); 88``` 89 90```console 91$ node split.js -s / --fits a/b/c 92error: unknown option '--fits' 93(Did you mean --first?) 94$ node split.js -s / --first a/b/c 95[ 'a' ] 96``` 97 98Here is a more complete program using a subcommand and with descriptions for the help. In a multi-command program, you have an action handler for each command (or stand-alone executables for the commands). 99 100Example file: [string-util.js](./examples/string-util.js) 101 102```js 103const { Command } = require('commander'); 104const program = new Command(); 105 106program 107 .name('string-util') 108 .description('CLI to some JavaScript string utilities') 109 .version('0.8.0'); 110 111program.command('split') 112 .description('Split a string into substrings and display as an array') 113 .argument('<string>', 'string to split') 114 .option('--first', 'display just the first substring') 115 .option('-s, --separator <char>', 'separator character', ',') 116 .action((str, options) => { 117 const limit = options.first ? 1 : undefined; 118 console.log(str.split(options.separator, limit)); 119 }); 120 121program.parse(); 122``` 123 124```console 125$ node string-util.js help split 126Usage: string-util split [options] <string> 127 128Split a string into substrings and display as an array. 129 130Arguments: 131 string string to split 132 133Options: 134 --first display just the first substring 135 -s, --separator <char> separator character (default: ",") 136 -h, --help display help for command 137 138$ node string-util.js split --separator=/ a/b/c 139[ 'a', 'b', 'c' ] 140``` 141 142More samples can be found in the [examples](https://github.com/tj/commander.js/tree/master/examples) directory. 143 144## Declaring _program_ variable 145 146Commander exports a global object which is convenient for quick programs. 147This is used in the examples in this README for brevity. 148 149```js 150// CommonJS (.cjs) 151const { program } = require('commander'); 152``` 153 154For larger programs which may use commander in multiple ways, including unit testing, it is better to create a local Command object to use. 155 156```js 157// CommonJS (.cjs) 158const { Command } = require('commander'); 159const program = new Command(); 160``` 161 162```js 163// ECMAScript (.mjs) 164import { Command } from 'commander'; 165const program = new Command(); 166``` 167 168```ts 169// TypeScript (.ts) 170import { Command } from 'commander'; 171const program = new Command(); 172``` 173 174## Options 175 176Options are defined with the `.option()` method, also serving as documentation for the options. Each option can have a short flag (single character) and a long name, separated by a comma or space or vertical bar ('|'). 177 178The parsed options can be accessed by calling `.opts()` on a `Command` object, and are passed to the action handler. 179 180Multi-word options such as "--template-engine" are camel-cased, becoming `program.opts().templateEngine` etc. 181 182An option and its option-argument can be separated by a space, or combined into the same argument. The option-argument can follow the short option directly or follow an `=` for a long option. 183 184```sh 185serve -p 80 186serve -p80 187serve --port 80 188serve --port=80 189``` 190 191You can use `--` to indicate the end of the options, and any remaining arguments will be used without being interpreted. 192 193By default options on the command line are not positional, and can be specified before or after other arguments. 194 195There are additional related routines for when `.opts()` is not enough: 196 197- `.optsWithGlobals()` returns merged local and global option values 198- `.getOptionValue()` and `.setOptionValue()` work with a single option value 199- `.getOptionValueSource()` and `.setOptionValueWithSource()` include where the option value came from 200 201### Common option types, boolean and value 202 203The two most used option types are a boolean option, and an option which takes its value 204from the following argument (declared with angle brackets like `--expect <value>`). Both are `undefined` unless specified on command line. 205 206Example file: [options-common.js](./examples/options-common.js) 207 208```js 209program 210 .option('-d, --debug', 'output extra debugging') 211 .option('-s, --small', 'small pizza size') 212 .option('-p, --pizza-type <type>', 'flavour of pizza'); 213 214program.parse(process.argv); 215 216const options = program.opts(); 217if (options.debug) console.log(options); 218console.log('pizza details:'); 219if (options.small) console.log('- small pizza size'); 220if (options.pizzaType) console.log(`- ${options.pizzaType}`); 221``` 222 223```console 224$ pizza-options -p 225error: option '-p, --pizza-type <type>' argument missing 226$ pizza-options -d -s -p vegetarian 227{ debug: true, small: true, pizzaType: 'vegetarian' } 228pizza details: 229- small pizza size 230- vegetarian 231$ pizza-options --pizza-type=cheese 232pizza details: 233- cheese 234``` 235 236Multiple boolean short options may be combined together following the dash, and may be followed by a single short option taking a value. 237For example `-d -s -p cheese` may be written as `-ds -p cheese` or even `-dsp cheese`. 238 239Options with an expected option-argument are greedy and will consume the following argument whatever the value. 240So `--id -xyz` reads `-xyz` as the option-argument. 241 242`program.parse(arguments)` processes the arguments, leaving any args not consumed by the program options in the `program.args` array. The parameter is optional and defaults to `process.argv`. 243 244### Default option value 245 246You can specify a default value for an option. 247 248Example file: [options-defaults.js](./examples/options-defaults.js) 249 250```js 251program 252 .option('-c, --cheese <type>', 'add the specified type of cheese', 'blue'); 253 254program.parse(); 255 256console.log(`cheese: ${program.opts().cheese}`); 257``` 258 259```console 260$ pizza-options 261cheese: blue 262$ pizza-options --cheese stilton 263cheese: stilton 264``` 265 266### Other option types, negatable boolean and boolean|value 267 268You can define a boolean option long name with a leading `no-` to set the option value to false when used. 269Defined alone this also makes the option true by default. 270 271If you define `--foo` first, adding `--no-foo` does not change the default value from what it would 272otherwise be. 273 274Example file: [options-negatable.js](./examples/options-negatable.js) 275 276```js 277program 278 .option('--no-sauce', 'Remove sauce') 279 .option('--cheese <flavour>', 'cheese flavour', 'mozzarella') 280 .option('--no-cheese', 'plain with no cheese') 281 .parse(); 282 283const options = program.opts(); 284const sauceStr = options.sauce ? 'sauce' : 'no sauce'; 285const cheeseStr = (options.cheese === false) ? 'no cheese' : `${options.cheese} cheese`; 286console.log(`You ordered a pizza with ${sauceStr} and ${cheeseStr}`); 287``` 288 289```console 290$ pizza-options 291You ordered a pizza with sauce and mozzarella cheese 292$ pizza-options --sauce 293error: unknown option '--sauce' 294$ pizza-options --cheese=blue 295You ordered a pizza with sauce and blue cheese 296$ pizza-options --no-sauce --no-cheese 297You ordered a pizza with no sauce and no cheese 298``` 299 300You can specify an option which may be used as a boolean option but may optionally take an option-argument 301(declared with square brackets like `--optional [value]`). 302 303Example file: [options-boolean-or-value.js](./examples/options-boolean-or-value.js) 304 305```js 306program 307 .option('-c, --cheese [type]', 'Add cheese with optional type'); 308 309program.parse(process.argv); 310 311const options = program.opts(); 312if (options.cheese === undefined) console.log('no cheese'); 313else if (options.cheese === true) console.log('add cheese'); 314else console.log(`add cheese type ${options.cheese}`); 315``` 316 317```console 318$ pizza-options 319no cheese 320$ pizza-options --cheese 321add cheese 322$ pizza-options --cheese mozzarella 323add cheese type mozzarella 324``` 325 326Options with an optional option-argument are not greedy and will ignore arguments starting with a dash. 327So `id` behaves as a boolean option for `--id -5`, but you can use a combined form if needed like `--id=-5`. 328 329For information about possible ambiguous cases, see [options taking varying arguments](./docs/options-taking-varying-arguments.md). 330 331### Required option 332 333You may specify a required (mandatory) option using `.requiredOption()`. The option must have a value after parsing, usually specified on the command line, or perhaps from a default value (say from environment). The method is otherwise the same as `.option()` in format, taking flags and description, and optional default value or custom processing. 334 335Example file: [options-required.js](./examples/options-required.js) 336 337```js 338program 339 .requiredOption('-c, --cheese <type>', 'pizza must have cheese'); 340 341program.parse(); 342``` 343 344```console 345$ pizza 346error: required option '-c, --cheese <type>' not specified 347``` 348 349### Variadic option 350 351You may make an option variadic by appending `...` to the value placeholder when declaring the option. On the command line you 352can then specify multiple option-arguments, and the parsed option value will be an array. The extra arguments 353are read until the first argument starting with a dash. The special argument `--` stops option processing entirely. If a value 354is specified in the same argument as the option then no further values are read. 355 356Example file: [options-variadic.js](./examples/options-variadic.js) 357 358```js 359program 360 .option('-n, --number <numbers...>', 'specify numbers') 361 .option('-l, --letter [letters...]', 'specify letters'); 362 363program.parse(); 364 365console.log('Options: ', program.opts()); 366console.log('Remaining arguments: ', program.args); 367``` 368 369```console 370$ collect -n 1 2 3 --letter a b c 371Options: { number: [ '1', '2', '3' ], letter: [ 'a', 'b', 'c' ] } 372Remaining arguments: [] 373$ collect --letter=A -n80 operand 374Options: { number: [ '80' ], letter: [ 'A' ] } 375Remaining arguments: [ 'operand' ] 376$ collect --letter -n 1 -n 2 3 -- operand 377Options: { number: [ '1', '2', '3' ], letter: true } 378Remaining arguments: [ 'operand' ] 379``` 380 381For information about possible ambiguous cases, see [options taking varying arguments](./docs/options-taking-varying-arguments.md). 382 383### Version option 384 385The optional `version` method adds handling for displaying the command version. The default option flags are `-V` and `--version`, and when present the command prints the version number and exits. 386 387```js 388program.version('0.0.1'); 389``` 390 391```console 392$ ./examples/pizza -V 3930.0.1 394``` 395 396You may change the flags and description by passing additional parameters to the `version` method, using 397the same syntax for flags as the `option` method. 398 399```js 400program.version('0.0.1', '-v, --vers', 'output the current version'); 401``` 402 403### More configuration 404 405You can add most options using the `.option()` method, but there are some additional features available 406by constructing an `Option` explicitly for less common cases. 407 408Example files: [options-extra.js](./examples/options-extra.js), [options-env.js](./examples/options-env.js), [options-conflicts.js](./examples/options-conflicts.js), [options-implies.js](./examples/options-implies.js) 409 410```js 411program 412 .addOption(new Option('-s, --secret').hideHelp()) 413 .addOption(new Option('-t, --timeout <delay>', 'timeout in seconds').default(60, 'one minute')) 414 .addOption(new Option('-d, --drink <size>', 'drink size').choices(['small', 'medium', 'large'])) 415 .addOption(new Option('-p, --port <number>', 'port number').env('PORT')) 416 .addOption(new Option('--donate [amount]', 'optional donation in dollars').preset('20').argParser(parseFloat)) 417 .addOption(new Option('--disable-server', 'disables the server').conflicts('port')) 418 .addOption(new Option('--free-drink', 'small drink included free ').implies({ drink: 'small' })); 419``` 420 421```console 422$ extra --help 423Usage: help [options] 424 425Options: 426 -t, --timeout <delay> timeout in seconds (default: one minute) 427 -d, --drink <size> drink cup size (choices: "small", "medium", "large") 428 -p, --port <number> port number (env: PORT) 429 --donate [amount] optional donation in dollars (preset: "20") 430 --disable-server disables the server 431 --free-drink small drink included free 432 -h, --help display help for command 433 434$ extra --drink huge 435error: option '-d, --drink <size>' argument 'huge' is invalid. Allowed choices are small, medium, large. 436 437$ PORT=80 extra --donate --free-drink 438Options: { timeout: 60, donate: 20, port: '80', freeDrink: true, drink: 'small' } 439 440$ extra --disable-server --port 8000 441error: option '--disable-server' cannot be used with option '-p, --port <number>' 442``` 443 444Specify a required (mandatory) option using the `Option` method `.makeOptionMandatory()`. This matches the `Command` method [.requiredOption()](#required-option). 445 446### Custom option processing 447 448You may specify a function to do custom processing of option-arguments. The callback function receives two parameters, 449the user specified option-argument and the previous value for the option. It returns the new value for the option. 450 451This allows you to coerce the option-argument to the desired type, or accumulate values, or do entirely custom processing. 452 453You can optionally specify the default/starting value for the option after the function parameter. 454 455Example file: [options-custom-processing.js](./examples/options-custom-processing.js) 456 457```js 458function myParseInt(value, dummyPrevious) { 459 // parseInt takes a string and a radix 460 const parsedValue = parseInt(value, 10); 461 if (isNaN(parsedValue)) { 462 throw new commander.InvalidArgumentError('Not a number.'); 463 } 464 return parsedValue; 465} 466 467function increaseVerbosity(dummyValue, previous) { 468 return previous + 1; 469} 470 471function collect(value, previous) { 472 return previous.concat([value]); 473} 474 475function commaSeparatedList(value, dummyPrevious) { 476 return value.split(','); 477} 478 479program 480 .option('-f, --float <number>', 'float argument', parseFloat) 481 .option('-i, --integer <number>', 'integer argument', myParseInt) 482 .option('-v, --verbose', 'verbosity that can be increased', increaseVerbosity, 0) 483 .option('-c, --collect <value>', 'repeatable value', collect, []) 484 .option('-l, --list <items>', 'comma separated list', commaSeparatedList) 485; 486 487program.parse(); 488 489const options = program.opts(); 490if (options.float !== undefined) console.log(`float: ${options.float}`); 491if (options.integer !== undefined) console.log(`integer: ${options.integer}`); 492if (options.verbose > 0) console.log(`verbosity: ${options.verbose}`); 493if (options.collect.length > 0) console.log(options.collect); 494if (options.list !== undefined) console.log(options.list); 495``` 496 497```console 498$ custom -f 1e2 499float: 100 500$ custom --integer 2 501integer: 2 502$ custom -v -v -v 503verbose: 3 504$ custom -c a -c b -c c 505[ 'a', 'b', 'c' ] 506$ custom --list x,y,z 507[ 'x', 'y', 'z' ] 508``` 509 510## Commands 511 512You can specify (sub)commands using `.command()` or `.addCommand()`. There are two ways these can be implemented: using an action handler attached to the command, or as a stand-alone executable file (described in more detail later). The subcommands may be nested ([example](./examples/nestedCommands.js)). 513 514In the first parameter to `.command()` you specify the command name. You may append the command-arguments after the command name, or specify them separately using `.argument()`. The arguments may be `<required>` or `[optional]`, and the last argument may also be `variadic...`. 515 516You can use `.addCommand()` to add an already configured subcommand to the program. 517 518For example: 519 520```js 521// Command implemented using action handler (description is supplied separately to `.command`) 522// Returns new command for configuring. 523program 524 .command('clone <source> [destination]') 525 .description('clone a repository into a newly created directory') 526 .action((source, destination) => { 527 console.log('clone command called'); 528 }); 529 530// Command implemented using stand-alone executable file, indicated by adding description as second parameter to `.command`. 531// Returns `this` for adding more commands. 532program 533 .command('start <service>', 'start named service') 534 .command('stop [service]', 'stop named service, or all if no name supplied'); 535 536// Command prepared separately. 537// Returns `this` for adding more commands. 538program 539 .addCommand(build.makeBuildCommand()); 540``` 541 542Configuration options can be passed with the call to `.command()` and `.addCommand()`. Specifying `hidden: true` will 543remove the command from the generated help output. Specifying `isDefault: true` will run the subcommand if no other 544subcommand is specified ([example](./examples/defaultCommand.js)). 545 546You can add alternative names for a command with `.alias()`. ([example](./examples/alias.js)) 547 548For safety, `.addCommand()` does not automatically copy the inherited settings from the parent command. There is a helper routine `.copyInheritedSettings()` for copying the settings when they are wanted. 549 550### Command-arguments 551 552For subcommands, you can specify the argument syntax in the call to `.command()` (as shown above). This 553is the only method usable for subcommands implemented using a stand-alone executable, but for other subcommands 554you can instead use the following method. 555 556To configure a command, you can use `.argument()` to specify each expected command-argument. 557You supply the argument name and an optional description. The argument may be `<required>` or `[optional]`. 558You can specify a default value for an optional command-argument. 559 560Example file: [argument.js](./examples/argument.js) 561 562```js 563program 564 .version('0.1.0') 565 .argument('<username>', 'user to login') 566 .argument('[password]', 'password for user, if required', 'no password given') 567 .action((username, password) => { 568 console.log('username:', username); 569 console.log('password:', password); 570 }); 571``` 572 573 The last argument of a command can be variadic, and only the last argument. To make an argument variadic you 574 append `...` to the argument name. A variadic argument is passed to the action handler as an array. For example: 575 576```js 577program 578 .version('0.1.0') 579 .command('rmdir') 580 .argument('<dirs...>') 581 .action(function (dirs) { 582 dirs.forEach((dir) => { 583 console.log('rmdir %s', dir); 584 }); 585 }); 586``` 587 588There is a convenience method to add multiple arguments at once, but without descriptions: 589 590```js 591program 592 .arguments('<username> <password>'); 593``` 594 595#### More configuration 596 597There are some additional features available by constructing an `Argument` explicitly for less common cases. 598 599Example file: [arguments-extra.js](./examples/arguments-extra.js) 600 601```js 602program 603 .addArgument(new commander.Argument('<drink-size>', 'drink cup size').choices(['small', 'medium', 'large'])) 604 .addArgument(new commander.Argument('[timeout]', 'timeout in seconds').default(60, 'one minute')) 605``` 606 607#### Custom argument processing 608 609You may specify a function to do custom processing of command-arguments (like for option-arguments). 610The callback function receives two parameters, the user specified command-argument and the previous value for the argument. 611It returns the new value for the argument. 612 613The processed argument values are passed to the action handler, and saved as `.processedArgs`. 614 615You can optionally specify the default/starting value for the argument after the function parameter. 616 617Example file: [arguments-custom-processing.js](./examples/arguments-custom-processing.js) 618 619```js 620program 621 .command('add') 622 .argument('<first>', 'integer argument', myParseInt) 623 .argument('[second]', 'integer argument', myParseInt, 1000) 624 .action((first, second) => { 625 console.log(`${first} + ${second} = ${first + second}`); 626 }) 627; 628``` 629 630### Action handler 631 632The action handler gets passed a parameter for each command-argument you declared, and two additional parameters 633which are the parsed options and the command object itself. 634 635Example file: [thank.js](./examples/thank.js) 636 637```js 638program 639 .argument('<name>') 640 .option('-t, --title <honorific>', 'title to use before name') 641 .option('-d, --debug', 'display some debugging') 642 .action((name, options, command) => { 643 if (options.debug) { 644 console.error('Called %s with options %o', command.name(), options); 645 } 646 const title = options.title ? `${options.title} ` : ''; 647 console.log(`Thank-you ${title}${name}`); 648 }); 649``` 650 651If you prefer, you can work with the command directly and skip declaring the parameters for the action handler. The `this` keyword is set to the running command and can be used from a function expression (but not from an arrow function). 652 653Example file: [action-this.js](./examples/action-this.js) 654 655```js 656program 657 .command('serve') 658 .argument('<script>') 659 .option('-p, --port <number>', 'port number', 80) 660 .action(function() { 661 console.error('Run script %s on port %s', this.args[0], this.opts().port); 662 }); 663``` 664 665You may supply an `async` action handler, in which case you call `.parseAsync` rather than `.parse`. 666 667```js 668async function run() { /* code goes here */ } 669 670async function main() { 671 program 672 .command('run') 673 .action(run); 674 await program.parseAsync(process.argv); 675} 676``` 677 678A command's options and arguments on the command line are validated when the command is used. Any unknown options or missing arguments will be reported as an error. You can suppress the unknown option checks with `.allowUnknownOption()`. By default it is not an error to 679pass more arguments than declared, but you can make this an error with `.allowExcessArguments(false)`. 680 681### Stand-alone executable (sub)commands 682 683When `.command()` is invoked with a description argument, this tells Commander that you're going to use stand-alone executables for subcommands. 684Commander will search the files in the directory of the entry script for a file with the name combination `command-subcommand`, like `pm-install` or `pm-search` in the example below. The search includes trying common file extensions, like `.js`. 685You may specify a custom name (and path) with the `executableFile` configuration option. 686You may specify a custom search directory for subcommands with `.executableDir()`. 687 688You handle the options for an executable (sub)command in the executable, and don't declare them at the top-level. 689 690Example file: [pm](./examples/pm) 691 692```js 693program 694 .name('pm') 695 .version('0.1.0') 696 .command('install [name]', 'install one or more packages') 697 .command('search [query]', 'search with optional query') 698 .command('update', 'update installed packages', { executableFile: 'myUpdateSubCommand' }) 699 .command('list', 'list packages installed', { isDefault: true }); 700 701program.parse(process.argv); 702``` 703 704If the program is designed to be installed globally, make sure the executables have proper modes, like `755`. 705 706### Life cycle hooks 707 708You can add callback hooks to a command for life cycle events. 709 710Example file: [hook.js](./examples/hook.js) 711 712```js 713program 714 .option('-t, --trace', 'display trace statements for commands') 715 .hook('preAction', (thisCommand, actionCommand) => { 716 if (thisCommand.opts().trace) { 717 console.log(`About to call action handler for subcommand: ${actionCommand.name()}`); 718 console.log('arguments: %O', actionCommand.args); 719 console.log('options: %o', actionCommand.opts()); 720 } 721 }); 722``` 723 724The callback hook can be `async`, in which case you call `.parseAsync` rather than `.parse`. You can add multiple hooks per event. 725 726The supported events are: 727 728| event name | when hook called | callback parameters | 729| :-- | :-- | :-- | 730| `preAction`, `postAction` | before/after action handler for this command and its nested subcommands | `(thisCommand, actionCommand)` | 731| `preSubcommand` | before parsing direct subcommand | `(thisCommand, subcommand)` | 732 733## Automated help 734 735The help information is auto-generated based on the information commander already knows about your program. The default 736help option is `-h,--help`. 737 738Example file: [pizza](./examples/pizza) 739 740```console 741$ node ./examples/pizza --help 742Usage: pizza [options] 743 744An application for pizza ordering 745 746Options: 747 -p, --peppers Add peppers 748 -c, --cheese <type> Add the specified type of cheese (default: "marble") 749 -C, --no-cheese You do not want any cheese 750 -h, --help display help for command 751``` 752 753A `help` command is added by default if your command has subcommands. It can be used alone, or with a subcommand name to show 754further help for the subcommand. These are effectively the same if the `shell` program has implicit help: 755 756```sh 757shell help 758shell --help 759 760shell help spawn 761shell spawn --help 762``` 763 764### Custom help 765 766You can add extra text to be displayed along with the built-in help. 767 768Example file: [custom-help](./examples/custom-help) 769 770```js 771program 772 .option('-f, --foo', 'enable some foo'); 773 774program.addHelpText('after', ` 775 776Example call: 777 $ custom-help --help`); 778``` 779 780Yields the following help output: 781 782```Text 783Usage: custom-help [options] 784 785Options: 786 -f, --foo enable some foo 787 -h, --help display help for command 788 789Example call: 790 $ custom-help --help 791``` 792 793The positions in order displayed are: 794 795- `beforeAll`: add to the program for a global banner or header 796- `before`: display extra information before built-in help 797- `after`: display extra information after built-in help 798- `afterAll`: add to the program for a global footer (epilog) 799 800The positions "beforeAll" and "afterAll" apply to the command and all its subcommands. 801 802The second parameter can be a string, or a function returning a string. The function is passed a context object for your convenience. The properties are: 803 804- error: a boolean for whether the help is being displayed due to a usage error 805- command: the Command which is displaying the help 806 807### Display help after errors 808 809The default behaviour for usage errors is to just display a short error message. 810You can change the behaviour to show the full help or a custom help message after an error. 811 812```js 813program.showHelpAfterError(); 814// or 815program.showHelpAfterError('(add --help for additional information)'); 816``` 817 818```console 819$ pizza --unknown 820error: unknown option '--unknown' 821(add --help for additional information) 822``` 823 824The default behaviour is to suggest correct spelling after an error for an unknown command or option. You 825can disable this. 826 827```js 828program.showSuggestionAfterError(false); 829``` 830 831```console 832$ pizza --hepl 833error: unknown option '--hepl' 834(Did you mean --help?) 835``` 836 837### Display help from code 838 839`.help()`: display help information and exit immediately. You can optionally pass `{ error: true }` to display on stderr and exit with an error status. 840 841`.outputHelp()`: output help information without exiting. You can optionally pass `{ error: true }` to display on stderr. 842 843`.helpInformation()`: get the built-in command help information as a string for processing or displaying yourself. 844 845### .name 846 847The command name appears in the help, and is also used for locating stand-alone executable subcommands. 848 849You may specify the program name using `.name()` or in the Command constructor. For the program, Commander will 850fallback to using the script name from the full arguments passed into `.parse()`. However, the script name varies 851depending on how your program is launched so you may wish to specify it explicitly. 852 853```js 854program.name('pizza'); 855const pm = new Command('pm'); 856``` 857 858Subcommands get a name when specified using `.command()`. If you create the subcommand yourself to use with `.addCommand()`, 859then set the name using `.name()` or in the Command constructor. 860 861### .usage 862 863This allows you to customise the usage description in the first line of the help. Given: 864 865```js 866program 867 .name("my-command") 868 .usage("[global options] command") 869``` 870 871The help will start with: 872 873```Text 874Usage: my-command [global options] command 875``` 876 877### .description and .summary 878 879The description appears in the help for the command. You can optionally supply a shorter 880summary to use when listed as a subcommand of the program. 881 882```js 883program 884 .command("duplicate") 885 .summary("make a copy") 886 .description(`Make a copy of the current project. 887This may require additional disk space. 888 `); 889``` 890 891### .helpOption(flags, description) 892 893By default every command has a help option. You may change the default help flags and description. Pass false to disable the built-in help option. 894 895```js 896program 897 .helpOption('-e, --HELP', 'read more information'); 898``` 899 900### .addHelpCommand() 901 902A help command is added by default if your command has subcommands. You can explicitly turn on or off the implicit help command with `.addHelpCommand()` and `.addHelpCommand(false)`. 903 904You can both turn on and customise the help command by supplying the name and description: 905 906```js 907program.addHelpCommand('assist [command]', 'show assistance'); 908``` 909 910### More configuration 911 912The built-in help is formatted using the Help class. 913You can configure the Help behaviour by modifying data properties and methods using `.configureHelp()`, or by subclassing using `.createHelp()` if you prefer. 914 915The data properties are: 916 917- `helpWidth`: specify the wrap width, useful for unit tests 918- `sortSubcommands`: sort the subcommands alphabetically 919- `sortOptions`: sort the options alphabetically 920- `showGlobalOptions`: show a section with the global options from the parent command(s) 921 922There are methods getting the visible lists of arguments, options, and subcommands. There are methods for formatting the items in the lists, with each item having a _term_ and _description_. Take a look at `.formatHelp()` to see how they are used. 923 924Example file: [configure-help.js](./examples/configure-help.js) 925 926```js 927program.configureHelp({ 928 sortSubcommands: true, 929 subcommandTerm: (cmd) => cmd.name() // Just show the name, instead of short usage. 930}); 931``` 932 933## Custom event listeners 934 935You can execute custom actions by listening to command and option events. 936 937```js 938program.on('option:verbose', function () { 939 process.env.VERBOSE = this.opts().verbose; 940}); 941``` 942 943## Bits and pieces 944 945### .parse() and .parseAsync() 946 947The first argument to `.parse` is the array of strings to parse. You may omit the parameter to implicitly use `process.argv`. 948 949If the arguments follow different conventions than node you can pass a `from` option in the second parameter: 950 951- 'node': default, `argv[0]` is the application and `argv[1]` is the script being run, with user parameters after that 952- 'electron': `argv[1]` varies depending on whether the electron application is packaged 953- 'user': all of the arguments from the user 954 955For example: 956 957```js 958program.parse(process.argv); // Explicit, node conventions 959program.parse(); // Implicit, and auto-detect electron 960program.parse(['-f', 'filename'], { from: 'user' }); 961``` 962 963### Parsing Configuration 964 965If the default parsing does not suit your needs, there are some behaviours to support other usage patterns. 966 967By default program options are recognised before and after subcommands. To only look for program options before subcommands, use `.enablePositionalOptions()`. This lets you use 968an option for a different purpose in subcommands. 969 970Example file: [positional-options.js](./examples/positional-options.js) 971 972With positional options, the `-b` is a program option in the first line and a subcommand option in the second line: 973 974```sh 975program -b subcommand 976program subcommand -b 977``` 978 979By default options are recognised before and after command-arguments. To only process options that come 980before the command-arguments, use `.passThroughOptions()`. This lets you pass the arguments and following options through to another program 981without needing to use `--` to end the option processing. 982To use pass through options in a subcommand, the program needs to enable positional options. 983 984Example file: [pass-through-options.js](./examples/pass-through-options.js) 985 986With pass through options, the `--port=80` is a program option in the first line and passed through as a command-argument in the second line: 987 988```sh 989program --port=80 arg 990program arg --port=80 991``` 992 993By default the option processing shows an error for an unknown option. To have an unknown option treated as an ordinary command-argument and continue looking for options, use `.allowUnknownOption()`. This lets you mix known and unknown options. 994 995By default the argument processing does not display an error for more command-arguments than expected. 996To display an error for excess arguments, use`.allowExcessArguments(false)`. 997 998### Legacy options as properties 999 1000Before Commander 7, the option values were stored as properties on the command. 1001This was convenient to code but the downside was possible clashes with 1002existing properties of `Command`. You can revert to the old behaviour to run unmodified legacy code by using `.storeOptionsAsProperties()`. 1003 1004```js 1005program 1006 .storeOptionsAsProperties() 1007 .option('-d, --debug') 1008 .action((commandAndOptions) => { 1009 if (commandAndOptions.debug) { 1010 console.error(`Called ${commandAndOptions.name()}`); 1011 } 1012 }); 1013``` 1014 1015### TypeScript 1016 1017extra-typings: There is an optional project to infer extra type information from the option and argument definitions. 1018This adds strong typing to the options returned by `.opts()` and the parameters to `.action()`. 1019See [commander-js/extra-typings](https://github.com/commander-js/extra-typings) for more. 1020 1021``` 1022import { Command } from '@commander-js/extra-typings'; 1023``` 1024 1025ts-node: If you use `ts-node` and stand-alone executable subcommands written as `.ts` files, you need to call your program through node to get the subcommands called correctly. e.g. 1026 1027```sh 1028node -r ts-node/register pm.ts 1029``` 1030 1031### createCommand() 1032 1033This factory function creates a new command. It is exported and may be used instead of using `new`, like: 1034 1035```js 1036const { createCommand } = require('commander'); 1037const program = createCommand(); 1038``` 1039 1040`createCommand` is also a method of the Command object, and creates a new command rather than a subcommand. This gets used internally 1041when creating subcommands using `.command()`, and you may override it to 1042customise the new subcommand (example file [custom-command-class.js](./examples/custom-command-class.js)). 1043 1044### Node options such as `--harmony` 1045 1046You can enable `--harmony` option in two ways: 1047 1048- Use `#! /usr/bin/env node --harmony` in the subcommands scripts. (Note Windows does not support this pattern.) 1049- Use the `--harmony` option when call the command, like `node --harmony examples/pm publish`. The `--harmony` option will be preserved when spawning subcommand process. 1050 1051### Debugging stand-alone executable subcommands 1052 1053An executable subcommand is launched as a separate child process. 1054 1055If you are using the node inspector for [debugging](https://nodejs.org/en/docs/guides/debugging-getting-started/) executable subcommands using `node --inspect` et al, 1056the inspector port is incremented by 1 for the spawned subcommand. 1057 1058If you are using VSCode to debug executable subcommands you need to set the `"autoAttachChildProcesses": true` flag in your launch.json configuration. 1059 1060### Display error 1061 1062This routine is available to invoke the Commander error handling for your own error conditions. (See also the next section about exit handling.) 1063 1064As well as the error message, you can optionally specify the `exitCode` (used with `process.exit`) 1065and `code` (used with `CommanderError`). 1066 1067```js 1068program.error('Password must be longer than four characters'); 1069program.error('Custom processing has failed', { exitCode: 2, code: 'my.custom.error' }); 1070``` 1071 1072### Override exit and output handling 1073 1074By default Commander calls `process.exit` when it detects errors, or after displaying the help or version. You can override 1075this behaviour and optionally supply a callback. The default override throws a `CommanderError`. 1076 1077The override callback is passed a `CommanderError` with properties `exitCode` number, `code` string, and `message`. The default override behaviour is to throw the error, except for async handling of executable subcommand completion which carries on. The normal display of error messages or version or help 1078is not affected by the override which is called after the display. 1079 1080```js 1081program.exitOverride(); 1082 1083try { 1084 program.parse(process.argv); 1085} catch (err) { 1086 // custom processing... 1087} 1088``` 1089 1090By default Commander is configured for a command-line application and writes to stdout and stderr. 1091You can modify this behaviour for custom applications. In addition, you can modify the display of error messages. 1092 1093Example file: [configure-output.js](./examples/configure-output.js) 1094 1095```js 1096function errorColor(str) { 1097 // Add ANSI escape codes to display text in red. 1098 return `\x1b[31m${str}\x1b[0m`; 1099} 1100 1101program 1102 .configureOutput({ 1103 // Visibly override write routines as example! 1104 writeOut: (str) => process.stdout.write(`[OUT] ${str}`), 1105 writeErr: (str) => process.stdout.write(`[ERR] ${str}`), 1106 // Highlight errors in color. 1107 outputError: (str, write) => write(errorColor(str)) 1108 }); 1109``` 1110 1111### Additional documentation 1112 1113There is more information available about: 1114 1115- [deprecated](./docs/deprecated.md) features still supported for backwards compatibility 1116- [options taking varying arguments](./docs/options-taking-varying-arguments.md) 1117 1118## Support 1119 1120The current version of Commander is fully supported on Long Term Support versions of Node.js, and requires at least v12.20.0. 1121(For older versions of Node.js, use an older version of Commander.) 1122 1123The main forum for free and community support is the project [Issues](https://github.com/tj/commander.js/issues) on GitHub. 1124 1125### Commander for enterprise 1126 1127Available as part of the Tidelift Subscription 1128 1129The maintainers of Commander and thousands of other packages are working with Tidelift to deliver commercial support and maintenance for the open source dependencies you use to build your applications. Save time, reduce risk, and improve code health, while paying the maintainers of the exact dependencies you use. [Learn more.](https://tidelift.com/subscription/pkg/npm-commander?utm_source=npm-commander&utm_medium=referral&utm_campaign=enterprise&utm_term=repo) 1130