Files
digital-psychology/apps/api/internal/service/companion/service.go
T
jackyu66gitandCursor 89756f65b4 feat(ECR-012–016): 合规、题库、时辰刷新、头像、MBTI OEJTS 与埋点
落地输入合规、探索题库、报告日/时辰刷新、账号头像、OEJTS 量表,并补齐 H5 埋点与 Admin 漏斗;同步 ESS 工件、切至自建 Git、清理 GitHub Actions。

Co-authored-by: Cursor <cursoragent@cursor.com>
2026-08-13 01:27:58 +08:00

68 lines
1.6 KiB
Go

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
}