1 // Copyright ⓒ 2015-2016 Kevin B. Knapp and [`clap-rs` contributors](https://github.com/clap-rs/clap/blob/master/CONTRIBUTORS.md).
2 // Licensed under the MIT license
3 // (see LICENSE or <http://opensource.org/licenses/MIT>) All files in the project carrying such
4 // notice may not be copied, modified, or distributed except according to those terms.
5 
6 //! `clap` is a simple-to-use, efficient, and full-featured library for parsing command line
7 //! arguments and subcommands when writing console/terminal applications.
8 //!
9 //! ## About
10 //!
11 //! `clap` is used to parse *and validate* the string of command line arguments provided by the user
12 //! at runtime. You provide the list of valid possibilities, and `clap` handles the rest. This means
13 //! you focus on your *applications* functionality, and less on the parsing and validating of
14 //! arguments.
15 //!
16 //! `clap` also provides the traditional version and help switches (or flags) 'for free' meaning
17 //! automatically with no configuration. It does this by checking list of valid possibilities you
18 //! supplied and adding only the ones you haven't already defined. If you are using subcommands,
19 //! `clap` will also auto-generate a `help` subcommand for you in addition to the traditional flags.
20 //!
21 //! Once `clap` parses the user provided string of arguments, it returns the matches along with any
22 //! applicable values. If the user made an error or typo, `clap` informs them of the mistake and
23 //! exits gracefully (or returns a `Result` type and allows you to perform any clean up prior to
24 //! exit). Because of this, you can make reasonable assumptions in your code about the validity of
25 //! the arguments.
26 //!
27 //!
28 //! ## Quick Example
29 //!
30 //! The following examples show a quick example of some of the very basic functionality of `clap`.
31 //! For more advanced usage, such as requirements, conflicts, groups, multiple values and
32 //! occurrences see the [documentation](https://docs.rs/clap/), [examples/] directory of
33 //! this repository or the [video tutorials].
34 //!
35 //! **NOTE:** All of these examples are functionally the same, but show different styles in which to
36 //! use `clap`
37 //!
38 //! The first example shows a method that allows more advanced configuration options (not shown in
39 //! this small example), or even dynamically generating arguments when desired. The downside is it's
40 //! more verbose.
41 //!
42 //! ```no_run
43 //! // (Full example with detailed comments in examples/01b_quick_example.rs)
44 //! //
45 //! // This example demonstrates clap's full 'builder pattern' style of creating arguments which is
46 //! // more verbose, but allows easier editing, and at times more advanced options, or the possibility
47 //! // to generate arguments dynamically.
48 //! extern crate clap;
49 //! use clap::{Arg, App, SubCommand};
50 //!
51 //! fn main() {
52 //!     let matches = App::new("My Super Program")
53 //!                           .version("1.0")
54 //!                           .author("Kevin K. <kbknapp@gmail.com>")
55 //!                           .about("Does awesome things")
56 //!                           .arg(Arg::with_name("config")
57 //!                                .short("c")
58 //!                                .long("config")
59 //!                                .value_name("FILE")
60 //!                                .help("Sets a custom config file")
61 //!                                .takes_value(true))
62 //!                           .arg(Arg::with_name("INPUT")
63 //!                                .help("Sets the input file to use")
64 //!                                .required(true)
65 //!                                .index(1))
66 //!                           .arg(Arg::with_name("v")
67 //!                                .short("v")
68 //!                                .multiple(true)
69 //!                                .help("Sets the level of verbosity"))
70 //!                           .subcommand(SubCommand::with_name("test")
71 //!                                       .about("controls testing features")
72 //!                                       .version("1.3")
73 //!                                       .author("Someone E. <someone_else@other.com>")
74 //!                                       .arg(Arg::with_name("debug")
75 //!                                           .short("d")
76 //!                                           .help("print debug information verbosely")))
77 //!                           .get_matches();
78 //!
79 //!     // Gets a value for config if supplied by user, or defaults to "default.conf"
80 //!     let config = matches.value_of("config").unwrap_or("default.conf");
81 //!     println!("Value for config: {}", config);
82 //!
83 //!     // Calling .unwrap() is safe here because "INPUT" is required (if "INPUT" wasn't
84 //!     // required we could have used an 'if let' to conditionally get the value)
85 //!     println!("Using input file: {}", matches.value_of("INPUT").unwrap());
86 //!
87 //!     // Vary the output based on how many times the user used the "verbose" flag
88 //!     // (i.e. 'myprog -v -v -v' or 'myprog -vvv' vs 'myprog -v'
89 //!     match matches.occurrences_of("v") {
90 //!         0 => println!("No verbose info"),
91 //!         1 => println!("Some verbose info"),
92 //!         2 => println!("Tons of verbose info"),
93 //!         3 | _ => println!("Don't be crazy"),
94 //!     }
95 //!
96 //!     // You can handle information about subcommands by requesting their matches by name
97 //!     // (as below), requesting just the name used, or both at the same time
98 //!     if let Some(matches) = matches.subcommand_matches("test") {
99 //!         if matches.is_present("debug") {
100 //!             println!("Printing debug info...");
101 //!         } else {
102 //!             println!("Printing normally...");
103 //!         }
104 //!     }
105 //!
106 //!     // more program logic goes here...
107 //! }
108 //! ```
109 //!
110 //! The next example shows a far less verbose method, but sacrifices some of the advanced
111 //! configuration options (not shown in this small example). This method also takes a *very* minor
112 //! runtime penalty.
113 //!
114 //! ```no_run
115 //! // (Full example with detailed comments in examples/01a_quick_example.rs)
116 //! //
117 //! // This example demonstrates clap's "usage strings" method of creating arguments
118 //! // which is less verbose
119 //! extern crate clap;
120 //! use clap::{Arg, App, SubCommand};
121 //!
122 //! fn main() {
123 //!     let matches = App::new("myapp")
124 //!                           .version("1.0")
125 //!                           .author("Kevin K. <kbknapp@gmail.com>")
126 //!                           .about("Does awesome things")
127 //!                           .args_from_usage(
128 //!                               "-c, --config=[FILE] 'Sets a custom config file'
129 //!                               <INPUT>              'Sets the input file to use'
130 //!                               -v...                'Sets the level of verbosity'")
131 //!                           .subcommand(SubCommand::with_name("test")
132 //!                                       .about("controls testing features")
133 //!                                       .version("1.3")
134 //!                                       .author("Someone E. <someone_else@other.com>")
135 //!                                       .arg_from_usage("-d, --debug 'Print debug information'"))
136 //!                           .get_matches();
137 //!
138 //!     // Same as previous example...
139 //! }
140 //! ```
141 //!
142 //! This third method shows how you can use a YAML file to build your CLI and keep your Rust source
143 //! tidy or support multiple localized translations by having different YAML files for each
144 //! localization.
145 //!
146 //! First, create the `cli.yml` file to hold your CLI options, but it could be called anything we
147 //! like:
148 //!
149 //! ```yaml
150 //! name: myapp
151 //! version: "1.0"
152 //! author: Kevin K. <kbknapp@gmail.com>
153 //! about: Does awesome things
154 //! args:
155 //!     - config:
156 //!         short: c
157 //!         long: config
158 //!         value_name: FILE
159 //!         help: Sets a custom config file
160 //!         takes_value: true
161 //!     - INPUT:
162 //!         help: Sets the input file to use
163 //!         required: true
164 //!         index: 1
165 //!     - verbose:
166 //!         short: v
167 //!         multiple: true
168 //!         help: Sets the level of verbosity
169 //! subcommands:
170 //!     - test:
171 //!         about: controls testing features
172 //!         version: "1.3"
173 //!         author: Someone E. <someone_else@other.com>
174 //!         args:
175 //!             - debug:
176 //!                 short: d
177 //!                 help: print debug information
178 //! ```
179 //!
180 //! Since this feature requires additional dependencies that not everyone may want, it is *not*
181 //! compiled in by default and we need to enable a feature flag in Cargo.toml:
182 //!
183 //! Simply change your `clap = "~2.27.0"` to `clap = {version = "~2.27.0", features = ["yaml"]}`.
184 //!
185 //! At last we create our `main.rs` file just like we would have with the previous two examples:
186 //!
187 //! ```ignore
188 //! // (Full example with detailed comments in examples/17_yaml.rs)
189 //! //
190 //! // This example demonstrates clap's building from YAML style of creating arguments which is far
191 //! // more clean, but takes a very small performance hit compared to the other two methods.
192 //! #[macro_use]
193 //! extern crate clap;
194 //! use clap::App;
195 //!
196 //! fn main() {
197 //!     // The YAML file is found relative to the current file, similar to how modules are found
198 //!     let yaml = load_yaml!("cli.yml");
199 //!     let matches = App::from_yaml(yaml).get_matches();
200 //!
201 //!     // Same as previous examples...
202 //! }
203 //! ```
204 //!
205 //! Finally there is a macro version, which is like a hybrid approach offering the speed of the
206 //! builder pattern (the first example), but without all the verbosity.
207 //!
208 //! ```no_run
209 //! #[macro_use]
210 //! extern crate clap;
211 //!
212 //! fn main() {
213 //!     let matches = clap_app!(myapp =>
214 //!         (version: "1.0")
215 //!         (author: "Kevin K. <kbknapp@gmail.com>")
216 //!         (about: "Does awesome things")
217 //!         (@arg CONFIG: -c --config +takes_value "Sets a custom config file")
218 //!         (@arg INPUT: +required "Sets the input file to use")
219 //!         (@arg debug: -d ... "Sets the level of debugging information")
220 //!         (@subcommand test =>
221 //!             (about: "controls testing features")
222 //!             (version: "1.3")
223 //!             (author: "Someone E. <someone_else@other.com>")
224 //!             (@arg verbose: -v --verbose "Print test information verbosely")
225 //!         )
226 //!     ).get_matches();
227 //!
228 //!     // Same as before...
229 //! }
230 //! ```
231 //!
232 //! If you were to compile any of the above programs and run them with the flag `--help` or `-h` (or
233 //! `help` subcommand, since we defined `test` as a subcommand) the following would be output
234 //!
235 //! ```text
236 //! $ myprog --help
237 //! My Super Program 1.0
238 //! Kevin K. <kbknapp@gmail.com>
239 //! Does awesome things
240 //!
241 //! USAGE:
242 //!     MyApp [FLAGS] [OPTIONS] <INPUT> [SUBCOMMAND]
243 //!
244 //! FLAGS:
245 //!     -h, --help       Prints this message
246 //!     -v               Sets the level of verbosity
247 //!     -V, --version    Prints version information
248 //!
249 //! OPTIONS:
250 //!     -c, --config <FILE>    Sets a custom config file
251 //!
252 //! ARGS:
253 //!     INPUT    The input file to use
254 //!
255 //! SUBCOMMANDS:
256 //!     help    Prints this message
257 //!     test    Controls testing features
258 //! ```
259 //!
260 //! **NOTE:** You could also run `myapp test --help` to see similar output and options for the
261 //! `test` subcommand.
262 //!
263 //! ## Try it!
264 //!
265 //! ### Pre-Built Test
266 //!
267 //! To try out the pre-built example, use the following steps:
268 //!
269 //! * Clone the repository `$ git clone https://github.com/clap-rs/clap && cd clap-rs/tests`
270 //! * Compile the example `$ cargo build --release`
271 //! * Run the help info `$ ./target/release/claptests --help`
272 //! * Play with the arguments!
273 //!
274 //! ### BYOB (Build Your Own Binary)
275 //!
276 //! To test out `clap`'s default auto-generated help/version follow these steps:
277 //!
278 //! * Create a new cargo project `$ cargo new fake --bin && cd fake`
279 //! * Add `clap` to your `Cargo.toml`
280 //!
281 //! ```toml
282 //! [dependencies]
283 //! clap = "2"
284 //! ```
285 //!
286 //! * Add the following to your `src/main.rs`
287 //!
288 //! ```no_run
289 //! extern crate clap;
290 //! use clap::App;
291 //!
292 //! fn main() {
293 //!   App::new("fake").version("v1.0-beta").get_matches();
294 //! }
295 //! ```
296 //!
297 //! * Build your program `$ cargo build --release`
298 //! * Run with help or version `$ ./target/release/fake --help` or `$ ./target/release/fake
299 //! --version`
300 //!
301 //! ## Usage
302 //!
303 //! For full usage, add `clap` as a dependency in your `Cargo.toml` (it is **highly** recommended to
304 //! use the `~major.minor.patch` style versions in your `Cargo.toml`, for more information see
305 //! [Compatibility Policy](#compatibility-policy)) to use from crates.io:
306 //!
307 //! ```toml
308 //! [dependencies]
309 //! clap = "~2.27.0"
310 //! ```
311 //!
312 //! Or get the latest changes from the master branch at github:
313 //!
314 //! ```toml
315 //! [dependencies.clap]
316 //! git = "https://github.com/clap-rs/clap.git"
317 //! ```
318 //!
319 //! Add `extern crate clap;` to your crate root.
320 //!
321 //! Define a list of valid arguments for your program (see the
322 //! [documentation](https://docs.rs/clap/) or [examples/] directory of this repo)
323 //!
324 //! Then run `cargo build` or `cargo update && cargo build` for your project.
325 //!
326 //! ### Optional Dependencies / Features
327 //!
328 //! #### Features enabled by default
329 //!
330 //! * `suggestions`: Turns on the `Did you mean '--myoption'?` feature for when users make typos. (builds dependency `strsim`)
331 //! * `color`: Turns on colored error messages. This feature only works on non-Windows OSs. (builds dependency `ansi-term` and `atty`)
332 //! * `wrap_help`: Wraps the help at the actual terminal width when
333 //!  available, instead of 120 characters. (builds dependency `textwrap`
334 //! with feature `term_size`)
335 //!
336 //! To disable these, add this to your `Cargo.toml`:
337 //!
338 //! ```toml
339 //! [dependencies.clap]
340 //! version = "~2.27.0"
341 //! default-features = false
342 //! ```
343 //!
344 //! You can also selectively enable only the features you'd like to include, by adding:
345 //!
346 //! ```toml
347 //! [dependencies.clap]
348 //! version = "~2.27.0"
349 //! default-features = false
350 //!
351 //! # Cherry-pick the features you'd like to use
352 //! features = [ "suggestions", "color" ]
353 //! ```
354 //!
355 //! #### Opt-in features
356 //!
357 //! * **"yaml"**: Enables building CLIs from YAML documents. (builds dependency `yaml-rust`)
358 //! * **"unstable"**: Enables unstable `clap` features that may change from release to release
359 //!
360 //! ### Dependencies Tree
361 //!
362 //! The following graphic depicts `clap`s dependency graph (generated using
363 //! [cargo-graph](https://github.com/kbknapp/cargo-graph)).
364 //!
365 //!  * **Dashed** Line: Optional dependency
366 //!  * **Red** Color: **NOT** included by default (must use cargo `features` to enable)
367 //!  * **Blue** Color: Dev dependency, only used while developing.
368 //!
369 //! ![clap dependencies](https://raw.githubusercontent.com/clap-rs/clap/master/clap_dep_graph.png)
370 //!
371 //! ### More Information
372 //!
373 //! You can find complete documentation on the [docs.rs](https://docs.rs/clap/) for this project.
374 //!
375 //! You can also find usage examples in the [examples/] directory of this repo.
376 //!
377 //! #### Video Tutorials
378 //!
379 //! There's also the video tutorial series [Argument Parsing with Rust v2][video tutorials].
380 //!
381 //! These videos slowly trickle out as I finish them and currently a work in progress.
382 //!
383 //! ## How to Contribute
384 //!
385 //! Contributions are always welcome! And there is a multitude of ways in which you can help
386 //! depending on what you like to do, or are good at. Anything from documentation, code cleanup,
387 //! issue completion, new features, you name it, even filing issues is contributing and greatly
388 //! appreciated!
389 //!
390 //! Another really great way to help is if you find an interesting, or helpful way in which to use
391 //! `clap`. You can either add it to the [examples/] directory, or file an issue and tell
392 //! me. I'm all about giving credit where credit is due :)
393 //!
394 //! Please read [CONTRIBUTING.md](https://raw.githubusercontent.com/clap-rs/clap/master/.github/CONTRIBUTING.md) before you start contributing.
395 //!
396 //!
397 //! ### Testing Code
398 //!
399 //! To test with all features both enabled and disabled, you can run theese commands:
400 //!
401 //! ```text
402 //! $ cargo test --no-default-features
403 //! $ cargo test --features "yaml unstable"
404 //! ```
405 //!
406 //! Alternatively, if you have [`just`](https://github.com/casey/just) installed you can run the
407 //! prebuilt recipes. *Not* using `just` is perfectly fine as well, it simply bundles commands
408 //! automatically.
409 //!
410 //! For example, to test the code, as above simply run:
411 //!
412 //! ```text
413 //! $ just run-tests
414 //! ```
415 //!
416 //! From here on, I will list the appropriate `cargo` command as well as the `just` command.
417 //!
418 //! Sometimes it's helpful to only run a subset of the tests, which can be done via:
419 //!
420 //! ```text
421 //! $ cargo test --test <test_name>
422 //!
423 //! # Or
424 //!
425 //! $ just run-test <test_name>
426 //! ```
427 //!
428 //! ### Linting Code
429 //!
430 //! During the CI process `clap` runs against many different lints using
431 //! [`clippy`](https://github.com/Manishearth/rust-clippy). In order to check if these lints pass on
432 //! your own computer prior to submitting a PR you'll need a nightly compiler.
433 //!
434 //! In order to check the code for lints run either:
435 //!
436 //! ```text
437 //! $ rustup override add nightly
438 //! $ cargo build --features lints
439 //! $ rustup override remove
440 //!
441 //! # Or
442 //!
443 //! $ just lint
444 //! ```
445 //!
446 //! ### Debugging Code
447 //!
448 //! Another helpful technique is to see the `clap` debug output while developing features. In order
449 //! to see the debug output while running the full test suite or individual tests, run:
450 //!
451 //! ```text
452 //! $ cargo test --features debug
453 //!
454 //! # Or for individual tests
455 //! $ cargo test --test <test_name> --features debug
456 //!
457 //! # The corresponding just command for individual debugging tests is:
458 //! $ just debug <test_name>
459 //! ```
460 //!
461 //! ### Goals
462 //!
463 //! There are a few goals of `clap` that I'd like to maintain throughout contributions. If your
464 //! proposed changes break, or go against any of these goals we'll discuss the changes further
465 //! before merging (but will *not* be ignored, all contributes are welcome!). These are by no means
466 //! hard-and-fast rules, as I'm no expert and break them myself from time to time (even if by
467 //! mistake or ignorance).
468 //!
469 //! * Remain backwards compatible when possible
470 //!   - If backwards compatibility *must* be broken, use deprecation warnings if at all possible before
471 //!   removing legacy code - This does not apply for security concerns
472 //! * Parse arguments quickly
473 //!   - Parsing of arguments shouldn't slow down usage of the main program - This is also true of
474 //!   generating help and usage information (although *slightly* less stringent, as the program is about
475 //!   to exit)
476 //! * Try to be cognizant of memory usage
477 //!   - Once parsing is complete, the memory footprint of `clap` should be low since the  main program
478 //!   is the star of the show
479 //! * `panic!` on *developer* error, exit gracefully on *end-user* error
480 //!
481 //! ### Compatibility Policy
482 //!
483 //! Because `clap` takes `SemVer` and compatibility seriously, this is the official policy regarding
484 //! breaking changes and previous versions of Rust.
485 //!
486 //! `clap` will pin the minimum required version of Rust to the CI builds. Bumping the minimum
487 //! version of Rust is considered a minor breaking change, meaning *at a minimum* the minor version
488 //! of `clap` will be bumped.
489 //!
490 //! In order to keep from being surprised by breaking changes, it is **highly** recommended to use
491 //! the `~major.minor.patch` style in your `Cargo.toml`:
492 //!
493 //! ```toml
494 //! [dependencies] clap = "~2.27.0"
495 //! ```
496 //!
497 //! This will cause *only* the patch version to be updated upon a `cargo update` call, and therefore
498 //! cannot break due to new features, or bumped minimum versions of Rust.
499 //!
500 //! #### Minimum Version of Rust
501 //!
502 //! `clap` will officially support current stable Rust, minus two releases, but may work with prior
503 //! releases as well. For example, current stable Rust at the time of this writing is 1.21.0,
504 //! meaning `clap` is guaranteed to compile with 1.19.0 and beyond. At the 1.22.0 release, `clap`
505 //! will be guaranteed to compile with 1.20.0 and beyond, etc.
506 //!
507 //! Upon bumping the minimum version of Rust (assuming it's within the stable-2 range), it *must* be
508 //! clearly annotated in the `CHANGELOG.md`
509 //!
510 //! ## License
511 //!
512 //! `clap` is licensed under the MIT license. Please read the [LICENSE-MIT][license] file in
513 //! this repository for more information.
514 //!
515 //! [examples/]: https://github.com/clap-rs/clap/tree/master/examples
516 //! [video tutorials]: https://www.youtube.com/playlist?list=PLza5oFLQGTl2Z5T8g1pRkIynR3E0_pc7U
517 //! [license]: https://raw.githubusercontent.com/clap-rs/clap/master/LICENSE-MIT
518 
519 #![crate_type = "lib"]
520 #![doc(html_root_url = "https://docs.rs/clap/2.33.0")]
521 #![deny(missing_docs, missing_debug_implementations, missing_copy_implementations, trivial_casts,
522         unused_import_braces, unused_allocation)]
523 // Lints we'd like to deny but are currently failing for upstream crates
524 //      unused_qualifications       (bitflags, clippy)
525 //      trivial_numeric_casts       (bitflags)
526 #![cfg_attr(not(any(feature = "lints", feature = "nightly")), forbid(unstable_features))]
527 #![cfg_attr(feature = "lints", feature(plugin))]
528 #![cfg_attr(feature = "lints", plugin(clippy))]
529 // Need to disable deny(warnings) while deprecations are active
530 // #![cfg_attr(feature = "lints", deny(warnings))]
531 #![cfg_attr(feature = "lints", allow(cyclomatic_complexity))]
532 #![cfg_attr(feature = "lints", allow(doc_markdown))]
533 #![cfg_attr(feature = "lints", allow(explicit_iter_loop))]
534 
535 #[cfg(all(feature = "color", not(target_os = "windows")))]
536 extern crate ansi_term;
537 #[cfg(feature = "color")]
538 extern crate atty;
539 #[macro_use]
540 extern crate bitflags;
541 #[cfg(feature = "suggestions")]
542 extern crate strsim;
543 #[cfg(feature = "wrap_help")]
544 extern crate term_size;
545 extern crate textwrap;
546 extern crate unicode_width;
547 #[cfg(feature = "vec_map")]
548 extern crate vec_map;
549 #[cfg(feature = "yaml")]
550 extern crate yaml_rust;
551 
552 #[cfg(feature = "yaml")]
553 pub use yaml_rust::YamlLoader;
554 pub use args::{Arg, ArgGroup, ArgMatches, ArgSettings, OsValues, SubCommand, Values};
555 pub use app::{App, AppSettings};
556 pub use fmt::Format;
557 pub use errors::{Error, ErrorKind, Result};
558 pub use completions::Shell;
559 
560 #[macro_use]
561 mod macros;
562 mod app;
563 mod args;
564 mod usage_parser;
565 mod fmt;
566 mod suggestions;
567 mod errors;
568 mod osstringext;
569 mod strext;
570 mod completions;
571 mod map;
572 
573 const INTERNAL_ERROR_MSG: &'static str = "Fatal internal error. Please consider filing a bug \
574                                           report at https://github.com/clap-rs/clap/issues";
575 const INVALID_UTF8: &'static str = "unexpected invalid UTF-8 code point";
576 
577 #[cfg(unstable)]
578 pub use derive::{ArgEnum, ClapApp, FromArgMatches, IntoApp};
579 
580 #[cfg(unstable)]
581 mod derive {
582     /// @TODO @release @docs
583     pub trait ClapApp: IntoApp + FromArgMatches + Sized {
584         /// @TODO @release @docs
parse() -> Self585         fn parse() -> Self { Self::from_argmatches(Self::into_app().get_matches()) }
586 
587         /// @TODO @release @docs
parse_from<I, T>(argv: I) -> Self where I: IntoIterator<Item = T>, T: Into<OsString> + Clone,588         fn parse_from<I, T>(argv: I) -> Self
589         where
590             I: IntoIterator<Item = T>,
591             T: Into<OsString> + Clone,
592         {
593             Self::from_argmatches(Self::into_app().get_matches_from(argv))
594         }
595 
596         /// @TODO @release @docs
try_parse() -> Result<Self, clap::Error>597         fn try_parse() -> Result<Self, clap::Error> {
598             Self::try_from_argmatches(Self::into_app().get_matches_safe()?)
599         }
600 
601 
602         /// @TODO @release @docs
try_parse_from<I, T>(argv: I) -> Result<Self, clap::Error> where I: IntoIterator<Item = T>, T: Into<OsString> + Clone,603         fn try_parse_from<I, T>(argv: I) -> Result<Self, clap::Error>
604         where
605             I: IntoIterator<Item = T>,
606             T: Into<OsString> + Clone,
607         {
608             Self::try_from_argmatches(Self::into_app().get_matches_from_safe(argv)?)
609         }
610     }
611 
612     /// @TODO @release @docs
613     pub trait IntoApp {
614         /// @TODO @release @docs
into_app<'a, 'b>() -> clap::App<'a, 'b>615         fn into_app<'a, 'b>() -> clap::App<'a, 'b>;
616     }
617 
618     /// @TODO @release @docs
619     pub trait FromArgMatches: Sized {
620         /// @TODO @release @docs
from_argmatches<'a>(matches: clap::ArgMatches<'a>) -> Self621         fn from_argmatches<'a>(matches: clap::ArgMatches<'a>) -> Self;
622 
623         /// @TODO @release @docs
try_from_argmatches<'a>(matches: clap::ArgMatches<'a>) -> Result<Self, clap::Error>624         fn try_from_argmatches<'a>(matches: clap::ArgMatches<'a>) -> Result<Self, clap::Error>;
625     }
626 
627     /// @TODO @release @docs
628     pub trait ArgEnum {}
629 }
630