package companion import ( "context" "errors" "time" "github.com/google/uuid" "github.com/jackc/pgx/v5" core "github.com/yuxingu/digital-psychology/apps/api/internal/companion" "github.com/yuxingu/digital-psychology/apps/api/internal/model" "github.com/yuxingu/digital-psychology/apps/api/internal/repository" "github.com/yuxingu/digital-psychology/apps/api/internal/textsafe" ) // Service exposes solar terms and moods. type Service struct { Moods *repository.MoodRepo } // TodaySolar returns today's tip. func (s *Service) TodaySolar() core.SolarTerm { return core.TodaySolar(time.Now()) } // SaveMoodInput for POST /moods. type SaveMoodInput struct { Score *int Note *string Day *time.Time } // SaveMood upserts mood for a day (default today). func (s *Service) SaveMood(ctx context.Context, userID uuid.UUID, in SaveMoodInput) (*model.Mood, error) { if in.Score != nil && (*in.Score < 1 || *in.Score > 5) { return nil, errors.New("score must be 1-5") } if in.Note != nil { n, err := textsafe.Check(textsafe.Note, *in.Note) if err != nil { return nil, err } if n == "" { in.Note = nil } else { in.Note = &n } } day := time.Now() if in.Day != nil { day = *in.Day } return s.Moods.UpsertToday(ctx, userID, day, in.Score, in.Note) } // GetTodayMood returns today's mood or nil when none. func (s *Service) GetTodayMood(ctx context.Context, userID uuid.UUID) (*model.Mood, error) { m, err := s.Moods.GetToday(ctx, userID, time.Now()) if err != nil { if errors.Is(err, pgx.ErrNoRows) { return nil, nil } return nil, err } return m, nil }