]> git.proxmox.com Git - rustc.git/blame - vendor/clap/src/macros.rs
New upstream version 1.63.0+dfsg1
[rustc.git] / vendor / clap / src / macros.rs
CommitLineData
04454e1e
FG
1/// Deprecated in [Issue #3087](https://github.com/clap-rs/clap/issues/3087), maybe [`clap::Parser`][crate::Parser] would fit your use case?
2#[cfg(feature = "yaml")]
923072b8
FG
3#[cfg_attr(
4 feature = "deprecated",
5 deprecated(
6 since = "3.0.0",
7 note = "Deprecated in Issue #3087, maybe clap::Parser would fit your use case?"
8 )
04454e1e
FG
9)]
10#[doc(hidden)]
11#[macro_export]
12macro_rules! load_yaml {
13 ($yaml:expr) => {
14 &$crate::YamlLoader::load_from_str(include_str!($yaml)).expect("failed to load YAML file")
15 [0]
16 };
17}
18
19/// Deprecated, replaced with [`ArgMatches::value_of_t`][crate::ArgMatches::value_of_t]
20#[macro_export]
923072b8
FG
21#[cfg_attr(
22 feature = "deprecated",
23 deprecated(since = "3.0.0", note = "Replaced with `ArgMatches::value_of_t`")
24)]
04454e1e
FG
25#[doc(hidden)]
26macro_rules! value_t {
27 ($m:ident, $v:expr, $t:ty) => {
28 $crate::value_t!($m.value_of($v), $t)
29 };
30 ($m:ident.value_of($v:expr), $t:ty) => {
31 $m.value_of_t::<$t>($v)
32 };
33}
34
35/// Deprecated, replaced with [`ArgMatches::value_of_t_or_exit`][crate::ArgMatches::value_of_t_or_exit]
36#[macro_export]
923072b8
FG
37#[cfg_attr(
38 feature = "deprecated",
39 deprecated(
40 since = "3.0.0",
41 note = "Replaced with `ArgMatches::value_of_t_or_exit`"
42 )
04454e1e
FG
43)]
44#[doc(hidden)]
45macro_rules! value_t_or_exit {
46 ($m:ident, $v:expr, $t:ty) => {
47 value_t_or_exit!($m.value_of($v), $t)
48 };
49 ($m:ident.value_of($v:expr), $t:ty) => {
50 $m.value_of_t_or_exit::<$t>($v)
51 };
52}
53
54/// Deprecated, replaced with [`ArgMatches::values_of_t`][crate::ArgMatches::value_of_t]
55#[macro_export]
923072b8
FG
56#[cfg_attr(
57 feature = "deprecated",
58 deprecated(since = "3.0.0", note = "Replaced with `ArgMatches::values_of_t`")
59)]
04454e1e
FG
60#[doc(hidden)]
61macro_rules! values_t {
62 ($m:ident, $v:expr, $t:ty) => {
63 values_t!($m.values_of($v), $t)
64 };
65 ($m:ident.values_of($v:expr), $t:ty) => {
66 $m.values_of_t::<$t>($v)
67 };
68}
69
70/// Deprecated, replaced with [`ArgMatches::values_of_t_or_exit`][crate::ArgMatches::value_of_t_or_exit]
71#[macro_export]
923072b8
FG
72#[cfg_attr(
73 feature = "deprecated",
74 deprecated(
75 since = "3.0.0",
76 note = "Replaced with `ArgMatches::values_of_t_or_exit`"
77 )
04454e1e
FG
78)]
79#[doc(hidden)]
80macro_rules! values_t_or_exit {
81 ($m:ident, $v:expr, $t:ty) => {
82 values_t_or_exit!($m.values_of($v), $t)
83 };
84 ($m:ident.values_of($v:expr), $t:ty) => {
85 $m.values_of_t_or_exit::<$t>($v)
86 };
87}
88
923072b8
FG
89#[cfg_attr(
90 feature = "deprecated",
91 deprecated(since = "3.0.0", note = "Replaced with `ArgEnum`")
92)]
93#[doc(hidden)]
94#[macro_export]
95macro_rules! _clap_count_exprs {
96 () => { 0 };
97 ($e:expr) => { 1 };
98 ($e:expr, $($es:expr),+) => { 1 + $crate::_clap_count_exprs!($($es),*) };
99}
100
04454e1e 101/// Deprecated, replaced with [`ArgEnum`][crate::ArgEnum]
923072b8
FG
102#[cfg_attr(
103 feature = "deprecated",
104 deprecated(since = "3.0.0", note = "Replaced with `ArgEnum`")
105)]
04454e1e
FG
106#[doc(hidden)]
107#[macro_export]
108macro_rules! arg_enum {
109 (@as_item $($i:item)*) => ($($i)*);
110 (@impls ( $($tts:tt)* ) -> ($e:ident, $($v:ident),+)) => {
111 $crate::arg_enum!(@as_item
112 $($tts)*
113
114 impl ::std::str::FromStr for $e {
115 type Err = String;
116
117 fn from_str(s: &str) -> ::std::result::Result<Self,Self::Err> {
118 #[allow(deprecated, unused_imports)]
119 use ::std::ascii::AsciiExt;
120 match s {
121 $(stringify!($v) |
122 _ if s.eq_ignore_ascii_case(stringify!($v)) => Ok($e::$v)),+,
123 _ => Err({
124 let v = vec![
125 $(stringify!($v),)+
126 ];
127 format!("valid values: {}",
128 v.join(", "))
129 }),
130 }
131 }
132 }
133 impl ::std::fmt::Display for $e {
134 fn fmt(&self, f: &mut ::std::fmt::Formatter) -> ::std::fmt::Result {
135 match *self {
136 $($e::$v => write!(f, stringify!($v)),)+
137 }
138 }
139 }
140 impl $e {
141 #[allow(dead_code)]
142 pub fn variants() -> [&'static str; $crate::_clap_count_exprs!($(stringify!($v)),+)] {
143 [
144 $(stringify!($v),)+
145 ]
146 }
147 });
148 };
149 ($(#[$($m:meta),+])+ pub enum $e:ident { $($v:ident $(=$val:expr)*,)+ } ) => {
150 $crate::arg_enum!(@impls
151 ($(#[$($m),+])+
152 pub enum $e {
153 $($v$(=$val)*),+
154 }) -> ($e, $($v),+)
155 );
156 };
157 ($(#[$($m:meta),+])+ pub enum $e:ident { $($v:ident $(=$val:expr)*),+ } ) => {
158 $crate::arg_enum!(@impls
159 ($(#[$($m),+])+
160 pub enum $e {
161 $($v$(=$val)*),+
162 }) -> ($e, $($v),+)
163 );
164 };
165 ($(#[$($m:meta),+])+ enum $e:ident { $($v:ident $(=$val:expr)*,)+ } ) => {
166 $crate::arg_enum!(@impls
167 ($(#[$($m),+])+
168 enum $e {
169 $($v$(=$val)*),+
170 }) -> ($e, $($v),+)
171 );
172 };
173 ($(#[$($m:meta),+])+ enum $e:ident { $($v:ident $(=$val:expr)*),+ } ) => {
174 $crate::arg_enum!(@impls
175 ($(#[$($m),+])+
176 enum $e {
177 $($v$(=$val)*),+
178 }) -> ($e, $($v),+)
179 );
180 };
181 (pub enum $e:ident { $($v:ident $(=$val:expr)*,)+ } ) => {
182 $crate::arg_enum!(@impls
183 (pub enum $e {
184 $($v$(=$val)*),+
185 }) -> ($e, $($v),+)
186 );
187 };
188 (pub enum $e:ident { $($v:ident $(=$val:expr)*),+ } ) => {
189 $crate::arg_enum!(@impls
190 (pub enum $e {
191 $($v$(=$val)*),+
192 }) -> ($e, $($v),+)
193 );
194 };
195 (enum $e:ident { $($v:ident $(=$val:expr)*,)+ } ) => {
196 $crate::arg_enum!(@impls
197 (enum $e {
198 $($v$(=$val)*),+
199 }) -> ($e, $($v),+)
200 );
201 };
202 (enum $e:ident { $($v:ident $(=$val:expr)*),+ } ) => {
203 $crate::arg_enum!(@impls
204 (enum $e {
205 $($v$(=$val)*),+
206 }) -> ($e, $($v),+)
207 );
208 };
209}
210
211/// Allows you to pull the version from your Cargo.toml at compile time as
212/// `MAJOR.MINOR.PATCH_PKGVERSION_PRE`
213///
214/// # Examples
215///
216/// ```no_run
217/// # #[macro_use]
218/// # extern crate clap;
219/// # use clap::Command;
220/// # fn main() {
221/// let m = Command::new("cmd")
222/// .version(crate_version!())
223/// .get_matches();
224/// # }
225/// ```
226#[cfg(feature = "cargo")]
227#[macro_export]
228macro_rules! crate_version {
229 () => {
230 env!("CARGO_PKG_VERSION")
231 };
232}
233
234/// Allows you to pull the authors for the command from your Cargo.toml at
235/// compile time in the form:
236/// `"author1 lastname <author1@example.com>:author2 lastname <author2@example.com>"`
237///
238/// You can replace the colons with a custom separator by supplying a
239/// replacement string, so, for example,
240/// `crate_authors!(",\n")` would become
241/// `"author1 lastname <author1@example.com>,\nauthor2 lastname <author2@example.com>,\nauthor3 lastname <author3@example.com>"`
242///
243/// # Examples
244///
245/// ```no_run
246/// # #[macro_use]
247/// # extern crate clap;
248/// # use clap::Command;
249/// # fn main() {
250/// let m = Command::new("cmd")
251/// .author(crate_authors!("\n"))
252/// .get_matches();
253/// # }
254/// ```
255#[cfg(feature = "cargo")]
256#[macro_export]
257macro_rules! crate_authors {
258 ($sep:expr) => {{
923072b8
FG
259 static CACHED: clap::once_cell::sync::Lazy<String> =
260 clap::once_cell::sync::Lazy::new(|| env!("CARGO_PKG_AUTHORS").replace(':', $sep));
04454e1e
FG
261
262 let s: &'static str = &*CACHED;
263 s
264 }};
265 () => {
266 env!("CARGO_PKG_AUTHORS")
267 };
268}
269
270/// Allows you to pull the description from your Cargo.toml at compile time.
271///
272/// # Examples
273///
274/// ```no_run
275/// # #[macro_use]
276/// # extern crate clap;
277/// # use clap::Command;
278/// # fn main() {
279/// let m = Command::new("cmd")
280/// .about(crate_description!())
281/// .get_matches();
282/// # }
283/// ```
284#[cfg(feature = "cargo")]
285#[macro_export]
286macro_rules! crate_description {
287 () => {
288 env!("CARGO_PKG_DESCRIPTION")
289 };
290}
291
292/// Allows you to pull the name from your Cargo.toml at compile time.
293///
294/// # Examples
295///
296/// ```no_run
297/// # #[macro_use]
298/// # extern crate clap;
299/// # use clap::Command;
300/// # fn main() {
301/// let m = Command::new(crate_name!())
302/// .get_matches();
303/// # }
304/// ```
305#[cfg(feature = "cargo")]
306#[macro_export]
307macro_rules! crate_name {
308 () => {
309 env!("CARGO_PKG_NAME")
310 };
311}
312
313/// Allows you to build the `Command` instance from your Cargo.toml at compile time.
314///
315/// **NOTE:** Changing the values in your `Cargo.toml` does not trigger a re-build automatically,
316/// and therefore won't change the generated output until you recompile.
317///
318/// In some cases you can "trick" the compiler into triggering a rebuild when your
319/// `Cargo.toml` is changed by including this in your `src/main.rs` file
320/// `include_str!("../Cargo.toml");`
321///
322/// # Examples
323///
324/// ```no_run
325/// # #[macro_use]
326/// # extern crate clap;
327/// # fn main() {
328/// let m = command!().get_matches();
329/// # }
330/// ```
331#[cfg(feature = "cargo")]
332#[macro_export]
333macro_rules! command {
334 () => {{
335 $crate::command!($crate::crate_name!())
336 }};
337 ($name:expr) => {{
338 let mut cmd = $crate::Command::new($name).version($crate::crate_version!());
339
340 let author = $crate::crate_authors!();
341 if !author.is_empty() {
342 cmd = cmd.author(author)
343 }
344
345 let about = $crate::crate_description!();
346 if !about.is_empty() {
347 cmd = cmd.about(about)
348 }
349
350 cmd
351 }};
352}
353
923072b8
FG
354/// Requires `cargo` feature flag to be enabled.
355#[cfg(not(feature = "cargo"))]
356#[macro_export]
357macro_rules! command {
358 () => {{
359 compile_error!("`cargo` feature flag is required");
360 }};
361 ($name:expr) => {{
362 compile_error!("`cargo` feature flag is required");
363 }};
364}
365
04454e1e
FG
366/// Deprecated, replaced with [`clap::command!`][crate::command]
367#[cfg(feature = "cargo")]
923072b8
FG
368#[cfg_attr(
369 feature = "deprecated",
370 deprecated(since = "3.1.0", note = "Replaced with `clap::command!")
371)]
04454e1e
FG
372#[macro_export]
373macro_rules! app_from_crate {
374 () => {{
375 let mut cmd = $crate::Command::new($crate::crate_name!()).version($crate::crate_version!());
376
377 let author = $crate::crate_authors!(", ");
378 if !author.is_empty() {
379 cmd = cmd.author(author)
380 }
381
382 let about = $crate::crate_description!();
383 if !about.is_empty() {
384 cmd = cmd.about(about)
385 }
386
387 cmd
388 }};
389 ($sep:expr) => {{
390 let mut cmd = $crate::Command::new($crate::crate_name!()).version($crate::crate_version!());
391
392 let author = $crate::crate_authors!($sep);
393 if !author.is_empty() {
394 cmd = cmd.author(author)
395 }
396
397 let about = $crate::crate_description!();
398 if !about.is_empty() {
399 cmd = cmd.about(about)
400 }
401
402 cmd
403 }};
404}
405
406#[doc(hidden)]
407#[macro_export]
408macro_rules! arg_impl {
409 ( @string $val:ident ) => {
410 stringify!($val)
411 };
412 ( @string $val:literal ) => {{
413 let ident_or_string_literal: &str = $val;
414 ident_or_string_literal
415 }};
416 ( @string $val:tt ) => {
417 ::std::compile_error!("Only identifiers or string literals supported");
418 };
419 ( @string ) => {
420 None
421 };
422
423 ( @char $val:ident ) => {{
424 let ident_or_char_literal = stringify!($val);
425 debug_assert_eq!(
426 ident_or_char_literal.len(),
427 1,
428 "Single-letter identifier expected, got {}",
429 ident_or_char_literal
430 );
431 ident_or_char_literal.chars().next().unwrap()
432 }};
433 ( @char $val:literal ) => {{
434 let ident_or_char_literal: char = $val;
435 ident_or_char_literal
436 }};
437 ( @char ) => {{
438 None
439 }};
440
441 (
442 @arg
443 ($arg:expr)
444 --$long:ident
445 $($tail:tt)*
446 ) => {
447 $crate::arg_impl! {
448 @arg
449 ({
450 debug_assert_eq!($arg.get_value_names(), None, "Flags should precede values");
923072b8
FG
451 #[allow(deprecated)]
452 {
453 debug_assert!(!$arg.is_multiple_occurrences_set(), "Flags should precede `...`");
454 }
04454e1e
FG
455
456 let mut arg = $arg;
457 let long = $crate::arg_impl! { @string $long };
458 if arg.get_id().is_empty() {
459 arg = arg.id(long);
460 }
461 arg.long(long)
462 })
463 $($tail)*
464 }
465 };
466 (
467 @arg
468 ($arg:expr)
469 --$long:literal
470 $($tail:tt)*
471 ) => {
472 $crate::arg_impl! {
473 @arg
474 ({
475 debug_assert_eq!($arg.get_value_names(), None, "Flags should precede values");
923072b8
FG
476 #[allow(deprecated)]
477 {
478 debug_assert!(!$arg.is_multiple_occurrences_set(), "Flags should precede `...`");
479 }
04454e1e
FG
480
481 let mut arg = $arg;
482 let long = $crate::arg_impl! { @string $long };
483 if arg.get_id().is_empty() {
484 arg = arg.id(long);
485 }
486 arg.long(long)
487 })
488 $($tail)*
489 }
490 };
491 (
492 @arg
493 ($arg:expr)
494 -$short:ident
495 $($tail:tt)*
496 ) => {
497 $crate::arg_impl! {
498 @arg
499 ({
500 debug_assert_eq!($arg.get_long(), None, "Short flags should precede long flags");
501 debug_assert_eq!($arg.get_value_names(), None, "Flags should precede values");
923072b8
FG
502 #[allow(deprecated)]
503 {
504 debug_assert!(!$arg.is_multiple_occurrences_set(), "Flags should precede `...`");
505 }
04454e1e
FG
506
507 $arg.short($crate::arg_impl! { @char $short })
508 })
509 $($tail)*
510 }
511 };
512 (
513 @arg
514 ($arg:expr)
515 -$short:literal
516 $($tail:tt)*
517 ) => {
518 $crate::arg_impl! {
519 @arg
520 ({
521 debug_assert_eq!($arg.get_long(), None, "Short flags should precede long flags");
522 debug_assert_eq!($arg.get_value_names(), None, "Flags should precede values");
923072b8
FG
523 #[allow(deprecated)]
524 {
525 debug_assert!(!$arg.is_multiple_occurrences_set(), "Flags should precede `...`");
526 }
04454e1e
FG
527
528 $arg.short($crate::arg_impl! { @char $short })
529 })
530 $($tail)*
531 }
532 };
533 (
534 @arg
535 ($arg:expr)
536 <$value_name:ident>
537 $($tail:tt)*
538 ) => {
539 $crate::arg_impl! {
540 @arg
541 ({
923072b8
FG
542 #[allow(deprecated)]
543 {
544 debug_assert!(!$arg.is_multiple_occurrences_set(), "Values should precede `...`");
545 }
546 debug_assert_eq!($arg.get_value_names(), None, "Multiple values not yet supported");
547
548 let mut arg = $arg;
549
550 arg = arg.required(true);
551 arg = arg.takes_value(true);
552
553 let value_name = $crate::arg_impl! { @string $value_name };
554 if arg.get_id().is_empty() {
555 arg = arg.id(value_name);
556 }
557 arg.value_name(value_name)
558 })
559 $($tail)*
560 }
561 };
562 (
563 @arg
564 ($arg:expr)
565 <$value_name:literal>
566 $($tail:tt)*
567 ) => {
568 $crate::arg_impl! {
569 @arg
570 ({
571 #[allow(deprecated)]
572 {
573 debug_assert!(!$arg.is_multiple_occurrences_set(), "Values should precede `...`");
574 }
04454e1e
FG
575 debug_assert_eq!($arg.get_value_names(), None, "Multiple values not yet supported");
576
577 let mut arg = $arg;
578
579 arg = arg.required(true);
580 arg = arg.takes_value(true);
581
582 let value_name = $crate::arg_impl! { @string $value_name };
583 if arg.get_id().is_empty() {
584 arg = arg.id(value_name);
585 }
586 arg.value_name(value_name)
587 })
588 $($tail)*
589 }
590 };
591 (
592 @arg
593 ($arg:expr)
594 [$value_name:ident]
595 $($tail:tt)*
596 ) => {
597 $crate::arg_impl! {
598 @arg
599 ({
923072b8
FG
600 #[allow(deprecated)]
601 {
602 debug_assert!(!$arg.is_multiple_occurrences_set(), "Values should precede `...`");
603 }
04454e1e
FG
604 debug_assert_eq!($arg.get_value_names(), None, "Multiple values not yet supported");
605
606 let mut arg = $arg;
607
608 if arg.get_long().is_none() && arg.get_short().is_none() {
609 arg = arg.required(false);
610 } else {
611 arg = arg.min_values(0).max_values(1);
612 }
613 arg = arg.takes_value(true);
614
615 let value_name = $crate::arg_impl! { @string $value_name };
616 if arg.get_id().is_empty() {
617 arg = arg.id(value_name);
618 }
619 arg.value_name(value_name)
620 })
621 $($tail)*
622 }
623 };
624 (
625 @arg
626 ($arg:expr)
923072b8 627 [$value_name:literal]
04454e1e
FG
628 $($tail:tt)*
629 ) => {
630 $crate::arg_impl! {
631 @arg
632 ({
923072b8
FG
633 #[allow(deprecated)]
634 {
635 debug_assert!(!$arg.is_multiple_occurrences_set(), "Values should precede `...`");
636 }
637 debug_assert_eq!($arg.get_value_names(), None, "Multiple values not yet supported");
638
639 let mut arg = $arg;
640
641 if arg.get_long().is_none() && arg.get_short().is_none() {
642 arg = arg.required(false);
643 } else {
644 arg = arg.min_values(0).max_values(1);
645 }
646 arg = arg.takes_value(true);
647
648 let value_name = $crate::arg_impl! { @string $value_name };
649 if arg.get_id().is_empty() {
650 arg = arg.id(value_name);
651 }
652 arg.value_name(value_name)
04454e1e
FG
653 })
654 $($tail)*
655 }
656 };
923072b8
FG
657 (
658 @arg
659 ($arg:expr)
660 ...
661 $($tail:tt)*
662 ) => {
663 $crate::arg_impl! {
664 @arg
665 ({#[allow(deprecated)]{
666 $arg.multiple_occurrences(true)
667 }})
668 $($tail)*
669 }
670 };
04454e1e
FG
671 (
672 @arg
673 ($arg:expr)
674 $help:literal
675 ) => {
676 $arg.help($help)
677 };
678 (
679 @arg
680 ($arg:expr)
681 ) => {
682 $arg
683 };
684}
685
686/// Create an [`Arg`] from a usage string.
687///
688/// Allows creation of basic settings for the [`Arg`].
689///
690/// **NOTE**: Not all settings may be set using the usage string method. Some properties are
691/// only available via the builder pattern.
692///
693/// # Syntax
694///
695/// Usage strings typically following the form:
696///
697/// ```notrust
698/// [explicit name] [short] [long] [value names] [...] [help string]
699/// ```
700///
701/// ### Explicit Name
702///
703/// The name may be either a bare-word or a string, followed by a `:`, like `name:` or
704/// `"name":`.
705///
706/// *Note:* This is an optional field, if it's omitted the argument will use one of the additional
707/// fields as the name using the following priority order:
708///
709/// 1. Explicit Name
710/// 2. Long
711/// 3. Value Name
712///
713/// See [`Arg::name`][crate::Arg::name].
714///
715/// ### Short
716///
717/// A short flag is a `-` followed by either a bare-character or quoted character, like `-f` or
718/// `-'f'`.
719///
720/// See [`Arg::short`][crate::Arg::short].
721///
722/// ### Long
723///
724/// A long flag is a `--` followed by either a bare-word or a string, like `--foo` or
725/// `--"foo"`.
726///
727/// See [`Arg::long`][crate::Arg::long].
728///
729/// ### Values (Value Notation)
730///
731/// This is set by placing bare-word between:
732/// - `[]` like `[FOO]`
733/// - Positional argument: optional
734/// - Named argument: optional value
735/// - `<>` like `<FOO>`: required
736///
737/// See [`Arg::value_name`][crate::Arg::value_name].
738///
739/// ### `...`
740///
741/// `...` (three consecutive dots/periods) specifies that this argument may occur multiple
742/// times (not to be confused with multiple values per occurrence).
743///
744/// See [`Arg::multiple_occurrences`][crate::Arg::multiple_occurrences].
745///
746/// ### Help String
747///
923072b8 748/// The help string is denoted between a pair of double quotes `""` and may contain any
04454e1e
FG
749/// characters.
750///
751/// # Examples
752///
753/// ```rust
754/// # use clap::{Command, Arg, arg};
755/// Command::new("prog")
756/// .args(&[
757/// arg!(--config <FILE> "a required file for the configuration and no short"),
758/// arg!(-d --debug ... "turns on debugging information and allows multiples"),
759/// arg!([input] "an optional input file to use")
760/// ])
761/// # ;
762/// ```
763/// [`Arg`]: ./struct.Arg.html
764#[macro_export]
765macro_rules! arg {
766 ( $name:ident: $($tail:tt)+ ) => {
767 $crate::arg_impl! {
768 @arg ($crate::Arg::new($crate::arg_impl! { @string $name })) $($tail)+
769 }
770 };
771 ( $($tail:tt)+ ) => {{
772 let arg = $crate::arg_impl! {
773 @arg ($crate::Arg::default()) $($tail)+
774 };
775 debug_assert!(!arg.get_id().is_empty(), "Without a value or long flag, the `name:` prefix is required");
776 arg
777 }};
778}
779
780/// Deprecated, replaced with [`clap::Parser`][crate::Parser] and [`clap::arg!`][crate::arg] (Issue clap-rs/clap#2835)
923072b8
FG
781#[cfg_attr(
782 feature = "deprecated",
783 deprecated(
784 since = "3.0.0",
785 note = "Replaced with `clap::Parser` for a declarative API (Issue clap-rs/clap#2835)"
786 )
04454e1e
FG
787)]
788#[doc(hidden)]
789#[macro_export]
790macro_rules! clap_app {
791 (@app ($builder:expr)) => { $builder };
792 (@app ($builder:expr) (@arg ($name:expr): $($tail:tt)*) $($tt:tt)*) => {
793 $crate::clap_app!{ @app
794 ($builder.arg(
795 $crate::clap_app!{ @arg ($crate::Arg::new($name)) (-) $($tail)* }))
796 $($tt)*
797 }
798 };
799 (@app ($builder:expr) (@arg $name:ident: $($tail:tt)*) $($tt:tt)*) => {
800 $crate::clap_app!{ @app
801 ($builder.arg(
802 $crate::clap_app!{ @arg ($crate::Arg::new(stringify!($name))) (-) $($tail)* }))
803 $($tt)*
804 }
805 };
806 (@app ($builder:expr) (@setting $setting:ident) $($tt:tt)*) => {
807 $crate::clap_app!{ @app
808 ($builder.setting($crate::AppSettings::$setting))
809 $($tt)*
810 }
811 };
812// Treat the application builder as an argument to set its attributes
813 (@app ($builder:expr) (@attributes $($attr:tt)*) $($tt:tt)*) => {
814 $crate::clap_app!{ @app ($crate::clap_app!{ @arg ($builder) $($attr)* }) $($tt)* }
815 };
816 (@app ($builder:expr) (@group $name:ident => $($tail:tt)*) $($tt:tt)*) => {
817 $crate::clap_app!{ @app
818 ($crate::clap_app!{ @group ($builder, $crate::ArgGroup::new(stringify!($name))) $($tail)* })
819 $($tt)*
820 }
821 };
822 (@app ($builder:expr) (@group $name:ident !$ident:ident => $($tail:tt)*) $($tt:tt)*) => {
823 $crate::clap_app!{ @app
824 ($crate::clap_app!{ @group ($builder, $crate::ArgGroup::new(stringify!($name)).$ident(false)) $($tail)* })
825 $($tt)*
826 }
827 };
828 (@app ($builder:expr) (@group $name:ident +$ident:ident => $($tail:tt)*) $($tt:tt)*) => {
829 $crate::clap_app!{ @app
830 ($crate::clap_app!{ @group ($builder, $crate::ArgGroup::new(stringify!($name)).$ident(true)) $($tail)* })
831 $($tt)*
832 }
833 };
834// Handle subcommand creation
835 (@app ($builder:expr) (@subcommand $name:ident => $($tail:tt)*) $($tt:tt)*) => {
836 $crate::clap_app!{ @app
837 ($builder.subcommand(
838 $crate::clap_app!{ @app ($crate::Command::new(stringify!($name))) $($tail)* }
839 ))
840 $($tt)*
841 }
842 };
843// Yaml like function calls - used for setting various meta directly against the app
844 (@app ($builder:expr) ($ident:ident: $($v:expr),*) $($tt:tt)*) => {
845// $crate::clap_app!{ @app ($builder.$ident($($v),*)) $($tt)* }
846 $crate::clap_app!{ @app
847 ($builder.$ident($($v),*))
848 $($tt)*
849 }
850 };
851
852// Add members to group and continue argument handling with the parent builder
853 (@group ($builder:expr, $group:expr)) => { $builder.group($group) };
854 // Treat the group builder as an argument to set its attributes
855 (@group ($builder:expr, $group:expr) (@attributes $($attr:tt)*) $($tt:tt)*) => {
856 $crate::clap_app!{ @group ($builder, $crate::clap_app!{ @arg ($group) (-) $($attr)* }) $($tt)* }
857 };
858 (@group ($builder:expr, $group:expr) (@arg $name:ident: $($tail:tt)*) $($tt:tt)*) => {
859 $crate::clap_app!{ @group
860 ($crate::clap_app!{ @app ($builder) (@arg $name: $($tail)*) },
861 $group.arg(stringify!($name)))
862 $($tt)*
863 }
864 };
865
866// No more tokens to munch
867 (@arg ($arg:expr) $modes:tt) => { $arg };
868// Shorthand tokens influenced by the usage_string
869 (@arg ($arg:expr) $modes:tt --($long:expr) $($tail:tt)*) => {
870 $crate::clap_app!{ @arg ($arg.long($long)) $modes $($tail)* }
871 };
872 (@arg ($arg:expr) $modes:tt --$long:ident $($tail:tt)*) => {
873 $crate::clap_app!{ @arg ($arg.long(stringify!($long))) $modes $($tail)* }
874 };
875 (@arg ($arg:expr) $modes:tt -$short:ident $($tail:tt)*) => {
876 $crate::clap_app!{ @arg ($arg.short(stringify!($short).chars().next().unwrap())) $modes $($tail)* }
877 };
878 (@arg ($arg:expr) (-) <$var:ident> $($tail:tt)*) => {
879 $crate::clap_app!{ @arg ($arg.value_name(stringify!($var))) (+) +takes_value +required $($tail)* }
880 };
881 (@arg ($arg:expr) (+) <$var:ident> $($tail:tt)*) => {
882 $crate::clap_app!{ @arg ($arg.value_name(stringify!($var))) (+) $($tail)* }
883 };
884 (@arg ($arg:expr) (-) [$var:ident] $($tail:tt)*) => {
885 $crate::clap_app!{ @arg ($arg.value_name(stringify!($var))) (+) +takes_value $($tail)* }
886 };
887 (@arg ($arg:expr) (+) [$var:ident] $($tail:tt)*) => {
888 $crate::clap_app!{ @arg ($arg.value_name(stringify!($var))) (+) $($tail)* }
889 };
890 (@arg ($arg:expr) $modes:tt ... $($tail:tt)*) => {
891 $crate::clap_app!{ @arg ($arg) $modes +multiple +takes_value $($tail)* }
892 };
893// Shorthand magic
894 (@arg ($arg:expr) $modes:tt #{$n:expr, $m:expr} $($tail:tt)*) => {
895 $crate::clap_app!{ @arg ($arg) $modes min_values($n) max_values($m) $($tail)* }
896 };
897 (@arg ($arg:expr) $modes:tt * $($tail:tt)*) => {
898 $crate::clap_app!{ @arg ($arg) $modes +required $($tail)* }
899 };
900// !foo -> .foo(false)
901 (@arg ($arg:expr) $modes:tt !$ident:ident $($tail:tt)*) => {
902 $crate::clap_app!{ @arg ($arg.$ident(false)) $modes $($tail)* }
903 };
904// +foo -> .foo(true)
905 (@arg ($arg:expr) $modes:tt +$ident:ident $($tail:tt)*) => {
906 $crate::clap_app!{ @arg ($arg.$ident(true)) $modes $($tail)* }
907 };
908// Validator
909 (@arg ($arg:expr) $modes:tt {$fn_:expr} $($tail:tt)*) => {
910 $crate::clap_app!{ @arg ($arg.validator($fn_)) $modes $($tail)* }
911 };
912 (@as_expr $expr:expr) => { $expr };
913// Help
914 (@arg ($arg:expr) $modes:tt $desc:tt) => { $arg.help($crate::clap_app!{ @as_expr $desc }) };
915// Handle functions that need to be called multiple times for each argument
916 (@arg ($arg:expr) $modes:tt $ident:ident[$($target:ident)*] $($tail:tt)*) => {
917 $crate::clap_app!{ @arg ($arg $( .$ident(stringify!($target)) )*) $modes $($tail)* }
918 };
919// Inherit builder's functions, e.g. `index(2)`, `requires_if("val", "arg")`
920 (@arg ($arg:expr) $modes:tt $ident:ident($($expr:expr),*) $($tail:tt)*) => {
921 $crate::clap_app!{ @arg ($arg.$ident($($expr),*)) $modes $($tail)* }
922 };
923// Inherit builder's functions with trailing comma, e.g. `index(2,)`, `requires_if("val", "arg",)`
924 (@arg ($arg:expr) $modes:tt $ident:ident($($expr:expr,)*) $($tail:tt)*) => {
925 $crate::clap_app!{ @arg ($arg.$ident($($expr),*)) $modes $($tail)* }
926 };
927
928// Build a subcommand outside of an app.
929 (@subcommand $name:ident => $($tail:tt)*) => {
930 $crate::clap_app!{ @app ($crate::Command::new(stringify!($name))) $($tail)* }
931 };
932// Start the magic
933 (($name:expr) => $($tail:tt)*) => {{
934 $crate::clap_app!{ @app ($crate::Command::new($name)) $($tail)*}
935 }};
936
937 ($name:ident => $($tail:tt)*) => {{
938 $crate::clap_app!{ @app ($crate::Command::new(stringify!($name))) $($tail)*}
939 }};
940}
941
942macro_rules! impl_settings {
943 ($settings:ident, $flags:ident,
944 $(
945 $(#[$inner:ident $($args:tt)*])*
946 $setting:ident => $flag:path
947 ),+
948 ) => {
949 impl $flags {
950 #[allow(dead_code)]
951 pub(crate) fn empty() -> Self {
952 $flags(Flags::empty())
953 }
954
955 #[allow(dead_code)]
956 pub(crate) fn insert(&mut self, rhs: Self) {
957 self.0.insert(rhs.0);
958 }
959
960 #[allow(dead_code)]
961 pub(crate) fn remove(&mut self, rhs: Self) {
962 self.0.remove(rhs.0);
963 }
964
965 #[allow(dead_code)]
966 pub(crate) fn set(&mut self, s: $settings) {
967 #[allow(deprecated)] // some Settings might be deprecated
968 match s {
969 $(
970 $(#[$inner $($args)*])*
971 $settings::$setting => self.0.insert($flag),
972 )*
973 }
974 }
975
976 #[allow(dead_code)]
977 pub(crate) fn unset(&mut self, s: $settings) {
978 #[allow(deprecated)] // some Settings might be deprecated
979 match s {
980 $(
981 $(#[$inner $($args)*])*
982 $settings::$setting => self.0.remove($flag),
983 )*
984 }
985 }
986
987 #[allow(dead_code)]
988 pub(crate) fn is_set(&self, s: $settings) -> bool {
989 #[allow(deprecated)] // some Settings might be deprecated
990 match s {
991 $(
992 $(#[$inner $($args)*])*
993 $settings::$setting => self.0.contains($flag),
994 )*
995 }
996 }
997 }
998
999 impl BitOr for $flags {
1000 type Output = Self;
1001
1002 fn bitor(mut self, rhs: Self) -> Self::Output {
1003 self.0.insert(rhs.0);
1004 self
1005 }
1006 }
1007
1008 impl From<$settings> for $flags {
1009 fn from(setting: $settings) -> Self {
1010 let mut flags = $flags::empty();
1011 flags.set(setting);
1012 flags
1013 }
1014 }
1015
1016 impl BitOr<$settings> for $flags {
1017 type Output = Self;
1018
1019 fn bitor(mut self, rhs: $settings) -> Self::Output {
1020 self.set(rhs);
1021 self
1022 }
1023 }
1024
1025 impl BitOr for $settings {
1026 type Output = $flags;
1027
1028 fn bitor(self, rhs: Self) -> Self::Output {
1029 let mut flags = $flags::empty();
1030 flags.set(self);
1031 flags.set(rhs);
1032 flags
1033 }
1034 }
1035 }
1036}
1037
1038// Convenience for writing to stderr thanks to https://github.com/BurntSushi
1039macro_rules! wlnerr {
1040 ($($arg:tt)*) => ({
1041 use std::io::{Write, stderr};
1042 writeln!(&mut stderr(), $($arg)*).ok();
1043 })
1044}
1045
1046#[cfg(feature = "debug")]
1047macro_rules! debug {
1048 ($($arg:tt)*) => ({
1049 let prefix = format!("[{:>w$}] \t", module_path!(), w = 28);
1050 let body = format!($($arg)*);
923072b8 1051 let mut color = $crate::output::fmt::Colorizer::new($crate::output::fmt::Stream::Stderr, $crate::ColorChoice::Auto);
04454e1e
FG
1052 color.hint(prefix);
1053 color.hint(body);
1054 color.none("\n");
1055 let _ = color.print();
1056 })
1057}
1058
1059#[cfg(not(feature = "debug"))]
1060macro_rules! debug {
1061 ($($arg:tt)*) => {};
1062}