Enum clap::builder::ArgAction

source ·
#[non_exhaustive]
pub enum ArgAction {
    Set,
    Append,
    SetTrue,
    SetFalse,
    Count,
    Help,
    Version,
}
Expand description

Behavior of arguments when they are encountered while parsing

Examples

let cmd = Command::new("mycmd")
   .arg(
       Arg::new("special-help")
           .short('?')
           .action(clap::ArgAction::Help)
   );

// Existing help still exists
let err = cmd.clone().try_get_matches_from(["mycmd", "-h"]).unwrap_err();
assert_eq!(err.kind(), clap::error::ErrorKind::DisplayHelp);

// New help available
let err = cmd.try_get_matches_from(["mycmd", "-?"]).unwrap_err();
assert_eq!(err.kind(), clap::error::ErrorKind::DisplayHelp);

Variants (Non-exhaustive)§

This enum is marked as non-exhaustive
Non-exhaustive enums could have additional variants added in future. Therefore, when matching against variants of non-exhaustive enums, an extra wildcard arm must be added to account for any future variants.
§

Set

When encountered, store the associated value(s) in ArgMatches

NOTE: If the argument has previously been seen, it will result in a ArgumentConflict unless Command::args_override_self(true) is set.

Examples

let cmd = Command::new("mycmd")
    .arg(
        Arg::new("flag")
            .long("flag")
            .action(clap::ArgAction::Set)
    );

let matches = cmd.try_get_matches_from(["mycmd", "--flag", "value"]).unwrap();
assert!(matches.contains_id("flag"));
assert_eq!(
    matches.get_many::<String>("flag").unwrap_or_default().map(|v| v.as_str()).collect::<Vec<_>>(),
    vec!["value"]
);
§

Append

When encountered, store the associated value(s) in ArgMatches

Examples

let cmd = Command::new("mycmd")
    .arg(
        Arg::new("flag")
            .long("flag")
            .action(clap::ArgAction::Append)
    );

let matches = cmd.try_get_matches_from(["mycmd", "--flag", "value1", "--flag", "value2"]).unwrap();
assert!(matches.contains_id("flag"));
assert_eq!(
    matches.get_many::<String>("flag").unwrap_or_default().map(|v| v.as_str()).collect::<Vec<_>>(),
    vec!["value1", "value2"]
);
§

SetTrue

When encountered, act as if "true" was encountered on the command-line

If no default_value is set, it will be false.

No value is allowed. To optionally accept a value, see Arg::default_missing_value

NOTE: If the argument has previously been seen, it will result in a ArgumentConflict unless Command::args_override_self(true) is set.

Examples

let cmd = Command::new("mycmd")
    .arg(
        Arg::new("flag")
            .long("flag")
            .action(clap::ArgAction::SetTrue)
    );

let matches = cmd.clone().try_get_matches_from(["mycmd", "--flag"]).unwrap();
assert!(matches.contains_id("flag"));
assert_eq!(
    matches.get_one::<bool>("flag").copied(),
    Some(true)
);

let matches = cmd.try_get_matches_from(["mycmd"]).unwrap();
assert!(matches.contains_id("flag"));
assert_eq!(
    matches.get_one::<bool>("flag").copied(),
    Some(false)
);

You can use TypedValueParser::map to have the flag control an application-specific type:

let cmd = Command::new("mycmd")
    .arg(
        Arg::new("flag")
            .long("flag")
            .action(clap::ArgAction::SetTrue)
            .value_parser(
                BoolishValueParser::new()
                .map(|b| -> usize {
                    if b { 10 } else { 5 }
                })
            )
    );

let matches = cmd.clone().try_get_matches_from(["mycmd", "--flag"]).unwrap();
assert!(matches.contains_id("flag"));
assert_eq!(
    matches.get_one::<usize>("flag").copied(),
    Some(10)
);

