Skip to content

cli: improve output and consistency for unknown (sub)commands - #5234

Merged
thaJeztah merged 2 commits into
docker:masterfrom
thaJeztah:nicer_missing_commands
Jul 16, 2024
Merged

cli: improve output and consistency for unknown (sub)commands#5234
thaJeztah merged 2 commits into
docker:masterfrom
thaJeztah:nicer_missing_commands

Conversation

@thaJeztah

@thaJeztahthaJeztah commented Jul 4, 2024

Copy link
Copy Markdown
Member

cli: improve output and consistency for unknown (sub)commands

Before this patch, output for invalid top-level and sub-commands differed.
For top-level commands, the CLI would print an error-message and a suggestion
to use --help. For missing subcommands, we would hit a different code-path,
and different output, which includes full "usage" / "help" output.

While it is a common convention to show usage output, and may have been
a nice gesture when docker was still young and only had a few commands
and options ("you did something wrong; here's an overview of what you
can use"), that's no longer the case, and many commands have a very
long output.

The result of this is that the error message, which is the relevant
information in this case - "You mis-typed something" - is lost in the
output, and hard to find (sometimes even requiring scrolling back).

The output is also confusing, because it looks like something ran
successfully (most of the output is not about the error!).

Even further; the suggested resolution (try --help to see the correct
options) is rather redundant, because running teh command with --help
produces exactly the same output as was just showh, baring the error
message. As a fun fact, due to the usage output being printed, the
output even contains not one, but two "call to actions";

  • See 'docker volume --help'. (under the erro message)
  • Run 'docker volume COMMAND --help' for more information on a command.
    (under the usage output)

In short; the output is too verbose, confusing, and doesn't provide
a good UX. Let's reduce the output produced so that the focus is on the
important information.

This patch:

  • Changes the usage to the short-usage.
  • Changes the error-message to mention the full command instead of only
    the command after docker (so docker no-such-command instead of
    no-such-command).
  • Prefixes the error message with the binary / root-command name
    (usually docker:); this is something we can still decide on, but
    it's a pattern we already use in some places. The motivation for this
    is that docker commands can often produce output that's a combination
    of output from the CLI itself, output from the daemon, and even output
    from the container. The docker: prefix helps to distinguish where
    the message originated from (the docker CLI in this case).
  • Adds an empty line between the error-message and the "call to action"
    (Run 'docker volume --help'... in the example below). This helps
    separating the error message ("unkown flag") from the call-to-action.

Before this patch:

Unknown top-level command:

docker nosuchcommand foo
docker: 'nosuchcommand' is not a docker command.
See 'docker --help'

Unknown sub-command:

docker volume nosuchcommand foo
Usage: docker volume COMMAND
Manage volumes
Commands:
create Create a volume
inspect Display detailed information on one or more volumes
ls List volumes
prune Remove unused local volumes
rm Remove one or more volumes
update Update a volume (cluster volumes only)
Run 'docker volume COMMAND --help' for more information on a command.

After this patch:

Unknown top-level command:

docker nosuchcommand foo
docker: unknown command: docker nosuchcommand
Run 'docker --help' for more information

Unknown sub-command:

docker volume nosuchcommand foo
docker: unknown command: 'docker volume nosuchcommand'
Usage: docker volume COMMAND
Run 'docker volume --help' for more information

cli: improve argument validation output

Improve the output for these validation errors:

  • Removes the short command description from the output. This information
    does not provide much useful help, and distracts from the error message.
  • Reduces punctuation, and
  • Prefixes the error message with the binary / root-command name
    (usually docker:) to be consistent with other similar errors.
  • Adds an empty line between the error-message and the "call to action"
    (Run 'docker volume --help'... in the example below). This helps
    separating the error message and "usage" from the call-to-action.

Before this patch:

$ docker volume ls one two three
"docker volume ls" accepts no arguments.
See 'docker volume ls --help'.
Usage: docker volume ls [OPTIONS]
List volumes
$ docker volume create one two three
"docker volume create" requires at most 1 argument.
See 'docker volume create --help'.
Usage: docker volume create [OPTIONS] [VOLUME]
Create a volume

With this patch:

$ docker volume ls one two three
docker: 'docker volume ls' accepts no arguments
Usage: docker volume ls [OPTIONS]
Run 'docker volume ls --help' for more information
$ docker voludocker volume create one two three
docker: 'docker volume create' requires at most 1 argument
Usage: docker volume create [OPTIONS] [VOLUME]
SRun 'docker volume create --help' for more information

- Description for the changelog

- improve output and consistency for unknown (sub)commands
- improve output for invalid arguments

- A picture of a cute animal (not mandatory but encouraged)

@codecov-commenter

codecov-commenter commented Jul 4, 2024

Copy link
Copy Markdown

Codecov Report

Attention: Patch coverage is 61.90476% with 8 lines in your changes missing coverage. Please review.

Project coverage is 61.46%. Comparing base (5aae44b) to head (c60b360).

Additional details and impacted files
@@ Coverage Diff @@## master #5234 +/- ##
==========================================
- Coverage 61.48% 61.46% -0.03% 
==========================================
Files 298 298 Lines 20813 20816 +3 ==========================================
- Hits 12797 12794 -3 - Misses 7104 7110 +6 
Partials 912 912 

@thaJeztah
thaJeztah marked this pull request as draft July 4, 2024 23:28
@thaJeztahthaJeztah changed the title cli: improve output and consistency for missing (sub)commandscli: improve output and consistency for unknown (sub)commandsJul 5, 2024
Before this patch, output for invalid top-level and sub-commands differed.
For top-level commands, the CLI would print an error-message and a suggestion
to use `--help`. For missing *subcommands*, we would hit a different code-path,
and different output, which includes full "usage" / "help" output.
While it is a common convention to show usage output, and may have been
a nice gesture when docker was still young and only had a few commands
and options ("you did something wrong; here's an overview of what you
can use"), that's no longer the case, and many commands have a _very_
long output.
The result of this is that the error message, which is the relevant
information in this case - "You mis-typed something" - is lost in the
output, and hard to find (sometimes even requiring scrolling back).
The output is also confusing, because it _looks_ like something ran
successfully (most of the output is not about the error!).
Even further; the suggested resolution (try `--help` to see the correct
options) is rather redundant, because running teh command with `--help`
produces _exactly_ the same output as was just showh, baring the error
message. As a fun fact, due to the usage output being printed, the
output even contains not one, but _two_ "call to actions";
- `See 'docker volume --help'.` (under the erro message)
- `Run 'docker volume COMMAND --help' for more information on a command.`
(under the usage output)
In short; the output is too verbose, confusing, and doesn't provide
a good UX. Let's reduce the output produced so that the focus is on the
important information.
This patch:
- Changes the usage to the short-usage.
- Changes the error-message to mention the _full_ command instead of only
the command after `docker` (so `docker no-such-command` instead of
`no-such-command`).
- Prefixes the error message with the binary / root-command name
(usually `docker:`); this is something we can still decide on, but
it's a pattern we already use in some places. The motivation for this
is that `docker` commands can often produce output that's a combination
of output from the CLI itself, output from the daemon, and even output
from the container. The `docker:` prefix helps to distinguish where
the message originated from (the `docker` CLI in this case).
- Adds an empty line between the error-message and the "call to action"
(`Run 'docker volume --help'...` in the example below). This helps
separating the error message ("unkown flag") from the call-to-action.
Before this patch:
Unknown top-level command:
docker nosuchcommand foo
docker: 'nosuchcommand' is not a docker command.
See 'docker --help'
Unknown sub-command:
docker volume nosuchcommand foo
Usage: docker volume COMMAND
Manage volumes
Commands:
create Create a volume
inspect Display detailed information on one or more volumes
ls List volumes
prune Remove unused local volumes
rm Remove one or more volumes
update Update a volume (cluster volumes only)
Run 'docker volume COMMAND --help' for more information on a command.
After this patch:
Unknown top-level command:
docker nosuchcommand foo
docker: unknown command: docker nosuchcommand
Run 'docker --help' for more information
Unknown sub-command:
docker volume nosuchcommand foo
docker: unknown command: 'docker volume nosuchcommand'
Usage: docker volume COMMAND
Run 'docker volume --help' for more information
Signed-off-by: Sebastiaan van Stijn <github@gone.nl>
@thaJeztah
thaJeztahforce-pushed the nicer_missing_commands branch 3 times, most recently from 5590f9a to 3efd491CompareJuly 5, 2024 01:04
@thaJeztahthaJeztah self-assigned this Jul 5, 2024
@thaJeztah
thaJeztahforce-pushed the nicer_missing_commands branch 7 times, most recently from 642bde5 to 0a836a9CompareJuly 5, 2024 01:32
Improve the output for these validation errors:
- Removes the short command description from the output. This information
does not provide much useful help, and distracts from the error message.
- Reduces punctuation, and
- Prefixes the error message with the binary / root-command name
(usually `docker:`) to be consistent with other similar errors.
- Adds an empty line between the error-message and the "call to action"
(`Run 'docker volume --help'...` in the example below). This helps
separating the error message and "usage" from the call-to-action.
Before this patch:
$ docker volume ls one two three
"docker volume ls" accepts no arguments.
See 'docker volume ls --help'.
Usage: docker volume ls [OPTIONS]
List volumes
$ docker volume create one two three
"docker volume create" requires at most 1 argument.
See 'docker volume create --help'.
Usage: docker volume create [OPTIONS] [VOLUME]
Create a volume
With this patch:
$ docker volume ls one two three
docker: 'docker volume ls' accepts no arguments
Usage: docker volume ls [OPTIONS]
Run 'docker volume ls --help' for more information
$ docker voludocker volume create one two three
docker: 'docker volume create' requires at most 1 argument
Usage: docker volume create [OPTIONS] [VOLUME]
SRun 'docker volume create --help' for more information
Signed-off-by: Sebastiaan van Stijn <github@gone.nl>
@thaJeztah
thaJeztahforce-pushed the nicer_missing_commands branch from 0a836a9 to c60b360CompareJuly 5, 2024 01:35
@thaJeztah
thaJeztah marked this pull request as ready for review July 5, 2024 09:49
@thaJeztah
thaJeztah requested review from a team and silvin-lubecki as code ownersJuly 5, 2024 09:49

@krissettokrissetto left a comment

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

overall LGTM, just left a small suggestion in the comments

Comment threadcli/required.go
if cmd.HasSubCommands() {
return errors.Errorf("\n" + strings.TrimRight(cmd.UsageString(), "\n"))
return errors.Errorf(
"%[1]s: unknown command: %[2]s %[3]s\n\nUsage: %[4]s\n\nRun '%[2]s --help' for more information",

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

For consistency with other error messages where we print out commands the user has inputted (or could input, like Run '%[2]s --help' for more information further in this message), maybe it could make sense to surround %[2]s %[3]s with single quotes' as well.

I think it could make the message a little bit more readable, given we are prefixing docker: as well. WDYT?

Copy link
Copy Markdown
MemberAuthor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

OHMAN I went back and forth on some of these; initially I had the quotes, but then also looked at unknown flag: which didn't have them; that one is generated by Cobra (or spf13/flags), so not something I could immediately change.

Overall I somewhat think that the quotes may be good to add yes; perhaps still ok for a follow-up pass?

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Yeah for sure! It's definitely a minor thing, but if users are anything like me they do appreciate consistency in the outputs. We'll get to it in a separate pass 👍

@BenehikoBenehiko left a comment

Copy link
Copy Markdown
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

LGTM

Sign up for freeto join this conversation on GitHub. Already have an account? Sign in to comment

Projects

None yet

Development

Successfully merging this pull request may close these issues.

4 participants

@thaJeztah@codecov-commenter@Benehiko@krissetto