1727: Fix `-- subcommand` error r=pksunkara a=ldm0



Co-authored-by: Donough Liu <ldm2993593805@163.com>
This commit is contained in:
bors[bot] 2020-03-05 13:01:05 +00:00 committed by GitHub
commit 19c20f7c00
No known key found for this signature in database
GPG key ID: 4AEE18F83AFDEB23
4 changed files with 30 additions and 20 deletions

View file

@ -698,7 +698,7 @@ pub enum AppSettings {
/// **CAUTION:** This setting can interfere with [positional/free arguments], take care when
/// designing CLIs which allow inferred subcommands and have potential positional/free
/// arguments whose values could start with the same characters as subcommands. If this is the
/// case, it's recommended to use settings such as [`AppSeettings::ArgsNegateSubcommands`] in
/// case, it's recommended to use settings such as [`AppSettings::ArgsNegateSubcommands`] in
/// conjunction with this setting.
///
/// # Examples
@ -716,7 +716,7 @@ pub enum AppSettings {
/// [`subcommands`]: ./struct..html
/// [positional/free arguments]: ./struct.Arg.html#method.index
/// [aliases]: ./struct.App.html#method.alias
/// [`AppSeettings::ArgsNegateSubcommands`]: ./enum.AppSettings.html#variant.ArgsNegateSubcommands
/// [`AppSettings::ArgsNegateSubcommands`]: ./enum.AppSettings.html#variant.ArgsNegateSubcommands
InferSubcommands,
/// Specifies that the parser should not assume the first argument passed is the binary name.

View file

@ -2929,7 +2929,7 @@ impl<'help> Arg<'help> {
/// `--option=val1,val2,val3` is three values for the `--option` argument. If you wish to
/// change the delimiter to another character you can use [`Arg::value_delimiter(char)`],
/// alternatively you can turn delimiting values **OFF** by using
/// [`Arg::unset_setting(ArgSettings::UseValueDelimiter`]
/// [`Arg::unset_setting(ArgSettings::UseValueDelimiter)`]
///
/// # Examples
///
@ -2954,7 +2954,7 @@ impl<'help> Arg<'help> {
/// assert_eq!(m.value_of("mode"), Some("fast"));
/// ```
/// [`Arg::value_delimiter(char)`]: ./struct.Arg.html#method.value_delimiter
/// [`Arg::unset_setting(ArgSettings::UseValueDelimiter`]: ./enum.ArgSettings.html#variant.UseValueDelimiter
/// [`Arg::unset_setting(ArgSettings::UseValueDelimiter)`]: ./enum.ArgSettings.html#variant.UseValueDelimiter
/// [multiple values]: ./enum.ArgSettings.html#variant.MultipleValues
pub fn takes_value(self, tv: bool) -> Self {
if tv {

View file

@ -541,23 +541,24 @@ where
// get the next value from the iterator
continue;
}
}
if !(self.is_set(AS::ArgsNegateSubcommands) && self.is_set(AS::ValidArgFound)
|| self.is_set(AS::AllowExternalSubcommands)
|| self.is_set(AS::InferSubcommands))
{
let cands =
suggestions::did_you_mean(&*arg_os.to_string_lossy(), sc_names!(self.app));
if !cands.is_empty() {
let cands: Vec<_> = cands.iter().map(|cand| format!("'{}'", cand)).collect();
return Err(ClapError::invalid_subcommand(
arg_os.to_string_lossy().into_owned(),
cands.join(" or "),
self.app.bin_name.as_ref().unwrap_or(&self.app.name),
&*Usage::new(self).create_usage_with_title(&[]),
self.app.color(),
));
if !(self.is_set(AS::ArgsNegateSubcommands) && self.is_set(AS::ValidArgFound)
|| self.is_set(AS::AllowExternalSubcommands)
|| self.is_set(AS::InferSubcommands))
{
let cands =
suggestions::did_you_mean(&*arg_os.to_string_lossy(), sc_names!(self.app));
if !cands.is_empty() {
let cands: Vec<_> =
cands.iter().map(|cand| format!("'{}'", cand)).collect();
return Err(ClapError::invalid_subcommand(
arg_os.to_string_lossy().into_owned(),
cands.join(" or "),
self.app.bin_name.as_ref().unwrap_or(&self.app.name),
&*Usage::new(self).create_usage_with_title(&[]),
self.app.color(),
));
}
}
}

View file

@ -283,3 +283,12 @@ fn issue_1161_multiple_hyphen_hyphen() {
assert_eq!(expected, actual);
}
#[test]
fn issue_1722_not_emit_error_when_arg_follows_similar_to_a_subcommand() {
let m = App::new("myprog")
.subcommand(App::new("subcommand"))
.arg(Arg::with_name("argument"))
.try_get_matches_from(vec!["myprog", "--", "subcommand"]);
assert_eq!(m.unwrap().value_of("argument"), Some("subcommand"));
}