let matches = cmd.try_get_matches_from(["mycmd"]).unwrap();
assert!(matches.contains_id("flag"));
assert_eq!(
    matches.get_one::<usize>("flag").copied(),
    Some(5)
);
§

SetFalse

When encountered, act as if "false" was encountered on the command-line

If no default_value is set, it will be true.

No value is allowed. To optionally accept a value, see Arg::default_missing_value

NOTE: If the argument has previously been seen, it will result in a ArgumentConflict unless Command::args_override_self(true) is set.

Examples

let cmd = Command::new("mycmd")
    .arg(
        Arg::new("flag")
            .long("flag")
            .action(clap::ArgAction::SetFalse)
    );

let matches = cmd.clone().try_get_matches_from(["mycmd", "--flag"]).unwrap();
assert!(matches.contains_id("flag"));
assert_eq!(
    matches.get_one::<bool>("flag").copied(),
    Some(false)
);

let matches = cmd.try_get_matches_from(["mycmd"]).unwrap();
assert!(matches.contains_id("flag"));
assert_eq!(
    matches.get_one::<bool>("flag").copied(),
    Some(true)
);
§

Count

When encountered, increment a u8 counter

If no default_value is set, it will be 0.

No value is allowed. To optionally accept a value, see Arg::default_missing_value

Examples

let cmd = Command::new("mycmd")
    .arg(
        Arg::new("flag")
            .long("flag")
            .action(clap::ArgAction::Count)
    );

let matches = cmd.clone().try_get_matches_from(["mycmd", "--flag", "--flag"]).unwrap();
assert!(matches.contains_id("flag"));
assert_eq!(
    matches.get_count("flag"),
    2
);

let matches = cmd.try_get_matches_from(["mycmd"]).unwrap();
assert!(matches.contains_id("flag"));
assert_eq!(
    matches.get_count("flag"),
    0
);
§

Help

When encountered, display Command::print_help

Depending on the flag, Command::print_long_help may be shown

Examples

let cmd = Command::new("mycmd")
   .arg(
       Arg::new("special-help")
           .short('?')
           .action(clap::ArgAction::Help)
   );

// Existing help still exists
let err = cmd.clone().try_get_matches_from(["mycmd", "-h"]).unwrap_err();
assert_eq!(err.kind(), clap::error::ErrorKind::DisplayHelp);

// New help available
let err = cmd.try_get_matches_from(["mycmd", "-?"]).unwrap_err();
assert_eq!(err.kind(), clap::error::ErrorKind::DisplayHelp);
§

Version

When encountered, display Command::version

Depending on the flag, Command::long_version may be shown

Examples

let cmd = Command::new("mycmd")
    .version("1.0.0")
    .arg(
        Arg::new("special-version")
            .long("special-version")
            .action(clap::ArgAction::Version)
    );

// Existing help still exists
let err = cmd.clone().try_get_matches_from(["mycmd", "--version"]).unwrap_err();
assert_eq!(err.kind(), clap::error::ErrorKind::DisplayVersion);

// New help available
let err = cmd.try_get_matches_from(["mycmd", "--special-version"]).unwrap_err();
assert_eq!(err.kind(), clap::error::ErrorKind::DisplayVersion);

Implementations§

Returns whether this action accepts values on the command-line

default_values and env may still be processed.

