Rework stop command

- Compute the set difference between the latest interval's tag set and the given tag set
- If no tags given, the difference is set to `{}`
- In case of an empty difference, close the current open interval, apply exclusions and update the database
- In case of a non-empty difference, just add a new open interval and let the overlap resolution do the job...

Signed-off-by: Thomas Lauf <thomas.lauf@tngtech.com>
This commit is contained in:
Thomas Lauf 2020-08-19 14:51:07 +02:00
parent 96aaa71eb4
commit 3feba61459

View file

@ -87,28 +87,20 @@ int CmdStop (
throw format ("The current interval does not have the '{1}' tag.", *diff.begin ()); throw format ("The current interval does not have the '{1}' tag.", *diff.begin ());
} }
else if (!filter.tags ().empty ())
{
std::set_difference(latest.tags ().begin (), latest.tags ().end (),
filter.tags ().begin (), filter.tags ().end (),
std::inserter(diff, diff.begin()));
}
journal.startTransaction (); journal.startTransaction ();
Interval modified {latest}; if (diff.empty ())
// If a stop date is specified (and occupies filter.start) then use
// that instead of the current time.
if (filter.is_started ())
{ {
if (modified.start >= filter.start) Interval modified { latest };
{
throw std::string ("The end of a date range must be after the start.");
}
modified.end = filter.start; modified.end = filter.start;
}
else
{
modified.end = Datetime ();
}
// Close the interval.
database.deleteInterval (latest); database.deleteInterval (latest);
validate (cli, rules, database, modified); validate (cli, rules, database, modified);
@ -121,36 +113,21 @@ int CmdStop (
std::cout << intervalSummarize (database, rules, interval); std::cout << intervalSummarize (database, rules, interval);
} }
} }
// If tags are specified, but are not a full set of tags, remove them
// before closing the interval.
if (! filter.tags ().empty () &&
setIntersect (filter.tags (), latest.tags ()).size () != latest.tags ().size ())
{
for (auto& tag : filter.tags ())
{
if (modified.hasTag (tag))
{
modified.untag (tag);
} }
else else
{ {
throw format ("The current interval does not have the '{1}' tag.", tag); Interval next { filter.start, 0 };
} for (auto& tag : diff)
} {
next.tag (tag);
} }
// Open a new interval with remaining tags, if any. validate (cli, rules, database, next);
if (! filter.tags ().empty () && database.addInterval (next, verbose);
modified.tags ().size () != latest.tags ().size ())
{
modified.start = modified.end;
modified.end = {0};
validate (cli, rules, database, modified);
database.addInterval (modified, verbose);
if (verbose) if (verbose)
{ {
std::cout << '\n' << intervalSummarize (database, rules, modified); std::cout << '\n' << intervalSummarize (database, rules, next);
} }
} }