diff --git a/CMakeLists.txt b/CMakeLists.txt index 2c1a6b0..321860a 100644 --- a/CMakeLists.txt +++ b/CMakeLists.txt @@ -15,7 +15,9 @@ find_package(ignition-cmake3 REQUIRED) # Configure the project #============================================================================ set(c++standard 17) -ign_configure_project(VERSION_SUFFIX pre1) +ign_configure_project( + REPLACE_IGNITION_INCLUDE_PATH gz/utils + VERSION_SUFFIX pre1) #============================================================================ # Set project-specific options diff --git a/cli/include/CMakeLists.txt b/cli/include/CMakeLists.txt index 3e21b27..148a1f5 100644 --- a/cli/include/CMakeLists.txt +++ b/cli/include/CMakeLists.txt @@ -4,15 +4,15 @@ # target_include_directories(@tgt@ INTERFACE "$") # that for the usual include directories are handled by ign_add_component if(IGN_UTILS_VENDOR_CLI11) - add_subdirectory(vendored-cli/ignition/utils) - target_include_directories(${ign_utils_cli_target_name} + add_subdirectory(vendored-cli/gz/utils) + target_include_directories(${gz_utils_cli_target_name} INTERFACE "$") else() - add_subdirectory(external-cli/ignition/utils) - target_include_directories(${ign_utils_cli_target_name} + add_subdirectory(external-cli/gz/utils) + target_include_directories(${gz_utils_cli_target_name} INTERFACE "$") endif() -add_subdirectory(ignition/utils) +add_subdirectory(gz/utils) diff --git a/cli/include/external-cli/ignition/utils/CMakeLists.txt b/cli/include/external-cli/gz/utils/CMakeLists.txt similarity index 100% rename from cli/include/external-cli/ignition/utils/CMakeLists.txt rename to cli/include/external-cli/gz/utils/CMakeLists.txt diff --git a/cli/include/external-cli/gz/utils/cli/App.hpp b/cli/include/external-cli/gz/utils/cli/App.hpp new file mode 100644 index 0000000..dce0aa8 --- /dev/null +++ b/cli/include/external-cli/gz/utils/cli/App.hpp @@ -0,0 +1,18 @@ +/* + * Copyright (C) 2021 Open Source Robotics Foundation + * + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + * + */ + +#include diff --git a/cli/include/external-cli/gz/utils/cli/CLI.hpp b/cli/include/external-cli/gz/utils/cli/CLI.hpp new file mode 100644 index 0000000..03d4cde --- /dev/null +++ b/cli/include/external-cli/gz/utils/cli/CLI.hpp @@ -0,0 +1,18 @@ +/* + * Copyright (C) 2021 Open Source Robotics Foundation + * + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + * + */ + +#include diff --git a/cli/include/external-cli/gz/utils/cli/Config.hpp b/cli/include/external-cli/gz/utils/cli/Config.hpp new file mode 100644 index 0000000..41133fa --- /dev/null +++ b/cli/include/external-cli/gz/utils/cli/Config.hpp @@ -0,0 +1,18 @@ +/* + * Copyright (C) 2021 Open Source Robotics Foundation + * + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + * + */ + +#include diff --git a/cli/include/external-cli/gz/utils/cli/ConfigFwd.hpp b/cli/include/external-cli/gz/utils/cli/ConfigFwd.hpp new file mode 100644 index 0000000..a97570e --- /dev/null +++ b/cli/include/external-cli/gz/utils/cli/ConfigFwd.hpp @@ -0,0 +1,18 @@ +/* + * Copyright (C) 2021 Open Source Robotics Foundation + * + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + * + */ + +#include diff --git a/cli/include/external-cli/gz/utils/cli/Error.hpp b/cli/include/external-cli/gz/utils/cli/Error.hpp new file mode 100644 index 0000000..4f5bebf --- /dev/null +++ b/cli/include/external-cli/gz/utils/cli/Error.hpp @@ -0,0 +1,18 @@ +/* + * Copyright (C) 2021 Open Source Robotics Foundation + * + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + * + */ + +#include diff --git a/cli/include/external-cli/gz/utils/cli/Formatter.hpp b/cli/include/external-cli/gz/utils/cli/Formatter.hpp new file mode 100644 index 0000000..2cabea5 --- /dev/null +++ b/cli/include/external-cli/gz/utils/cli/Formatter.hpp @@ -0,0 +1,18 @@ +/* + * Copyright (C) 2021 Open Source Robotics Foundation + * + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + * + */ + +#include diff --git a/cli/include/external-cli/gz/utils/cli/FormatterFwd.hpp b/cli/include/external-cli/gz/utils/cli/FormatterFwd.hpp new file mode 100644 index 0000000..ec407b3 --- /dev/null +++ b/cli/include/external-cli/gz/utils/cli/FormatterFwd.hpp @@ -0,0 +1,18 @@ +/* + * Copyright (C) 2021 Open Source Robotics Foundation + * + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + * + */ + +#include diff --git a/cli/include/external-cli/gz/utils/cli/Macros.hpp b/cli/include/external-cli/gz/utils/cli/Macros.hpp new file mode 100644 index 0000000..9af7813 --- /dev/null +++ b/cli/include/external-cli/gz/utils/cli/Macros.hpp @@ -0,0 +1,18 @@ +/* + * Copyright (C) 2021 Open Source Robotics Foundation + * + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + * + */ + +#include diff --git a/cli/include/external-cli/gz/utils/cli/Option.hpp b/cli/include/external-cli/gz/utils/cli/Option.hpp new file mode 100644 index 0000000..7f8379b --- /dev/null +++ b/cli/include/external-cli/gz/utils/cli/Option.hpp @@ -0,0 +1,18 @@ +/* + * Copyright (C) 2021 Open Source Robotics Foundation + * + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + * + */ + +#include diff --git a/cli/include/external-cli/gz/utils/cli/Split.hpp b/cli/include/external-cli/gz/utils/cli/Split.hpp new file mode 100644 index 0000000..6995e99 --- /dev/null +++ b/cli/include/external-cli/gz/utils/cli/Split.hpp @@ -0,0 +1,18 @@ +/* + * Copyright (C) 2021 Open Source Robotics Foundation + * + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + * + */ + +#include diff --git a/cli/include/external-cli/gz/utils/cli/StringTools.hpp b/cli/include/external-cli/gz/utils/cli/StringTools.hpp new file mode 100644 index 0000000..f3d996d --- /dev/null +++ b/cli/include/external-cli/gz/utils/cli/StringTools.hpp @@ -0,0 +1,18 @@ +/* + * Copyright (C) 2021 Open Source Robotics Foundation + * + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + * + */ + +#include diff --git a/cli/include/external-cli/gz/utils/cli/Timer.hpp b/cli/include/external-cli/gz/utils/cli/Timer.hpp new file mode 100644 index 0000000..63758f6 --- /dev/null +++ b/cli/include/external-cli/gz/utils/cli/Timer.hpp @@ -0,0 +1,18 @@ +/* + * Copyright (C) 2021 Open Source Robotics Foundation + * + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + * + */ + +#include diff --git a/cli/include/external-cli/gz/utils/cli/TypeTools.hpp b/cli/include/external-cli/gz/utils/cli/TypeTools.hpp new file mode 100644 index 0000000..979a7e8 --- /dev/null +++ b/cli/include/external-cli/gz/utils/cli/TypeTools.hpp @@ -0,0 +1,18 @@ +/* + * Copyright (C) 2021 Open Source Robotics Foundation + * + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + * + */ + +#include diff --git a/cli/include/external-cli/gz/utils/cli/Validators.hpp b/cli/include/external-cli/gz/utils/cli/Validators.hpp new file mode 100644 index 0000000..219bc51 --- /dev/null +++ b/cli/include/external-cli/gz/utils/cli/Validators.hpp @@ -0,0 +1,18 @@ +/* + * Copyright (C) 2021 Open Source Robotics Foundation + * + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + * + */ + +#include diff --git a/cli/include/external-cli/gz/utils/cli/Version.hpp b/cli/include/external-cli/gz/utils/cli/Version.hpp new file mode 100644 index 0000000..0b4772b --- /dev/null +++ b/cli/include/external-cli/gz/utils/cli/Version.hpp @@ -0,0 +1,18 @@ +/* + * Copyright (C) 2021 Open Source Robotics Foundation + * + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + * + */ + +#include diff --git a/cli/include/external-cli/ignition/utils/cli/App.hpp b/cli/include/external-cli/ignition/utils/cli/App.hpp index dce0aa8..bf8b209 100644 --- a/cli/include/external-cli/ignition/utils/cli/App.hpp +++ b/cli/include/external-cli/ignition/utils/cli/App.hpp @@ -15,4 +15,4 @@ * */ -#include +#include diff --git a/cli/include/external-cli/ignition/utils/cli/CLI.hpp b/cli/include/external-cli/ignition/utils/cli/CLI.hpp index 03d4cde..2f13af5 100644 --- a/cli/include/external-cli/ignition/utils/cli/CLI.hpp +++ b/cli/include/external-cli/ignition/utils/cli/CLI.hpp @@ -15,4 +15,4 @@ * */ -#include +#include diff --git a/cli/include/external-cli/ignition/utils/cli/Config.hpp b/cli/include/external-cli/ignition/utils/cli/Config.hpp index 41133fa..9c0aa6d 100644 --- a/cli/include/external-cli/ignition/utils/cli/Config.hpp +++ b/cli/include/external-cli/ignition/utils/cli/Config.hpp @@ -15,4 +15,4 @@ * */ -#include +#include diff --git a/cli/include/external-cli/ignition/utils/cli/ConfigFwd.hpp b/cli/include/external-cli/ignition/utils/cli/ConfigFwd.hpp index a97570e..4cd3458 100644 --- a/cli/include/external-cli/ignition/utils/cli/ConfigFwd.hpp +++ b/cli/include/external-cli/ignition/utils/cli/ConfigFwd.hpp @@ -15,4 +15,4 @@ * */ -#include +#include diff --git a/cli/include/external-cli/ignition/utils/cli/Error.hpp b/cli/include/external-cli/ignition/utils/cli/Error.hpp index 4f5bebf..2645c6e 100644 --- a/cli/include/external-cli/ignition/utils/cli/Error.hpp +++ b/cli/include/external-cli/ignition/utils/cli/Error.hpp @@ -15,4 +15,4 @@ * */ -#include +#include diff --git a/cli/include/external-cli/ignition/utils/cli/Formatter.hpp b/cli/include/external-cli/ignition/utils/cli/Formatter.hpp index 2cabea5..9015d9f 100644 --- a/cli/include/external-cli/ignition/utils/cli/Formatter.hpp +++ b/cli/include/external-cli/ignition/utils/cli/Formatter.hpp @@ -15,4 +15,4 @@ * */ -#include +#include diff --git a/cli/include/external-cli/ignition/utils/cli/FormatterFwd.hpp b/cli/include/external-cli/ignition/utils/cli/FormatterFwd.hpp index ec407b3..673339c 100644 --- a/cli/include/external-cli/ignition/utils/cli/FormatterFwd.hpp +++ b/cli/include/external-cli/ignition/utils/cli/FormatterFwd.hpp @@ -15,4 +15,4 @@ * */ -#include +#include diff --git a/cli/include/external-cli/ignition/utils/cli/Macros.hpp b/cli/include/external-cli/ignition/utils/cli/Macros.hpp index 9af7813..2b65982 100644 --- a/cli/include/external-cli/ignition/utils/cli/Macros.hpp +++ b/cli/include/external-cli/ignition/utils/cli/Macros.hpp @@ -15,4 +15,4 @@ * */ -#include +#include diff --git a/cli/include/external-cli/ignition/utils/cli/Option.hpp b/cli/include/external-cli/ignition/utils/cli/Option.hpp index 7f8379b..d29b97a 100644 --- a/cli/include/external-cli/ignition/utils/cli/Option.hpp +++ b/cli/include/external-cli/ignition/utils/cli/Option.hpp @@ -15,4 +15,4 @@ * */ -#include +#include diff --git a/cli/include/external-cli/ignition/utils/cli/Split.hpp b/cli/include/external-cli/ignition/utils/cli/Split.hpp index 6995e99..63682e7 100644 --- a/cli/include/external-cli/ignition/utils/cli/Split.hpp +++ b/cli/include/external-cli/ignition/utils/cli/Split.hpp @@ -15,4 +15,4 @@ * */ -#include +#include diff --git a/cli/include/external-cli/ignition/utils/cli/StringTools.hpp b/cli/include/external-cli/ignition/utils/cli/StringTools.hpp index f3d996d..715b332 100644 --- a/cli/include/external-cli/ignition/utils/cli/StringTools.hpp +++ b/cli/include/external-cli/ignition/utils/cli/StringTools.hpp @@ -15,4 +15,4 @@ * */ -#include +#include diff --git a/cli/include/external-cli/ignition/utils/cli/Timer.hpp b/cli/include/external-cli/ignition/utils/cli/Timer.hpp index 63758f6..a3823b6 100644 --- a/cli/include/external-cli/ignition/utils/cli/Timer.hpp +++ b/cli/include/external-cli/ignition/utils/cli/Timer.hpp @@ -15,4 +15,4 @@ * */ -#include +#include diff --git a/cli/include/external-cli/ignition/utils/cli/TypeTools.hpp b/cli/include/external-cli/ignition/utils/cli/TypeTools.hpp index 979a7e8..e8b521f 100644 --- a/cli/include/external-cli/ignition/utils/cli/TypeTools.hpp +++ b/cli/include/external-cli/ignition/utils/cli/TypeTools.hpp @@ -15,4 +15,4 @@ * */ -#include +#include diff --git a/cli/include/external-cli/ignition/utils/cli/Validators.hpp b/cli/include/external-cli/ignition/utils/cli/Validators.hpp index 219bc51..06c7c4e 100644 --- a/cli/include/external-cli/ignition/utils/cli/Validators.hpp +++ b/cli/include/external-cli/ignition/utils/cli/Validators.hpp @@ -15,4 +15,4 @@ * */ -#include +#include diff --git a/cli/include/external-cli/ignition/utils/cli/Version.hpp b/cli/include/external-cli/ignition/utils/cli/Version.hpp index 0b4772b..a02dde7 100644 --- a/cli/include/external-cli/ignition/utils/cli/Version.hpp +++ b/cli/include/external-cli/ignition/utils/cli/Version.hpp @@ -15,4 +15,4 @@ * */ -#include +#include diff --git a/cli/include/ignition/utils/CMakeLists.txt b/cli/include/gz/utils/CMakeLists.txt similarity index 100% rename from cli/include/ignition/utils/CMakeLists.txt rename to cli/include/gz/utils/CMakeLists.txt diff --git a/cli/include/gz/utils/cli/GzFormatter.hpp b/cli/include/gz/utils/cli/GzFormatter.hpp new file mode 100644 index 0000000..997e1bf --- /dev/null +++ b/cli/include/gz/utils/cli/GzFormatter.hpp @@ -0,0 +1,170 @@ +/* + * Copyright (C) 2022 Open Source Robotics Foundation + * + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + * + */ + +#ifndef GZ_UTILS_CLI_IGNITION_FORMATTER_HPP_ +#define GZ_UTILS_CLI_IGNITION_FORMATTER_HPP_ + +#include +#include +#include +#include +#include + +#include "gz/utils/cli/App.hpp" +#include "gz/utils/cli/FormatterFwd.hpp" + +////////////////////////////////////////////////// +/// \brief CLI Formatter class that implements custom Ignition-specific +/// formatting. +/// +/// More information on custom formatters: +/// https://cliutils.github.io/CLI11/book/chapters/formatting.html +class IgnitionFormatter: public CLI::Formatter { + +////////////////////////////////////////////////// +public: explicit IgnitionFormatter(const CLI::App *_app) +{ + // find needs/needed_by for root options + for (const CLI::Option *appOpt: _app->get_options()) + { + for(const CLI::Option *needsOpt : appOpt->get_needs()) + { + this->needed_by.insert({needsOpt->get_name(), appOpt->get_name()}); + this->needs.insert({appOpt->get_name(), needsOpt->get_name()}); + } + } + + // find needs/needed_by for subcommand (or command group) options + auto subcommands = _app->get_subcommands([](const CLI::App*){return true;}); + for (const CLI::App *sub : subcommands) + { + // find needs/needed_by for root options + for (const CLI::Option *subOpt: sub->get_options()) + { + for(const CLI::Option *needsOpt : subOpt->get_needs()) + { + this->needed_by.insert({needsOpt->get_name(), subOpt->get_name()}); + this->needs.insert({subOpt->get_name(), needsOpt->get_name()}); + } + } + } +} + +////////////////////////////////////////////////// +public: std::string make_option_name( + const CLI::Option *opt, bool is_positional) const override { + if (is_positional) + return opt->get_name(true, false); + + std::stringstream out; + + auto snames = opt->get_snames(); + auto lnames = opt->get_lnames(); + + std::vector sname_list; + std::transform(snames.begin(), snames.end(), std::back_inserter(sname_list), + [](const std::string &sname) { return "-" + sname; }); + + std::vector lname_list; + std::transform(lnames.begin(), lnames.end(), std::back_inserter(lname_list), + [](const std::string &lname) { return "--" + lname; }); + + // If no short options, just use long + if (sname_list.empty()) + { + out << CLI::detail::join(lname_list); + } + else + { + out << CLI::detail::join(sname_list); + // Put lnames in brackets to look like ruby formatting + if (!lnames.empty()) + { + out << " [" << CLI::detail::join(lname_list) << "]"; + } + } + + return out.str(); +} + + +////////////////////////////////////////////////// +public: std::string make_option_opts(const CLI::Option *opt) const override { + std::stringstream out; + + if(opt->get_type_size() != 0) { + if(!opt->get_type_name().empty()) + out << " " << get_label(opt->get_type_name()); + if(!opt->get_default_str().empty()) + out << "=" << opt->get_default_str(); + if(opt->get_expected_max() == CLI::detail::expected_max_vector_size) + out << " ..."; + else if(opt->get_expected_min() > 1) + out << " x " << opt->get_expected(); + } + if(!opt->get_envname().empty()) + out << " (" << get_label("Env") << ":" << opt->get_envname() << ")"; + return out.str(); +} + + +////////////////////////////////////////////////// +std::string make_option_desc(const CLI::Option *opt) const override { + std::stringstream out; + + out << opt->get_description(); + + if (opt->get_required()) + { + out << "\nREQUIRED"; + } + + auto range = this->needs.equal_range(opt->get_name()); + std::for_each( + range.first, + range.second, + [&out](const auto &opt_name) + { + out << "\nRequires: " << opt_name.second; + }); + + range = this->needed_by.equal_range(opt->get_name()); + std::for_each( + range.first, + range.second, + [&out](const auto &opt_name) + { + out << "\nRequired by: " << opt_name.second; + }); + + if (!opt->get_excludes().empty()) { + out << "\n" << get_label("Excludes") << ":"; + for(const CLI::Option *op : opt->get_excludes()) + out << " " << op->get_name(); + } + + return out.str() + '\n'; +} + +/// \brief Track dependent options +private: std::unordered_multimap needs; + +/// \brief Track dependent options (inverse) +private: std::unordered_multimap needed_by; +}; + +#endif // GZ_UTILS_CLI_IGNITION_FORMATTER_HPP_ diff --git a/cli/include/ignition/utils/cli/IgnitionFormatter.hpp b/cli/include/ignition/utils/cli/IgnitionFormatter.hpp index 72bc115..90c31a6 100644 --- a/cli/include/ignition/utils/cli/IgnitionFormatter.hpp +++ b/cli/include/ignition/utils/cli/IgnitionFormatter.hpp @@ -15,156 +15,4 @@ * */ -#ifndef IGNITION_UTILS_CLI_IGNITION_FORMATTER_HPP_ -#define IGNITION_UTILS_CLI_IGNITION_FORMATTER_HPP_ - -#include -#include -#include -#include -#include - -#include "ignition/utils/cli/App.hpp" -#include "ignition/utils/cli/FormatterFwd.hpp" - -////////////////////////////////////////////////// -/// \brief CLI Formatter class that implements custom Ignition-specific -/// formatting. -/// -/// More information on custom formatters: -/// https://cliutils.github.io/CLI11/book/chapters/formatting.html -class IgnitionFormatter: public CLI::Formatter { - -////////////////////////////////////////////////// -public: explicit IgnitionFormatter(const CLI::App *_app) -{ - // find needs/needed_by for root options - for (const CLI::Option *appOpt: _app->get_options()) - { - for(const CLI::Option *needsOpt : appOpt->get_needs()) - { - this->needed_by.insert({needsOpt->get_name(), appOpt->get_name()}); - this->needs.insert({appOpt->get_name(), needsOpt->get_name()}); - } - } - - // find needs/needed_by for subcommand (or command group) options - auto subcommands = _app->get_subcommands([](const CLI::App*){return true;}); - for (const CLI::App *sub : subcommands) - { - // find needs/needed_by for root options - for (const CLI::Option *subOpt: sub->get_options()) - { - for(const CLI::Option *needsOpt : subOpt->get_needs()) - { - this->needed_by.insert({needsOpt->get_name(), subOpt->get_name()}); - this->needs.insert({subOpt->get_name(), needsOpt->get_name()}); - } - } - } -} - -////////////////////////////////////////////////// -public: std::string make_option_name( - const CLI::Option *opt, bool is_positional) const override { - if (is_positional) - return opt->get_name(true, false); - - std::stringstream out; - - auto snames = opt->get_snames(); - auto lnames = opt->get_lnames(); - - std::vector sname_list; - std::transform(snames.begin(), snames.end(), std::back_inserter(sname_list), - [](const std::string &sname) { return "-" + sname; }); - - std::vector lname_list; - std::transform(lnames.begin(), lnames.end(), std::back_inserter(lname_list), - [](const std::string &lname) { return "--" + lname; }); - - // If no short options, just use long - if (sname_list.empty()) - { - out << CLI::detail::join(lname_list); - } - else - { - out << CLI::detail::join(sname_list); - // Put lnames in brackets to look like ruby formatting - if (!lnames.empty()) - { - out << " [" << CLI::detail::join(lname_list) << "]"; - } - } - - return out.str(); -} - - -////////////////////////////////////////////////// -public: std::string make_option_opts(const CLI::Option *opt) const override { - std::stringstream out; - - if(opt->get_type_size() != 0) { - if(!opt->get_type_name().empty()) - out << " " << get_label(opt->get_type_name()); - if(!opt->get_default_str().empty()) - out << "=" << opt->get_default_str(); - if(opt->get_expected_max() == CLI::detail::expected_max_vector_size) - out << " ..."; - else if(opt->get_expected_min() > 1) - out << " x " << opt->get_expected(); - } - if(!opt->get_envname().empty()) - out << " (" << get_label("Env") << ":" << opt->get_envname() << ")"; - return out.str(); -} - - -////////////////////////////////////////////////// -std::string make_option_desc(const CLI::Option *opt) const override { - std::stringstream out; - - out << opt->get_description(); - - if (opt->get_required()) - { - out << "\nREQUIRED"; - } - - auto range = this->needs.equal_range(opt->get_name()); - std::for_each( - range.first, - range.second, - [&out](const auto &opt_name) - { - out << "\nRequires: " << opt_name.second; - }); - - range = this->needed_by.equal_range(opt->get_name()); - std::for_each( - range.first, - range.second, - [&out](const auto &opt_name) - { - out << "\nRequired by: " << opt_name.second; - }); - - if (!opt->get_excludes().empty()) { - out << "\n" << get_label("Excludes") << ":"; - for(const CLI::Option *op : opt->get_excludes()) - out << " " << op->get_name(); - } - - return out.str() + '\n'; -} - -/// \brief Track dependent options -private: std::unordered_multimap needs; - -/// \brief Track dependent options (inverse) -private: std::unordered_multimap needed_by; -}; - -#endif // IGNITION_UTILS_CLI_IGNITION_FORMATTER_HPP_ +#include diff --git a/cli/include/vendored-cli/ignition/utils/CMakeLists.txt b/cli/include/vendored-cli/gz/utils/CMakeLists.txt similarity index 100% rename from cli/include/vendored-cli/ignition/utils/CMakeLists.txt rename to cli/include/vendored-cli/gz/utils/CMakeLists.txt diff --git a/cli/include/vendored-cli/gz/utils/cli/App.hpp b/cli/include/vendored-cli/gz/utils/cli/App.hpp new file mode 100644 index 0000000..111a13d --- /dev/null +++ b/cli/include/vendored-cli/gz/utils/cli/App.hpp @@ -0,0 +1,3094 @@ +// Copyright (c) 2017-2020, University of Cincinnati, developed by Henry Schreiner +// under NSF AWARD 1414736 and by the respective contributors. +// All rights reserved. +// +// SPDX-License-Identifier: BSD-3-Clause + +#pragma once + +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include + +// CLI Library includes +#include "ConfigFwd.hpp" +#include "Error.hpp" +#include "FormatterFwd.hpp" +#include "Macros.hpp" +#include "Option.hpp" +#include "Split.hpp" +#include "StringTools.hpp" +#include "TypeTools.hpp" + +namespace CLI { + +#ifndef CLI11_PARSE +#define CLI11_PARSE(app, argc, argv) \ + try { \ + (app).parse((argc), (argv)); \ + } catch(const CLI::ParseError &e) { \ + return (app).exit(e); \ + } +#endif + +namespace detail { +enum class Classifier { NONE, POSITIONAL_MARK, SHORT, LONG, WINDOWS, SUBCOMMAND, SUBCOMMAND_TERMINATOR }; +struct AppFriend; +} // namespace detail + +namespace FailureMessage { +std::string simple(const App *app, const Error &e); +std::string help(const App *app, const Error &e); +} // namespace FailureMessage + +/// enumeration of modes of how to deal with extras in config files + +enum class config_extras_mode : char { error = 0, ignore, capture }; + +class App; + +using App_p = std::shared_ptr; + +class Option_group; +/// Creates a command line program, with very few defaults. +/** To use, create a new `Program()` instance with `argc`, `argv`, and a help description. The templated + * add_option methods make it easy to prepare options. Remember to call `.start` before starting your + * program, so that the options can be evaluated and the help option doesn't accidentally run your program. */ +class App { + friend Option; + friend detail::AppFriend; + + protected: + // This library follows the Google style guide for member names ending in underscores + + /// @name Basics + ///@{ + + /// Subcommand name or program name (from parser if name is empty) + std::string name_{}; + + /// Description of the current program/subcommand + std::string description_{}; + + /// If true, allow extra arguments (ie, don't throw an error). INHERITABLE + bool allow_extras_{false}; + + /// If ignore, allow extra arguments in the ini file (ie, don't throw an error). INHERITABLE + /// if error error on an extra argument, and if capture feed it to the app + config_extras_mode allow_config_extras_{config_extras_mode::ignore}; + + /// If true, return immediately on an unrecognized option (implies allow_extras) INHERITABLE + bool prefix_command_{false}; + + /// If set to true the name was automatically generated from the command line vs a user set name + bool has_automatic_name_{false}; + + /// If set to true the subcommand is required to be processed and used, ignored for main app + bool required_{false}; + + /// If set to true the subcommand is disabled and cannot be used, ignored for main app + bool disabled_{false}; + + /// Flag indicating that the pre_parse_callback has been triggered + bool pre_parse_called_{false}; + + /// Flag indicating that the callback for the subcommand should be executed immediately on parse completion which is + /// before help or ini files are processed. INHERITABLE + bool immediate_callback_{false}; + + /// This is a function that runs prior to the start of parsing + std::function pre_parse_callback_{}; + + /// This is a function that runs when parsing has finished. + std::function parse_complete_callback_{}; + /// This is a function that runs when all processing has completed + std::function final_callback_{}; + + ///@} + /// @name Options + ///@{ + + /// The default values for options, customizable and changeable INHERITABLE + OptionDefaults option_defaults_{}; + + /// The list of options, stored locally + std::vector options_{}; + + ///@} + /// @name Help + ///@{ + + /// Footer to put after all options in the help output INHERITABLE + std::string footer_{}; + + /// This is a function that generates a footer to put after all other options in help output + std::function footer_callback_{}; + + /// A pointer to the help flag if there is one INHERITABLE + Option *help_ptr_{nullptr}; + + /// A pointer to the help all flag if there is one INHERITABLE + Option *help_all_ptr_{nullptr}; + + /// This is the formatter for help printing. Default provided. INHERITABLE (same pointer) + std::shared_ptr formatter_{new Formatter()}; + + /// The error message printing function INHERITABLE + std::function failure_message_{FailureMessage::simple}; + + ///@} + /// @name Parsing + ///@{ + + using missing_t = std::vector>; + + /// Pair of classifier, string for missing options. (extra detail is removed on returning from parse) + /// + /// This is faster and cleaner than storing just a list of strings and reparsing. This may contain the -- separator. + missing_t missing_{}; + + /// This is a list of pointers to options with the original parse order + std::vector