Examples found in repository?
src/builder/arg.rs (line 3937)
3936
3937
3938
3939
3940
3941
3942
3943
3944
3945
3946
3947
3948
3949
3950
3951
3952
3953
3954
3955
3956
3957
3958
3959
3960
3961
3962
3963
3964
3965
3966
3967
3968
3969
3970
3971
3972
3973
3974
3975
3976
3977
3978
3979
3980
3981
3982
3983
3984
3985
3986
3987
3988
3989
3990
3991
3992
3993
3994
3995
3996
3997
3998
3999
4000
4001
4002
4003
4004
4005
4006
4007
4008
4009
4010
4011
4012
4013
4014
4015
4016
4017
4018
4019
4020
4021
4022
4023
4024
4025
4026
4027
4028
4029
4030
4031
4032
4033
4034
4035
4036
4037
4038
4039
4040
4041
4042
4043
4044
4045
4046
4047
4048
4049
4050
4051
4052
4053
4054
4055
4056
4057
4058
4059
4060
4061
4062
4063
4064
4065
4066
4067
4068
4069
4070
4071
4072
4073
4074
4075
4076
4077
4078
4079
4080
4081
4082
4083
4084
4085
4086
4087
4088
4089
4090
4091
4092
4093
4094
4095
4096
4097
4098
4099
4100
4101
4102
4103
4104
4105
4106
    pub(crate) fn is_takes_value_set(&self) -> bool {
        self.get_action().takes_values()
    }

    /// Report whether [`Arg::allow_hyphen_values`] is set
    pub fn is_allow_hyphen_values_set(&self) -> bool {
        self.is_set(ArgSettings::AllowHyphenValues)
    }

    /// Report whether [`Arg::allow_negative_numbers`] is set
    pub fn is_allow_negative_numbers_set(&self) -> bool {
        self.is_set(ArgSettings::AllowNegativeNumbers)
    }

    /// Behavior when parsing the argument
    pub fn get_action(&self) -> &super::ArgAction {
        const DEFAULT: super::ArgAction = super::ArgAction::Set;
        self.action.as_ref().unwrap_or(&DEFAULT)
    }

    /// Configured parser for argument values
    ///
    /// # Example
    ///
    /// ```rust
    /// let cmd = clap::Command::new("raw")
    ///     .arg(
    ///         clap::Arg::new("port")
    ///             .value_parser(clap::value_parser!(usize))
    ///     );
    /// let value_parser = cmd.get_arguments()
    ///     .find(|a| a.get_id() == "port").unwrap()
    ///     .get_value_parser();
    /// println!("{:?}", value_parser);
    /// ```
    pub fn get_value_parser(&self) -> &super::ValueParser {
        if let Some(value_parser) = self.value_parser.as_ref() {
            value_parser
        } else {
            static DEFAULT: super::ValueParser = super::ValueParser::string();
            &DEFAULT
        }
    }

    /// Report whether [`Arg::global`] is set
    pub fn is_global_set(&self) -> bool {
        self.is_set(ArgSettings::Global)
    }

    /// Report whether [`Arg::next_line_help`] is set
    pub fn is_next_line_help_set(&self) -> bool {
        self.is_set(ArgSettings::NextLineHelp)
    }

    /// Report whether [`Arg::hide`] is set
    pub fn is_hide_set(&self) -> bool {
        self.is_set(ArgSettings::Hidden)
    }

    /// Report whether [`Arg::hide_default_value`] is set
    pub fn is_hide_default_value_set(&self) -> bool {
        self.is_set(ArgSettings::HideDefaultValue)
    }

    /// Report whether [`Arg::hide_possible_values`] is set
    pub fn is_hide_possible_values_set(&self) -> bool {
        self.is_set(ArgSettings::HidePossibleValues)
    }

    /// Report whether [`Arg::hide_env`] is set
    #[cfg(feature = "env")]
    pub fn is_hide_env_set(&self) -> bool {
        self.is_set(ArgSettings::HideEnv)
    }

    /// Report whether [`Arg::hide_env_values`] is set
    #[cfg(feature = "env")]
    pub fn is_hide_env_values_set(&self) -> bool {
        self.is_set(ArgSettings::HideEnvValues)
    }

    /// Report whether [`Arg::hide_short_help`] is set
    pub fn is_hide_short_help_set(&self) -> bool {
        self.is_set(ArgSettings::HiddenShortHelp)
    }

    /// Report whether [`Arg::hide_long_help`] is set
    pub fn is_hide_long_help_set(&self) -> bool {
        self.is_set(ArgSettings::HiddenLongHelp)
    }

    /// Report whether [`Arg::require_equals`] is set
    pub fn is_require_equals_set(&self) -> bool {
        self.is_set(ArgSettings::RequireEquals)
    }

    /// Reports whether [`Arg::exclusive`] is set
    pub fn is_exclusive_set(&self) -> bool {
        self.is_set(ArgSettings::Exclusive)
    }

    /// Report whether [`Arg::trailing_var_arg`] is set
    pub fn is_trailing_var_arg_set(&self) -> bool {
        self.is_set(ArgSettings::TrailingVarArg)
    }

    /// Reports whether [`Arg::last`] is set
    pub fn is_last_set(&self) -> bool {
        self.is_set(ArgSettings::Last)
    }

    /// Reports whether [`Arg::ignore_case`] is set
    pub fn is_ignore_case_set(&self) -> bool {
        self.is_set(ArgSettings::IgnoreCase)
    }
}

