1 #[cfg(debug_assertions)]
2 mod debug_asserts;
3 mod settings;
4 #[cfg(test)]
5 mod tests;
6 
7 pub use self::settings::{AppFlags, AppSettings};
8 
9 // Std
10 use std::{
11     collections::HashMap,
12     env,
13     ffi::OsString,
14     fmt,
15     io::{self, Write},
16     ops::Index,
17     path::Path,
18 };
19 
20 // Third Party
21 use os_str_bytes::RawOsStr;
22 #[cfg(feature = "yaml")]
23 use yaml_rust::Yaml;
24 
25 // Internal
26 use crate::{
27     build::{arg::ArgProvider, Arg, ArgGroup, ArgSettings},
28     mkeymap::MKeyMap,
29     output::{fmt::Colorizer, Help, HelpWriter, Usage},
30     parse::{ArgMatcher, ArgMatches, Input, Parser},
31     util::{color::ColorChoice, Id, Key},
32     Error, ErrorKind, Result as ClapResult, INTERNAL_ERROR_MSG,
33 };
34 
35 /// Build a command-line interface.
36 ///
37 /// This includes defining arguments, subcommands, parser behavior, and help output.
38 /// Once all configuration is complete,
39 /// the [`App::get_matches`] family of methods starts the runtime-parsing
40 /// process. These methods then return information about the user supplied
41 /// arguments (or lack thereof).
42 ///
43 /// When deriving a [`Parser`][crate::Parser], you can use
44 /// [`IntoApp::into_app`][crate::IntoApp::into_app] to access the
45 /// `App`.
46 ///
47 /// # Examples
48 ///
49 /// ```no_run
50 /// # use clap::{App, Arg};
51 /// let m = App::new("My Program")
52 ///     .author("Me, me@mail.com")
53 ///     .version("1.0.2")
54 ///     .about("Explains in brief what the program does")
55 ///     .arg(
56 ///         Arg::new("in_file").index(1)
57 ///     )
58 ///     .after_help("Longer explanation to appear after the options when \
59 ///                  displaying the help information from --help or -h")
60 ///     .get_matches();
61 ///
62 /// // Your program logic starts here...
63 /// ```
64 /// [`App::get_matches`]: App::get_matches()
65 #[derive(Default, Debug, Clone, PartialEq, Eq)]
66 pub struct App<'help> {
67     pub(crate) id: Id,
68     pub(crate) name: String,
69     pub(crate) long_flag: Option<&'help str>,
70     pub(crate) short_flag: Option<char>,
71     pub(crate) bin_name: Option<String>,
72     pub(crate) author: Option<&'help str>,
73     pub(crate) version: Option<&'help str>,
74     pub(crate) long_version: Option<&'help str>,
75     pub(crate) about: Option<&'help str>,
76     pub(crate) long_about: Option<&'help str>,
77     pub(crate) before_help: Option<&'help str>,
78     pub(crate) before_long_help: Option<&'help str>,
79     pub(crate) after_help: Option<&'help str>,
80     pub(crate) after_long_help: Option<&'help str>,
81     pub(crate) aliases: Vec<(&'help str, bool)>, // (name, visible)
82     pub(crate) short_flag_aliases: Vec<(char, bool)>, // (name, visible)
83     pub(crate) long_flag_aliases: Vec<(&'help str, bool)>, // (name, visible)
84     pub(crate) usage_str: Option<&'help str>,
85     pub(crate) usage: Option<String>,
86     pub(crate) help_str: Option<&'help str>,
87     pub(crate) disp_ord: Option<usize>,
88     pub(crate) term_w: Option<usize>,
89     pub(crate) max_w: Option<usize>,
90     pub(crate) template: Option<&'help str>,
91     pub(crate) settings: AppFlags,
92     pub(crate) g_settings: AppFlags,
93     pub(crate) args: MKeyMap<'help>,
94     pub(crate) subcommands: Vec<App<'help>>,
95     pub(crate) replacers: HashMap<&'help str, &'help [&'help str]>,
96     pub(crate) groups: Vec<ArgGroup<'help>>,
97     pub(crate) current_help_heading: Option<&'help str>,
98     pub(crate) subcommand_value_name: Option<&'help str>,
99     pub(crate) subcommand_heading: Option<&'help str>,
100 }
101 
102 impl<'help> App<'help> {
103     /// Creates a new instance of an `App`.
104     ///
105     /// It is common, but not required, to use binary name as the `name`. This
106     /// name will only be displayed to the user when they request to print
107     /// version or help and usage information.
108     ///
109     /// See also [`app_from_crate!`](crate::app_from_crate!) and [`crate_name!`](crate::crate_name!).
110     ///
111     /// # Examples
112     ///
113     /// ```no_run
114     /// # use clap::App;
115     /// App::new("My Program")
116     /// # ;
117     /// ```
new<S: Into<String>>(name: S) -> Self118     pub fn new<S: Into<String>>(name: S) -> Self {
119         /// The actual implementation of `new`, non-generic to save code size.
120         ///
121         /// If we don't do this rustc will unnecessarily generate multiple versions
122         /// of this code.
123         fn new_inner<'help>(name: String) -> App<'help> {
124             App {
125                 id: Id::from(&*name),
126                 name,
127                 ..Default::default()
128             }
129             .arg(
130                 Arg::new("help")
131                     .long("help")
132                     .help("Print help information")
133                     .global(true)
134                     .generated(),
135             )
136             .arg(
137                 Arg::new("version")
138                     .long("version")
139                     .help("Print version information")
140                     .global(true)
141                     .generated(),
142             )
143         }
144 
145         new_inner(name.into())
146     }
147 
148     /// Adds an [argument] to the list of valid possibilities.
149     ///
150     /// # Examples
151     ///
152     /// ```no_run
153     /// # use clap::{App, arg, Arg};
154     /// App::new("myprog")
155     ///     // Adding a single "flag" argument with a short and help text, using Arg::new()
156     ///     .arg(
157     ///         Arg::new("debug")
158     ///            .short('d')
159     ///            .help("turns on debugging mode")
160     ///     )
161     ///     // Adding a single "option" argument with a short, a long, and help text using the less
162     ///     // verbose Arg::from()
163     ///     .arg(
164     ///         arg!(-c --config <CONFIG> "Optionally sets a config file to use")
165     ///     )
166     /// # ;
167     /// ```
168     /// [argument]: Arg
169     #[must_use]
arg<A: Into<Arg<'help>>>(mut self, a: A) -> Self170     pub fn arg<A: Into<Arg<'help>>>(mut self, a: A) -> Self {
171         let mut arg = a.into();
172         arg.help_heading.get_or_insert(self.current_help_heading);
173         self.args.push(arg);
174         self
175     }
176 
177     /// Adds multiple [arguments] to the list of valid possibilities.
178     ///
179     /// # Examples
180     ///
181     /// ```no_run
182     /// # use clap::{App, arg, Arg};
183     /// App::new("myprog")
184     ///     .args(&[
185     ///         arg!("[debug] -d 'turns on debugging info'"),
186     ///         Arg::new("input").index(1).help("the input file to use")
187     ///     ])
188     /// # ;
189     /// ```
190     /// [arguments]: Arg
191     #[must_use]
args<I, T>(mut self, args: I) -> Self where I: IntoIterator<Item = T>, T: Into<Arg<'help>>,192     pub fn args<I, T>(mut self, args: I) -> Self
193     where
194         I: IntoIterator<Item = T>,
195         T: Into<Arg<'help>>,
196     {
197         let args = args.into_iter();
198         let (lower, _) = args.size_hint();
199         self.args.reserve(lower);
200 
201         for arg in args {
202             self = self.arg(arg);
203         }
204         self
205     }
206 
207     /// Allows one to mutate an [`Arg`] after it's been added to an [`App`].
208     ///
209     /// This can be useful for modifying the auto-generated help or version arguments.
210     ///
211     /// # Examples
212     ///
213     /// ```rust
214     /// # use clap::{App, Arg};
215     ///
216     /// let mut app = App::new("foo")
217     ///     .arg(Arg::new("bar")
218     ///         .short('b'))
219     ///     .mut_arg("bar", |a| a.short('B'));
220     ///
221     /// let res = app.try_get_matches_from_mut(vec!["foo", "-b"]);
222     ///
223     /// // Since we changed `bar`'s short to "B" this should err as there
224     /// // is no `-b` anymore, only `-B`
225     ///
226     /// assert!(res.is_err());
227     ///
228     /// let res = app.try_get_matches_from_mut(vec!["foo", "-B"]);
229     /// assert!(res.is_ok());
230     /// ```
231     #[must_use]
mut_arg<T, F>(mut self, arg_id: T, f: F) -> Self where F: FnOnce(Arg<'help>) -> Arg<'help>, T: Key + Into<&'help str>,232     pub fn mut_arg<T, F>(mut self, arg_id: T, f: F) -> Self
233     where
234         F: FnOnce(Arg<'help>) -> Arg<'help>,
235         T: Key + Into<&'help str>,
236     {
237         let arg_id: &str = arg_id.into();
238         let id = Id::from(arg_id);
239 
240         let mut a = self.args.remove_by_name(&id).unwrap_or_else(|| Arg {
241             id,
242             name: arg_id,
243             ..Arg::default()
244         });
245 
246         if a.provider == ArgProvider::Generated {
247             a.provider = ArgProvider::GeneratedMutated;
248         }
249 
250         self.args.push(f(a));
251         self
252     }
253 
254     /// Adds an [`ArgGroup`] to the application.
255     ///
256     /// [`ArgGroup`]s are a family of related arguments.
257     /// By placing them in a logical group, you can build easier requirement and exclusion rules.
258     ///
259     /// Example use cases:
260     /// - Make an entire [`ArgGroup`] required, meaning that one (and *only*
261     ///   one) argument from that group must be present at runtime.
262     /// - Name an [`ArgGroup`] as a conflict to another argument.
263     ///   Meaning any of the arguments that belong to that group will cause a failure if present with
264     ///   the conflicting argument.
265     /// - Ensure exclusion between arguments.
266     /// - Extract a value from a group instead of determining exactly which argument was used.
267     ///
268     /// # Examples
269     ///
270     /// The following example demonstrates using an [`ArgGroup`] to ensure that one, and only one,
271     /// of the arguments from the specified group is present at runtime.
272     ///
273     /// ```no_run
274     /// # use clap::{App, arg, ArgGroup};
275     /// App::new("app")
276     ///     .arg(arg!("--set-ver [ver] 'set the version manually'"))
277     ///     .arg(arg!("--major 'auto increase major'"))
278     ///     .arg(arg!("--minor 'auto increase minor'"))
279     ///     .arg(arg!("--patch 'auto increase patch'"))
280     ///     .group(ArgGroup::new("vers")
281     ///          .args(&["set-ver", "major", "minor","patch"])
282     ///          .required(true))
283     /// # ;
284     /// ```
285     #[inline]
286     #[must_use]
group<G: Into<ArgGroup<'help>>>(mut self, group: G) -> Self287     pub fn group<G: Into<ArgGroup<'help>>>(mut self, group: G) -> Self {
288         self.groups.push(group.into());
289         self
290     }
291 
292     /// Adds multiple [`ArgGroup`]s to the [`App`] at once.
293     ///
294     /// # Examples
295     ///
296     /// ```no_run
297     /// # use clap::{App, arg, ArgGroup};
298     /// App::new("app")
299     ///     .arg(arg!("--set-ver [ver] 'set the version manually'"))
300     ///     .arg(arg!("--major         'auto increase major'"))
301     ///     .arg(arg!("--minor         'auto increase minor'"))
302     ///     .arg(arg!("--patch         'auto increase patch'"))
303     ///     .arg(arg!("-c [FILE]       'a config file'"))
304     ///     .arg(arg!("-i [IFACE]      'an interface'"))
305     ///     .groups(&[
306     ///         ArgGroup::new("vers")
307     ///             .args(&["set-ver", "major", "minor","patch"])
308     ///             .required(true),
309     ///         ArgGroup::new("input")
310     ///             .args(&["c", "i"])
311     ///     ])
312     /// # ;
313     /// ```
314     #[must_use]
groups<I, T>(mut self, groups: I) -> Self where I: IntoIterator<Item = T>, T: Into<ArgGroup<'help>>,315     pub fn groups<I, T>(mut self, groups: I) -> Self
316     where
317         I: IntoIterator<Item = T>,
318         T: Into<ArgGroup<'help>>,
319     {
320         for g in groups.into_iter() {
321             self = self.group(g.into());
322         }
323         self
324     }
325 
326     /// Adds a subcommand to the list of valid possibilities.
327     ///
328     /// Subcommands are effectively sub-[`App`]s, because they can contain their own arguments,
329     /// subcommands, version, usage, etc. They also function just like [`App`]s, in that they get
330     /// their own auto generated help, version, and usage.
331     ///
332     /// A subcommand's [`App::name`] will be used for:
333     /// - The argument the user passes in
334     /// - Programmatically looking up the subcommand
335     ///
336     /// # Examples
337     ///
338     /// ```no_run
339     /// # use clap::{App, arg};
340     /// App::new("myprog")
341     ///     .subcommand(App::new("config")
342     ///         .about("Controls configuration features")
343     ///         .arg(arg!("<config> 'Required configuration file to use'")))
344     /// # ;
345     /// ```
346     #[inline]
347     #[must_use]
subcommand<S: Into<App<'help>>>(mut self, subcmd: S) -> Self348     pub fn subcommand<S: Into<App<'help>>>(mut self, subcmd: S) -> Self {
349         self.subcommands.push(subcmd.into());
350         self
351     }
352 
353     /// Adds multiple subcommands to the list of valid possibilities.
354     ///
355     /// # Examples
356     ///
357     /// ```rust
358     /// # use clap::{App, Arg, };
359     /// # App::new("myprog")
360     /// .subcommands( vec![
361     ///        App::new("config").about("Controls configuration functionality")
362     ///                                 .arg(Arg::new("config_file").index(1)),
363     ///        App::new("debug").about("Controls debug functionality")])
364     /// # ;
365     /// ```
366     /// [`IntoIterator`]: std::iter::IntoIterator
367     #[must_use]
subcommands<I, T>(mut self, subcmds: I) -> Self where I: IntoIterator<Item = T>, T: Into<App<'help>>,368     pub fn subcommands<I, T>(mut self, subcmds: I) -> Self
369     where
370         I: IntoIterator<Item = T>,
371         T: Into<App<'help>>,
372     {
373         for subcmd in subcmds.into_iter() {
374             self.subcommands.push(subcmd.into());
375         }
376         self
377     }
378 
379     /// Catch problems earlier in the development cycle.
380     ///
381     /// Most error states are handled as asserts under the assumption they are programming mistake
382     /// and not something to handle at runtime.  Rather than relying on tests (manual or automated)
383     /// that exhaustively test your CLI to ensure the asserts are evaluated, this will run those
384     /// asserts in a way convenient for running as a test.
385     ///
386     /// **Note::** This will not help with asserts in [`ArgMatches`], those will need exhaustive
387     /// testing of your CLI.
388     ///
389     /// # Examples
390     ///
391     /// ```rust
392     /// # use clap::{App, Arg};
393     /// fn app() -> App<'static> {
394     ///     App::new("foo")
395     ///         .arg(Arg::new("bar").short('b')
396     ///     )
397     /// }
398     ///
399     /// #[test]
400     /// fn verify_app() {
401     ///     app().debug_assert();
402     /// }
403     ///
404     /// fn main() {
405     ///     let m = app().get_matches_from(vec!["foo", "-b"]);
406     ///     println!("{}", m.is_present("bar"));
407     /// }
408     /// ```
debug_assert(mut self)409     pub fn debug_assert(mut self) {
410         self._build_all();
411     }
412 
413     /// Custom error message for post-parsing validation
414     ///
415     /// # Examples
416     ///
417     /// ```rust
418     /// # use clap::{App, ErrorKind};
419     /// let mut app = App::new("myprog");
420     /// let err = app.error(ErrorKind::InvalidValue, "Some failure case");
421     /// ```
error(&mut self, kind: ErrorKind, message: impl std::fmt::Display) -> Error422     pub fn error(&mut self, kind: ErrorKind, message: impl std::fmt::Display) -> Error {
423         Error::raw(kind, message).format(self)
424     }
425 
426     /// Parse [`env::args_os`], exiting on failure.
427     ///
428     /// # Panics
429     ///
430     /// If contradictory arguments or settings exist.
431     ///
432     /// # Examples
433     ///
434     /// ```no_run
435     /// # use clap::{App, Arg};
436     /// let matches = App::new("myprog")
437     ///     // Args and options go here...
438     ///     .get_matches();
439     /// ```
440     /// [`env::args_os`]: std::env::args_os()
441     /// [`App::try_get_matches_from_mut`]: App::try_get_matches_from_mut()
442     #[inline]
get_matches(self) -> ArgMatches443     pub fn get_matches(self) -> ArgMatches {
444         self.get_matches_from(&mut env::args_os())
445     }
446 
447     /// Parse [`env::args_os`], exiting on failure.
448     ///
449     /// Like [`App::get_matches`] but doesn't consume the `App`.
450     ///
451     /// # Panics
452     ///
453     /// If contradictory arguments or settings exist.
454     ///
455     /// # Examples
456     ///
457     /// ```no_run
458     /// # use clap::{App, Arg};
459     /// let mut app = App::new("myprog")
460     ///     // Args and options go here...
461     ///     ;
462     /// let matches = app.get_matches_mut();
463     /// ```
464     /// [`env::args_os`]: std::env::args_os()
465     /// [`App::get_matches`]: App::get_matches()
get_matches_mut(&mut self) -> ArgMatches466     pub fn get_matches_mut(&mut self) -> ArgMatches {
467         self.try_get_matches_from_mut(&mut env::args_os())
468             .unwrap_or_else(|e| e.exit())
469     }
470 
471     /// Parse [`env::args_os`], returning a [`clap::Result`] on failure.
472     ///
473     /// **NOTE:** This method WILL NOT exit when `--help` or `--version` (or short versions) are
474     /// used. It will return a [`clap::Error`], where the [`kind`] is a
475     /// [`ErrorKind::DisplayHelp`] or [`ErrorKind::DisplayVersion`] respectively. You must call
476     /// [`Error::exit`] or perform a [`std::process::exit`].
477     ///
478     /// # Panics
479     ///
480     /// If contradictory arguments or settings exist.
481     ///
482     /// # Examples
483     ///
484     /// ```no_run
485     /// # use clap::{App, Arg};
486     /// let matches = App::new("myprog")
487     ///     // Args and options go here...
488     ///     .try_get_matches()
489     ///     .unwrap_or_else(|e| e.exit());
490     /// ```
491     /// [`env::args_os`]: std::env::args_os()
492     /// [`Error::exit`]: crate::Error::exit()
493     /// [`std::process::exit`]: std::process::exit()
494     /// [`clap::Result`]: Result
495     /// [`clap::Error`]: crate::Error
496     /// [`kind`]: crate::Error
497     /// [`ErrorKind::DisplayHelp`]: crate::ErrorKind::DisplayHelp
498     /// [`ErrorKind::DisplayVersion`]: crate::ErrorKind::DisplayVersion
499     #[inline]
try_get_matches(self) -> ClapResult<ArgMatches>500     pub fn try_get_matches(self) -> ClapResult<ArgMatches> {
501         // Start the parsing
502         self.try_get_matches_from(&mut env::args_os())
503     }
504 
505     /// Parse the specified arguments, exiting on failure.
506     ///
507     /// **NOTE:** The first argument will be parsed as the binary name unless
508     /// [`AppSettings::NoBinaryName`] is used.
509     ///
510     /// # Panics
511     ///
512     /// If contradictory arguments or settings exist.
513     ///
514     /// # Examples
515     ///
516     /// ```no_run
517     /// # use clap::{App, Arg};
518     /// let arg_vec = vec!["my_prog", "some", "args", "to", "parse"];
519     ///
520     /// let matches = App::new("myprog")
521     ///     // Args and options go here...
522     ///     .get_matches_from(arg_vec);
523     /// ```
524     /// [`App::get_matches`]: App::get_matches()
525     /// [`clap::Result`]: Result
526     /// [`Vec`]: std::vec::Vec
get_matches_from<I, T>(mut self, itr: I) -> ArgMatches where I: IntoIterator<Item = T>, T: Into<OsString> + Clone,527     pub fn get_matches_from<I, T>(mut self, itr: I) -> ArgMatches
528     where
529         I: IntoIterator<Item = T>,
530         T: Into<OsString> + Clone,
531     {
532         self.try_get_matches_from_mut(itr).unwrap_or_else(|e| {
533             drop(self);
534             e.exit()
535         })
536     }
537 
538     /// Parse the specified arguments, returning a [`clap::Result`] on failure.
539     ///
540     /// **NOTE:** This method WILL NOT exit when `--help` or `--version` (or short versions) are
541     /// used. It will return a [`clap::Error`], where the [`kind`] is a [`ErrorKind::DisplayHelp`]
542     /// or [`ErrorKind::DisplayVersion`] respectively. You must call [`Error::exit`] or
543     /// perform a [`std::process::exit`] yourself.
544     ///
545     /// **NOTE:** The first argument will be parsed as the binary name unless
546     /// [`AppSettings::NoBinaryName`] is used.
547     ///
548     /// # Panics
549     ///
550     /// If contradictory arguments or settings exist.
551     ///
552     /// # Examples
553     ///
554     /// ```no_run
555     /// # use clap::{App, Arg};
556     /// let arg_vec = vec!["my_prog", "some", "args", "to", "parse"];
557     ///
558     /// let matches = App::new("myprog")
559     ///     // Args and options go here...
560     ///     .try_get_matches_from(arg_vec)
561     ///     .unwrap_or_else(|e| e.exit());
562     /// ```
563     /// [`App::get_matches_from`]: App::get_matches_from()
564     /// [`App::try_get_matches`]: App::try_get_matches()
565     /// [`Error::exit`]: crate::Error::exit()
566     /// [`std::process::exit`]: std::process::exit()
567     /// [`clap::Error`]: crate::Error
568     /// [`Error::exit`]: crate::Error::exit()
569     /// [`kind`]: crate::Error
570     /// [`ErrorKind::DisplayHelp`]: crate::ErrorKind::DisplayHelp
571     /// [`ErrorKind::DisplayVersion`]: crate::ErrorKind::DisplayVersion
572     /// [`clap::Result`]: Result
try_get_matches_from<I, T>(mut self, itr: I) -> ClapResult<ArgMatches> where I: IntoIterator<Item = T>, T: Into<OsString> + Clone,573     pub fn try_get_matches_from<I, T>(mut self, itr: I) -> ClapResult<ArgMatches>
574     where
575         I: IntoIterator<Item = T>,
576         T: Into<OsString> + Clone,
577     {
578         self.try_get_matches_from_mut(itr)
579     }
580 
581     /// Parse the specified arguments, returning a [`clap::Result`] on failure.
582     ///
583     /// Like [`App::try_get_matches_from`] but doesn't consume the `App`.
584     ///
585     /// **NOTE:** This method WILL NOT exit when `--help` or `--version` (or short versions) are
586     /// used. It will return a [`clap::Error`], where the [`kind`] is a [`ErrorKind::DisplayHelp`]
587     /// or [`ErrorKind::DisplayVersion`] respectively. You must call [`Error::exit`] or
588     /// perform a [`std::process::exit`] yourself.
589     ///
590     /// **NOTE:** The first argument will be parsed as the binary name unless
591     /// [`AppSettings::NoBinaryName`] is used.
592     ///
593     /// # Panics
594     ///
595     /// If contradictory arguments or settings exist.
596     ///
597     /// # Examples
598     ///
599     /// ```no_run
600     /// # use clap::{App, Arg};
601     /// let arg_vec = vec!["my_prog", "some", "args", "to", "parse"];
602     ///
603     /// let mut app = App::new("myprog");
604     ///     // Args and options go here...
605     /// let matches = app.try_get_matches_from_mut(arg_vec)
606     ///     .unwrap_or_else(|e| e.exit());
607     /// ```
608     /// [`App::try_get_matches_from`]: App::try_get_matches_from()
609     /// [`clap::Result`]: Result
610     /// [`clap::Error`]: crate::Error
611     /// [`kind`]: crate::Error
try_get_matches_from_mut<I, T>(&mut self, itr: I) -> ClapResult<ArgMatches> where I: IntoIterator<Item = T>, T: Into<OsString> + Clone,612     pub fn try_get_matches_from_mut<I, T>(&mut self, itr: I) -> ClapResult<ArgMatches>
613     where
614         I: IntoIterator<Item = T>,
615         T: Into<OsString> + Clone,
616     {
617         let mut it = Input::from(itr.into_iter());
618 
619         #[cfg(feature = "unstable-multicall")]
620         if self.settings.is_set(AppSettings::Multicall) {
621             if let Some((argv0, _)) = it.next() {
622                 let argv0 = Path::new(&argv0);
623                 if let Some(command) = argv0.file_stem().and_then(|f| f.to_str()) {
624                     // Stop borrowing command so we can get another mut ref to it.
625                     let command = command.to_owned();
626                     debug!(
627                         "App::try_get_matches_from_mut: Parsed command {} from argv",
628                         command
629                     );
630 
631                     debug!("App::try_get_matches_from_mut: Reinserting command into arguments so subcommand parser matches it");
632                     it.insert(&[&command]);
633                     debug!("App::try_get_matches_from_mut: Clearing name and bin_name so that displayed command name starts with applet name");
634                     self.name.clear();
635                     self.bin_name = None;
636                     return self._do_parse(&mut it);
637                 }
638             }
639         };
640 
641         // Get the name of the program (argument 1 of env::args()) and determine the
642         // actual file
643         // that was used to execute the program. This is because a program called
644         // ./target/release/my_prog -a
645         // will have two arguments, './target/release/my_prog', '-a' but we don't want
646         // to display
647         // the full path when displaying help messages and such
648         if !self.settings.is_set(AppSettings::NoBinaryName) {
649             if let Some((name, _)) = it.next() {
650                 let p = Path::new(name);
651 
652                 if let Some(f) = p.file_name() {
653                     if let Some(s) = f.to_str() {
654                         if self.bin_name.is_none() {
655                             self.bin_name = Some(s.to_owned());
656                         }
657                     }
658                 }
659             }
660         }
661 
662         self._do_parse(&mut it)
663     }
664 
665     /// Prints the short help message (`-h`) to [`io::stdout()`].
666     ///
667     /// See also [`App::print_long_help`].
668     ///
669     /// # Examples
670     ///
671     /// ```rust
672     /// # use clap::App;
673     /// let mut app = App::new("myprog");
674     /// app.print_help();
675     /// ```
676     /// [`io::stdout()`]: std::io::stdout()
print_help(&mut self) -> io::Result<()>677     pub fn print_help(&mut self) -> io::Result<()> {
678         self._build();
679         let color = self.get_color();
680 
681         let mut c = Colorizer::new(false, color);
682         let parser = Parser::new(self);
683         let usage = Usage::new(parser.app, &parser.required);
684         Help::new(HelpWriter::Buffer(&mut c), parser.app, &usage, false).write_help()?;
685         c.print()
686     }
687 
688     /// Prints the long help message (`--help`) to [`io::stdout()`].
689     ///
690     /// See also [`App::print_help`].
691     ///
692     /// # Examples
693     ///
694     /// ```rust
695     /// # use clap::App;
696     /// let mut app = App::new("myprog");
697     /// app.print_long_help();
698     /// ```
699     /// [`io::stdout()`]: std::io::stdout()
700     /// [`BufWriter`]: std::io::BufWriter
701     /// [`-h` (short)]: Arg::help()
702     /// [`--help` (long)]: Arg::long_help()
print_long_help(&mut self) -> io::Result<()>703     pub fn print_long_help(&mut self) -> io::Result<()> {
704         self._build();
705         let color = self.get_color();
706 
707         let mut c = Colorizer::new(false, color);
708         let parser = Parser::new(self);
709         let usage = Usage::new(parser.app, &parser.required);
710         Help::new(HelpWriter::Buffer(&mut c), parser.app, &usage, true).write_help()?;
711         c.print()
712     }
713 
714     /// Writes the short help message (`-h`) to a [`io::Write`] object.
715     ///
716     /// See also [`App::write_long_help`].
717     ///
718     /// # Examples
719     ///
720     /// ```rust
721     /// # use clap::App;
722     /// use std::io;
723     /// let mut app = App::new("myprog");
724     /// let mut out = io::stdout();
725     /// app.write_help(&mut out).expect("failed to write to stdout");
726     /// ```
727     /// [`io::Write`]: std::io::Write
728     /// [`-h` (short)]: Arg::help()
729     /// [`--help` (long)]: Arg::long_help()
write_help<W: Write>(&mut self, w: &mut W) -> io::Result<()>730     pub fn write_help<W: Write>(&mut self, w: &mut W) -> io::Result<()> {
731         self._build();
732 
733         let parser = Parser::new(self);
734         let usage = Usage::new(parser.app, &parser.required);
735         Help::new(HelpWriter::Normal(w), parser.app, &usage, false).write_help()?;
736         w.flush()
737     }
738 
739     /// Writes the long help message (`--help`) to a [`io::Write`] object.
740     ///
741     /// See also [`App::write_help`].
742     ///
743     /// # Examples
744     ///
745     /// ```rust
746     /// # use clap::App;
747     /// use std::io;
748     /// let mut app = App::new("myprog");
749     /// let mut out = io::stdout();
750     /// app.write_long_help(&mut out).expect("failed to write to stdout");
751     /// ```
752     /// [`io::Write`]: std::io::Write
753     /// [`-h` (short)]: Arg::help()
754     /// [`--help` (long)]: Arg::long_help()
write_long_help<W: Write>(&mut self, w: &mut W) -> io::Result<()>755     pub fn write_long_help<W: Write>(&mut self, w: &mut W) -> io::Result<()> {
756         self._build();
757 
758         let parser = Parser::new(self);
759         let usage = Usage::new(parser.app, &parser.required);
760         Help::new(HelpWriter::Normal(w), parser.app, &usage, true).write_help()?;
761         w.flush()
762     }
763 
764     /// Version message rendered as if the user ran `-V`.
765     ///
766     /// See also [`App::render_long_version`].
767     ///
768     /// ### Coloring
769     ///
770     /// This function does not try to color the message nor it inserts any [ANSI escape codes].
771     ///
772     /// ### Examples
773     ///
774     /// ```rust
775     /// # use clap::App;
776     /// use std::io;
777     /// let app = App::new("myprog");
778     /// println!("{}", app.render_version());
779     /// ```
780     /// [`io::Write`]: std::io::Write
781     /// [`-V` (short)]: App::version()
782     /// [`--version` (long)]: App::long_version()
783     /// [ANSI escape codes]: https://en.wikipedia.org/wiki/ANSI_escape_code
render_version(&self) -> String784     pub fn render_version(&self) -> String {
785         self._render_version(false)
786     }
787 
788     /// Version message rendered as if the user ran `--version`.
789     ///
790     /// See also [`App::render_version`].
791     ///
792     /// ### Coloring
793     ///
794     /// This function does not try to color the message nor it inserts any [ANSI escape codes].
795     ///
796     /// ### Examples
797     ///
798     /// ```rust
799     /// # use clap::App;
800     /// use std::io;
801     /// let app = App::new("myprog");
802     /// println!("{}", app.render_long_version());
803     /// ```
804     /// [`io::Write`]: std::io::Write
805     /// [`-V` (short)]: App::version()
806     /// [`--version` (long)]: App::long_version()
807     /// [ANSI escape codes]: https://en.wikipedia.org/wiki/ANSI_escape_code
render_long_version(&self) -> String808     pub fn render_long_version(&self) -> String {
809         self._render_version(true)
810     }
811 
812     /// Usage statement
813     ///
814     /// ### Examples
815     ///
816     /// ```rust
817     /// # use clap::App;
818     /// use std::io;
819     /// let mut app = App::new("myprog");
820     /// println!("{}", app.render_usage());
821     /// ```
render_usage(&mut self) -> String822     pub fn render_usage(&mut self) -> String {
823         // If there are global arguments, or settings we need to propagate them down to subcommands
824         // before parsing incase we run into a subcommand
825         self._build();
826 
827         let parser = Parser::new(self);
828         Usage::new(parser.app, &parser.required).create_usage_with_title(&[])
829     }
830 }
831 
832 /// App Settings
833 impl<'help> App<'help> {
834     /// (Re)Sets the program's name.
835     ///
836     /// See [`App::new`] for more details.
837     ///
838     /// # Examples
839     ///
840     /// ```ignore
841     /// # use clap::{App, load_yaml};
842     /// let yaml = load_yaml!("app.yaml");
843     /// let app = App::from(yaml)
844     ///     .name(crate_name!());
845     ///
846     /// // continued logic goes here, such as `app.get_matches()` etc.
847     /// ```
848     #[must_use]
name<S: Into<String>>(mut self, name: S) -> Self849     pub fn name<S: Into<String>>(mut self, name: S) -> Self {
850         self.name = name.into();
851         self
852     }
853 
854     /// Overrides the runtime-determined name of the binary for help and error messages.
855     ///
856     /// This should only be used when absolutely necessary, such as when the binary name for your
857     /// application is misleading, or perhaps *not* how the user should invoke your program.
858     ///
859     /// **Pro-tip:** When building things such as third party `cargo`
860     /// subcommands, this setting **should** be used!
861     ///
862     /// **NOTE:** This *does not* change or set the name of the binary file on
863     /// disk. It only changes what clap thinks the name is for the purposes of
864     /// error or help messages.
865     ///
866     /// # Examples
867     ///
868     /// ```no_run
869     /// # use clap::App;
870     /// App::new("My Program")
871     ///      .bin_name("my_binary")
872     /// # ;
873     /// ```
874     #[must_use]
bin_name<S: Into<String>>(mut self, name: S) -> Self875     pub fn bin_name<S: Into<String>>(mut self, name: S) -> Self {
876         self.bin_name = Some(name.into());
877         self
878     }
879 
880     /// Sets the author(s) for the help message.
881     ///
882     /// **Pro-tip:** Use `clap`s convenience macro [`crate_authors!`] to
883     /// automatically set your application's author(s) to the same thing as your
884     /// crate at compile time.
885     ///
886     /// # Examples
887     ///
888     /// ```no_run
889     /// # use clap::App;
890     /// App::new("myprog")
891     ///      .author("Me, me@mymain.com")
892     /// # ;
893     /// ```
894     /// [`crate_authors!`]: ./macro.crate_authors!.html
895     #[must_use]
author<S: Into<&'help str>>(mut self, author: S) -> Self896     pub fn author<S: Into<&'help str>>(mut self, author: S) -> Self {
897         self.author = Some(author.into());
898         self
899     }
900 
901     /// Sets the program's description for the short help (`-h`).
902     ///
903     /// If [`App::long_about`] is not specified, this message will be displayed for `--help`.
904     ///
905     /// **NOTE:** Only `App::about` (short format) is used in completion
906     /// script generation in order to be concise.
907     ///
908     /// See also [`crate_description!`](crate::crate_description!).
909     ///
910     /// # Examples
911     ///
912     /// ```no_run
913     /// # use clap::App;
914     /// App::new("myprog")
915     ///     .about("Does really amazing things for great people")
916     /// # ;
917     /// ```
918     #[must_use]
about<O: Into<Option<&'help str>>>(mut self, about: O) -> Self919     pub fn about<O: Into<Option<&'help str>>>(mut self, about: O) -> Self {
920         self.about = about.into();
921         self
922     }
923 
924     /// Sets the program's description for the long help (`--help`).
925     ///
926     /// If [`App::about`] is not specified, this message will be displayed for `-h`.
927     ///
928     /// **NOTE:** Only [`App::about`] (short format) is used in completion
929     /// script generation in order to be concise.
930     ///
931     /// # Examples
932     ///
933     /// ```no_run
934     /// # use clap::App;
935     /// App::new("myprog")
936     ///     .long_about(
937     /// "Does really amazing things to great people. Now let's talk a little
938     ///  more in depth about how this subcommand really works. It may take about
939     ///  a few lines of text, but that's ok!")
940     /// # ;
941     /// ```
942     /// [`App::about`]: App::about()
943     #[must_use]
long_about<O: Into<Option<&'help str>>>(mut self, long_about: O) -> Self944     pub fn long_about<O: Into<Option<&'help str>>>(mut self, long_about: O) -> Self {
945         self.long_about = long_about.into();
946         self
947     }
948 
949     /// Free-form help text for after auto-generated short help (`-h`).
950     ///
951     /// This is often used to describe how to use the arguments, caveats to be noted, or license
952     /// and contact information.
953     ///
954     /// If [`App::after_long_help`] is not specified, this message will be displayed for `--help`.
955     ///
956     /// # Examples
957     ///
958     /// ```no_run
959     /// # use clap::App;
960     /// App::new("myprog")
961     ///     .after_help("Does really amazing things for great people... but be careful with -R!")
962     /// # ;
963     /// ```
964     ///
965     #[must_use]
after_help<S: Into<&'help str>>(mut self, help: S) -> Self966     pub fn after_help<S: Into<&'help str>>(mut self, help: S) -> Self {
967         self.after_help = Some(help.into());
968         self
969     }
970 
971     /// Free-form help text for after auto-generated long help (`--help`).
972     ///
973     /// This is often used to describe how to use the arguments, caveats to be noted, or license
974     /// and contact information.
975     ///
976     /// If [`App::after_help`] is not specified, this message will be displayed for `-h`.
977     ///
978     /// # Examples
979     ///
980     /// ```no_run
981     /// # use clap::App;
982     /// App::new("myprog")
983     ///     .after_long_help("Does really amazing things to great people... but be careful with -R, \
984     ///                      like, for real, be careful with this!")
985     /// # ;
986     /// ```
987     #[must_use]
after_long_help<S: Into<&'help str>>(mut self, help: S) -> Self988     pub fn after_long_help<S: Into<&'help str>>(mut self, help: S) -> Self {
989         self.after_long_help = Some(help.into());
990         self
991     }
992 
993     /// Free-form help text for before auto-generated short help (`-h`).
994     ///
995     /// This is often used for header, copyright, or license information.
996     ///
997     /// If [`App::before_long_help`] is not specified, this message will be displayed for `--help`.
998     ///
999     /// # Examples
1000     ///
1001     /// ```no_run
1002     /// # use clap::App;
1003     /// App::new("myprog")
1004     ///     .before_help("Some info I'd like to appear before the help info")
1005     /// # ;
1006     /// ```
1007     #[must_use]
before_help<S: Into<&'help str>>(mut self, help: S) -> Self1008     pub fn before_help<S: Into<&'help str>>(mut self, help: S) -> Self {
1009         self.before_help = Some(help.into());
1010         self
1011     }
1012 
1013     /// Free-form help text for before auto-generated long help (`--help`).
1014     ///
1015     /// This is often used for header, copyright, or license information.
1016     ///
1017     /// If [`App::before_help`] is not specified, this message will be displayed for `-h`.
1018     ///
1019     /// # Examples
1020     ///
1021     /// ```no_run
1022     /// # use clap::App;
1023     /// App::new("myprog")
1024     ///     .before_long_help("Some verbose and long info I'd like to appear before the help info")
1025     /// # ;
1026     /// ```
1027     #[must_use]
before_long_help<S: Into<&'help str>>(mut self, help: S) -> Self1028     pub fn before_long_help<S: Into<&'help str>>(mut self, help: S) -> Self {
1029         self.before_long_help = Some(help.into());
1030         self
1031     }
1032 
1033     /// Sets the version for the short version (`-V`) and help messages.
1034     ///
1035     /// If [`App::long_version`] is not specified, this message will be displayed for `--version`.
1036     ///
1037     /// **Pro-tip:** Use `clap`s convenience macro [`crate_version!`] to
1038     /// automatically set your application's version to the same thing as your
1039     /// crate at compile time.
1040     ///
1041     /// # Examples
1042     ///
1043     /// ```no_run
1044     /// # use clap::App;
1045     /// App::new("myprog")
1046     ///     .version("v0.1.24")
1047     /// # ;
1048     /// ```
1049     /// [`crate_version!`]: ./macro.crate_version!.html
1050     #[must_use]
version<S: Into<&'help str>>(mut self, ver: S) -> Self1051     pub fn version<S: Into<&'help str>>(mut self, ver: S) -> Self {
1052         self.version = Some(ver.into());
1053         self
1054     }
1055 
1056     /// Sets the version for the long version (`--version`) and help messages.
1057     ///
1058     /// If [`App::version`] is not specified, this message will be displayed for `-V`.
1059     ///
1060     /// **Pro-tip:** Use `clap`s convenience macro [`crate_version!`] to
1061     /// automatically set your application's version to the same thing as your
1062     /// crate at compile time.
1063     ///
1064     /// # Examples
1065     ///
1066     /// ```no_run
1067     /// # use clap::App;
1068     /// App::new("myprog")
1069     ///     .long_version(
1070     /// "v0.1.24
1071     ///  commit: abcdef89726d
1072     ///  revision: 123
1073     ///  release: 2
1074     ///  binary: myprog")
1075     /// # ;
1076     /// ```
1077     /// [`crate_version!`]: ./macro.crate_version!.html
1078     #[must_use]
long_version<S: Into<&'help str>>(mut self, ver: S) -> Self1079     pub fn long_version<S: Into<&'help str>>(mut self, ver: S) -> Self {
1080         self.long_version = Some(ver.into());
1081         self
1082     }
1083 
1084     /// Overrides the `clap` generated usage string for help and error messages.
1085     ///
1086     /// **NOTE:** Using this setting disables `clap`s "context-aware" usage
1087     /// strings. After this setting is set, this will be *the only* usage string
1088     /// displayed to the user!
1089     ///
1090     /// # Examples
1091     ///
1092     /// ```no_run
1093     /// # use clap::{App, Arg};
1094     /// App::new("myprog")
1095     ///     .override_usage("myapp [-clDas] <some_file>")
1096     /// # ;
1097     /// ```
1098     /// [`ArgMatches::usage`]: ArgMatches::usage()
1099     #[must_use]
override_usage<S: Into<&'help str>>(mut self, usage: S) -> Self1100     pub fn override_usage<S: Into<&'help str>>(mut self, usage: S) -> Self {
1101         self.usage_str = Some(usage.into());
1102         self
1103     }
1104 
1105     /// Overrides the `clap` generated help message (both `-h` and `--help`).
1106     ///
1107     /// This should only be used when the auto-generated message does not suffice.
1108     ///
1109     /// **NOTE:** This **only** replaces the help message for the current
1110     /// command, meaning if you are using subcommands, those help messages will
1111     /// still be auto-generated unless you specify a [`App::override_help`] for
1112     /// them as well.
1113     ///
1114     /// # Examples
1115     ///
1116     /// ```no_run
1117     /// # use clap::{App, Arg};
1118     /// App::new("myapp")
1119     ///     .override_help("myapp v1.0\n\
1120     ///            Does awesome things\n\
1121     ///            (C) me@mail.com\n\n\
1122     ///
1123     ///            USAGE: myapp <opts> <command>\n\n\
1124     ///
1125     ///            Options:\n\
1126     ///            -h, --help       Display this message\n\
1127     ///            -V, --version    Display version info\n\
1128     ///            -s <stuff>       Do something with stuff\n\
1129     ///            -v               Be verbose\n\n\
1130     ///
1131     ///            Commands:\n\
1132     ///            help             Print this message\n\
1133     ///            work             Do some work")
1134     /// # ;
1135     /// ```
1136     #[must_use]
override_help<S: Into<&'help str>>(mut self, help: S) -> Self1137     pub fn override_help<S: Into<&'help str>>(mut self, help: S) -> Self {
1138         self.help_str = Some(help.into());
1139         self
1140     }
1141 
1142     /// Sets the help template to be used, overriding the default format.
1143     ///
1144     /// **NOTE:** The template system is by design very simple. Therefore, the
1145     /// tags have to be written in the lowercase and without spacing.
1146     ///
1147     /// Tags are given inside curly brackets.
1148     ///
1149     /// Valid tags are:
1150     ///
1151     ///   * `{bin}`                 - Binary name.
1152     ///   * `{version}`             - Version number.
1153     ///   * `{author}`              - Author information.
1154     ///   * `{author-with-newline}` - Author followed by `\n`.
1155     ///   * `{author-section}`      - Author preceded and followed by `\n`.
1156     ///   * `{about}`               - General description (from [`App::about`] or
1157     ///                               [`App::long_about`]).
1158     ///   * `{about-with-newline}`  - About followed by `\n`.
1159     ///   * `{about-section}`       - About preceded and followed by '\n'.
1160     ///   * `{usage-heading}`       - Automatically generated usage heading.
1161     ///   * `{usage}`               - Automatically generated or given usage string.
1162     ///   * `{all-args}`            - Help for all arguments (options, flags, positional
1163     ///                               arguments, and subcommands) including titles.
1164     ///   * `{options}`             - Help for options.
1165     ///   * `{positionals}`         - Help for positional arguments.
1166     ///   * `{subcommands}`         - Help for subcommands.
1167     ///   * `{after-help}`          - Help from [`App::after_help`] or [`App::after_long_help`].
1168     ///   * `{before-help}`         - Help from [`App::before_help`] or [`App::before_long_help`].
1169     ///
1170     /// # Examples
1171     ///
1172     /// ```no_run
1173     /// # use clap::App;
1174     /// App::new("myprog")
1175     ///     .version("1.0")
1176     ///     .help_template("{bin} ({version}) - {usage}")
1177     /// # ;
1178     /// ```
1179     /// [`App::about`]: App::about()
1180     /// [`App::long_about`]: App::long_about()
1181     /// [`App::after_help`]: App::after_help()
1182     /// [`App::after_long_help`]: App::after_long_help()
1183     /// [`App::before_help`]: App::before_help()
1184     /// [`App::before_long_help`]: App::before_long_help()
1185     #[must_use]
help_template<S: Into<&'help str>>(mut self, s: S) -> Self1186     pub fn help_template<S: Into<&'help str>>(mut self, s: S) -> Self {
1187         self.template = Some(s.into());
1188         self
1189     }
1190 
1191     /// Apply a setting for the current command or subcommand.
1192     ///
1193     /// See [`App::global_setting`] to apply a setting to this command and all subcommands.
1194     ///
1195     /// See [`AppSettings`] for a full list of possibilities and examples.
1196     ///
1197     /// # Examples
1198     ///
1199     /// ```no_run
1200     /// # use clap::{App, AppSettings};
1201     /// App::new("myprog")
1202     ///     .setting(AppSettings::SubcommandRequired)
1203     ///     .setting(AppSettings::AllowLeadingHyphen)
1204     /// # ;
1205     /// ```
1206     /// or
1207     /// ```no_run
1208     /// # use clap::{App, AppSettings};
1209     /// App::new("myprog")
1210     ///     .setting(AppSettings::SubcommandRequired | AppSettings::AllowLeadingHyphen)
1211     /// # ;
1212     /// ```
1213     #[inline]
1214     #[must_use]
setting<F>(mut self, setting: F) -> Self where F: Into<AppFlags>,1215     pub fn setting<F>(mut self, setting: F) -> Self
1216     where
1217         F: Into<AppFlags>,
1218     {
1219         self.settings.insert(setting.into());
1220         self
1221     }
1222 
1223     /// Remove a setting for the current command or subcommand.
1224     ///
1225     /// See [`AppSettings`] for a full list of possibilities and examples.
1226     ///
1227     /// # Examples
1228     ///
1229     /// ```no_run
1230     /// # use clap::{App, AppSettings};
1231     /// App::new("myprog")
1232     ///     .unset_setting(AppSettings::SubcommandRequired)
1233     ///     .setting(AppSettings::AllowLeadingHyphen)
1234     /// # ;
1235     /// ```
1236     /// or
1237     /// ```no_run
1238     /// # use clap::{App, AppSettings};
1239     /// App::new("myprog")
1240     ///     .unset_setting(AppSettings::SubcommandRequired | AppSettings::AllowLeadingHyphen)
1241     /// # ;
1242     /// ```
1243     #[inline]
1244     #[must_use]
unset_setting<F>(mut self, setting: F) -> Self where F: Into<AppFlags>,1245     pub fn unset_setting<F>(mut self, setting: F) -> Self
1246     where
1247         F: Into<AppFlags>,
1248     {
1249         self.settings.remove(setting.into());
1250         self
1251     }
1252 
1253     /// Apply a setting for the current command and all subcommands.
1254     ///
1255     /// See [`App::setting`] to apply a setting only to this command.
1256     ///
1257     /// See [`AppSettings`] for a full list of possibilities and examples.
1258     ///
1259     /// # Examples
1260     ///
1261     /// ```no_run
1262     /// # use clap::{App, AppSettings};
1263     /// App::new("myprog")
1264     ///     .global_setting(AppSettings::AllowNegativeNumbers)
1265     /// # ;
1266     /// ```
1267     #[inline]
1268     #[must_use]
global_setting(mut self, setting: AppSettings) -> Self1269     pub fn global_setting(mut self, setting: AppSettings) -> Self {
1270         self.settings.set(setting);
1271         self.g_settings.set(setting);
1272         self
1273     }
1274 
1275     /// Remove a setting and stop propagating down to subcommands.
1276     ///
1277     /// See [`AppSettings`] for a full list of possibilities and examples.
1278     ///
1279     /// # Examples
1280     ///
1281     /// ```no_run
1282     /// # use clap::{App, AppSettings};
1283     /// App::new("myprog")
1284     ///     .unset_global_setting(AppSettings::AllowNegativeNumbers)
1285     /// # ;
1286     /// ```
1287     /// [global]: App::global_setting()
1288     #[inline]
1289     #[must_use]
unset_global_setting(mut self, setting: AppSettings) -> Self1290     pub fn unset_global_setting(mut self, setting: AppSettings) -> Self {
1291         self.settings.unset(setting);
1292         self.g_settings.unset(setting);
1293         self
1294     }
1295 
1296     /// Sets when to color output.
1297     ///
1298     /// **NOTE:** This choice is propagated to all child subcommands.
1299     ///
1300     /// **NOTE:** Default behaviour is [`ColorChoice::Auto`].
1301     ///
1302     /// # Examples
1303     ///
1304     /// ```no_run
1305     /// # use clap::{App, ColorChoice};
1306     /// App::new("myprog")
1307     ///     .color(ColorChoice::Never)
1308     ///     .get_matches();
1309     /// ```
1310     /// [`ColorChoice::Auto`]: crate::ColorChoice::Auto
1311     #[cfg(feature = "color")]
1312     #[inline]
1313     #[must_use]
color(self, color: ColorChoice) -> Self1314     pub fn color(self, color: ColorChoice) -> Self {
1315         #[allow(deprecated)]
1316         match color {
1317             ColorChoice::Auto => self.global_setting(AppSettings::ColorAuto),
1318             ColorChoice::Always => self.global_setting(AppSettings::ColorAlways),
1319             ColorChoice::Never => self.global_setting(AppSettings::ColorNever),
1320         }
1321     }
1322 
1323     /// Set the default section heading for future args.
1324     ///
1325     /// This will be used for any arg that hasn't had [`Arg::help_heading`] called.
1326     ///
1327     /// This is useful if the default `OPTIONS` or `ARGS` headings are
1328     /// not specific enough for one's use case.
1329     ///
1330     /// For subcommands, see [`App::subcommand_help_heading`]
1331     ///
1332     /// [`App::arg`]: App::arg()
1333     /// [`Arg::help_heading`]: crate::Arg::help_heading()
1334     #[inline]
1335     #[must_use]
help_heading<O>(mut self, heading: O) -> Self where O: Into<Option<&'help str>>,1336     pub fn help_heading<O>(mut self, heading: O) -> Self
1337     where
1338         O: Into<Option<&'help str>>,
1339     {
1340         self.current_help_heading = heading.into();
1341         self
1342     }
1343 
1344     /// Sets the terminal width at which to wrap help messages.
1345     ///
1346     /// Using `0` will ignore terminal widths and use source formatting.
1347     ///
1348     /// Defaults to current terminal width when `wrap_help` feature flag is enabled.  If the flag
1349     /// is disabled or it cannot be determined, the default is 100.
1350     ///
1351     /// **NOTE:** This setting applies globally and *not* on a per-command basis.
1352     ///
1353     /// # Examples
1354     ///
1355     /// ```no_run
1356     /// # use clap::App;
1357     /// App::new("myprog")
1358     ///     .term_width(80)
1359     /// # ;
1360     /// ```
1361     #[inline]
1362     #[must_use]
term_width(mut self, width: usize) -> Self1363     pub fn term_width(mut self, width: usize) -> Self {
1364         self.term_w = Some(width);
1365         self
1366     }
1367 
1368     /// Sets the maximum terminal width at which to wrap help messages.
1369     ///
1370     /// This only applies when setting the current terminal width.  See [`App::term_width`] for
1371     /// more details.
1372     ///
1373     /// Using `0` will ignore terminal widths and use source formatting.
1374     ///
1375     /// **NOTE:** This setting applies globally and *not* on a per-command basis.
1376     ///
1377     /// # Examples
1378     ///
1379     /// ```no_run
1380     /// # use clap::App;
1381     /// App::new("myprog")
1382     ///     .max_term_width(100)
1383     /// # ;
1384     /// ```
1385     #[inline]
1386     #[must_use]
max_term_width(mut self, w: usize) -> Self1387     pub fn max_term_width(mut self, w: usize) -> Self {
1388         self.max_w = Some(w);
1389         self
1390     }
1391 
1392     /// Replaces an argument or subcommand used on the CLI at runtime with other arguments or subcommands.
1393     ///
1394     /// **Note:** This is gated behind [`unstable-replace`](https://github.com/clap-rs/clap/issues/2836)
1395     ///
1396     /// When this method is used, `name` is removed from the CLI, and `target`
1397     /// is inserted in its place. Parsing continues as if the user typed
1398     /// `target` instead of `name`.
1399     ///
1400     /// This can be used to create "shortcuts" for subcommands, or if a
1401     /// particular argument has the semantic meaning of several other specific
1402     /// arguments and values.
1403     ///
1404     /// # Examples
1405     ///
1406     /// We'll start with the "subcommand short" example. In this example, let's
1407     /// assume we have a program with a subcommand `module` which can be invoked
1408     /// via `app module`. Now let's also assume `module` also has a subcommand
1409     /// called `install` which can be invoked `app module install`. If for some
1410     /// reason users needed to be able to reach `app module install` via the
1411     /// short-hand `app install`, we'd have several options.
1412     ///
1413     /// We *could* create another sibling subcommand to `module` called
1414     /// `install`, but then we would need to manage another subcommand and manually
1415     /// dispatch to `app module install` handling code. This is error prone and
1416     /// tedious.
1417     ///
1418     /// We could instead use [`App::replace`] so that, when the user types `app
1419     /// install`, `clap` will replace `install` with `module install` which will
1420     /// end up getting parsed as if the user typed the entire incantation.
1421     ///
1422     /// ```rust
1423     /// # use clap::App;
1424     /// let m = App::new("app")
1425     ///     .subcommand(App::new("module")
1426     ///         .subcommand(App::new("install")))
1427     ///     .replace("install", &["module", "install"])
1428     ///     .get_matches_from(vec!["app", "install"]);
1429     ///
1430     /// assert!(m.subcommand_matches("module").is_some());
1431     /// assert!(m.subcommand_matches("module").unwrap().subcommand_matches("install").is_some());
1432     /// ```
1433     ///
1434     /// Now let's show an argument example!
1435     ///
1436     /// Let's assume we have an application with two flags `--save-context` and
1437     /// `--save-runtime`. But often users end up needing to do *both* at the
1438     /// same time. We can add a third flag `--save-all` which semantically means
1439     /// the same thing as `app --save-context --save-runtime`. To implement that,
1440     /// we have several options.
1441     ///
1442     /// We could create this third argument and manually check if that argument
1443     /// and in our own consumer code handle the fact that both `--save-context`
1444     /// and `--save-runtime` *should* have been used. But again this is error
1445     /// prone and tedious. If we had code relying on checking `--save-context`
1446     /// and we forgot to update that code to *also* check `--save-all` it'd mean
1447     /// an error!
1448     ///
1449     /// Luckily we can use [`App::replace`] so that when the user types
1450     /// `--save-all`, `clap` will replace that argument with `--save-context
1451     /// --save-runtime`, and parsing will continue like normal. Now all our code
1452     /// that was originally checking for things like `--save-context` doesn't
1453     /// need to change!
1454     ///
1455     /// ```rust
1456     /// # use clap::{App, Arg};
1457     /// let m = App::new("app")
1458     ///     .arg(Arg::new("save-context")
1459     ///         .long("save-context"))
1460     ///     .arg(Arg::new("save-runtime")
1461     ///         .long("save-runtime"))
1462     ///     .replace("--save-all", &["--save-context", "--save-runtime"])
1463     ///     .get_matches_from(vec!["app", "--save-all"]);
1464     ///
1465     /// assert!(m.is_present("save-context"));
1466     /// assert!(m.is_present("save-runtime"));
1467     /// ```
1468     ///
1469     /// This can also be used with options, for example if our application with
1470     /// `--save-*` above also had a `--format=TYPE` option. Let's say it
1471     /// accepted `txt` or `json` values. However, when `--save-all` is used,
1472     /// only `--format=json` is allowed, or valid. We could change the example
1473     /// above to enforce this:
1474     ///
1475     /// ```rust
1476     /// # use clap::{App, Arg};
1477     /// let m = App::new("app")
1478     ///     .arg(Arg::new("save-context")
1479     ///         .long("save-context"))
1480     ///     .arg(Arg::new("save-runtime")
1481     ///         .long("save-runtime"))
1482     ///     .arg(Arg::new("format")
1483     ///         .long("format")
1484     ///         .takes_value(true)
1485     ///         .possible_values(["txt", "json"]))
1486     ///     .replace("--save-all", &["--save-context", "--save-runtime", "--format=json"])
1487     ///     .get_matches_from(vec!["app", "--save-all"]);
1488     ///
1489     /// assert!(m.is_present("save-context"));
1490     /// assert!(m.is_present("save-runtime"));
1491     /// assert_eq!(m.value_of("format"), Some("json"));
1492     /// ```
1493     ///
1494     /// [`App::replace`]: App::replace()
1495     #[inline]
1496     #[cfg(feature = "unstable-replace")]
1497     #[must_use]
replace(mut self, name: &'help str, target: &'help [&'help str]) -> Self1498     pub fn replace(mut self, name: &'help str, target: &'help [&'help str]) -> Self {
1499         self.replacers.insert(name, target);
1500         self
1501     }
1502 }
1503 
1504 /// Subcommand-specific Settings
1505 impl<'help> App<'help> {
1506     /// Sets the short version of the subcommand flag without the preceding `-`.
1507     ///
1508     /// Allows the subcommand to be used as if it were an [`Arg::short`].
1509     ///
1510     /// # Examples
1511     ///
1512     /// ```
1513     /// # use clap::{App, Arg};
1514     /// let matches = App::new("pacman")
1515     ///     .subcommand(
1516     ///         App::new("sync").short_flag('S').arg(
1517     ///             Arg::new("search")
1518     ///                 .short('s')
1519     ///                 .long("search")
1520     ///                 .help("search remote repositories for matching strings"),
1521     ///         ),
1522     ///     )
1523     ///     .get_matches_from(vec!["pacman", "-Ss"]);
1524     ///
1525     /// assert_eq!(matches.subcommand_name().unwrap(), "sync");
1526     /// let sync_matches = matches.subcommand_matches("sync").unwrap();
1527     /// assert!(sync_matches.is_present("search"));
1528     /// ```
1529     /// [`Arg::short`]: Arg::short()
1530     #[must_use]
short_flag(mut self, short: char) -> Self1531     pub fn short_flag(mut self, short: char) -> Self {
1532         self.short_flag = Some(short);
1533         self
1534     }
1535 
1536     /// Sets the long version of the subcommand flag without the preceding `--`.
1537     ///
1538     /// Allows the subcommand to be used as if it were an [`Arg::long`].
1539     ///
1540     /// **NOTE:** Any leading `-` characters will be stripped.
1541     ///
1542     /// # Examples
1543     ///
1544     /// To set `long_flag` use a word containing valid UTF-8 codepoints. If you supply a double leading
1545     /// `--` such as `--sync` they will be stripped. Hyphens in the middle of the word; however,
1546     /// will *not* be stripped (i.e. `sync-file` is allowed).
1547     ///
1548     /// ```
1549     /// # use clap::{App, Arg};
1550     /// let matches = App::new("pacman")
1551     ///     .subcommand(
1552     ///         App::new("sync").long_flag("sync").arg(
1553     ///             Arg::new("search")
1554     ///                 .short('s')
1555     ///                 .long("search")
1556     ///                 .help("search remote repositories for matching strings"),
1557     ///         ),
1558     ///     )
1559     ///     .get_matches_from(vec!["pacman", "--sync", "--search"]);
1560     ///
1561     /// assert_eq!(matches.subcommand_name().unwrap(), "sync");
1562     /// let sync_matches = matches.subcommand_matches("sync").unwrap();
1563     /// assert!(sync_matches.is_present("search"));
1564     /// ```
1565     ///
1566     /// [`Arg::long`]: Arg::long()
1567     #[must_use]
long_flag(mut self, long: &'help str) -> Self1568     pub fn long_flag(mut self, long: &'help str) -> Self {
1569         self.long_flag = Some(long.trim_start_matches(|c| c == '-'));
1570         self
1571     }
1572 
1573     /// Sets a hidden alias to this subcommand.
1574     ///
1575     /// This allows the subcommand to be accessed via *either* the original name, or this given
1576     /// alias. This is more efficient and easier than creating multiple hidden subcommands as one
1577     /// only needs to check for the existence of this command, and not all aliased variants.
1578     ///
1579     /// **NOTE:** Aliases defined with this method are *hidden* from the help
1580     /// message. If you're looking for aliases that will be displayed in the help
1581     /// message, see [`App::visible_alias`].
1582     ///
1583     /// **NOTE:** When using aliases and checking for the existence of a
1584     /// particular subcommand within an [`ArgMatches`] struct, one only needs to
1585     /// search for the original name and not all aliases.
1586     ///
1587     /// # Examples
1588     ///
1589     /// ```rust
1590     /// # use clap::{App, Arg, };
1591     /// let m = App::new("myprog")
1592     ///     .subcommand(App::new("test")
1593     ///         .alias("do-stuff"))
1594     ///     .get_matches_from(vec!["myprog", "do-stuff"]);
1595     /// assert_eq!(m.subcommand_name(), Some("test"));
1596     /// ```
1597     /// [`App::visible_alias`]: App::visible_alias()
1598     #[must_use]
alias<S: Into<&'help str>>(mut self, name: S) -> Self1599     pub fn alias<S: Into<&'help str>>(mut self, name: S) -> Self {
1600         self.aliases.push((name.into(), false));
1601         self
1602     }
1603 
1604     /// Add an alias, which functions as  "hidden" short flag subcommand
1605     ///
1606     /// This will automatically dispatch as if this subcommand was used. This is more efficient,
1607     /// and easier than creating multiple hidden subcommands as one only needs to check for the
1608     /// existence of this command, and not all variants.
1609     ///
1610     /// # Examples
1611     ///
1612     /// ```no_run
1613     /// # use clap::{App, Arg, };
1614     /// let m = App::new("myprog")
1615     ///             .subcommand(App::new("test").short_flag('t')
1616     ///                 .short_flag_alias('d'))
1617     ///             .get_matches_from(vec!["myprog", "-d"]);
1618     /// assert_eq!(m.subcommand_name(), Some("test"));
1619     /// ```
1620     #[must_use]
short_flag_alias(mut self, name: char) -> Self1621     pub fn short_flag_alias(mut self, name: char) -> Self {
1622         assert!(name != '-', "short alias name cannot be `-`");
1623         self.short_flag_aliases.push((name, false));
1624         self
1625     }
1626 
1627     /// Add an alias, which functions as a "hidden" long flag subcommand.
1628     ///
1629     /// This will automatically dispatch as if this subcommand was used. This is more efficient,
1630     /// and easier than creating multiple hidden subcommands as one only needs to check for the
1631     /// existence of this command, and not all variants.
1632     ///
1633     /// # Examples
1634     ///
1635     /// ```no_run
1636     /// # use clap::{App, Arg, };
1637     /// let m = App::new("myprog")
1638     ///             .subcommand(App::new("test").long_flag("test")
1639     ///                 .long_flag_alias("testing"))
1640     ///             .get_matches_from(vec!["myprog", "--testing"]);
1641     /// assert_eq!(m.subcommand_name(), Some("test"));
1642     /// ```
1643     #[must_use]
long_flag_alias(mut self, name: &'help str) -> Self1644     pub fn long_flag_alias(mut self, name: &'help str) -> Self {
1645         self.long_flag_aliases.push((name, false));
1646         self
1647     }
1648 
1649     /// Sets multiple hidden aliases to this subcommand.
1650     ///
1651     /// This allows the subcommand to be accessed via *either* the original name or any of the
1652     /// given aliases. This is more efficient, and easier than creating multiple hidden subcommands
1653     /// as one only needs to check for the existence of this command and not all aliased variants.
1654     ///
1655     /// **NOTE:** Aliases defined with this method are *hidden* from the help
1656     /// message. If looking for aliases that will be displayed in the help
1657     /// message, see [`App::visible_aliases`].
1658     ///
1659     /// **NOTE:** When using aliases and checking for the existence of a
1660     /// particular subcommand within an [`ArgMatches`] struct, one only needs to
1661     /// search for the original name and not all aliases.
1662     ///
1663     /// # Examples
1664     ///
1665     /// ```rust
1666     /// # use clap::{App, Arg};
1667     /// let m = App::new("myprog")
1668     ///     .subcommand(App::new("test")
1669     ///         .aliases(&["do-stuff", "do-tests", "tests"]))
1670     ///         .arg(Arg::new("input")
1671     ///             .help("the file to add")
1672     ///             .index(1)
1673     ///             .required(false))
1674     ///     .get_matches_from(vec!["myprog", "do-tests"]);
1675     /// assert_eq!(m.subcommand_name(), Some("test"));
1676     /// ```
1677     /// [`App::visible_aliases`]: App::visible_aliases()
1678     #[must_use]
aliases(mut self, names: &[&'help str]) -> Self1679     pub fn aliases(mut self, names: &[&'help str]) -> Self {
1680         self.aliases.extend(names.iter().map(|n| (*n, false)));
1681         self
1682     }
1683 
1684     /// Add aliases, which function as "hidden" short flag subcommands.
1685     ///
1686     /// These will automatically dispatch as if this subcommand was used. This is more efficient,
1687     /// and easier than creating multiple hidden subcommands as one only needs to check for the
1688     /// existence of this command, and not all variants.
1689     ///
1690     /// # Examples
1691     ///
1692     /// ```rust
1693     /// # use clap::{App, Arg, };
1694     /// let m = App::new("myprog")
1695     ///     .subcommand(App::new("test").short_flag('t')
1696     ///         .short_flag_aliases(&['a', 'b', 'c']))
1697     ///         .arg(Arg::new("input")
1698     ///             .help("the file to add")
1699     ///             .index(1)
1700     ///             .required(false))
1701     ///     .get_matches_from(vec!["myprog", "-a"]);
1702     /// assert_eq!(m.subcommand_name(), Some("test"));
1703     /// ```
1704     #[must_use]
short_flag_aliases(mut self, names: &[char]) -> Self1705     pub fn short_flag_aliases(mut self, names: &[char]) -> Self {
1706         for s in names {
1707             assert!(s != &'-', "short alias name cannot be `-`");
1708             self.short_flag_aliases.push((*s, false));
1709         }
1710         self
1711     }
1712 
1713     /// Add aliases, which function as "hidden" long flag subcommands.
1714     ///
1715     /// These will automatically dispatch as if this subcommand was used. This is more efficient,
1716     /// and easier than creating multiple hidden subcommands as one only needs to check for the
1717     /// existence of this command, and not all variants.
1718     ///
1719     /// # Examples
1720     ///
1721     /// ```rust
1722     /// # use clap::{App, Arg, };
1723     /// let m = App::new("myprog")
1724     ///             .subcommand(App::new("test").long_flag("test")
1725     ///                 .long_flag_aliases(&["testing", "testall", "test_all"]))
1726     ///                 .arg(Arg::new("input")
1727     ///                             .help("the file to add")
1728     ///                             .index(1)
1729     ///                             .required(false))
1730     ///             .get_matches_from(vec!["myprog", "--testing"]);
1731     /// assert_eq!(m.subcommand_name(), Some("test"));
1732     /// ```
1733     #[must_use]
long_flag_aliases(mut self, names: &[&'help str]) -> Self1734     pub fn long_flag_aliases(mut self, names: &[&'help str]) -> Self {
1735         for s in names {
1736             self.long_flag_aliases.push((s, false));
1737         }
1738         self
1739     }
1740 
1741     /// Sets a visible alias to this subcommand.
1742     ///
1743     /// This allows the subcommand to be accessed via *either* the
1744     /// original name or the given alias. This is more efficient and easier
1745     /// than creating hidden subcommands as one only needs to check for
1746     /// the existence of this command and not all aliased variants.
1747     ///
1748     /// **NOTE:** The alias defined with this method is *visible* from the help
1749     /// message and displayed as if it were just another regular subcommand. If
1750     /// looking for an alias that will not be displayed in the help message, see
1751     /// [`App::alias`].
1752     ///
1753     /// **NOTE:** When using aliases and checking for the existence of a
1754     /// particular subcommand within an [`ArgMatches`] struct, one only needs to
1755     /// search for the original name and not all aliases.
1756     ///
1757     /// # Examples
1758     ///
1759     /// ```no_run
1760     /// # use clap::{App, Arg};
1761     /// let m = App::new("myprog")
1762     ///     .subcommand(App::new("test")
1763     ///         .visible_alias("do-stuff"))
1764     ///     .get_matches_from(vec!["myprog", "do-stuff"]);
1765     /// assert_eq!(m.subcommand_name(), Some("test"));
1766     /// ```
1767     /// [`App::alias`]: App::alias()
1768     #[must_use]
visible_alias<S: Into<&'help str>>(mut self, name: S) -> Self1769     pub fn visible_alias<S: Into<&'help str>>(mut self, name: S) -> Self {
1770         self.aliases.push((name.into(), true));
1771         self
1772     }
1773 
1774     /// Add an alias, which functions as  "visible" short flag subcommand
1775     ///
1776     /// This will automatically dispatch as if this subcommand was used. This is more efficient,
1777     /// and easier than creating multiple hidden subcommands as one only needs to check for the
1778     /// existence of this command, and not all variants.
1779     ///
1780     /// See also [`App::short_flag_alias`].
1781     ///
1782     /// # Examples
1783     ///
1784     /// ```no_run
1785     /// # use clap::{App, Arg, };
1786     /// let m = App::new("myprog")
1787     ///             .subcommand(App::new("test").short_flag('t')
1788     ///                 .visible_short_flag_alias('d'))
1789     ///             .get_matches_from(vec!["myprog", "-d"]);
1790     /// assert_eq!(m.subcommand_name(), Some("test"));
1791     /// ```
1792     /// [`App::short_flag_alias`]: App::short_flag_alias()
1793     #[must_use]
visible_short_flag_alias(mut self, name: char) -> Self1794     pub fn visible_short_flag_alias(mut self, name: char) -> Self {
1795         assert!(name != '-', "short alias name cannot be `-`");
1796         self.short_flag_aliases.push((name, true));
1797         self
1798     }
1799 
1800     /// Add an alias, which functions as a "visible" long flag subcommand.
1801     ///
1802     /// This will automatically dispatch as if this subcommand was used. This is more efficient,
1803     /// and easier than creating multiple hidden subcommands as one only needs to check for the
1804     /// existence of this command, and not all variants.
1805     ///
1806     /// See also [`App::long_flag_alias`].
1807     ///
1808     /// # Examples
1809     ///
1810     /// ```no_run
1811     /// # use clap::{App, Arg, };
1812     /// let m = App::new("myprog")
1813     ///             .subcommand(App::new("test").long_flag("test")
1814     ///                 .visible_long_flag_alias("testing"))
1815     ///             .get_matches_from(vec!["myprog", "--testing"]);
1816     /// assert_eq!(m.subcommand_name(), Some("test"));
1817     /// ```
1818     /// [`App::long_flag_alias`]: App::long_flag_alias()
1819     #[must_use]
visible_long_flag_alias(mut self, name: &'help str) -> Self1820     pub fn visible_long_flag_alias(mut self, name: &'help str) -> Self {
1821         self.long_flag_aliases.push((name, true));
1822         self
1823     }
1824 
1825     /// Sets multiple visible aliases to this subcommand.
1826     ///
1827     /// This allows the subcommand to be accessed via *either* the
1828     /// original name or any of the given aliases. This is more efficient and easier
1829     /// than creating multiple hidden subcommands as one only needs to check for
1830     /// the existence of this command and not all aliased variants.
1831     ///
1832     /// **NOTE:** The alias defined with this method is *visible* from the help
1833     /// message and displayed as if it were just another regular subcommand. If
1834     /// looking for an alias that will not be displayed in the help message, see
1835     /// [`App::alias`].
1836     ///
1837     /// **NOTE:** When using aliases, and checking for the existence of a
1838     /// particular subcommand within an [`ArgMatches`] struct, one only needs to
1839     /// search for the original name and not all aliases.
1840     ///
1841     /// # Examples
1842     ///
1843     /// ```no_run
1844     /// # use clap::{App, Arg, };
1845     /// let m = App::new("myprog")
1846     ///     .subcommand(App::new("test")
1847     ///         .visible_aliases(&["do-stuff", "tests"]))
1848     ///     .get_matches_from(vec!["myprog", "do-stuff"]);
1849     /// assert_eq!(m.subcommand_name(), Some("test"));
1850     /// ```
1851     /// [`App::alias`]: App::alias()
1852     #[must_use]
visible_aliases(mut self, names: &[&'help str]) -> Self1853     pub fn visible_aliases(mut self, names: &[&'help str]) -> Self {
1854         self.aliases.extend(names.iter().map(|n| (*n, true)));
1855         self
1856     }
1857 
1858     /// Add aliases, which function as *visible* short flag subcommands.
1859     ///
1860     /// See [`App::short_flag_aliases`].
1861     ///
1862     /// # Examples
1863     ///
1864     /// ```no_run
1865     /// # use clap::{App, Arg, };
1866     /// let m = App::new("myprog")
1867     ///             .subcommand(App::new("test").short_flag('b')
1868     ///                 .visible_short_flag_aliases(&['t']))
1869     ///             .get_matches_from(vec!["myprog", "-t"]);
1870     /// assert_eq!(m.subcommand_name(), Some("test"));
1871     /// ```
1872     /// [`App::short_flag_aliases`]: App::short_flag_aliases()
1873     #[must_use]
visible_short_flag_aliases(mut self, names: &[char]) -> Self1874     pub fn visible_short_flag_aliases(mut self, names: &[char]) -> Self {
1875         for s in names {
1876             assert!(s != &'-', "short alias name cannot be `-`");
1877             self.short_flag_aliases.push((*s, true));
1878         }
1879         self
1880     }
1881 
1882     /// Add aliases, which function as *visible* long flag subcommands.
1883     ///
1884     /// See [`App::long_flag_aliases`].
1885     ///
1886     /// # Examples
1887     ///
1888     /// ```no_run
1889     /// # use clap::{App, Arg, };
1890     /// let m = App::new("myprog")
1891     ///             .subcommand(App::new("test").long_flag("test")
1892     ///                 .visible_long_flag_aliases(&["testing", "testall", "test_all"]))
1893     ///             .get_matches_from(vec!["myprog", "--testing"]);
1894     /// assert_eq!(m.subcommand_name(), Some("test"));
1895     /// ```
1896     /// [`App::long_flag_aliases`]: App::long_flag_aliases()
1897     #[must_use]
visible_long_flag_aliases(mut self, names: &[&'help str]) -> Self1898     pub fn visible_long_flag_aliases(mut self, names: &[&'help str]) -> Self {
1899         for s in names {
1900             self.long_flag_aliases.push((s, true));
1901         }
1902         self
1903     }
1904 
1905     /// Set the placement of this subcommand within the help.
1906     ///
1907     /// Subcommands with a lower value will be displayed first in the help message.  Subcommands
1908     /// with duplicate display orders will be displayed in alphabetical order.
1909     ///
1910     /// This is helpful when one would like to emphasize frequently used subcommands, or prioritize
1911     /// those towards the top of the list.
1912     ///
1913     /// **NOTE:** The default is 999 for all subcommands.
1914     ///
1915     /// # Examples
1916     ///
1917     /// ```rust
1918     /// # use clap::{App, };
1919     /// let m = App::new("cust-ord")
1920     ///     .subcommand(App::new("alpha") // typically subcommands are grouped
1921     ///                                                // alphabetically by name. Subcommands
1922     ///                                                // without a display_order have a value of
1923     ///                                                // 999 and are displayed alphabetically with
1924     ///                                                // all other 999 subcommands
1925     ///         .about("Some help and text"))
1926     ///     .subcommand(App::new("beta")
1927     ///         .display_order(1)   // In order to force this subcommand to appear *first*
1928     ///                             // all we have to do is give it a value lower than 999.
1929     ///                             // Any other subcommands with a value of 1 will be displayed
1930     ///                             // alphabetically with this one...then 2 values, then 3, etc.
1931     ///         .about("I should be first!"))
1932     ///     .get_matches_from(vec![
1933     ///         "cust-ord", "--help"
1934     ///     ]);
1935     /// ```
1936     ///
1937     /// The above example displays the following help message
1938     ///
1939     /// ```text
1940     /// cust-ord
1941     ///
1942     /// USAGE:
1943     ///     cust-ord [OPTIONS]
1944     ///
1945     /// OPTIONS:
1946     ///     -h, --help       Print help information
1947     ///     -V, --version    Print version information
1948     ///
1949     /// SUBCOMMANDS:
1950     ///     beta    I should be first!
1951     ///     alpha   Some help and text
1952     /// ```
1953     #[inline]
1954     #[must_use]
display_order(mut self, ord: usize) -> Self1955     pub fn display_order(mut self, ord: usize) -> Self {
1956         self.disp_ord = Some(ord);
1957         self
1958     }
1959 
1960     /// Sets the value name used for subcommands when printing usage and help.
1961     ///
1962     /// By default, this is "SUBCOMMAND".
1963     ///
1964     /// See also [`App::subcommand_help_heading`]
1965     ///
1966     /// # Examples
1967     ///
1968     /// ```no_run
1969     /// # use clap::{App, Arg};
1970     /// App::new("myprog")
1971     ///     .subcommand(App::new("sub1"))
1972     ///     .print_help()
1973     /// # ;
1974     /// ```
1975     ///
1976     /// will produce
1977     ///
1978     /// ```text
1979     /// myprog
1980     ///
1981     /// USAGE:
1982     ///     myprog [SUBCOMMAND]
1983     ///
1984     /// OPTIONS:
1985     ///     -h, --help       Print help information
1986     ///     -V, --version    Print version information
1987     ///
1988     /// SUBCOMMANDS:
1989     ///     help    Print this message or the help of the given subcommand(s)
1990     ///     sub1
1991     /// ```
1992     ///
1993     /// but usage of `subcommand_value_name`
1994     ///
1995     /// ```no_run
1996     /// # use clap::{App, Arg};
1997     /// App::new("myprog")
1998     ///     .subcommand(App::new("sub1"))
1999     ///     .subcommand_value_name("THING")
2000     ///     .print_help()
2001     /// # ;
2002     /// ```
2003     ///
2004     /// will produce
2005     ///
2006     /// ```text
2007     /// myprog
2008     ///
2009     /// USAGE:
2010     ///     myprog [THING]
2011     ///
2012     /// OPTIONS:
2013     ///     -h, --help       Print help information
2014     ///     -V, --version    Print version information
2015     ///
2016     /// SUBCOMMANDS:
2017     ///     help    Print this message or the help of the given subcommand(s)
2018     ///     sub1
2019     /// ```
2020     #[must_use]
subcommand_value_name<S>(mut self, value_name: S) -> Self where S: Into<&'help str>,2021     pub fn subcommand_value_name<S>(mut self, value_name: S) -> Self
2022     where
2023         S: Into<&'help str>,
2024     {
2025         self.subcommand_value_name = Some(value_name.into());
2026         self
2027     }
2028 
2029     /// Sets the help heading used for subcommands when printing usage and help.
2030     ///
2031     /// By default, this is "SUBCOMMANDS".
2032     ///
2033     /// See also [`App::subcommand_value_name`]
2034     ///
2035     /// # Examples
2036     ///
2037     /// ```no_run
2038     /// # use clap::{App, Arg};
2039     /// App::new("myprog")
2040     ///     .subcommand(App::new("sub1"))
2041     ///     .print_help()
2042     /// # ;
2043     /// ```
2044     ///
2045     /// will produce
2046     ///
2047     /// ```text
2048     /// myprog
2049     ///
2050     /// USAGE:
2051     ///     myprog [SUBCOMMAND]
2052     ///
2053     /// OPTIONS:
2054     ///     -h, --help       Print help information
2055     ///     -V, --version    Print version information
2056     ///
2057     /// SUBCOMMANDS:
2058     ///     help    Print this message or the help of the given subcommand(s)
2059     ///     sub1
2060     /// ```
2061     ///
2062     /// but usage of `subcommand_help_heading`
2063     ///
2064     /// ```no_run
2065     /// # use clap::{App, Arg};
2066     /// App::new("myprog")
2067     ///     .subcommand(App::new("sub1"))
2068     ///     .subcommand_help_heading("THINGS")
2069     ///     .print_help()
2070     /// # ;
2071     /// ```
2072     ///
2073     /// will produce
2074     ///
2075     /// ```text
2076     /// myprog
2077     ///
2078     /// USAGE:
2079     ///     myprog [SUBCOMMAND]
2080     ///
2081     /// OPTIONS:
2082     ///     -h, --help       Print help information
2083     ///     -V, --version    Print version information
2084     ///
2085     /// THINGS:
2086     ///     help    Print this message or the help of the given subcommand(s)
2087     ///     sub1
2088     /// ```
2089     #[must_use]
subcommand_help_heading<T>(mut self, heading: T) -> Self where T: Into<&'help str>,2090     pub fn subcommand_help_heading<T>(mut self, heading: T) -> Self
2091     where
2092         T: Into<&'help str>,
2093     {
2094         self.subcommand_heading = Some(heading.into());
2095         self
2096     }
2097 }
2098 
2099 /// Reflection
2100 impl<'help> App<'help> {
2101     /// Get the name of the binary.
2102     #[inline]
get_bin_name(&self) -> Option<&str>2103     pub fn get_bin_name(&self) -> Option<&str> {
2104         self.bin_name.as_deref()
2105     }
2106 
2107     /// Set binary name. Uses `&mut self` instead of `self`.
set_bin_name<S: Into<String>>(&mut self, name: S)2108     pub fn set_bin_name<S: Into<String>>(&mut self, name: S) {
2109         self.bin_name = Some(name.into());
2110     }
2111 
2112     /// Get the name of the app.
2113     #[inline]
get_name(&self) -> &str2114     pub fn get_name(&self) -> &str {
2115         &self.name
2116     }
2117 
2118     /// Get the version of the app.
2119     #[inline]
get_version(&self) -> Option<&'help str>2120     pub fn get_version(&self) -> Option<&'help str> {
2121         self.version
2122     }
2123 
2124     /// Get the long version of the app.
2125     #[inline]
get_long_version(&self) -> Option<&'help str>2126     pub fn get_long_version(&self) -> Option<&'help str> {
2127         self.long_version
2128     }
2129 
2130     /// Get the authors of the app.
2131     #[inline]
get_author(&self) -> Option<&'help str>2132     pub fn get_author(&self) -> Option<&'help str> {
2133         self.author
2134     }
2135 
2136     /// Get the short flag of the subcommand.
2137     #[inline]
get_short_flag(&self) -> Option<char>2138     pub fn get_short_flag(&self) -> Option<char> {
2139         self.short_flag
2140     }
2141 
2142     /// Get the long flag of the subcommand.
2143     #[inline]
get_long_flag(&self) -> Option<&'help str>2144     pub fn get_long_flag(&self) -> Option<&'help str> {
2145         self.long_flag
2146     }
2147 
2148     /// Get the help message specified via [`App::about`].
2149     ///
2150     /// [`App::about`]: App::about()
2151     #[inline]
get_about(&self) -> Option<&'help str>2152     pub fn get_about(&self) -> Option<&'help str> {
2153         self.about
2154     }
2155 
2156     /// Get the help message specified via [`App::long_about`].
2157     ///
2158     /// [`App::long_about`]: App::long_about()
2159     #[inline]
get_long_about(&self) -> Option<&'help str>2160     pub fn get_long_about(&self) -> Option<&'help str> {
2161         self.long_about
2162     }
2163 
2164     /// Get the custom section heading specified via [`App::help_heading`].
2165     ///
2166     /// [`App::help_heading`]: App::help_heading()
2167     #[inline]
get_help_heading(&self) -> Option<&'help str>2168     pub fn get_help_heading(&self) -> Option<&'help str> {
2169         self.current_help_heading
2170     }
2171 
2172     /// Iterate through the *visible* aliases for this subcommand.
2173     #[inline]
get_visible_aliases(&self) -> impl Iterator<Item = &'help str> + '_2174     pub fn get_visible_aliases(&self) -> impl Iterator<Item = &'help str> + '_ {
2175         self.aliases.iter().filter(|(_, vis)| *vis).map(|a| a.0)
2176     }
2177 
2178     /// Iterate through the *visible* short aliases for this subcommand.
2179     #[inline]
get_visible_short_flag_aliases(&self) -> impl Iterator<Item = char> + '_2180     pub fn get_visible_short_flag_aliases(&self) -> impl Iterator<Item = char> + '_ {
2181         self.short_flag_aliases
2182             .iter()
2183             .filter(|(_, vis)| *vis)
2184             .map(|a| a.0)
2185     }
2186 
2187     /// Iterate through the *visible* long aliases for this subcommand.
2188     #[inline]
get_visible_long_flag_aliases(&self) -> impl Iterator<Item = &'help str> + '_2189     pub fn get_visible_long_flag_aliases(&self) -> impl Iterator<Item = &'help str> + '_ {
2190         self.long_flag_aliases
2191             .iter()
2192             .filter(|(_, vis)| *vis)
2193             .map(|a| a.0)
2194     }
2195 
2196     /// Iterate through the set of *all* the aliases for this subcommand, both visible and hidden.
2197     #[inline]
get_all_aliases(&self) -> impl Iterator<Item = &str> + '_2198     pub fn get_all_aliases(&self) -> impl Iterator<Item = &str> + '_ {
2199         self.aliases.iter().map(|a| a.0)
2200     }
2201 
2202     /// Iterate through the set of *all* the short aliases for this subcommand, both visible and hidden.
2203     #[inline]
get_all_short_flag_aliases(&self) -> impl Iterator<Item = char> + '_2204     pub fn get_all_short_flag_aliases(&self) -> impl Iterator<Item = char> + '_ {
2205         self.short_flag_aliases.iter().map(|a| a.0)
2206     }
2207 
2208     /// Iterate through the set of *all* the long aliases for this subcommand, both visible and hidden.
2209     #[inline]
get_all_long_flag_aliases(&self) -> impl Iterator<Item = &'help str> + '_2210     pub fn get_all_long_flag_aliases(&self) -> impl Iterator<Item = &'help str> + '_ {
2211         self.long_flag_aliases.iter().map(|a| a.0)
2212     }
2213 
2214     /// Check if the given [`AppSettings`] variant is currently set on the `App`.
2215     ///
2216     /// This checks both [local] and [global settings].
2217     ///
2218     /// [local]: App::setting()
2219     /// [global settings]: App::global_setting()
2220     #[inline]
is_set(&self, s: AppSettings) -> bool2221     pub fn is_set(&self, s: AppSettings) -> bool {
2222         self.settings.is_set(s) || self.g_settings.is_set(s)
2223     }
2224 
2225     /// Should we color the output?
2226     #[inline(never)]
get_color(&self) -> ColorChoice2227     pub fn get_color(&self) -> ColorChoice {
2228         debug!("App::color: Color setting...");
2229 
2230         if cfg!(feature = "color") {
2231             #[allow(deprecated)]
2232             if self.is_set(AppSettings::ColorNever) {
2233                 debug!("Never");
2234                 ColorChoice::Never
2235             } else if self.is_set(AppSettings::ColorAlways) {
2236                 debug!("Always");
2237                 ColorChoice::Always
2238             } else {
2239                 debug!("Auto");
2240                 ColorChoice::Auto
2241             }
2242         } else {
2243             ColorChoice::Never
2244         }
2245     }
2246 
2247     /// Iterate through the set of subcommands, getting a reference to each.
2248     #[inline]
get_subcommands(&self) -> impl Iterator<Item = &App<'help>>2249     pub fn get_subcommands(&self) -> impl Iterator<Item = &App<'help>> {
2250         self.subcommands.iter()
2251     }
2252 
2253     /// Iterate through the set of subcommands, getting a mutable reference to each.
2254     #[inline]
get_subcommands_mut(&mut self) -> impl Iterator<Item = &mut App<'help>>2255     pub fn get_subcommands_mut(&mut self) -> impl Iterator<Item = &mut App<'help>> {
2256         self.subcommands.iter_mut()
2257     }
2258 
2259     /// Returns `true` if this `App` has subcommands.
2260     #[inline]
has_subcommands(&self) -> bool2261     pub fn has_subcommands(&self) -> bool {
2262         !self.subcommands.is_empty()
2263     }
2264 
2265     /// Returns the help heading for listing subcommands.
2266     #[inline]
get_subommand_help_heading(&self) -> Option<&str>2267     pub fn get_subommand_help_heading(&self) -> Option<&str> {
2268         self.subcommand_heading
2269     }
2270 
2271     /// Returns the subcommand value name.
2272     #[inline]
get_subcommand_value_name(&self) -> Option<&str>2273     pub fn get_subcommand_value_name(&self) -> Option<&str> {
2274         self.subcommand_value_name
2275     }
2276 
2277     /// Returns the help heading for listing subcommands.
2278     #[inline]
get_after_help(&self) -> Option<&str>2279     pub fn get_after_help(&self) -> Option<&str> {
2280         self.after_help
2281     }
2282 
2283     /// Returns the help heading for listing subcommands.
2284     #[inline]
get_after_long_help(&self) -> Option<&str>2285     pub fn get_after_long_help(&self) -> Option<&str> {
2286         self.after_long_help
2287     }
2288 
2289     /// Find subcommand such that its name or one of aliases equals `name`.
2290     ///
2291     /// This does not recurse through subcommands of subcommands.
2292     #[inline]
find_subcommand<T>(&self, name: &T) -> Option<&App<'help>> where T: PartialEq<str> + ?Sized,2293     pub fn find_subcommand<T>(&self, name: &T) -> Option<&App<'help>>
2294     where
2295         T: PartialEq<str> + ?Sized,
2296     {
2297         self.get_subcommands().find(|s| s.aliases_to(name))
2298     }
2299 
2300     /// Find subcommand such that its name or one of aliases equals `name`, returning
2301     /// a mutable reference to the subcommand.
2302     ///
2303     /// This does not recurse through subcommands of subcommands.
2304     #[inline]
find_subcommand_mut<T>(&mut self, name: &T) -> Option<&mut App<'help>> where T: PartialEq<str> + ?Sized,2305     pub fn find_subcommand_mut<T>(&mut self, name: &T) -> Option<&mut App<'help>>
2306     where
2307         T: PartialEq<str> + ?Sized,
2308     {
2309         self.get_subcommands_mut().find(|s| s.aliases_to(name))
2310     }
2311 
2312     /// Iterate through the set of arguments.
2313     #[inline]
get_arguments(&self) -> impl Iterator<Item = &Arg<'help>>2314     pub fn get_arguments(&self) -> impl Iterator<Item = &Arg<'help>> {
2315         self.args.args()
2316     }
2317 
2318     /// Iterate through the *positionals* arguments.
2319     #[inline]
get_positionals(&self) -> impl Iterator<Item = &Arg<'help>>2320     pub fn get_positionals(&self) -> impl Iterator<Item = &Arg<'help>> {
2321         self.get_arguments().filter(|a| a.is_positional())
2322     }
2323 
2324     /// Iterate through the *options*.
get_opts(&self) -> impl Iterator<Item = &Arg<'help>>2325     pub fn get_opts(&self) -> impl Iterator<Item = &Arg<'help>> {
2326         self.get_arguments()
2327             .filter(|a| a.is_set(ArgSettings::TakesValue) && !a.is_positional())
2328     }
2329 
2330     /// Get a list of all arguments the given argument conflicts with.
2331     ///
2332     /// If the provided argument is declared as global, the conflicts will be determined
2333     /// based on the propagation rules of global arguments.
2334     ///
2335     /// ### Panics
2336     ///
2337     /// If the given arg contains a conflict with an argument that is unknown to
2338     /// this `App`.
get_arg_conflicts_with(&self, arg: &Arg) -> Vec<&Arg<'help>>2339     pub fn get_arg_conflicts_with(&self, arg: &Arg) -> Vec<&Arg<'help>> // FIXME: This could probably have been an iterator
2340     {
2341         if arg.get_global() {
2342             self.get_global_arg_conflicts_with(arg)
2343         } else {
2344             arg.blacklist
2345                 .iter()
2346                 .map(|id| {
2347                     self.args.args().find(|arg| arg.id == *id).expect(
2348                         "App::get_arg_conflicts_with: \
2349                     The passed arg conflicts with an arg unknown to the app",
2350                     )
2351                 })
2352                 .collect()
2353         }
2354     }
2355 
2356     // Get a unique list of all arguments of all commands and continuous subcommands the given argument conflicts with.
2357     //
2358     // This behavior follows the propagation rules of global arguments.
2359     // It is useful for finding conflicts for arguments declared as global.
2360     //
2361     // ### Panics
2362     //
2363     // If the given arg contains a conflict with an argument that is unknown to
2364     // this `App`.
get_global_arg_conflicts_with(&self, arg: &Arg) -> Vec<&Arg<'help>>2365     fn get_global_arg_conflicts_with(&self, arg: &Arg) -> Vec<&Arg<'help>> // FIXME: This could probably have been an iterator
2366     {
2367         arg.blacklist
2368             .iter()
2369             .map(|id| {
2370                 self.args
2371                     .args()
2372                     .chain(
2373                         self.get_subcommands_containing(arg)
2374                             .iter()
2375                             .flat_map(|x| x.args.args()),
2376                     )
2377                     .find(|arg| arg.id == *id)
2378                     .expect(
2379                         "App::get_arg_conflicts_with: \
2380                     The passed arg conflicts with an arg unknown to the app",
2381                     )
2382             })
2383             .collect()
2384     }
2385 
2386     // Get a list of subcommands which contain the provided Argument
2387     //
2388     // This command will only include subcommands in its list for which the subcommands
2389     // parent also contains the Argument.
2390     //
2391     // This search follows the propagation rules of global arguments.
2392     // It is useful to finding subcommands, that have inherited a global argument.
2393     //
2394     // **NOTE:** In this case only Sucommand_1 will be included
2395     //   Subcommand_1 (contains Arg)
2396     //     Subcommand_1.1 (doesn't contain Arg)
2397     //       Subcommand_1.1.1 (contains Arg)
2398     //
get_subcommands_containing(&self, arg: &Arg) -> Vec<&App<'help>>2399     fn get_subcommands_containing(&self, arg: &Arg) -> Vec<&App<'help>> {
2400         let mut vec = std::vec::Vec::new();
2401         for idx in 0..self.subcommands.len() {
2402             if self.subcommands[idx].args.args().any(|ar| ar.id == arg.id) {
2403                 vec.push(&self.subcommands[idx]);
2404                 vec.append(&mut self.subcommands[idx].get_subcommands_containing(arg));
2405             }
2406         }
2407         vec
2408     }
2409 }
2410 
2411 /// Deprecated
2412 impl<'help> App<'help> {
2413     /// Deprecated in [Issue #3087](https://github.com/clap-rs/clap/issues/3087), maybe [`clap::Parser`][crate::Parser] would fit your use case?
2414     #[cfg(feature = "yaml")]
2415     #[deprecated(
2416         since = "3.0.0",
2417         note = "Deprecated in Issue #3087, maybe clap::Parser would fit your use case?"
2418     )]
from_yaml(y: &'help Yaml) -> Self2419     pub fn from_yaml(y: &'help Yaml) -> Self {
2420         #![allow(deprecated)]
2421         let yaml_file_hash = y.as_hash().expect("YAML file must be a hash");
2422         // We WANT this to panic on error...so expect() is good.
2423         let (mut a, yaml, err) = if let Some(name) = y["name"].as_str() {
2424             (App::new(name), yaml_file_hash, "app".into())
2425         } else {
2426             let (name_yaml, value_yaml) = yaml_file_hash
2427                 .iter()
2428                 .next()
2429                 .expect("There must be one subcommand in the YAML file");
2430             let name_str = name_yaml
2431                 .as_str()
2432                 .expect("Subcommand name must be a string");
2433 
2434             (
2435                 App::new(name_str),
2436                 value_yaml.as_hash().expect("Subcommand must be a hash"),
2437                 format!("subcommand '{}'", name_str),
2438             )
2439         };
2440 
2441         for (k, v) in yaml {
2442             a = match k.as_str().expect("App fields must be strings") {
2443                 "version" => yaml_to_str!(a, v, version),
2444                 "long_version" => yaml_to_str!(a, v, long_version),
2445                 "author" => yaml_to_str!(a, v, author),
2446                 "bin_name" => yaml_to_str!(a, v, bin_name),
2447                 "about" => yaml_to_str!(a, v, about),
2448                 "long_about" => yaml_to_str!(a, v, long_about),
2449                 "before_help" => yaml_to_str!(a, v, before_help),
2450                 "after_help" => yaml_to_str!(a, v, after_help),
2451                 "template" => yaml_to_str!(a, v, help_template),
2452                 "usage" => yaml_to_str!(a, v, override_usage),
2453                 "help" => yaml_to_str!(a, v, override_help),
2454                 "help_message" => yaml_to_str!(a, v, help_message),
2455                 "version_message" => yaml_to_str!(a, v, version_message),
2456                 "alias" => yaml_to_str!(a, v, alias),
2457                 "aliases" => yaml_vec_or_str!(a, v, alias),
2458                 "visible_alias" => yaml_to_str!(a, v, visible_alias),
2459                 "visible_aliases" => yaml_vec_or_str!(a, v, visible_alias),
2460                 "display_order" => yaml_to_usize!(a, v, display_order),
2461                 "args" => {
2462                     if let Some(vec) = v.as_vec() {
2463                         for arg_yaml in vec {
2464                             a = a.arg(Arg::from_yaml(arg_yaml));
2465                         }
2466                     } else {
2467                         panic!("Failed to convert YAML value {:?} to a vec", v);
2468                     }
2469                     a
2470                 }
2471                 "subcommands" => {
2472                     if let Some(vec) = v.as_vec() {
2473                         for sc_yaml in vec {
2474                             a = a.subcommand(App::from_yaml(sc_yaml));
2475                         }
2476                     } else {
2477                         panic!("Failed to convert YAML value {:?} to a vec", v);
2478                     }
2479                     a
2480                 }
2481                 "groups" => {
2482                     if let Some(vec) = v.as_vec() {
2483                         for ag_yaml in vec {
2484                             a = a.group(ArgGroup::from(ag_yaml));
2485                         }
2486                     } else {
2487                         panic!("Failed to convert YAML value {:?} to a vec", v);
2488                     }
2489                     a
2490                 }
2491                 "setting" | "settings" => {
2492                     yaml_to_setting!(a, v, setting, AppSettings, "AppSetting", err)
2493                 }
2494                 "global_setting" | "global_settings" => {
2495                     yaml_to_setting!(a, v, global_setting, AppSettings, "AppSetting", err)
2496                 }
2497                 _ => a,
2498             }
2499         }
2500 
2501         a
2502     }
2503 
2504     /// Deprecated, replaced with [`App::override_usage`]
2505     #[deprecated(since = "3.0.0", note = "Replaced with `App::override_usage`")]
2506     #[must_use]
usage<S: Into<&'help str>>(self, usage: S) -> Self2507     pub fn usage<S: Into<&'help str>>(self, usage: S) -> Self {
2508         self.override_usage(usage)
2509     }
2510 
2511     /// Deprecated, replaced with [`App::override_help`]
2512     #[deprecated(since = "3.0.0", note = "Replaced with `App::override_help`")]
2513     #[must_use]
help<S: Into<&'help str>>(self, help: S) -> Self2514     pub fn help<S: Into<&'help str>>(self, help: S) -> Self {
2515         self.override_help(help)
2516     }
2517 
2518     /// Deprecated, replaced with [`App::mut_arg`]
2519     #[deprecated(since = "3.0.0", note = "Replaced with `App::mut_arg`")]
2520     #[must_use]
help_short(self, c: char) -> Self2521     pub fn help_short(self, c: char) -> Self {
2522         self.mut_arg("help", |a| a.short(c))
2523     }
2524 
2525     /// Deprecated, replaced with [`App::mut_arg`]
2526     #[deprecated(since = "3.0.0", note = "Replaced with `App::mut_arg`")]
2527     #[must_use]
version_short(self, c: char) -> Self2528     pub fn version_short(self, c: char) -> Self {
2529         self.mut_arg("version", |a| a.short(c))
2530     }
2531 
2532     /// Deprecated, replaced with [`App::mut_arg`]
2533     #[deprecated(since = "3.0.0", note = "Replaced with `App::mut_arg`")]
2534     #[must_use]
help_message(self, s: impl Into<&'help str>) -> Self2535     pub fn help_message(self, s: impl Into<&'help str>) -> Self {
2536         self.mut_arg("help", |a| a.help(s.into()))
2537     }
2538 
2539     /// Deprecated, replaced with [`App::mut_arg`]
2540     #[deprecated(since = "3.0.0", note = "Replaced with `App::mut_arg`")]
2541     #[must_use]
version_message(self, s: impl Into<&'help str>) -> Self2542     pub fn version_message(self, s: impl Into<&'help str>) -> Self {
2543         self.mut_arg("version", |a| a.help(s.into()))
2544     }
2545 
2546     /// Deprecated, replaced with [`App::help_template`]
2547     #[deprecated(since = "3.0.0", note = "Replaced with `App::help_template`")]
2548     #[must_use]
template<S: Into<&'help str>>(self, s: S) -> Self2549     pub fn template<S: Into<&'help str>>(self, s: S) -> Self {
2550         self.help_template(s)
2551     }
2552 
2553     /// Deprecated, replaced with [`App::setting(a| b)`]
2554     #[deprecated(since = "3.0.0", note = "Replaced with `App::setting(a | b)`")]
2555     #[must_use]
settings(mut self, settings: &[AppSettings]) -> Self2556     pub fn settings(mut self, settings: &[AppSettings]) -> Self {
2557         for s in settings {
2558             self.settings.insert((*s).into());
2559         }
2560         self
2561     }
2562 
2563     /// Deprecated, replaced with [`App::unset_setting(a| b)`]
2564     #[deprecated(since = "3.0.0", note = "Replaced with `App::unset_setting(a | b)`")]
2565     #[must_use]
unset_settings(mut self, settings: &[AppSettings]) -> Self2566     pub fn unset_settings(mut self, settings: &[AppSettings]) -> Self {
2567         for s in settings {
2568             self.settings.remove((*s).into());
2569         }
2570         self
2571     }
2572 
2573     /// Deprecated, replaced with [`App::global_setting(a| b)`]
2574     #[deprecated(since = "3.0.0", note = "Replaced with `App::global_setting(a | b)`")]
2575     #[must_use]
global_settings(mut self, settings: &[AppSettings]) -> Self2576     pub fn global_settings(mut self, settings: &[AppSettings]) -> Self {
2577         for s in settings {
2578             self.settings.insert((*s).into());
2579             self.g_settings.insert((*s).into());
2580         }
2581         self
2582     }
2583 
2584     /// Deprecated, replaced with [`App::term_width`]
2585     #[deprecated(since = "3.0.0", note = "Replaced with `App::term_width`")]
2586     #[must_use]
set_term_width(self, width: usize) -> Self2587     pub fn set_term_width(self, width: usize) -> Self {
2588         self.term_width(width)
2589     }
2590 
2591     /// Deprecated in [Issue #3086](https://github.com/clap-rs/clap/issues/3086), see [`arg!`][crate::arg!].
2592     #[deprecated(since = "3.0.0", note = "Deprecated in Issue #3086, see `clap::arg!")]
2593     #[must_use]
arg_from_usage(self, usage: &'help str) -> Self2594     pub fn arg_from_usage(self, usage: &'help str) -> Self {
2595         #![allow(deprecated)]
2596         self.arg(Arg::from_usage(usage))
2597     }
2598 
2599     /// Deprecated in [Issue #3086](https://github.com/clap-rs/clap/issues/3086), see [`arg!`][crate::arg!].
2600     #[deprecated(since = "3.0.0", note = "Deprecated in Issue #3086, see `clap::arg!")]
2601     #[must_use]
args_from_usage(mut self, usage: &'help str) -> Self2602     pub fn args_from_usage(mut self, usage: &'help str) -> Self {
2603         #![allow(deprecated)]
2604         for line in usage.lines() {
2605             let l = line.trim();
2606             if l.is_empty() {
2607                 continue;
2608             }
2609             self = self.arg(Arg::from_usage(l));
2610         }
2611         self
2612     }
2613 
2614     /// Deprecated, replaced with [`App::render_version`]
2615     #[deprecated(since = "3.0.0", note = "Replaced with `App::render_version`")]
write_version<W: Write>(&self, w: &mut W) -> ClapResult<()>2616     pub fn write_version<W: Write>(&self, w: &mut W) -> ClapResult<()> {
2617         write!(w, "{}", self.render_version()).map_err(From::from)
2618     }
2619 
2620     /// Deprecated, replaced with [`App::render_long_version`]
2621     #[deprecated(since = "3.0.0", note = "Replaced with `App::render_long_version`")]
write_long_version<W: Write>(&self, w: &mut W) -> ClapResult<()>2622     pub fn write_long_version<W: Write>(&self, w: &mut W) -> ClapResult<()> {
2623         write!(w, "{}", self.render_long_version()).map_err(From::from)
2624     }
2625 
2626     /// Deprecated, replaced with [`App::try_get_matches`]
2627     #[deprecated(since = "3.0.0", note = "Replaced with `App::try_get_matches`")]
get_matches_safe(self) -> ClapResult<ArgMatches>2628     pub fn get_matches_safe(self) -> ClapResult<ArgMatches> {
2629         self.try_get_matches()
2630     }
2631 
2632     /// Deprecated, replaced with [`App::try_get_matches_from`]
2633     #[deprecated(since = "3.0.0", note = "Replaced with `App::try_get_matches_from`")]
get_matches_from_safe<I, T>(self, itr: I) -> ClapResult<ArgMatches> where I: IntoIterator<Item = T>, T: Into<OsString> + Clone,2634     pub fn get_matches_from_safe<I, T>(self, itr: I) -> ClapResult<ArgMatches>
2635     where
2636         I: IntoIterator<Item = T>,
2637         T: Into<OsString> + Clone,
2638     {
2639         self.try_get_matches_from(itr)
2640     }
2641 
2642     /// Deprecated, replaced with [`App::try_get_matches_from_mut`]
2643     #[deprecated(
2644         since = "3.0.0",
2645         note = "Replaced with `App::try_get_matches_from_mut`"
2646     )]
get_matches_from_safe_borrow<I, T>(&mut self, itr: I) -> ClapResult<ArgMatches> where I: IntoIterator<Item = T>, T: Into<OsString> + Clone,2647     pub fn get_matches_from_safe_borrow<I, T>(&mut self, itr: I) -> ClapResult<ArgMatches>
2648     where
2649         I: IntoIterator<Item = T>,
2650         T: Into<OsString> + Clone,
2651     {
2652         self.try_get_matches_from_mut(itr)
2653     }
2654 }
2655 
2656 // Internally used only
2657 impl<'help> App<'help> {
get_used_global_args(&self, matcher: &ArgMatcher) -> Vec<Id>2658     fn get_used_global_args(&self, matcher: &ArgMatcher) -> Vec<Id> {
2659         let global_args: Vec<_> = self
2660             .args
2661             .args()
2662             .filter(|a| a.get_global())
2663             .map(|ga| ga.id.clone())
2664             .collect();
2665         if let Some(used_subcommand) = matcher.subcommand.as_ref() {
2666             if let Some(used_subcommand) = self
2667                 .subcommands
2668                 .iter()
2669                 .find(|subcommand| subcommand.id == used_subcommand.id)
2670             {
2671                 return [global_args, used_subcommand.get_used_global_args(matcher)].concat();
2672             }
2673         }
2674         global_args
2675     }
2676 
_do_parse(&mut self, it: &mut Input) -> ClapResult<ArgMatches>2677     fn _do_parse(&mut self, it: &mut Input) -> ClapResult<ArgMatches> {
2678         debug!("App::_do_parse");
2679 
2680         // If there are global arguments, or settings we need to propagate them down to subcommands
2681         // before parsing in case we run into a subcommand
2682         self._build();
2683 
2684         let mut matcher = ArgMatcher::new(self);
2685 
2686         // do the real parsing
2687         let mut parser = Parser::new(self);
2688         if let Err(error) = parser.get_matches_with(&mut matcher, it) {
2689             if self.is_set(AppSettings::IgnoreErrors) {
2690                 debug!("App::_do_parse: ignoring error: {}", error);
2691             } else {
2692                 return Err(error);
2693             }
2694         }
2695 
2696         let global_arg_vec: Vec<Id> = self.get_used_global_args(&matcher);
2697 
2698         matcher.propagate_globals(&global_arg_vec);
2699 
2700         Ok(matcher.into_inner())
2701     }
2702 
2703     // used in clap_complete (https://github.com/clap-rs/clap_complete)
2704     #[doc(hidden)]
_build_all(&mut self)2705     pub fn _build_all(&mut self) {
2706         self._build();
2707         for subcmd in self.get_subcommands_mut() {
2708             subcmd._build();
2709         }
2710         self._build_bin_names();
2711     }
2712 
2713     // used in clap_complete (https://github.com/clap-rs/clap_complete)
2714     #[doc(hidden)]
_build(&mut self)2715     pub fn _build(&mut self) {
2716         debug!("App::_build");
2717         if !self.settings.is_set(AppSettings::Built) {
2718             // Make sure all the globally set flags apply to us as well
2719             self.settings = self.settings | self.g_settings;
2720 
2721             self._propagate();
2722             self._check_help_and_version();
2723             self._propagate_global_args();
2724             self._derive_display_order();
2725 
2726             let mut pos_counter = 1;
2727             let self_override = self.is_set(AppSettings::AllArgsOverrideSelf);
2728             for a in self.args.args_mut() {
2729                 // Fill in the groups
2730                 for g in &a.groups {
2731                     if let Some(ag) = self.groups.iter_mut().find(|grp| grp.id == *g) {
2732                         ag.args.push(a.id.clone());
2733                     } else {
2734                         let mut ag = ArgGroup::with_id(g.clone());
2735                         ag.args.push(a.id.clone());
2736                         self.groups.push(ag);
2737                     }
2738                 }
2739 
2740                 // Figure out implied settings
2741                 if a.is_set(ArgSettings::Last) {
2742                     // if an arg has `Last` set, we need to imply DontCollapseArgsInUsage so that args
2743                     // in the usage string don't get confused or left out.
2744                     self.settings.set(AppSettings::DontCollapseArgsInUsage);
2745                 }
2746                 if self_override {
2747                     let self_id = a.id.clone();
2748                     a.overrides.push(self_id);
2749                 }
2750                 a._build();
2751                 if a.is_positional() && a.index.is_none() {
2752                     a.index = Some(pos_counter);
2753                     pos_counter += 1;
2754                 }
2755             }
2756 
2757             self.args._build();
2758 
2759             #[cfg(debug_assertions)]
2760             self::debug_asserts::assert_app(self);
2761             self.settings.set(AppSettings::Built);
2762         } else {
2763             debug!("App::_build: already built");
2764         }
2765     }
2766 
_panic_on_missing_help(&self, help_required_globally: bool)2767     fn _panic_on_missing_help(&self, help_required_globally: bool) {
2768         if self.is_set(AppSettings::HelpExpected) || help_required_globally {
2769             let args_missing_help: Vec<String> = self
2770                 .args
2771                 .args()
2772                 .filter(|arg| arg.help.is_none() && arg.long_help.is_none())
2773                 .map(|arg| String::from(arg.name))
2774                 .collect();
2775 
2776             assert!(args_missing_help.is_empty(),
2777                     "AppSettings::HelpExpected is enabled for the App {}, but at least one of its arguments does not have either `help` or `long_help` set. List of such arguments: {}",
2778                     self.name,
2779                     args_missing_help.join(", ")
2780                 );
2781         }
2782 
2783         for sub_app in &self.subcommands {
2784             sub_app._panic_on_missing_help(help_required_globally);
2785         }
2786     }
2787 
2788     #[cfg(debug_assertions)]
two_args_of<F>(&self, condition: F) -> Option<(&Arg<'help>, &Arg<'help>)> where F: Fn(&Arg) -> bool,2789     fn two_args_of<F>(&self, condition: F) -> Option<(&Arg<'help>, &Arg<'help>)>
2790     where
2791         F: Fn(&Arg) -> bool,
2792     {
2793         two_elements_of(self.args.args().filter(|a: &&Arg| condition(a)))
2794     }
2795 
2796     // just in case
2797     #[allow(unused)]
two_groups_of<F>(&self, condition: F) -> Option<(&ArgGroup, &ArgGroup)> where F: Fn(&ArgGroup) -> bool,2798     fn two_groups_of<F>(&self, condition: F) -> Option<(&ArgGroup, &ArgGroup)>
2799     where
2800         F: Fn(&ArgGroup) -> bool,
2801     {
2802         two_elements_of(self.groups.iter().filter(|a| condition(a)))
2803     }
2804 
2805     /// Propagate global args
_propagate_global_args(&mut self)2806     pub(crate) fn _propagate_global_args(&mut self) {
2807         debug!("App::_propagate_global_args:{}", self.name);
2808 
2809         for sc in &mut self.subcommands {
2810             for a in self.args.args().filter(|a| a.get_global()) {
2811                 let mut propagate = false;
2812                 let is_generated = matches!(
2813                     a.provider,
2814                     ArgProvider::Generated | ArgProvider::GeneratedMutated
2815                 );
2816 
2817                 // Remove generated help and version args in the subcommand
2818                 //
2819                 // Don't remove if those args are further mutated
2820                 if is_generated {
2821                     let generated_pos = sc
2822                         .args
2823                         .args()
2824                         .position(|x| x.id == a.id && x.provider == ArgProvider::Generated);
2825 
2826                     if let Some(index) = generated_pos {
2827                         sc.args.remove(index);
2828                         propagate = true;
2829                     }
2830                 }
2831 
2832                 if propagate || sc.find(&a.id).is_none() {
2833                     sc.args.push(a.clone());
2834                 }
2835             }
2836         }
2837     }
2838 
2839     /// Propagate settings
_propagate(&mut self)2840     pub(crate) fn _propagate(&mut self) {
2841         debug!("App::_propagate:{}", self.name);
2842         let mut subcommands = std::mem::take(&mut self.subcommands);
2843         for sc in &mut subcommands {
2844             self._propagate_subcommand(sc);
2845         }
2846         self.subcommands = subcommands;
2847     }
2848 
_propagate_subcommand(&self, sc: &mut Self)2849     fn _propagate_subcommand(&self, sc: &mut Self) {
2850         // We have to create a new scope in order to tell rustc the borrow of `sc` is
2851         // done and to recursively call this method
2852         {
2853             if self.settings.is_set(AppSettings::PropagateVersion) {
2854                 if sc.version.is_none() && self.version.is_some() {
2855                     sc.version = Some(self.version.unwrap());
2856                 }
2857                 if sc.long_version.is_none() && self.long_version.is_some() {
2858                     sc.long_version = Some(self.long_version.unwrap());
2859                 }
2860             }
2861 
2862             sc.settings = sc.settings | self.g_settings;
2863             sc.g_settings = sc.g_settings | self.g_settings;
2864             sc.term_w = self.term_w;
2865             sc.max_w = self.max_w;
2866         }
2867     }
2868 
2869     #[allow(clippy::blocks_in_if_conditions)]
_check_help_and_version(&mut self)2870     pub(crate) fn _check_help_and_version(&mut self) {
2871         debug!("App::_check_help_and_version");
2872 
2873         if self.is_set(AppSettings::DisableHelpFlag)
2874             || self.args.args().any(|x| {
2875                 x.provider == ArgProvider::User
2876                     && (x.long == Some("help") || x.id == Id::help_hash())
2877             })
2878             || self
2879                 .subcommands
2880                 .iter()
2881                 .any(|sc| sc.long_flag == Some("help"))
2882         {
2883             debug!("App::_check_help_and_version: Removing generated help");
2884 
2885             let generated_help_pos = self
2886                 .args
2887                 .args()
2888                 .position(|x| x.id == Id::help_hash() && x.provider == ArgProvider::Generated);
2889 
2890             if let Some(index) = generated_help_pos {
2891                 self.args.remove(index);
2892             }
2893         } else {
2894             let other_arg_has_short = self.args.args().any(|x| x.short == Some('h'));
2895             let help = self
2896                 .args
2897                 .args_mut()
2898                 .find(|x| x.id == Id::help_hash())
2899                 .expect(INTERNAL_ERROR_MSG);
2900 
2901             if !(help.short.is_some()
2902                 || other_arg_has_short
2903                 || self.subcommands.iter().any(|sc| sc.short_flag == Some('h')))
2904             {
2905                 help.short = Some('h');
2906             }
2907         }
2908 
2909         // Determine if we should remove the generated --version flag
2910         //
2911         // Note that if only mut_arg() was used, the first expression will evaluate to `true`
2912         // however inside the condition block, we only check for Generated args, not
2913         // GeneratedMutated args, so the `mut_arg("version", ..) will be skipped and fall through
2914         // to the following condition below (Adding the short `-V`)
2915         if self.settings.is_set(AppSettings::DisableVersionFlag)
2916             || (self.version.is_none() && self.long_version.is_none())
2917             || self.args.args().any(|x| {
2918                 x.provider == ArgProvider::User
2919                     && (x.long == Some("version") || x.id == Id::version_hash())
2920             })
2921             || self
2922                 .subcommands
2923                 .iter()
2924                 .any(|sc| sc.long_flag == Some("version"))
2925         {
2926             debug!("App::_check_help_and_version: Removing generated version");
2927 
2928             // This is the check mentioned above that only checks for Generated, not
2929             // GeneratedMuated args by design.
2930             let generated_version_pos = self
2931                 .args
2932                 .args()
2933                 .position(|x| x.id == Id::version_hash() && x.provider == ArgProvider::Generated);
2934 
2935             if let Some(index) = generated_version_pos {
2936                 self.args.remove(index);
2937             }
2938         }
2939 
2940         // If we still have a generated --version flag, determine if we can apply the short `-V`
2941         if self.args.args().any(|x| {
2942             x.id == Id::version_hash()
2943                 && matches!(
2944                     x.provider,
2945                     ArgProvider::Generated | ArgProvider::GeneratedMutated
2946                 )
2947         }) {
2948             let other_arg_has_short = self.args.args().any(|x| x.short == Some('V'));
2949             let version = self
2950                 .args
2951                 .args_mut()
2952                 .find(|x| x.id == Id::version_hash())
2953                 .expect(INTERNAL_ERROR_MSG);
2954 
2955             if !(version.short.is_some()
2956                 || other_arg_has_short
2957                 || self.subcommands.iter().any(|sc| sc.short_flag == Some('V')))
2958             {
2959                 version.short = Some('V');
2960             }
2961         }
2962 
2963         if !self.is_set(AppSettings::DisableHelpSubcommand)
2964             && self.has_subcommands()
2965             && !self.subcommands.iter().any(|s| s.id == Id::help_hash())
2966         {
2967             debug!("App::_check_help_and_version: Building help subcommand");
2968             let mut help_subcmd = App::new("help")
2969                 .about("Print this message or the help of the given subcommand(s)")
2970                 .arg(
2971                     Arg::new("subcommand")
2972                         .index(1)
2973                         .takes_value(true)
2974                         .multiple_occurrences(true)
2975                         .value_name("SUBCOMMAND")
2976                         .help("The subcommand whose help message to display"),
2977                 );
2978             self._propagate_subcommand(&mut help_subcmd);
2979 
2980             // The parser acts like this is set, so let's set it so we don't falsely
2981             // advertise it to the user
2982             help_subcmd.version = None;
2983             help_subcmd.long_version = None;
2984             help_subcmd = help_subcmd
2985                 .setting(AppSettings::DisableHelpFlag)
2986                 .unset_global_setting(AppSettings::PropagateVersion);
2987 
2988             self.subcommands.push(help_subcmd);
2989         }
2990     }
2991 
_derive_display_order(&mut self)2992     pub(crate) fn _derive_display_order(&mut self) {
2993         debug!("App::_derive_display_order:{}", self.name);
2994 
2995         if self.settings.is_set(AppSettings::DeriveDisplayOrder) {
2996             for (i, a) in self
2997                 .args
2998                 .args_mut()
2999                 .filter(|a| !a.is_positional())
3000                 .filter(|a| a.provider != ArgProvider::Generated)
3001                 .enumerate()
3002             {
3003                 a.disp_ord.get_or_insert(i);
3004             }
3005             for (i, sc) in &mut self.subcommands.iter_mut().enumerate() {
3006                 sc.disp_ord.get_or_insert(i);
3007             }
3008         }
3009         for sc in &mut self.subcommands {
3010             sc._derive_display_order();
3011         }
3012     }
3013 
3014     // used in clap_complete (https://github.com/clap-rs/clap_complete)
3015     #[doc(hidden)]
_build_bin_names(&mut self)3016     pub fn _build_bin_names(&mut self) {
3017         debug!("App::_build_bin_names");
3018 
3019         if !self.is_set(AppSettings::BinNameBuilt) {
3020             for mut sc in &mut self.subcommands {
3021                 debug!("App::_build_bin_names:iter: bin_name set...");
3022 
3023                 if sc.bin_name.is_none() {
3024                     debug!("No");
3025                     let bin_name = format!(
3026                         "{}{}{}",
3027                         self.bin_name.as_ref().unwrap_or(&self.name),
3028                         if self.bin_name.is_some() { " " } else { "" },
3029                         &*sc.name
3030                     );
3031                     debug!(
3032                         "App::_build_bin_names:iter: Setting bin_name of {} to {}",
3033                         self.name, bin_name
3034                     );
3035                     sc.bin_name = Some(bin_name);
3036                 } else {
3037                     debug!("yes ({:?})", sc.bin_name);
3038                 }
3039                 debug!(
3040                     "App::_build_bin_names:iter: Calling build_bin_names from...{}",
3041                     sc.name
3042                 );
3043                 sc._build_bin_names();
3044             }
3045             self.set(AppSettings::BinNameBuilt);
3046         } else {
3047             debug!("App::_build_bin_names: already built");
3048         }
3049     }
3050 
_render_version(&self, use_long: bool) -> String3051     pub(crate) fn _render_version(&self, use_long: bool) -> String {
3052         debug!("App::_render_version");
3053 
3054         let ver = if use_long {
3055             self.long_version.or(self.version).unwrap_or("")
3056         } else {
3057             self.version.or(self.long_version).unwrap_or("")
3058         };
3059         if let Some(bn) = self.bin_name.as_ref() {
3060             if bn.contains(' ') {
3061                 // In case we're dealing with subcommands i.e. git mv is translated to git-mv
3062                 format!("{} {}\n", bn.replace(' ', "-"), ver)
3063             } else {
3064                 format!("{} {}\n", &self.name[..], ver)
3065             }
3066         } else {
3067             format!("{} {}\n", &self.name[..], ver)
3068         }
3069     }
3070 
format_group(&self, g: &Id) -> String3071     pub(crate) fn format_group(&self, g: &Id) -> String {
3072         let g_string = self
3073             .unroll_args_in_group(g)
3074             .iter()
3075             .filter_map(|x| self.find(x))
3076             .map(|x| {
3077                 if x.is_positional() {
3078                     // Print val_name for positional arguments. e.g. <file_name>
3079                     x.name_no_brackets().to_string()
3080                 } else {
3081                     // Print usage string for flags arguments, e.g. <--help>
3082                     x.to_string()
3083                 }
3084             })
3085             .collect::<Vec<_>>()
3086             .join("|");
3087         format!("<{}>", &*g_string)
3088     }
3089 }
3090 
3091 /// A workaround:
3092 /// <https://github.com/rust-lang/rust/issues/34511#issuecomment-373423999>
3093 pub(crate) trait Captures<'a> {}
3094 impl<'a, T> Captures<'a> for T {}
3095 
3096 // Internal Query Methods
3097 impl<'help> App<'help> {
3098     /// Iterate through the *flags* & *options* arguments.
get_non_positionals(&self) -> impl Iterator<Item = &Arg<'help>>3099     pub(crate) fn get_non_positionals(&self) -> impl Iterator<Item = &Arg<'help>> {
3100         self.get_arguments().filter(|a| !a.is_positional())
3101     }
3102 
3103     /// Iterate through the *positionals* that don't have custom heading.
get_positionals_with_no_heading(&self) -> impl Iterator<Item = &Arg<'help>>3104     pub(crate) fn get_positionals_with_no_heading(&self) -> impl Iterator<Item = &Arg<'help>> {
3105         self.get_positionals()
3106             .filter(|a| a.get_help_heading().is_none())
3107     }
3108 
3109     /// Iterate through the *flags* & *options* that don't have custom heading.
get_non_positionals_with_no_heading(&self) -> impl Iterator<Item = &Arg<'help>>3110     pub(crate) fn get_non_positionals_with_no_heading(&self) -> impl Iterator<Item = &Arg<'help>> {
3111         self.get_non_positionals()
3112             .filter(|a| a.get_help_heading().is_none())
3113     }
3114 
find(&self, arg_id: &Id) -> Option<&Arg<'help>>3115     pub(crate) fn find(&self, arg_id: &Id) -> Option<&Arg<'help>> {
3116         self.args.args().find(|a| a.id == *arg_id)
3117     }
3118 
3119     #[inline]
contains_short(&self, s: char) -> bool3120     pub(crate) fn contains_short(&self, s: char) -> bool {
3121         assert!(
3122             self.is_set(AppSettings::Built),
3123             "If App::_build hasn't been called, manually search through Arg shorts"
3124         );
3125 
3126         self.args.contains(s)
3127     }
3128 
3129     #[inline]
set(&mut self, s: AppSettings)3130     pub(crate) fn set(&mut self, s: AppSettings) {
3131         self.settings.set(s)
3132     }
3133 
3134     #[inline]
has_args(&self) -> bool3135     pub(crate) fn has_args(&self) -> bool {
3136         !self.args.is_empty()
3137     }
3138 
has_positionals(&self) -> bool3139     pub(crate) fn has_positionals(&self) -> bool {
3140         self.args.keys().any(|x| x.is_position())
3141     }
3142 
has_visible_subcommands(&self) -> bool3143     pub(crate) fn has_visible_subcommands(&self) -> bool {
3144         self.subcommands
3145             .iter()
3146             .any(|sc| sc.name != "help" && !sc.is_set(AppSettings::Hidden))
3147     }
3148 
3149     /// Check if this subcommand can be referred to as `name`. In other words,
3150     /// check if `name` is the name of this subcommand or is one of its aliases.
3151     #[inline]
aliases_to<T>(&self, name: &T) -> bool where T: PartialEq<str> + ?Sized,3152     pub(crate) fn aliases_to<T>(&self, name: &T) -> bool
3153     where
3154         T: PartialEq<str> + ?Sized,
3155     {
3156         *name == *self.get_name() || self.get_all_aliases().any(|alias| *name == *alias)
3157     }
3158 
3159     /// Check if this subcommand can be referred to as `name`. In other words,
3160     /// check if `name` is the name of this short flag subcommand or is one of its short flag aliases.
3161     #[inline]
short_flag_aliases_to(&self, flag: char) -> bool3162     pub(crate) fn short_flag_aliases_to(&self, flag: char) -> bool {
3163         Some(flag) == self.short_flag
3164             || self.get_all_short_flag_aliases().any(|alias| flag == alias)
3165     }
3166 
3167     /// Check if this subcommand can be referred to as `name`. In other words,
3168     /// check if `name` is the name of this long flag subcommand or is one of its long flag aliases.
3169     #[inline]
long_flag_aliases_to<T>(&self, flag: &T) -> bool where T: PartialEq<str> + ?Sized,3170     pub(crate) fn long_flag_aliases_to<T>(&self, flag: &T) -> bool
3171     where
3172         T: PartialEq<str> + ?Sized,
3173     {
3174         match self.long_flag {
3175             Some(long_flag) => {
3176                 flag == long_flag || self.get_all_long_flag_aliases().any(|alias| flag == alias)
3177             }
3178             None => self.get_all_long_flag_aliases().any(|alias| flag == alias),
3179         }
3180     }
3181 
3182     #[cfg(debug_assertions)]
id_exists(&self, id: &Id) -> bool3183     pub(crate) fn id_exists(&self, id: &Id) -> bool {
3184         self.args.args().any(|x| x.id == *id) || self.groups.iter().any(|x| x.id == *id)
3185     }
3186 
3187     /// Iterate through the groups this arg is member of.
groups_for_arg<'a>(&'a self, arg: &Id) -> impl Iterator<Item = Id> + 'a3188     pub(crate) fn groups_for_arg<'a>(&'a self, arg: &Id) -> impl Iterator<Item = Id> + 'a {
3189         debug!("App::groups_for_arg: id={:?}", arg);
3190         let arg = arg.clone();
3191         self.groups
3192             .iter()
3193             .filter(move |grp| grp.args.iter().any(|a| a == &arg))
3194             .map(|grp| grp.id.clone())
3195     }
3196 
find_group(&self, group_id: &Id) -> Option<&ArgGroup<'help>>3197     pub(crate) fn find_group(&self, group_id: &Id) -> Option<&ArgGroup<'help>> {
3198         self.groups.iter().find(|g| g.id == *group_id)
3199     }
3200 
3201     /// Iterate through all the names of all subcommands (not recursively), including aliases.
3202     /// Used for suggestions.
all_subcommand_names(&self) -> impl Iterator<Item = &str> + Captures<'help>3203     pub(crate) fn all_subcommand_names(&self) -> impl Iterator<Item = &str> + Captures<'help> {
3204         self.get_subcommands().flat_map(|sc| {
3205             let name = sc.get_name();
3206             let aliases = sc.get_all_aliases();
3207             std::iter::once(name).chain(aliases)
3208         })
3209     }
3210 
unroll_args_in_group(&self, group: &Id) -> Vec<Id>3211     pub(crate) fn unroll_args_in_group(&self, group: &Id) -> Vec<Id> {
3212         debug!("App::unroll_args_in_group: group={:?}", group);
3213         let mut g_vec = vec![group];
3214         let mut args = vec![];
3215 
3216         while let Some(g) = g_vec.pop() {
3217             for n in self
3218                 .groups
3219                 .iter()
3220                 .find(|grp| grp.id == *g)
3221                 .expect(INTERNAL_ERROR_MSG)
3222                 .args
3223                 .iter()
3224             {
3225                 debug!("App::unroll_args_in_group:iter: entity={:?}", n);
3226                 if !args.contains(n) {
3227                     if self.find(n).is_some() {
3228                         debug!("App::unroll_args_in_group:iter: this is an arg");
3229                         args.push(n.clone())
3230                     } else {
3231                         debug!("App::unroll_args_in_group:iter: this is a group");
3232                         g_vec.push(n);
3233                     }
3234                 }
3235             }
3236         }
3237 
3238         args
3239     }
3240 
unroll_requirements_for_arg(&self, arg: &Id, matcher: &ArgMatcher) -> Vec<Id>3241     pub(crate) fn unroll_requirements_for_arg(&self, arg: &Id, matcher: &ArgMatcher) -> Vec<Id> {
3242         let requires_if_or_not = |(val, req_arg): &(Option<&str>, Id)| -> Option<Id> {
3243             if let Some(v) = val {
3244                 if matcher
3245                     .get(arg)
3246                     .map(|ma| ma.contains_val(v))
3247                     .unwrap_or(false)
3248                 {
3249                     Some(req_arg.clone())
3250                 } else {
3251                     None
3252                 }
3253             } else {
3254                 Some(req_arg.clone())
3255             }
3256         };
3257 
3258         let mut processed = vec![];
3259         let mut r_vec = vec![arg];
3260         let mut args = vec![];
3261 
3262         while let Some(a) = r_vec.pop() {
3263             if processed.contains(&a) {
3264                 continue;
3265             }
3266 
3267             processed.push(a);
3268 
3269             if let Some(arg) = self.find(a) {
3270                 for r in arg.requires.iter().filter_map(requires_if_or_not) {
3271                     if let Some(req) = self.find(&r) {
3272                         if !req.requires.is_empty() {
3273                             r_vec.push(&req.id)
3274                         }
3275                     }
3276                     args.push(r);
3277                 }
3278             }
3279         }
3280 
3281         args
3282     }
3283 
3284     /// Find a flag subcommand name by short flag or an alias
find_short_subcmd(&self, c: char) -> Option<&str>3285     pub(crate) fn find_short_subcmd(&self, c: char) -> Option<&str> {
3286         self.get_subcommands()
3287             .find(|sc| sc.short_flag_aliases_to(c))
3288             .map(|sc| sc.get_name())
3289     }
3290 
3291     /// Find a flag subcommand name by long flag or an alias
find_long_subcmd(&self, long: &RawOsStr) -> Option<&str>3292     pub(crate) fn find_long_subcmd(&self, long: &RawOsStr) -> Option<&str> {
3293         self.get_subcommands()
3294             .find(|sc| sc.long_flag_aliases_to(long))
3295             .map(|sc| sc.get_name())
3296     }
3297 
get_display_order(&self) -> usize3298     pub(crate) fn get_display_order(&self) -> usize {
3299         self.disp_ord.unwrap_or(999)
3300     }
3301 }
3302 
3303 impl<'help> Index<&'_ Id> for App<'help> {
3304     type Output = Arg<'help>;
3305 
index(&self, key: &Id) -> &Self::Output3306     fn index(&self, key: &Id) -> &Self::Output {
3307         self.find(key).expect(INTERNAL_ERROR_MSG)
3308     }
3309 }
3310 
3311 impl fmt::Display for App<'_> {
fmt(&self, f: &mut fmt::Formatter) -> fmt::Result3312     fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result {
3313         write!(f, "{}", self.name)
3314     }
3315 }
3316 
two_elements_of<I, T>(mut iter: I) -> Option<(T, T)> where I: Iterator<Item = T>,3317 fn two_elements_of<I, T>(mut iter: I) -> Option<(T, T)>
3318 where
3319     I: Iterator<Item = T>,
3320 {
3321     let first = iter.next();
3322     let second = iter.next();
3323 
3324     match (first, second) {
3325         (Some(first), Some(second)) => Some((first, second)),
3326         _ => None,
3327     }
3328 }
3329