summaryrefslogtreecommitdiff
path: root/test/test_args.cc
diff options
context:
space:
mode:
authorJoel Klinghed <the_jk@spawned.biz>2021-11-17 22:34:57 +0100
committerJoel Klinghed <the_jk@spawned.biz>2021-11-17 22:34:57 +0100
commit6232d13f5321b87ddf12a1aa36b4545da45f173d (patch)
tree23f3316470a14136debd9d02f9e920ca2b06f4cc /test/test_args.cc
Travel3: Simple image and video display site
Reads the images and videos from filesystem and builds a site in memroy.
Diffstat (limited to 'test/test_args.cc')
-rw-r--r--test/test_args.cc264
1 files changed, 264 insertions, 0 deletions
diff --git a/test/test_args.cc b/test/test_args.cc
new file mode 100644
index 0000000..198323a
--- /dev/null
+++ b/test/test_args.cc
@@ -0,0 +1,264 @@
+#include "common.hh"
+
+#include "args.hh"
+
+#include <gtest/gtest.h>
+#include <memory>
+#include <sstream>
+#include <string>
+#include <vector>
+
+namespace {
+
+bool run(Args* args, std::vector<std::string> const& argv,
+ std::ostream& err, std::vector<std::string>* out) {
+ auto ptrs = std::make_unique<char*[]>(argv.size());
+ for (size_t i = 0; i < argv.size(); ++i)
+ ptrs[i] = const_cast<char*>(argv[i].c_str());
+ return args->run(argv.size(), ptrs.get(),
+ argv.empty() ? "test" : argv[0], err, out);
+}
+
+} // namespace
+
+TEST(args, empty) {
+ auto args = Args::create();
+ std::vector<std::string> argv;
+ std::stringstream err;
+ std::vector<std::string> arguments;
+ EXPECT_TRUE(run(args.get(), argv, err, &arguments));
+ EXPECT_TRUE(err.str().empty());
+ EXPECT_TRUE(arguments.empty());
+}
+
+TEST(args, only_arguments) {
+ auto args = Args::create();
+ auto* help = args->add_option('h', "help", "");
+ auto* config = args->add_option_with_arg('C', "config", "", "");
+ std::vector<std::string> argv{"test", "foo", "bar"};
+ std::stringstream err;
+ std::vector<std::string> arguments;
+ EXPECT_TRUE(run(args.get(), argv, err, &arguments));
+ EXPECT_TRUE(err.str().empty());
+ EXPECT_FALSE(help->is_set());
+ EXPECT_FALSE(config->is_set());
+ ASSERT_EQ(2, arguments.size());
+ EXPECT_EQ("foo", arguments[0]);
+ EXPECT_EQ("bar", arguments[1]);
+}
+
+TEST(args, everything) {
+ auto args = Args::create();
+ auto* help = args->add_option('h', "help", "");
+ auto* config = args->add_option_with_arg('C', "config", "", "");
+ std::vector<std::string> argv{"test", "--help", "-C", "config.txt", "arg"};
+ std::stringstream err;
+ std::vector<std::string> arguments;
+ EXPECT_TRUE(run(args.get(), argv, err, &arguments));
+ EXPECT_TRUE(err.str().empty());
+ EXPECT_TRUE(help->is_set());
+ EXPECT_TRUE(config->is_set());
+ EXPECT_EQ("config.txt", config->arg());
+ ASSERT_EQ(1, arguments.size());
+ EXPECT_EQ("arg", arguments[0]);
+}
+
+TEST(args, option_with_arg_short) {
+ auto args = Args::create();
+ auto* config = args->add_option_with_arg('C', "config", "", "");
+ std::vector<std::string> argv{"test", "-C", "config.txt"};
+ std::stringstream err;
+ std::vector<std::string> arguments;
+ EXPECT_TRUE(run(args.get(), argv, err, &arguments));
+ EXPECT_TRUE(err.str().empty());
+ EXPECT_TRUE(config->is_set());
+ EXPECT_EQ("config.txt", config->arg());
+ EXPECT_TRUE(arguments.empty());
+}
+
+TEST(args, option_with_arg_long_1) {
+ auto args = Args::create();
+ auto* config = args->add_option_with_arg('C', "config", "", "");
+ std::vector<std::string> argv{"test", "--config", "config.txt"};
+ std::stringstream err;
+ std::vector<std::string> arguments;
+ EXPECT_TRUE(run(args.get(), argv, err, &arguments));
+ EXPECT_TRUE(err.str().empty());
+ EXPECT_TRUE(config->is_set());
+ EXPECT_EQ("config.txt", config->arg());
+ EXPECT_TRUE(arguments.empty());
+}
+
+TEST(args, option_with_arg_long_2) {
+ auto args = Args::create();
+ auto* config = args->add_option_with_arg('C', "config", "", "");
+ std::vector<std::string> argv{"test", "--config=config.txt"};
+ std::stringstream err;
+ std::vector<std::string> arguments;
+ EXPECT_TRUE(run(args.get(), argv, err, &arguments));
+ EXPECT_TRUE(err.str().empty());
+ EXPECT_TRUE(config->is_set());
+ EXPECT_EQ("config.txt", config->arg());
+ EXPECT_TRUE(arguments.empty());
+}
+
+TEST(args, multiple_options_with_args) {
+ auto args = Args::create();
+ auto* config = args->add_option_with_arg('C', "config", "", "");
+ auto* pid = args->add_option_with_arg('p', "pid", "", "");
+ std::vector<std::string> argv{"test", "-Cp", "config.txt", "pid"};
+ std::stringstream err;
+ std::vector<std::string> arguments;
+ EXPECT_TRUE(run(args.get(), argv, err, &arguments));
+ EXPECT_TRUE(err.str().empty());
+ EXPECT_TRUE(config->is_set());
+ EXPECT_EQ("config.txt", config->arg());
+ EXPECT_TRUE(pid->is_set());
+ EXPECT_EQ("pid", pid->arg());
+ EXPECT_TRUE(arguments.empty());
+}
+
+TEST(args, end_of_options) {
+ auto args = Args::create();
+ auto* config = args->add_option_with_arg('C', "config", "", "");
+ std::vector<std::string> argv{"test", "--", "--config", "-C"};
+ std::stringstream err;
+ std::vector<std::string> arguments;
+ EXPECT_TRUE(run(args.get(), argv, err, &arguments));
+ EXPECT_TRUE(err.str().empty());
+ EXPECT_FALSE(config->is_set());
+ ASSERT_EQ(2, arguments.size());
+ EXPECT_EQ("--config", arguments[0]);
+ EXPECT_EQ("-C", arguments[1]);
+}
+
+TEST(args, unknown_long_option) {
+ auto args = Args::create();
+ std::vector<std::string> argv{"test", "--help"};
+ std::stringstream err;
+ std::vector<std::string> arguments;
+ EXPECT_FALSE(run(args.get(), argv, err, &arguments));
+ EXPECT_EQ("test: unrecognized option '--help'\n", err.str());
+}
+
+TEST(args, unknown_short_option) {
+ auto args = Args::create();
+ std::vector<std::string> argv{"test", "-H"};
+ std::stringstream err;
+ std::vector<std::string> arguments;
+ EXPECT_FALSE(run(args.get(), argv, err, &arguments));
+ EXPECT_EQ("test: invalid option -- 'H'\n", err.str());
+}
+
+TEST(args, option_not_expecting_argument) {
+ auto args = Args::create();
+ args->add_option('h', "help", "");
+ std::vector<std::string> argv{"test", "--help=foo"};
+ std::stringstream err;
+ std::vector<std::string> arguments;
+ EXPECT_FALSE(run(args.get(), argv, err, &arguments));
+ EXPECT_EQ("test: option '--help' doesn't allow an argument\n", err.str());
+}
+
+TEST(args, short_option_expecting_argument) {
+ auto args = Args::create();
+ args->add_option_with_arg('C', "config", "", "");
+ std::vector<std::string> argv{"test", "-C"};
+ std::stringstream err;
+ std::vector<std::string> arguments;
+ EXPECT_FALSE(run(args.get(), argv, err, &arguments));
+ EXPECT_EQ("test: option requires an argument -- 'C'\n", err.str());
+}
+
+TEST(args, long_option_expecting_argument) {
+ auto args = Args::create();
+ args->add_option_with_arg('C', "config", "", "");
+ std::vector<std::string> argv{"test", "--config"};
+ std::stringstream err;
+ std::vector<std::string> arguments;
+ EXPECT_FALSE(run(args.get(), argv, err, &arguments));
+ EXPECT_EQ("test: option '--config' requires an argument\n", err.str());
+}
+
+TEST(args, descriptions) {
+ auto args = Args::create();
+ args->add_option('h', "help", "display this text and exit.");
+ args->add_option_with_arg(
+ 'C', "config", "use FILE instead of the default", "FILE");
+ std::stringstream out;
+ // if the text fits it is (which is does) 80 is always used.
+ args->print_descriptions(out, 60);
+ EXPECT_EQ(" -h, --help "
+ "display this text and exit.\n"
+ " -C, --config=FILE "
+ "use FILE instead of the default\n",
+ out.str());
+}
+
+TEST(args, descriptions_only_long_or_short) {
+ auto args = Args::create();
+ args->add_option('\0', "help", "display this text and exit.");
+ args->add_option_with_arg(
+ 'C', "", "use FILE instead of the default", "FILE");
+ std::stringstream out;
+ // if the text fits it is (which is does) 80 is always used.
+ args->print_descriptions(out, 60);
+ EXPECT_EQ(" --help "
+ "display this text and exit.\n"
+ " -C FILE "
+ "use FILE instead of the default\n",
+ out.str());
+}
+
+TEST(args, descriptions_wrap) {
+ auto args = Args::create();
+ args->add_option('h', "help", "display this text and exit.");
+ args->add_option_with_arg(
+ 'C', "config", "use FILE instead of the default", "FILE");
+ std::stringstream out;
+ args->print_descriptions(out, 45);
+ EXPECT_EQ(" -h, --help display this text and\n"
+ " exit.\n"
+ " -C, --config=FILE use FILE instead of the\n"
+ " default\n",
+ out.str());
+}
+
+TEST(args, descriptions_multiline_wrap) {
+ auto args = Args::create();
+ args->add_option('h', "help", "display this text and exit."
+ " Or not, I'm not the boss of you."
+ " But you really should be doing something with your life.");
+ std::stringstream out;
+ args->print_descriptions(out, 45);
+ EXPECT_EQ(" -h, --help display this text and exit. Or\n"
+ " not, I'm not the boss of you.\n"
+ " But you really should be doing\n"
+ " something with your life.\n",
+ out.str());
+}
+
+TEST(args, descriptions_wrap_too_long_word) {
+ auto args = Args::create();
+ args->add_option('h', "help",
+ "aaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaa");
+ std::stringstream out;
+ args->print_descriptions(out, 40);
+ EXPECT_EQ(" -h, --help aaaaaaaaaaaaaaaaaaaaaaaaaa\n"
+ " aaaaaaaaaaaaaaaaaaa\n",
+ out.str());
+}
+
+TEST(args, descriptions_fallback) {
+ auto args = Args::create();
+ args->add_option('h', "help", "display this text and exit.");
+ args->add_option_with_arg(
+ 'C', "config", "use FILE instead of the default", "FILE");
+ std::stringstream out;
+ args->print_descriptions(out, 40);
+ EXPECT_EQ("-h, --help\n"
+ "display this text and exit.\n"
+ "-C, --config=FILE\n"
+ "use FILE instead of the default\n",
+ out.str());
+}