feat(mkdwarfs): support time strings for --set-time

This commit is contained in:
Marcus Holland-Moritz 2024-01-01 13:53:47 +01:00
parent 9e83ebd312
commit d432b4bfa9
3 changed files with 48 additions and 9 deletions

View File

@ -255,10 +255,14 @@ Most other options are concerned with compression tuning:
size of the file system. If the input only has a single group already,
setting this won't make any difference.
- `--set-time=`*time*|`now`:
- `--set-time=now`|*iso-8601-string*|*unix-timestamp*:
Set the time stamps for all entities to this value. This can significantly
reduce the size of the file system. You can pass either a unix time stamp
or `now`.
reduce the size of the file system. You can pass the string `now` for the
current time, an ISO 8601 string, or a unix timestamp (seconds since epoch).
The ISO 8601 string supports a space character instead of the `T` between
date and time and supports dashes as separators. Seconds or the full time
part may be omitted as long as this doesn't turn the whole string into a
single number (i.e. `2008-03-17` is supported, but `20080317` is not).
- `--keep-all-times`:
As of release 0.3.0, by default, `mkdwarfs` will only save the contents of

View File

@ -934,9 +934,15 @@ int mkdwarfs_main(int argc, sys_char** argv, iolayer const& iol) {
} else if (auto val = folly::tryTo<uint64_t>(timestamp)) {
options.timestamp = *val;
} else {
iol.err << "error: argument for option '--set-time' must be numeric or "
"`now`\n";
return 1;
try {
auto tp = parse_time_point(timestamp);
options.timestamp = std::chrono::duration_cast<std::chrono::seconds>(
tp.time_since_epoch())
.count();
} catch (std::exception const& e) {
iol.err << "error: " << e.what() << "\n";
return 1;
}
}
}

View File

@ -111,6 +111,10 @@ class mkdwarfs_tester {
return mkdwarfs_main(args, iol.get());
}
int run(std::initializer_list<std::string> args) {
return run(std::vector<std::string>(args));
}
int run(std::string args) { return run(test::parse_args(args)); }
filesystem_v2 fs_from_data(std::string data) {
@ -126,6 +130,9 @@ class mkdwarfs_tester {
return fs_from_data(std::move(fsimage.value()));
}
std::string out() const { return iol.out(); }
std::string err() const { return iol.err(); }
std::shared_ptr<test::test_file_access> fa;
std::shared_ptr<test::os_access_mock> os;
test::test_iolayer iol;
@ -471,8 +478,8 @@ TEST(mkdwarfs_test, set_time_now) {
auto t1 =
std::chrono::system_clock::to_time_t(std::chrono::system_clock::now());
EXPECT_EQ(reg.size(), 11);
EXPECT_EQ(opt.size(), 1);
ASSERT_EQ(reg.size(), 11);
ASSERT_EQ(opt.size(), 1);
EXPECT_GE(*opt.begin(), t0);
EXPECT_LE(*opt.begin(), t1);
@ -488,7 +495,29 @@ TEST(mkdwarfs_test, set_time_epoch) {
auto opt = get_all_fs_times(*optfs);
EXPECT_EQ(reg.size(), 11);
EXPECT_EQ(opt.size(), 1);
ASSERT_EQ(opt.size(), 1);
EXPECT_EQ(*opt.begin(), 100000001);
}
TEST(mkdwarfs_test, set_time_epoch_string) {
using namespace std::chrono_literals;
using std::chrono::sys_days;
auto optfs = build_with_args({"--set-time", "2020-01-01 01:02"});
ASSERT_TRUE(optfs);
auto opt = get_all_fs_times(*optfs);
ASSERT_EQ(opt.size(), 1);
EXPECT_EQ(*opt.begin(),
std::chrono::duration_cast<std::chrono::seconds>(
(sys_days{2020y / 1 / 1} + 1h + 2min).time_since_epoch())
.count());
}
TEST(mkdwarfs_test, set_time_error) {
auto t = mkdwarfs_tester::create_empty();
EXPECT_NE(0, t.run({"-i", "/", "-o", "-", "--set-time=InVaLiD"}));
EXPECT_THAT(t.err(), ::testing::HasSubstr("cannot parse time point"));
}