feat(todo): a task holds reminders at a time of their own, and keeps the fields it doesn't know
ReminderTime is a day and minutes after midnight, the wall clock without
a zone as TaskDate's; a task's reminderTimes are written as
[{"day", "time"}] and left out where there are none, so older payloads
read with none. The payload's schema stays 1 (as D17's view): what a
newer version wrote at its top that this one doesn't read is kept in
TaskContent.unknown and written back beneath the fields it knows, so a
task changed here keeps it (ADR 0033, D18).
Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
Signed-off-by: Tizian 「ティツィアーン」 <raisondetredev@pm.me>
This commit is contained in:
parent
8565db3d89
commit
3c68a22a5f
1 changed files with 155 additions and 2 deletions
|
|
@ -43,6 +43,10 @@ void main() {
|
|||
priority: Priority.p2,
|
||||
labelIds: const ['l1', 'l2'],
|
||||
reminders: const [30, 0],
|
||||
reminderTimes: const [
|
||||
ReminderTime(Day(2026, 11, 1), 20 * 60),
|
||||
ReminderTime(Day(2026, 11, 2), 6 * 60),
|
||||
],
|
||||
completedAt: DateTime(2026, 11, 2, 7),
|
||||
completions: [DateTime(2026, 10, 19, 7, 5), DateTime(2026, 10, 22, 6)],
|
||||
hideDoneSubTasks: true,
|
||||
|
|
@ -80,6 +84,10 @@ void main() {
|
|||
'priority': 2,
|
||||
'labelIds': ['l1', 'l2'],
|
||||
'reminders': [30, 0],
|
||||
'reminderTimes': [
|
||||
{'day': '2026-11-01', 'time': 1200},
|
||||
{'day': '2026-11-02', 'time': 360},
|
||||
],
|
||||
'completedAt': DateTime(2026, 11, 2, 7).toUtc().toIso8601String(),
|
||||
'completions': [
|
||||
DateTime(2026, 10, 19, 7, 5).toUtc().toIso8601String(),
|
||||
|
|
@ -136,6 +144,16 @@ void main() {
|
|||
'date': {'day': '2026-11-02', 'repeat': repeat},
|
||||
},
|
||||
{...base, 'date': 'today'},
|
||||
for (final at in [
|
||||
{'day': '2026-11-02'},
|
||||
{'day': 'soon', 'time': 60},
|
||||
{'day': '2026-11-02', 'time': 1440},
|
||||
'2026-11-02 13:00',
|
||||
])
|
||||
{
|
||||
...base,
|
||||
'reminderTimes': [at],
|
||||
},
|
||||
]) {
|
||||
expect(decodeTask(json(broken)), isNull, reason: '$broken');
|
||||
}
|
||||
|
|
@ -159,6 +177,55 @@ void main() {
|
|||
}
|
||||
});
|
||||
|
||||
test('of the schema before reminders at a time of their own reads with '
|
||||
'none (D18)', () {
|
||||
final older = decodeTask(
|
||||
json({
|
||||
'schemaVersion': 1,
|
||||
'title': 'A',
|
||||
'projectId': 'p',
|
||||
'date': {'day': '2026-11-02', 'time': 540},
|
||||
'reminders': [30],
|
||||
}),
|
||||
);
|
||||
expect(older?.reminders, [30]);
|
||||
expect(older?.reminderTimes, isEmpty);
|
||||
expect(older?.unknown, isEmpty);
|
||||
});
|
||||
|
||||
test('what a newer version wrote that this one doesn’t know is kept, '
|
||||
'and written back as it was, however the task changes here (D18)', () {
|
||||
final newer = {
|
||||
'schemaVersion': 1,
|
||||
'title': 'A',
|
||||
'projectId': 'p',
|
||||
'location': {'lat': 52.5, 'lon': 13.4},
|
||||
'note': 'kept',
|
||||
};
|
||||
final read = decodeTask(json(newer))!;
|
||||
expect(read.unknown, {
|
||||
'location': {'lat': 52.5, 'lon': 13.4},
|
||||
'note': 'kept',
|
||||
});
|
||||
final renamed = read.copyWith(title: 'B');
|
||||
expect(written(encodeTask(renamed)), {
|
||||
...newer,
|
||||
'title': 'B',
|
||||
'position': 0.0,
|
||||
});
|
||||
expect(decodeTask(encodeTask(renamed)), renamed);
|
||||
});
|
||||
|
||||
test('a field it knows wins over one kept as unknown of the same name', () {
|
||||
const task = TaskContent(
|
||||
title: 'A',
|
||||
projectId: 'p',
|
||||
unknown: {'title': 'stale', 'extra': 1},
|
||||
);
|
||||
expect(written(encodeTask(task))['title'], 'A');
|
||||
expect(written(encodeTask(task))['extra'], 1);
|
||||
});
|
||||
|
||||
test('a priority it doesn’t know is none', () {
|
||||
expect(
|
||||
decodeTask(
|
||||
|
|
|
|||
Loading…
Reference in a new issue