Skip to content

Commit

Permalink
C++17 std::filesystem::path support added (#447)
Browse files Browse the repository at this point in the history
  • Loading branch information
nigels-com authored Jan 14, 2025
1 parent f029892 commit 7795b6a
Show file tree
Hide file tree
Showing 2 changed files with 90 additions and 0 deletions.
15 changes: 15 additions & 0 deletions include/cxxopts.hpp
Original file line number Diff line number Diff line change
Expand Up @@ -73,6 +73,12 @@ THE SOFTWARE.
# define CXXOPTS_HAS_OPTIONAL
# endif
# endif
# if __has_include(<filesystem>)
# include <filesystem>
# ifdef __cpp_lib_filesystem
# define CXXOPTS_HAS_FILESYSTEM
# endif
# endif
#endif

#define CXXOPTS_FALLTHROUGH
Expand Down Expand Up @@ -1074,6 +1080,15 @@ parse_value(const std::string& text, std::optional<T>& value)
}
#endif

#ifdef CXXOPTS_HAS_FILESYSTEM
inline
void
parse_value(const std::string& text, std::filesystem::path& value)
{
value.assign(text);
}
#endif

inline
void parse_value(const std::string& text, char& c)
{
Expand Down
75 changes: 75 additions & 0 deletions test/options.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -732,6 +732,27 @@ TEST_CASE("std::optional", "[optional]") {
}
#endif

#ifdef CXXOPTS_HAS_FILESYSTEM
TEST_CASE("std::filesystem::path", "[path]") {
std::filesystem::path path;
cxxopts::Options options("path", " - tests path");
options.add_options()
("path", "a path", cxxopts::value<std::filesystem::path>(path));

Argv av({"path", "--path", "Hello World.txt"});

auto** argv = av.argv();
auto argc = av.argc();

REQUIRE(path.empty());

options.parse(argc, argv);

REQUIRE(!path.empty());
CHECK(path == "Hello World.txt");
}
#endif

TEST_CASE("Unrecognised options", "[options]") {
cxxopts::Options options("unknown_options", " - test unknown options");

Expand Down Expand Up @@ -877,6 +898,60 @@ TEST_CASE("Optional value", "[optional]")
}
#endif

#ifdef CXXOPTS_HAS_OPTIONAL
TEST_CASE("std::filesystem::path value", "[path]")
{
cxxopts::Options options("options", "query as std::fileystem::path");
options.add_options()
("a", "Path", cxxopts::value<std::filesystem::path>())
("b", "Path", cxxopts::value<std::filesystem::path>())
("c", "Path", cxxopts::value<std::filesystem::path>())
("d", "Path", cxxopts::value<std::filesystem::path>())
("e", "Path", cxxopts::value<std::filesystem::path>())
;

SECTION("Available") {
Argv av({
"available",
"-a", "hello.txt",
"-b", "C:\\Users\\JoeCitizen\\hello world.txt",
"-c", "/home/joecitzen/hello world.txt",
"-d", "../world.txt"
});

auto** argv = av.argv();
auto argc = av.argc();

auto result = options.parse(argc, argv);

CHECK(result.as_optional<std::filesystem::path>("a"));
CHECK(result.as_optional<std::filesystem::path>("b"));
CHECK(result.as_optional<std::filesystem::path>("c"));
CHECK(result.as_optional<std::filesystem::path>("d"));
CHECK(!result.as_optional<std::filesystem::path>("e"));

CHECK(result.as_optional<std::filesystem::path>("a") == "hello.txt");
CHECK(result.as_optional<std::filesystem::path>("b") == "C:\\Users\\JoeCitizen\\hello world.txt");
CHECK(result.as_optional<std::filesystem::path>("c") == "/home/joecitzen/hello world.txt");
CHECK(result.as_optional<std::filesystem::path>("d") == "../world.txt");
}

SECTION("Unavailable") {
Argv av({
"unavailable"
});

auto** argv = av.argv();
auto argc = av.argc();

auto result = options.parse(argc, argv);

CHECK(!result.as_optional<std::filesystem::path>("a"));
}

}
#endif

TEST_CASE("Initializer list with group", "[options]") {
cxxopts::Options options("Initializer list group", " - test initializer list with group");

Expand Down

0 comments on commit 7795b6a

Please sign in to comment.