Phase 6 follow-up: today-and-future events, one write per school-wide event
Two corrections found while preparing the first live run: - A scan that runs late in the day still records today's school events; the candidate window now starts at the local start of day instead of "now". - The Compass week calendar is school-wide, so one event is stored against each child. Write it once, with no child prefix in the title, and record the same Home Assistant event id on every child's item. A per-child event still keeps the child's name. Also report pending events as events, not rows, in `school calendar status`. Tests cover the window and the de-duplication. Co-Authored-By: Paperclip <noreply@paperclip.ing>
This commit is contained in:
@@ -188,31 +188,35 @@ func TestSyncDryRunWritesNothing(t *testing.T) {
|
||||
}
|
||||
}
|
||||
|
||||
func TestSyncIgnoresRoutineLessonsAndPastEvents(t *testing.T) {
|
||||
func TestSyncWindowIsTodayAndFuture(t *testing.T) {
|
||||
ctx := context.Background()
|
||||
st, childID := testStore(t)
|
||||
now := time.Now()
|
||||
day := StartOfDay(now)
|
||||
|
||||
seedEvent(t, st, childID, "5 - 11HLEGB5 - D8 - LHT", now.Add(3*time.Hour), "normal", "lesson")
|
||||
seedEvent(t, st, childID, "Year 11 Assembly - HALL", now.Add(-2*time.Hour), "high", "past")
|
||||
seedEvent(t, st, childID, "Yesterday excursion - CITY", day.Add(-time.Hour), "high", "yesterday")
|
||||
seedEvent(t, st, childID, "Year 11 Assembly - HALL", day.Add(time.Minute), "high", "today")
|
||||
|
||||
ha := newFakeHA(t, "calendar.school")
|
||||
c := testClient(t, ha.URL, "calendar.school")
|
||||
|
||||
candidates, err := st.CalendarCandidates(ctx, nil, nil, now, 0)
|
||||
candidates, err := st.CalendarCandidates(ctx, nil, nil, day, 0)
|
||||
if err != nil {
|
||||
t.Fatalf("candidates: %v", err)
|
||||
}
|
||||
// The store selects on importance; the lesson and the past event are
|
||||
// excluded because the parser never marks a lesson high and the past event
|
||||
// is behind `now`.
|
||||
if len(candidates) != 0 {
|
||||
// A routine lesson is never high, and yesterday is behind the window. The
|
||||
// event earlier today stays a candidate: a scan that runs late in the day
|
||||
// must still record today's school events.
|
||||
if len(candidates) != 1 || candidates[0].Title != "Year 11 Assembly - HALL" {
|
||||
t.Fatalf("candidates = %+v", candidates)
|
||||
}
|
||||
res, err := Sync(ctx, st, c, Options{Now: now}, silentLogger())
|
||||
if err != nil {
|
||||
t.Fatalf("Sync: %v", err)
|
||||
}
|
||||
if res.Created != 0 || ha.created() != 0 {
|
||||
t.Fatalf("result = %+v", res)
|
||||
if res.Candidates != 1 || res.Created != 1 || ha.created() != 1 {
|
||||
t.Fatalf("result = %+v (create calls %d)", res, ha.created())
|
||||
}
|
||||
}
|
||||
|
||||
@@ -236,3 +240,53 @@ func TestSyncReportsAReadFailureInsteadOfWritingBlind(t *testing.T) {
|
||||
t.Errorf("error = %q", res.Errors[0])
|
||||
}
|
||||
}
|
||||
|
||||
// TestSyncWritesASchoolWideEventOnce proves the shared Compass week calendar is
|
||||
// not duplicated: one event stored against both children is written once, and
|
||||
// both children's items record the same Home Assistant event id.
|
||||
func TestSyncWritesASchoolWideEventOnce(t *testing.T) {
|
||||
ctx := context.Background()
|
||||
st, harryID := testStore(t)
|
||||
if err := st.SeedChildren(ctx, "Finn"); err != nil {
|
||||
t.Fatalf("seed finn: %v", err)
|
||||
}
|
||||
finn, err := st.ChildByName(ctx, "Finn")
|
||||
if err != nil || finn == nil {
|
||||
t.Fatalf("finn: %v %v", finn, err)
|
||||
}
|
||||
|
||||
due := time.Now().Add(4 * time.Hour).UTC().Truncate(time.Minute)
|
||||
harryItem := seedEvent(t, st, harryID, "Year 11 Assembly - HALL - CMA", due, "high", "assembly")
|
||||
finnItem := seedEvent(t, st, finn.ID, "Year 11 Assembly - HALL - CMA", due, "high", "assembly")
|
||||
|
||||
ha := newFakeHA(t, "calendar.school")
|
||||
c := testClient(t, ha.URL, "calendar.school")
|
||||
|
||||
res, err := Sync(ctx, st, c, Options{Now: time.Now()}, silentLogger())
|
||||
if err != nil {
|
||||
t.Fatalf("Sync: %v", err)
|
||||
}
|
||||
if res.Candidates != 1 || res.Created != 1 {
|
||||
t.Fatalf("result = %+v", res)
|
||||
}
|
||||
if ha.created() != 1 {
|
||||
t.Fatalf("school-wide event was written %d times", ha.created())
|
||||
}
|
||||
// A school-wide event carries just its title, not a child's name.
|
||||
if got := str(ha.lastCreate["summary"]); got != "Year 11 Assembly - HALL - CMA" {
|
||||
t.Errorf("summary = %q", got)
|
||||
}
|
||||
uid := res.Events[0].UID
|
||||
if uid == "" {
|
||||
t.Fatal("event written without a Home Assistant id")
|
||||
}
|
||||
for _, id := range []int64{harryItem.ID, finnItem.ID} {
|
||||
ci, err := st.CalendarItemByID(ctx, id)
|
||||
if err != nil || ci == nil {
|
||||
t.Fatalf("item %d: %v %v", id, ci, err)
|
||||
}
|
||||
if ci.HAEventUID != uid {
|
||||
t.Errorf("item %d uid = %q, want %q", id, ci.HAEventUID, uid)
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
Reference in New Issue
Block a user