Commit 0d02b176 authored by David Faure's avatar David Faure
Browse files

Don't turn 20:00-26:00 into 20:00-02:00

Changing the input (like we do when it's invalid) means Osmose users
are told the input is invalid, which isn't the case for 26:00.

Normalize internally for evaluating, but not for toExpression().

This required adding a bool for pointInTime, since begin=10 end=10
can be either 10:00 or 10:00-10:00 (no longer stored as 10:00-34:00).
It makes things pretty straightforward actually: if there was a '-'
in the input, toExpression() outputs a '-', otherwise it doesn't.
parent 6c8e88d2
Pipeline #90734 passed with stage
in 41 seconds
......@@ -93,6 +93,7 @@ private Q_SLOTS:
T("Oct Su[-1]-Dec 31 08:00-18:00");
T("Oct Su[-1]-Dec 31 Su 08:00-18:00");
T("Mar Su[1]-Oct Su[1]: 11:00-20:00; PH 11:00-20:00");
T2("Mo 20:00-26:00", "Mo 20:00-26:00"); // https://github.com/osm-fr/osmose-backend/issues/1344
// from https://wiki.openstreetmap.org/wiki/Key:opening_hours#Simple_examples
T("Mo-Fr 08:00-17:30");
......
......@@ -49,8 +49,9 @@ static QDateTime resolveTime(Time t, QDate date, OpeningHoursPrivate *context)
bool Timespan::isMultiDay(QDate date, OpeningHoursPrivate *context) const
{
const auto beginDt = resolveTime(begin, date, context);
auto endDt = resolveTime(end, date, context);
if (endDt < beginDt || (end.hour >= 24 && begin.hour < 24)) {
const auto realEnd = adjustedEnd();
auto endDt = resolveTime(realEnd, date, context);
if (endDt < beginDt || (realEnd.hour >= 24 && begin.hour < 24)) {
return true;
}
......@@ -60,8 +61,9 @@ bool Timespan::isMultiDay(QDate date, OpeningHoursPrivate *context) const
SelectorResult Timespan::nextInterval(const Interval &interval, const QDateTime &dt, OpeningHoursPrivate *context) const
{
const auto beginDt = resolveTime(begin, dt.date(), context);
auto endDt = resolveTime(end, dt.date(), context);
if (endDt < beginDt || (end.hour >= 24 && begin.hour < 24)) {
const auto realEnd = adjustedEnd();
auto endDt = resolveTime(realEnd, dt.date(), context);
if (endDt < beginDt || (realEnd.hour >= 24 && begin.hour < 24)) {
endDt = endDt.addDays(1);
}
......
......@@ -382,27 +382,23 @@ Timespan:
Time[T] {
$$ = new Timespan;
$$->begin = $$->end = $T;
$$->pointInTime = true;
}
| Time[T] T_PLUS {
$$ = new Timespan;
$$->begin = $$->end = $T;
$$->pointInTime = true;
$$->openEnd = true;
}
| Time[T1] RangeSeparator Time[T2] {
$$ = new Timespan;
$$->begin = $T1;
$$->end = $T2;
if ($$->begin == $$->end) {
$$->end.hour += 24;
}
}
| Time[T1] RangeSeparator Time[T2] T_PLUS {
$$ = new Timespan;
$$->begin = $T1;
$$->end = $T2;
if ($$->begin == $$->end) {
$$->end.hour += 24;
}
$$->openEnd = true;
}
| Time[T1] RangeSeparator Time[T2] T_SLASH T_INTEGER[I] {
......
......@@ -68,7 +68,7 @@ QByteArray Time::toExpression(bool end) const
case Time::NoEvent:
if (hour % 24 == 0 && minute == 0 && end)
return "24:00";
return twoDigits(hour % 24) + ':' + twoDigits(minute);
return twoDigits(hour) + ':' + twoDigits(minute);
case Time::Dawn:
expr = "dawn";
break;
......@@ -84,7 +84,7 @@ QByteArray Time::toExpression(bool end) const
}
const int minutes = hour * 60 + minute;
if (minutes != 0) {
const QByteArray hhmm = twoDigits(qAbs(hour) % 24) + ':' + twoDigits(qAbs(minute));
const QByteArray hhmm = twoDigits(qAbs(hour)) + ':' + twoDigits(qAbs(minute));
expr = '(' + expr + (minutes > 0 ? '+' : '-') + hhmm + ')';
}
return expr;
......@@ -93,7 +93,7 @@ QByteArray Time::toExpression(bool end) const
int Timespan::requiredCapabilities() const
{
int c = Capability::None;
if ((interval > 0 || begin == end) && !openEnd) {
if ((interval > 0 || pointInTime) && !openEnd) {
c |= Capability::PointInTime;
} else {
c |= Capability::Interval;
......@@ -118,7 +118,7 @@ static QByteArray intervalToExpression(int minutes)
QByteArray Timespan::toExpression() const
{
QByteArray expr = begin.toExpression(false);
if (!(end == begin)) {
if (!pointInTime) {
expr += '-' + end.toExpression(true);
}
if (openEnd) {
......@@ -133,6 +133,14 @@ QByteArray Timespan::toExpression() const
return expr;
}
Time Timespan::adjustedEnd() const
{
if (begin == end) {
return { end.event, end.hour + 24, end.minute };
}
return end;
}
bool Timespan::operator==(Timespan &other) const
{
return begin == other.begin &&
......
......@@ -124,12 +124,14 @@ public:
bool isMultiDay(QDate date, OpeningHoursPrivate *context) const;
SelectorResult nextInterval(const Interval &interval, const QDateTime &dt, OpeningHoursPrivate *context) const;
QByteArray toExpression() const;
Time adjustedEnd() const;
bool operator==(Timespan &other) const;
Time begin = { Time::NoEvent, -1, -1 };
Time end = { Time::NoEvent, -1, -1 };
int interval = 0;
bool openEnd = false;
bool pointInTime = false;
std::unique_ptr<Timespan> next;
};
......
Supports Markdown
0% or .
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment