Files
wx_service/internal/quitcheckin/service/reminder_test.go
T

154 lines
3.6 KiB
Go

package service
import (
"context"
"testing"
"time"
quitmodel "wx_service/internal/quitcheckin/model"
"gorm.io/driver/sqlite"
"gorm.io/gorm"
"gorm.io/gorm/logger"
)
func setupReminderTestDB(t *testing.T) *gorm.DB {
t.Helper()
db, err := gorm.Open(sqlite.Open(":memory:"), &gorm.Config{
Logger: logger.Default.LogMode(logger.Silent),
})
if err != nil {
t.Fatalf("open sqlite: %v", err)
}
if err := db.AutoMigrate(
&quitmodel.Profile{},
&quitmodel.DailyStatus{},
&quitmodel.RelapseEvent{},
&quitmodel.RewardGoal{},
&quitmodel.DreamPreset{},
&quitmodel.SupervisorBinding{},
&quitmodel.SupervisorInvite{},
&quitmodel.SupervisorReminderSetting{},
&quitmodel.SupervisorReminderLog{},
&quitmodel.HPChangeLog{},
); err != nil {
t.Fatalf("auto migrate: %v", err)
}
return db
}
func TestReminderRunCreatesLogAfterNotifyTime(t *testing.T) {
t.Parallel()
db := setupReminderTestDB(t)
svc := NewService(db)
ctx := context.Background()
ownerUID := 4001
supervisorUID := 4002
startDate := time.Date(2026, 4, 10, 0, 0, 0, 0, time.Local)
now := time.Date(2026, 4, 16, 21, 30, 0, 0, time.Local)
// seed quit profile
if err := db.Create(&quitmodel.Profile{
UID: ownerUID,
QuitStartDate: startDate,
PackPriceCent: 2500,
BaselineCigsPerDay: 10,
NotifyTime: "21:00",
ResetRule: "relapse_clears_streak",
}).Error; err != nil {
t.Fatalf("seed profile: %v", err)
}
// seed binding
if err := db.Create(&quitmodel.SupervisorBinding{
OwnerUID: ownerUID,
SupervisorUID: supervisorUID,
Status: "active",
}).Error; err != nil {
t.Fatalf("seed binding: %v", err)
}
// enable reminder
if err := db.Create(&quitmodel.SupervisorReminderSetting{
OwnerUID: ownerUID,
Enabled: true,
NotifyTime: "21:00",
MaxPerDay: 1,
ChannelHint: "stub",
}).Error; err != nil {
t.Fatalf("seed setting: %v", err)
}
res, err := svc.RunMissedCheckinRemindersForSupervisor(ctx, supervisorUID, now)
if err != nil {
t.Fatalf("run: %v", err)
}
if res.Created != 1 {
t.Fatalf("created=%d want=1", res.Created)
}
// run again should be rate-limited
res2, err := svc.RunMissedCheckinRemindersForSupervisor(ctx, supervisorUID, now.Add(10*time.Minute))
if err != nil {
t.Fatalf("run2: %v", err)
}
if res2.Created != 0 {
t.Fatalf("created2=%d want=0", res2.Created)
}
}
func TestReminderRunSkipsBeforeNotifyTime(t *testing.T) {
t.Parallel()
db := setupReminderTestDB(t)
svc := NewService(db)
ctx := context.Background()
ownerUID := 4011
supervisorUID := 4012
startDate := time.Date(2026, 4, 10, 0, 0, 0, 0, time.Local)
now := time.Date(2026, 4, 16, 20, 50, 0, 0, time.Local)
if err := db.Create(&quitmodel.Profile{
UID: ownerUID,
QuitStartDate: startDate,
PackPriceCent: 2500,
BaselineCigsPerDay: 10,
NotifyTime: "21:00",
ResetRule: "relapse_clears_streak",
}).Error; err != nil {
t.Fatalf("seed profile: %v", err)
}
if err := db.Create(&quitmodel.SupervisorBinding{
OwnerUID: ownerUID,
SupervisorUID: supervisorUID,
Status: "active",
}).Error; err != nil {
t.Fatalf("seed binding: %v", err)
}
if err := db.Create(&quitmodel.SupervisorReminderSetting{
OwnerUID: ownerUID,
Enabled: true,
NotifyTime: "21:00",
MaxPerDay: 1,
ChannelHint: "stub",
}).Error; err != nil {
t.Fatalf("seed setting: %v", err)
}
res, err := svc.RunMissedCheckinRemindersForSupervisor(ctx, supervisorUID, now)
if err != nil {
t.Fatalf("run: %v", err)
}
if res.Created != 0 {
t.Fatalf("created=%d want=0", res.Created)
}
}