12#include "../Option.hpp"
45 std::string option_name, std::string option_description, callback_t callback, App *parent,
bool allow_non_standard)
47 std::tie(
snames_,
lnames_,
pname_) = detail::get_names(detail::split_names(option_name), allow_non_standard);
64 }
else if(value == detail::expected_max_vector_size) {
79 value_min = -value_min;
83 value_max = detail::expected_max_vector_size;
85 if(value_max < value_min) {
97 validator->non_modifying();
105 auto vp = std::make_shared<Validator>(std::move(validator));
106 if(!validator_name.empty()) {
107 vp->name(validator_name);
115 std::string validator_description,
116 std::string validator_name) {
118 auto vp = std::make_shared<Validator>(
119 std::move(validator_func), std::move(validator_description), std::move(validator_name));
132 auto vp = std::make_shared<Validator>(std::move(validator));
133 if(!transform_name.empty()) {
134 vp->name(transform_name);
142 auto vp = std::make_shared<Validator>(std::move(validator));
143 if(!transform_name.empty()) {
144 vp->name(transform_name);
146 vp->description(transform_description);
152 std::string transform_description,
153 std::string transform_name) {
154 auto vp = std::make_shared<Validator>(
155 [transform_func](std::string &val) {
156 val = transform_func(val);
157 return std::string{};
159 std::move(transform_description),
160 std::move(transform_name));
167 auto vp = std::make_shared<Validator>(
168 [func](std::string &inout) {
170 return std::string{};
179 if(validator_name == validator->
get_name()) {
180 return validator.get();
183 if((validator_name.empty()) && (!
validators_.empty())) {
186 throw OptionNotFound(std::string{
"Validator "} + validator_name +
" Not Found");
191 if(index >= 0 && index <
static_cast<int>(
validators_.size())) {
205 auto iterator = std::find(std::begin(
needs_), std::end(
needs_), opt);
207 if(iterator == std::end(
needs_)) {
242 auto *parent =
static_cast<T *
>(
parent_);
243 for(
const Option_p &opt : parent->options_) {
244 if(opt.get() ==
this) {
247 const auto &omatch = opt->matching_name(*
this);
248 if(!omatch.empty()) {
263 auto *parent =
static_cast<T *
>(
parent_);
264 for(
const Option_p &opt : parent->options_) {
265 if(opt.get() ==
this) {
268 const auto &omatch = opt->matching_name(*
this);
269 if(!omatch.empty()) {
271 throw OptionAlreadyAdded(
"adding ignore underscore caused a name conflict with " + omatch);
293CLI11_NODISCARD CLI11_INLINE std::string
294Option::get_name(
bool positional,
bool all_options,
bool disable_default_flag_values)
const {
300 std::vector<std::string> name_list;
304 name_list.push_back(
pname_);
307 for(
const std::string &sname :
snames_) {
308 name_list.push_back(
"-" + sname);
309 if(!disable_default_flag_values &&
check_fname(sname)) {
314 for(
const std::string &lname :
lnames_) {
315 name_list.push_back(
"--" + lname);
316 if(!disable_default_flag_values &&
check_fname(lname)) {
321 for(
const std::string &sname :
snames_)
322 name_list.push_back(
"-" + sname);
324 for(
const std::string &lname :
lnames_)
325 name_list.push_back(
"--" + lname);
328 return detail::join(name_list);
337 return std::string(2,
'-') +
lnames_[0];
341 return std::string(1,
'-') +
snames_[0];
348 bool used_default_str =
false;
350 used_default_str =
true;
365 if(send_results.empty()) {
368 bool local_result =
callback_(send_results);
369 if(used_default_str) {
381 static const std::string estring;
383 for(
const std::string &sname :
snames_) {
389 for(
const std::string &lname :
lnames_) {
392 if(lname.size() == 1 && bothConfigurable) {
402 if(bothConfigurable && other.
snames_.empty() && other.
fnames_.empty() && !other.
pname_.empty()) {
408 for(
const std::string &sname : other.
snames_)
411 for(
const std::string &lname : other.
lnames_)
420 if(name.length() > 2 && name[0] ==
'-' && name[1] ==
'-')
422 if(name.length() > 1 && name.front() ==
'-')
425 std::string local_pname =
pname_;
426 std::string local_name = name;
428 local_pname = detail::remove_underscore(local_pname);
429 local_name = detail::remove_underscore(local_name);
432 local_pname = detail::to_lower(local_pname);
433 local_name = detail::to_lower(local_name);
435 if(local_name == local_pname) {
448 std::string input_value)
const {
449 static const std::string trueString{
"true"};
450 static const std::string falseString{
"false"};
451 static const std::string emptyString{
"{}"};
454 if(!((input_value.empty()) || (input_value == emptyString))) {
456 if(default_ind >= 0) {
462 throw(ArgumentMismatch::FlagOverride(name));
465 if(input_value != trueString) {
466 throw(ArgumentMismatch::FlagOverride(name));
472 if((input_value.empty()) || (input_value == emptyString)) {
483 auto val = detail::to_flag_value(input_value);
488 return (val == 1) ? falseString : (val == (-1) ? trueString : std::to_string(-val));
494 _add_result(std::move(s),
results_);
500 results_added = _add_result(std::move(s),
results_);
508 _add_result(std::move(str),
results_);
518 _validate_results(res);
522 _reduce_results(extra, res);
524 res = std::move(extra);
532 if(option_type_size < 0) {
551 if(option_type_size_min < 0 || option_type_size_max < 0) {
554 option_type_size_min = (std::abs)(option_type_size_min);
555 option_type_size_max = (std::abs)(option_type_size_max);
558 if(option_type_size_min > option_type_size_max) {
605 full_type_name +=
":" + vtype;
609 return full_type_name;
612CLI11_INLINE
void Option::_validate_results(results_t &res)
const {
624 for(std::string &result : res) {
629 auto err_msg = _validate(result, (index >= 0) ? (index %
type_size_max_) : index);
631 throw ValidationError(
get_name(), err_msg);
642 for(std::string &result : res) {
643 auto err_msg = _validate(result, index);
646 throw ValidationError(
get_name(), err_msg);
652CLI11_INLINE
void Option::_reduce_results(results_t &out,
const results_t &original)
const {
660 case MultiOptionPolicy::TakeAll:
662 case MultiOptionPolicy::TakeLast: {
664 std::size_t trim_size = std::min<std::size_t>(
666 if(original.size() != trim_size) {
667 out.assign(original.end() -
static_cast<results_t::difference_type
>(trim_size), original.end());
670 case MultiOptionPolicy::Reverse: {
672 std::size_t trim_size = std::min<std::size_t>(
674 if(original.size() != trim_size || trim_size > 1) {
675 out.assign(original.end() -
static_cast<results_t::difference_type
>(trim_size), original.end());
677 std::reverse(out.begin(), out.end());
679 case MultiOptionPolicy::TakeFirst: {
680 std::size_t trim_size = std::min<std::size_t>(
682 if(original.size() != trim_size) {
683 out.assign(original.begin(), original.begin() +
static_cast<results_t::difference_type
>(trim_size));
686 case MultiOptionPolicy::Join:
687 if(original.size() > 1) {
688 out.push_back(detail::join(original, std::string(1, (
delimiter_ ==
'\0') ?
'\n' :
delimiter_)));
691 case MultiOptionPolicy::Sum:
692 out.push_back(detail::sum_string_vector(original));
694 case MultiOptionPolicy::Throw:
704 if(original.size() < num_min) {
705 throw ArgumentMismatch::AtLeast(
get_name(),
static_cast<int>(num_min), original.size());
707 if(original.size() > num_max) {
708 if(original.size() == 2 && num_max == 1 && original[1] ==
"%%" && original[0] ==
"{}") {
713 throw ArgumentMismatch::AtMost(
get_name(),
static_cast<int>(num_max), original.size());
723 out.emplace_back(
"{}");
724 out.emplace_back(
"%%");
727 out.emplace_back(
"%%");
731CLI11_INLINE std::string Option::_validate(std::string &result,
int index)
const {
738 auto v = vali->get_application_index();
739 if(v == -1 || v == index) {
741 err_msg = (*vali)(result);
742 }
catch(
const ValidationError &err) {
743 err_msg = err.what();
753CLI11_INLINE
int Option::_add_result(std::string &&result, std::vector<std::string> &res)
const {
754 int result_count = 0;
758 if(result.size() >= 4 && result[0] ==
'[' && result[1] ==
'[' && result.back() ==
']' &&
759 (*(result.end() - 2) ==
']')) {
761 std::string nstrs{
'['};
762 bool duplicated{
true};
763 for(std::size_t ii = 2; ii < result.size() - 2; ii += 2) {
764 if(result[ii] == result[ii + 1]) {
765 nstrs.push_back(result[ii]);
772 nstrs.push_back(
']');
773 res.push_back(std::move(nstrs));
780 result.front() ==
'[' &&
781 result.back() ==
']') {
784 result.erase(result.begin());
785 for(
auto &var : CLI::detail::split_up(result,
',')) {
787 result_count += _add_result(std::move(var), res);
793 res.push_back(std::move(result));
796 if((result.find_first_of(
delimiter_) != std::string::npos)) {
797 for(
const auto &var : CLI::detail::split(result,
delimiter_)) {
804 res.push_back(std::move(result));
Thrown when conversion call back fails, such as when an int fails to coerce to a string.
Definition Error.hpp:206
Thrown when an option is set to conflicting values (non-vector and multi args, for example).
Definition Error.hpp:97
Thrown when an option already exists.
Definition Error.hpp:145
bool always_capture_default_
Automatically capture default value.
Definition Option.hpp:96
MultiOptionPolicy multi_option_policy_
Policy for handling multiple arguments beyond the expected Max.
Definition Option.hpp:99
bool ignore_case_
Ignore the case when matching (option, not value).
Definition Option.hpp:81
bool configurable_
Allow this option to be given in a configuration file.
Definition Option.hpp:87
CallbackPriority callback_priority_
Priority of callback.
Definition Option.hpp:102
bool disable_flag_override_
Disable overriding flag values with '=value'.
Definition Option.hpp:90
bool required_
True if this is a required option.
Definition Option.hpp:78
char delimiter_
Specify a delimiter character for vector arguments.
Definition Option.hpp:93
std::string group_
The group membership.
Definition Option.hpp:75
bool ignore_underscore_
Ignore underscores when matching (option, not value).
Definition Option.hpp:84
CLI11_NODISCARD const std::string & get_group() const
Definition Option.hpp:136
void copy_to(T *other) const
Copy the contents to another similar class (one based on OptionBase).
Definition Option_inl.hpp:31
Definition Option.hpp:261
Option * type_size(int option_type_size)
Set a custom option size.
Definition Option_inl.hpp:531
Option * expected(int value)
Set the number of expected arguments.
Definition Option_inl.hpp:56
Option * check(Validator_p validator)
Adds a shared validator.
Definition Option_inl.hpp:96
std::string default_str_
A human readable default value, either manually set, captured, or captured by default.
Definition Option.hpp:296
CLI11_NODISCARD bool check_name(const std::string &name) const
Check a name. Requires "-" or "--" for short / long, supports positional name.
Definition Option_inl.hpp:418
std::function< std::string()> type_name_
Definition Option.hpp:304
@ reduced
a subset of results has been generated
Definition Option.hpp:355
@ callback_run
the callback has been executed
Definition Option.hpp:356
@ validated
the results have been validated
Definition Option.hpp:354
@ parsing
The option is currently collecting parsed results.
Definition Option.hpp:353
option_state current_option_state_
Whether the callback has run (needed for INI parsing).
Definition Option.hpp:359
int type_size_min_
The minimum number of arguments an option should be expecting.
Definition Option.hpp:317
CLI11_NODISCARD results_t reduced_results() const
Get a copy of the results.
Definition Option_inl.hpp:513
void clear()
Clear the parsed results (mostly for testing).
Definition Option_inl.hpp:50
Option * capture_default_str()
Capture the default value from the original value (if it can be captured).
Definition Option_inl.hpp:592
Option * needs(Option *opt)
Sets required options.
Definition Option_inl.hpp:197
CLI11_NODISCARD std::string get_type_name() const
Get the full typename for this option.
Definition Option_inl.hpp:599
CLI11_NODISCARD bool check_fname(std::string name) const
Requires "--" to be removed from string.
Definition Option.hpp:676
std::string pname_
A positional name.
Definition Option.hpp:283
int expected_min_
The minimum number of expected values.
Definition Option.hpp:320
Option * transform(Validator_p validator)
Adds a shared Validator.
Definition Option_inl.hpp:125
Option * ignore_case(bool value=true)
Definition Option_inl.hpp:239
std::set< Option * > needs_
A list of options that are required with this option.
Definition Option.hpp:328
void run_callback()
Process the callback.
Definition Option_inl.hpp:347
CLI11_NODISCARD std::string get_name(bool positional=false, bool all_options=false, bool disable_default_flag_values=false) const
Gets a comma separated list of names. Will include / prefer the positional name if positional is true...
Definition Option_inl.hpp:294
CLI11_NODISCARD bool check_sname(std::string name) const
Requires "-" to be removed from string.
Definition Option.hpp:666
bool flag_like_
Specify that the option should act like a flag vs regular option.
Definition Option.hpp:363
std::set< Option * > excludes_
A list of options that are excluded with this option.
Definition Option.hpp:331
bool force_callback_
flag indicating that the option should force the callback regardless if any results present
Definition Option.hpp:371
std::vector< std::string > fnames_
a list of flag names with specified default values;
Definition Option.hpp:280
CLI11_NODISCARD int get_items_expected_min() const
The total min number of expected string values to be used.
Definition Option.hpp:600
CLI11_NODISCARD const std::string & matching_name(const Option &other) const
If options share any of the same names, find it.
Definition Option_inl.hpp:380
CLI11_NODISCARD bool check_lname(std::string name) const
Requires "--" to be removed from string.
Definition Option.hpp:671
CLI11_NODISCARD int get_items_expected_max() const
Get the maximum number of items expected to be returned and used for the callback.
Definition Option.hpp:603
std::vector< std::string > snames_
A list of the short names (-a) without the leading dashes.
Definition Option.hpp:270
results_t proc_results_
results after reduction
Definition Option.hpp:350
bool remove_excludes(Option *opt)
Remove needs link from an option. Returns true if the option really was in the needs list.
Definition Option_inl.hpp:229
Option * multi_option_policy(MultiOptionPolicy value=MultiOptionPolicy::Throw)
Take the last argument if given multiple times (or another policy).
Definition Option_inl.hpp:280
std::vector< Validator_p > validators_
A list of Validators to run on each value parsed.
Definition Option.hpp:325
CLI11_NODISCARD const std::string & get_single_name() const
Get a single name for the option, first of lname, sname, pname, envname.
Definition Option_inl.hpp:574
Option * excludes(Option *opt)
Sets excluded options.
Definition Option_inl.hpp:214
App * parent_
link back up to the parent App for fallthrough
Definition Option.hpp:338
int expected_max_
The maximum number of expected values.
Definition Option.hpp:322
Option(std::string option_name, std::string option_description, callback_t callback, App *parent, bool allow_non_standard=false)
Making an option by hand is not defined, it must be made by the App class.
Definition Option_inl.hpp:44
CLI11_NODISCARD std::string get_flag_value(const std::string &name, std::string input_value) const
Definition Option_inl.hpp:447
CLI11_NODISCARD int get_items_expected() const
The total min number of expected string values to be used.
Definition Option.hpp:608
std::string description_
The description for help strings.
Definition Option.hpp:293
bool inject_separator_
flag indicating a separator needs to be injected after each argument call
Definition Option.hpp:367
Validator * get_validator(const std::string &validator_name="")
Get a named Validator.
Definition Option_inl.hpp:177
callback_t callback_
Options store a callback to do all the work.
Definition Option.hpp:341
CLI11_NODISCARD bool empty() const
True if the option was not passed.
Definition Option.hpp:391
CLI11_NODISCARD int get_expected_max() const
The max number of times the option expects to be included.
Definition Option.hpp:597
CLI11_NODISCARD int get_type_size() const
The number of arguments the option expects.
Definition Option.hpp:556
std::string envname_
If given, check the environment for this option.
Definition Option.hpp:286
std::function< std::string()> default_function_
Run this function to capture a default (ignore if empty).
Definition Option.hpp:307
Option * ignore_underscore(bool value=true)
Definition Option_inl.hpp:259
std::vector< std::pair< std::string, std::string > > default_flag_values_
Definition Option.hpp:277
Option * type_name_fn(std::function< std::string()> typefun)
Set the type function to run when displayed on this option.
Definition Option.hpp:758
int type_size_max_
Definition Option.hpp:315
bool allow_extra_args_
Specify that extra args beyond type_size_max should be allowed.
Definition Option.hpp:361
std::vector< std::string > lnames_
A list of the long names (--long) without the leading dashes.
Definition Option.hpp:273
Option * type_name(std::string typeval)
Set a custom option typestring.
Definition Option_inl.hpp:587
Option * add_result(std::string s)
Puts a result at the end.
Definition Option_inl.hpp:493
bool remove_needs(Option *opt)
Remove needs link from an option. Returns true if the option really was in the needs list.
Definition Option_inl.hpp:204
Option * each(const std::function< void(std::string)> &func)
Adds a user supplied function to run on each item passed in (communicate though lambda capture).
Definition Option_inl.hpp:166
results_t results_
complete Results of parsing
Definition Option.hpp:348
Thrown when counting a nonexistent option.
Definition Error.hpp:352
Some validators that are provided.
Definition Validators.hpp:55
Validator & non_modifying(bool no_modify=true)
Specify whether the Validator can be modifying or not.
Definition Validators.hpp:123
CLI11_NODISCARD std::string get_description() const
Generate type description information for the Validator.
Definition Validators_inl.hpp:61
CLI11_NODISCARD const std::string & get_name() const
Get the name of the Validator.
Definition Validators.hpp:113