Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

argparse: Accept the progname in the command path #9160

Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
16 changes: 15 additions & 1 deletion lib/stdlib/src/argparse.erl
Original file line number Diff line number Diff line change
Expand Up @@ -1592,7 +1592,21 @@ is_valid_command_help(_) ->

format_help({ProgName, Root}, Format) ->
Prefix = hd(maps:get(prefixes, Format, [$-])),
Nested = maps:get(command, Format, []),
Nested0 = maps:get(command, Format, [ProgName]),
%% The command path should always start with the progname, that's why it is
%% dropped here to keep the command and sub-commands only.
%%
%% However, earlier versions of this function did not drop that progname.
%% The function thus used to crash with a badkey excception if the caller
%% passed the `CmdPath' returned by `parse/2' to this function's `command'.
%% Therefore, to keep backward compatibility, if the command path does not
%% start with the progname, it uses the entire list untouched.
Nested = case Nested0 of
[ProgName | Tail] ->
Tail;
_ ->
Nested0
end,
%% descent into commands collecting all options on the way
{_CmdName, Cmd, AllArgs} = collect_options(ProgName, Root, Nested, []),
%% split arguments into Flags, Options, Positional, and create help lines
Expand Down
9 changes: 6 additions & 3 deletions lib/stdlib/test/argparse_SUITE.erl
Original file line number Diff line number Diff line change
Expand Up @@ -782,6 +782,9 @@ usage(Config) when is_list(Config) ->
" --unsafe unsafe atom (atom)\n"
" --safe safe atom (existing atom)\n"
" -foobar foobaring option\n",
?assertEqual(Usage, unicode:characters_to_list(argparse:help(Cmd,
#{progname => "erl", command => ["erl", "start"]}))),
%% Same assertion for the backward-compatible way of calling `argparse:help/2'.
?assertEqual(Usage, unicode:characters_to_list(argparse:help(Cmd,
#{progname => "erl", command => ["start"]}))),
FullCmd = "Usage:\n erl"
Expand Down Expand Up @@ -812,7 +815,7 @@ usage(Config) when is_list(Config) ->
" --float floating-point long form argument (float), default: 3.14\n"
" ---extra extra option very deep\n",
?assertEqual(CrawlerStatus, unicode:characters_to_list(argparse:help(Cmd,
#{progname => "erl", command => ["status", "crawler"]}))),
#{progname => "erl", command => ["erl", "status", "crawler"]}))),
ok.

usage_required_args() ->
Expand All @@ -821,7 +824,7 @@ usage_required_args() ->
usage_required_args(Config) when is_list(Config) ->
Cmd = #{commands => #{"test" => #{arguments => [#{name => required, required => true, long => "-req"}]}}},
Expected = "Usage:\n " ++ prog() ++ " test --req <required>\n\nOptional arguments:\n --req required\n",
?assertEqual(Expected, unicode:characters_to_list(argparse:help(Cmd, #{command => ["test"]}))).
?assertEqual(Expected, unicode:characters_to_list(argparse:help(Cmd, #{command => ["erl", "test"]}))).

usage_template() ->
[{doc, "Tests templates in help/usage"}].
Expand Down Expand Up @@ -888,7 +891,7 @@ usage_args_ordering(Config) when is_list(Config) ->
" second second\n"
" third third\n"
" fourth fourth\n",
unicode:characters_to_list(argparse:help(Cmd, #{command => ["cmd"]}))),
unicode:characters_to_list(argparse:help(Cmd, #{command => ["erl", "cmd"]}))),
ok.

parser_error_usage() ->
Expand Down
Loading