/// # Internally used only
impl Arg {
    pub(crate) fn _build(&mut self) {
        if self.action.is_none() {
            if self.num_vals == Some(ValueRange::EMPTY) {
                let action = super::ArgAction::SetTrue;
                self.action = Some(action);
            } else {
                let action =
                    if self.is_positional() && self.num_vals.unwrap_or_default().is_unbounded() {
                        // Allow collecting arguments interleaved with flags
                        //
                        // Bounded values are probably a group and the user should explicitly opt-in to
                        // Append
                        super::ArgAction::Append
                    } else {
                        super::ArgAction::Set
                    };
                self.action = Some(action);
            }
        }
        if let Some(action) = self.action.as_ref() {
            if let Some(default_value) = action.default_value() {
                if self.default_vals.is_empty() {
                    self.default_vals = vec![default_value.into()];
                }
            }
            if let Some(default_value) = action.default_missing_value() {
                if self.default_missing_vals.is_empty() {
                    self.default_missing_vals = vec![default_value.into()];
                }
            }
        }

        if self.value_parser.is_none() {
            if let Some(default) = self.action.as_ref().and_then(|a| a.default_value_parser()) {
                self.value_parser = Some(default);
            } else {
                self.value_parser = Some(super::ValueParser::string());
            }
        }

        let val_names_len = self.val_names.len();
        if val_names_len > 1 {
            self.num_vals.get_or_insert(val_names_len.into());
        } else {
            let nargs = if self.get_action().takes_values() {
                ValueRange::SINGLE
            } else {
                ValueRange::EMPTY
            };
            self.num_vals.get_or_insert(nargs);
        }
    }
More examples
Hide additional examples
src/builder/debug_asserts.rs (line 701)
689
690
691
692
693
694
695
696
697
698
699
700
701
702
703
704
705
706
707
708
709
710
711
712
713
714
715
716
717
718
719
720
721
722
723
724
725
726
727
728
729
730
731
732
733
734
735
736
737
738
739
740
741
742
743
744
745
746
747
748
749
750
751
752
753
754
755
756
757
758
759
760
761
762
763
764
765
766
767
768
769
770
771
772
773
774
775
776
777
778
779
780
781
782
783
784
785
786
787
788
789
790
791
792
793
794
795
796
797
798
799
800
801
802
803
804
805
806
807
808
809
810
811
812
813
814
815
816
fn assert_arg(arg: &Arg) {
    debug!("Arg::_debug_asserts:{}", arg.get_id());

    // Self conflict
    // TODO: this check should be recursive
    assert!(
        !arg.blacklist.iter().any(|x| x == arg.get_id()),
        "Argument '{}' cannot conflict with itself",
        arg.get_id(),
    );

    assert_eq!(
        arg.get_action().takes_values(),
        arg.is_takes_value_set(),
        "Argument `{}`'s selected action {:?} contradicts `takes_value`",
        arg.get_id(),
        arg.get_action()
    );
    if let Some(action_type_id) = arg.get_action().value_type_id() {
        assert_eq!(
            action_type_id,
            arg.get_value_parser().type_id(),
            "Argument `{}`'s selected action {:?} contradicts `value_parser` ({:?})",
            arg.get_id(),
            arg.get_action(),
            arg.get_value_parser()
        );
    }

    if arg.get_value_hint() != ValueHint::Unknown {
        assert!(
            arg.is_takes_value_set(),
            "Argument '{}' has value hint but takes no value",
            arg.get_id()
        );

        if arg.get_value_hint() == ValueHint::CommandWithArguments {
            assert!(
                arg.is_multiple_values_set(),
                "Argument '{}' uses hint CommandWithArguments and must accept multiple values",
                arg.get_id()
            )
        }
    }

    if arg.index.is_some() {
        assert!(
            arg.is_positional(),
            "Argument '{}' is a positional argument and can't have short or long name versions",
            arg.get_id()
        );
        assert!(
            arg.is_takes_value_set(),
            "Argument '{}` is positional, it must take a value{}",
            arg.get_id(),
            if arg.get_id() == Id::HELP {
                " (`mut_arg` no longer works with implicit `--help`)"
            } else if arg.get_id() == Id::VERSION {
                " (`mut_arg` no longer works with implicit `--version`)"
            } else {
                ""
            }
        );
    }

    let num_vals = arg.get_num_args().expect(INTERNAL_ERROR_MSG);
    // This can be the cause of later asserts, so put this first
    if num_vals != ValueRange::EMPTY {
        // HACK: Don't check for flags to make the derive easier
        let num_val_names = arg.get_value_names().unwrap_or(&[]).len();
        if num_vals.max_values() < num_val_names {
            panic!(
                "Argument {}: Too many value names ({}) compared to `num_args` ({})",
                arg.get_id(),
                num_val_names,
                num_vals
            );
        }
    }

    assert_eq!(
        num_vals.takes_values(),
        arg.is_takes_value_set(),
        "Argument {}: mismatch between `num_args` ({}) and `takes_value`",
        arg.get_id(),
        num_vals,
    );
    assert_eq!(
        num_vals.is_multiple(),
        arg.is_multiple_values_set(),
        "Argument {}: mismatch between `num_args` ({}) and `multiple_values`",
        arg.get_id(),
        num_vals,
    );

    if 1 < num_vals.min_values() {
        assert!(
            !arg.is_require_equals_set(),
            "Argument {}: cannot accept more than 1 arg (num_args={}) with require_equals",
            arg.get_id(),
            num_vals
        );
    }

    if num_vals == ValueRange::SINGLE {
        assert!(
            !arg.is_multiple_values_set(),
            "Argument {}: mismatch between `num_args` and `multiple_values`",
            arg.get_id()
        );
    }

    assert_arg_flags(arg);

    assert_defaults(arg, "default_value", arg.default_vals.iter());
    assert_defaults(
        arg,
        "default_missing_value",
        arg.default_missing_vals.iter(),
    );
    assert_defaults(
        arg,
        "default_value_if",
        arg.default_vals_ifs
            .iter()
            .filter_map(|(_, _, default)| default.as_ref()),
    );
}

Trait Implementations§

Returns a copy of the value. Read more
Performs copy-assignment from source. Read more
Formats the value using the given formatter. Read more
Convert to the intended resettable type
Convert to the intended resettable type

Auto Trait Implementations§

Blanket Implementations§

Gets the TypeId of self. Read more
Immutably borrows from an owned value. Read more
Mutably borrows from an owned value. Read more

Returns the argument unchanged.

Calls U::from(self).

That is, this conversion is whatever the implementation of From<T> for U chooses to do.

The resulting type after obtaining ownership.
Creates owned data from borrowed data, usually by cloning. Read more
Uses borrowed data to replace owned data, usually by cloning. Read more
The type returned in the event of a conversion error.
Performs the conversion.
The type returned in the event of a conversion error.
Performs the conversion.