@@ -240,6 +240,7 @@ class parser
240240 && std::invocable<validator_type, option_type>
241241 void add_option (option_type & value, config<validator_type> const & config)
242242 {
243+ check_parse_not_called (" add_option" );
243244 verify_option_config (config);
244245
245246 // copy variables into the lambda because the calls are pushed to a stack
@@ -266,6 +267,7 @@ class parser
266267 requires std::invocable<validator_type, bool >
267268 void add_flag (bool & value, config<validator_type> const & config)
268269 {
270+ check_parse_not_called (" add_flag" );
269271 verify_flag_config (config);
270272
271273 if (value)
@@ -308,6 +310,7 @@ class parser
308310 && std::invocable<validator_type, option_type>
309311 void add_positional_option (option_type & value, config<validator_type> const & config)
310312 {
313+ check_parse_not_called (" add_positional_option" );
311314 verify_positional_option_config (config);
312315
313316 if constexpr (detail::is_container_option<option_type>)
@@ -535,6 +538,7 @@ class parser
535538 */
536539 void add_section (std::string const & title, bool const advanced_only = false )
537540 {
541+ check_parse_not_called (" add_section" );
538542 std::visit (
539543 [&title, advanced_only](auto & f)
540544 {
@@ -554,6 +558,7 @@ class parser
554558 */
555559 void add_subsection (std::string const & title, bool const advanced_only = false )
556560 {
561+ check_parse_not_called (" add_subsection" );
557562 std::visit (
558563 [&title, advanced_only](auto & f)
559564 {
@@ -574,6 +579,7 @@ class parser
574579 */
575580 void add_line (std::string const & text, bool is_paragraph = false , bool const advanced_only = false )
576581 {
582+ check_parse_not_called (" add_line" );
577583 std::visit (
578584 [&text, is_paragraph, advanced_only](auto & f)
579585 {
@@ -603,6 +609,7 @@ class parser
603609 */
604610 void add_list_item (std::string const & key, std::string const & desc, bool const advanced_only = false )
605611 {
612+ check_parse_not_called (" add_list_item" );
606613 std::visit (
607614 [&key, &desc, advanced_only](auto & f)
608615 {
@@ -670,6 +677,7 @@ class parser
670677 */
671678 void add_subcommands (std::vector<std::string> const & subcommands)
672679 {
680+ check_parse_not_called (" add_subcommands" );
673681 for (auto const & sub : subcommands)
674682 {
675683 if (!std::regex_match (sub, app_name_regex))
@@ -1016,6 +1024,21 @@ class parser
10161024 if (!config.default_message .empty ())
10171025 throw design_error{" A positional option may not have a default message because it is always required." };
10181026 }
1027+
1028+ /* !\brief Throws a sharg::design_error if parse() was already called.
1029+ * \param[in] function_name The name of the function that was called after parse().
1030+ * \throws sharg::design_error
1031+ * \details
1032+ * This function is used when calling functions which have no effect (add_line, add_option, ...) or unexpected
1033+ * behavior (add_subcommands) after parse() was called.
1034+ * Has no effect when parse() encounters a special format (help, version, ...), since those will terminate
1035+ * the program.
1036+ */
1037+ inline void check_parse_not_called (std::string_view const function_name) const
1038+ {
1039+ if (parse_was_called)
1040+ throw design_error{detail::to_string (function_name.data (), " may only be used before calling parse()." )};
1041+ }
10191042};
10201043
10211044} // namespace sharg
0 commit comments