yargs / yargs/yargs

Help is shown if async command handler fails

Open
#2,394 3 comments 2 reactions 0 assignees View on GitHub

Nobody has claimed this yet.

Dominant language
JavaScript
Stars
11.5k
Forks
1k
PR merge metrics
No merged PRs in 30d

Description

When an async command handler throws an error (more specifically: when a command handler returns a promise that rejects), yargs shows the help output, even though the user specified a valid command and options. As a user I find this really confusing because it seems to imply that I mistyped a command. I don't expect to see the help output if a command fails for a reason other than me passing an invalid argument, like if a command fails from a connection error.

Help output is not shown when a non-async command handler throws an errors. This matches my expectations. I'd expect async command handlers would work like this too.

Example program with an async command handler that throws an error:

const yargs = require('yargs');

yargs
  .scriptName('fooAsync.js')
  .command(
    'upload',
    'Upload some data',
    {
      commit: {
        type: 'string',
        nargs: 1,
        defaultDescription: 'currently checked out commit',
      },
    },
    async argv => {
      console.log(`uploading (commit: ${argv.commit})`);
      throw new Error('uh oh upload failed');
    },
  )
  .parse();
% node fooAsync.js upload --commit ABC
uploading (commit: ABC)
fooAsync.js upload

Upload some data

Options:
  --help     Show help                                                 [boolean]
  --version  Show version number                                       [boolean]
  --commit                      [string] [default: currently checked out commit]

Error: uh oh upload failed
    at Object.handler (/Users/chris/Desktop/foo/fooAsync.js:17:13)
    at /Users/chris/Desktop/foo/node_modules/yargs/build/index.cjs:1:8993
    at j (/Users/chris/Desktop/foo/node_modules/yargs/build/index.cjs:1:4956)
    at _.handleValidationAndGetResult (/Users/chris/Desktop/foo/node_modules/yargs/build/index.cjs:1:8962)
    at _.applyMiddlewareAndGetResult (/Users/chris/Desktop/foo/node_modules/yargs/build/index.cjs:1:9604)
    at _.runCommand (/Users/chris/Desktop/foo/node_modules/yargs/build/index.cjs:1:7231)
    at [runYargsParserAndExecuteCommands] (/Users/chris/Desktop/foo/node_modules/yargs/build/index.cjs:1:58539)
    at te.parse (/Users/chris/Desktop/foo/node_modules/yargs/build/index.cjs:1:40478)
    at Object.<anonymous> (/Users/chris/Desktop/foo/fooAsync.js:20:4)
    at Module._compile (node:internal/modules/cjs/loader:1376:14)

Using yargs 17.7.2 and node v20.11.1, v21.7.1.

Contributor guide

Open the contributing guide

First steps

  1. Read the whole issue, then the project's contributing guide.
  2. Comment on the issue to say you are picking it up — it saves two people doing the same work.
  3. Fork the repository and make your change on a branch.
  4. Open a pull request that references the issue number.

Research direction

Start by reproducing the behavior with the async command handler example in the issue, using yargs 17.7.2 and Node.js. Trace the async handler path shown in the stack trace and verify that a rejected promise reports the error without displaying help, while invalid arguments still display help.

Written by the indexing model from the issue text.

Assessment

Tech stack
javascript
Domain
cli
Issue type
Bug
Difficulty
3/5
Estimated time
1-2 days
Activity status
Stale
Clarity
Clearly specified
Newbie friendliness
45/100

Get new issues in your inbox

A short digest of beginner-friendly GitHub issues.