66 lines
2.5 KiB
C++
66 lines
2.5 KiB
C++
#include <doctest/doctest.h>
|
|
|
|
#include "fgc/Paths.h"
|
|
|
|
#include <cstdlib>
|
|
|
|
using namespace fgc;
|
|
|
|
TEST_CASE("expandUser expands ~ and environment variables") {
|
|
setenv("HOME", "/home/tester", 1);
|
|
setenv("FOO", "bar", 1);
|
|
|
|
CHECK(paths::expandUser("~/x") == "/home/tester/x");
|
|
CHECK(paths::expandUser("~") == "/home/tester");
|
|
CHECK(paths::expandUser("$FOO/y") == "bar/y");
|
|
CHECK(paths::expandUser("${FOO}z") == "barz");
|
|
CHECK(paths::expandUser("/abs/path") == "/abs/path");
|
|
CHECK(paths::expandUser("") == "");
|
|
}
|
|
|
|
TEST_CASE("configSearchPaths honours the CLI argument first") {
|
|
auto p = paths::configSearchPaths("/explicit/config.ini");
|
|
REQUIRE(!p.empty());
|
|
CHECK(p.front() == "/explicit/config.ini");
|
|
}
|
|
|
|
TEST_CASE("hardwareSearchPaths looks in the documented order") {
|
|
unsetenv("FGC_HARDWARE");
|
|
auto p = paths::hardwareSearchPaths("", "/opt/fgc/config.ini");
|
|
|
|
auto at = [&](const std::string& s) {
|
|
for (size_t i = 0; i < p.size(); ++i)
|
|
if (p[i] == s) return static_cast<int>(i);
|
|
return -1;
|
|
};
|
|
// /etc is the normal answer on a tower - root-owned, per-device, and OUTSIDE
|
|
// the deploy tree - so it is searched before a checkout-local file.
|
|
REQUIRE(at("/etc/fire_gimbal_control/hardware.ini") >= 0);
|
|
REQUIRE(at("/opt/fgc/hardware.ini") >= 0);
|
|
CHECK(at("/etc/fire_gimbal_control/hardware.ini") < at("/opt/fgc/hardware.ini"));
|
|
|
|
SUBCASE("an explicit argument outranks everything") {
|
|
auto q = paths::hardwareSearchPaths("/tmp/mine.ini", "/opt/fgc/config.ini");
|
|
CHECK(q.front() == "/tmp/mine.ini");
|
|
}
|
|
SUBCASE("the environment outranks /etc but not the argument") {
|
|
setenv("FGC_HARDWARE", "/tmp/env.ini", 1);
|
|
auto q = paths::hardwareSearchPaths("/tmp/cli.ini", "/opt/fgc/config.ini");
|
|
REQUIRE(q.size() >= 2);
|
|
CHECK(q[0] == "/tmp/cli.ini");
|
|
CHECK(q[1] == "/tmp/env.ini");
|
|
unsetenv("FGC_HARDWARE");
|
|
}
|
|
SUBCASE("with no config path there is simply no sibling candidate") {
|
|
auto q = paths::hardwareSearchPaths("", "");
|
|
for (const auto& s : q) CHECK(s.find("/opt/fgc/") == std::string::npos);
|
|
}
|
|
}
|
|
|
|
TEST_CASE("resolveHardwarePath returns nothing when there is no hardware.ini") {
|
|
// Not an error: every existing tower is in this state until it is migrated,
|
|
// and the program must go on reading everything from config.ini.
|
|
unsetenv("FGC_HARDWARE");
|
|
CHECK_FALSE(paths::resolveHardwarePath("/nonexistent/nope.ini", "").has_value());
|
|
}
|