package scheduler import ( "testing" "time" "git.az-it.net/az/morz-infoboard/server/backend/internal/store" ) func ptrTime(t time.Time) *time.Time { return &t } func TestResolveDesiredState(t *testing.T) { // Donnerstag 10:00 UTC thu := time.Date(2026, 3, 26, 10, 0, 0, 0, time.UTC) // Samstag 10:00 UTC sat := time.Date(2026, 3, 28, 10, 0, 0, 0, time.UTC) tests := []struct { name string sc store.ScreenSchedule override *store.GlobalOverride now time.Time wantDesired string wantControl bool }{ { name: "per-screen override aktiv → on", sc: store.ScreenSchedule{OverrideOnUntil: ptrTime(thu.Add(time.Hour))}, now: thu, wantDesired: "on", wantControl: true, }, { name: "per-screen override abgelaufen → fällt durch zu Zeitplan", sc: store.ScreenSchedule{ ScheduleEnabled: true, PowerOnTime: "09:00", PowerOffTime: "17:00", OverrideOnUntil: ptrTime(thu.Add(-time.Hour)), // abgelaufen }, now: thu, wantDesired: "on", wantControl: true, // Zeitplan: 09:00–17:00, jetzt 10:00 }, { name: "per-screen override schlägt globalen Override off", sc: store.ScreenSchedule{OverrideOnUntil: ptrTime(thu.Add(time.Hour))}, override: &store.GlobalOverride{ Type: "off", Until: thu.Add(time.Hour), }, now: thu, wantDesired: "on", wantControl: true, }, { name: "globaler Override off aktiv → off", sc: store.ScreenSchedule{ScheduleEnabled: true, PowerOnTime: "09:00", PowerOffTime: "17:00"}, override: &store.GlobalOverride{ Type: "off", Until: thu.Add(time.Hour), }, now: thu, wantDesired: "off", wantControl: true, }, { name: "globaler Override on aktiv → on", sc: store.ScreenSchedule{}, override: &store.GlobalOverride{ Type: "on", Until: thu.Add(time.Hour), }, now: thu, wantDesired: "on", wantControl: true, }, { name: "globaler Override abgelaufen → fällt durch", sc: store.ScreenSchedule{ScheduleEnabled: true, PowerOnTime: "09:00", PowerOffTime: "17:00"}, override: &store.GlobalOverride{ Type: "off", Until: thu.Add(-time.Hour), // abgelaufen }, now: thu, wantDesired: "on", wantControl: true, }, { name: "Wochenende → off", sc: store.ScreenSchedule{ScheduleEnabled: true, PowerOnTime: "09:00", PowerOffTime: "17:00"}, now: sat, wantDesired: "off", wantControl: true, }, { name: "Wochenende + per-screen override → on", sc: store.ScreenSchedule{OverrideOnUntil: ptrTime(sat.Add(time.Hour))}, now: sat, wantDesired: "on", wantControl: true, }, { name: "normaler Zeitplan: innerhalb → on", sc: store.ScreenSchedule{ScheduleEnabled: true, PowerOnTime: "09:00", PowerOffTime: "17:00"}, now: thu, // 10:00 wantDesired: "on", wantControl: true, }, { name: "normaler Zeitplan: außerhalb → off", sc: store.ScreenSchedule{ScheduleEnabled: true, PowerOnTime: "09:00", PowerOffTime: "17:00"}, now: time.Date(2026, 3, 26, 8, 0, 0, 0, time.UTC), // 08:00 wantDesired: "off", wantControl: true, }, { name: "kein Zeitplan, kein Override → keine Steuerung", sc: store.ScreenSchedule{}, now: thu, wantDesired: "", wantControl: false, }, { name: "Zeitplan deaktiviert → keine Steuerung", sc: store.ScreenSchedule{ScheduleEnabled: false, PowerOnTime: "09:00", PowerOffTime: "17:00"}, now: thu, wantDesired: "", wantControl: false, }, } for _, tt := range tests { t.Run(tt.name, func(t *testing.T) { gotDesired, gotControl := resolveDesiredState(tt.sc, tt.override, tt.now) if gotDesired != tt.wantDesired || gotControl != tt.wantControl { t.Errorf("resolveDesiredState() = (%q, %v), want (%q, %v)", gotDesired, gotControl, tt.wantDesired, tt.wantControl) } }) } }