feat(ops): ECR-007 行为分析与 ECR-008 内容运营后台
落地埋点 ingest/数据看板、首页宫格 CMS 与测评上下架;含账号引导、问答流式与免责声明去重,以及 review P1 审计同事务修复。 Co-authored-by: Cursor <cursoragent@cursor.com>
This commit is contained in:
@@ -10,11 +10,14 @@ import (
|
||||
|
||||
"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/service/bootstrap"
|
||||
)
|
||||
|
||||
// Service manages personal archives.
|
||||
type Service struct {
|
||||
Repo *repository.ProfileRepo
|
||||
Repo *repository.ProfileRepo
|
||||
Reports *repository.ReportRepo
|
||||
Bootstrap *bootstrap.Service
|
||||
}
|
||||
|
||||
// CreateInput is validated create payload.
|
||||
@@ -43,7 +46,14 @@ func (s *Service) Create(ctx context.Context, userID uuid.UUID, in CreateInput)
|
||||
name = "TA"
|
||||
}
|
||||
}
|
||||
return s.Repo.Create(ctx, userID, in.Relation, name, in.BirthDate, in.RelationType, in.BirthTime, in.BirthPlace)
|
||||
p, err := s.Repo.Create(ctx, userID, in.Relation, name, in.BirthDate, in.RelationType, in.BirthTime, in.BirthPlace)
|
||||
if err != nil {
|
||||
return nil, err
|
||||
}
|
||||
if s.Bootstrap != nil {
|
||||
s.Bootstrap.GenerateForProfile(ctx, userID, p)
|
||||
}
|
||||
return p, nil
|
||||
}
|
||||
|
||||
// List returns user's profiles.
|
||||
@@ -89,7 +99,31 @@ func (s *Service) Update(ctx context.Context, userID, profileID uuid.UUID, in Up
|
||||
if bp == nil {
|
||||
bp = cur.BirthPlace
|
||||
}
|
||||
return s.Repo.UpdateForUser(ctx, userID, profileID, name, birth, rt, bt, bp, in.GeoLat, in.GeoLng, in.GeoVisible)
|
||||
birthChanged := !in.BirthDate.IsZero() && !sameDay(in.BirthDate, cur.BirthDate)
|
||||
timeChanged := in.BirthTime != nil && strPtr(in.BirthTime) != strPtr(cur.BirthTime)
|
||||
placeChanged := in.BirthPlace != nil && strPtr(in.BirthPlace) != strPtr(cur.BirthPlace)
|
||||
|
||||
p, err := s.Repo.UpdateForUser(ctx, userID, profileID, name, birth, rt, bt, bp, in.GeoLat, in.GeoLng, in.GeoVisible)
|
||||
if err != nil {
|
||||
return nil, err
|
||||
}
|
||||
if s.Bootstrap != nil && (birthChanged || timeChanged || placeChanged) {
|
||||
s.Bootstrap.GenerateForProfile(ctx, userID, p)
|
||||
}
|
||||
return p, nil
|
||||
}
|
||||
|
||||
func sameDay(a, b time.Time) bool {
|
||||
ay, am, ad := a.Date()
|
||||
by, bm, bd := b.Date()
|
||||
return ay == by && am == bm && ad == bd
|
||||
}
|
||||
|
||||
func strPtr(p *string) string {
|
||||
if p == nil {
|
||||
return ""
|
||||
}
|
||||
return *p
|
||||
}
|
||||
|
||||
// Delete soft-deletes an owned profile.
|
||||
@@ -97,5 +131,8 @@ func (s *Service) Delete(ctx context.Context, userID, profileID uuid.UUID) error
|
||||
if _, err := s.Repo.GetForUser(ctx, userID, profileID); err != nil {
|
||||
return errors.New("profile not found")
|
||||
}
|
||||
if s.Reports != nil {
|
||||
_ = s.Reports.SoftDeleteForProfile(ctx, userID, profileID)
|
||||
}
|
||||
return s.Repo.SoftDeleteForUser(ctx, userID, profileID)
|
||||
}
|
||||
|
||||
Reference in New Issue
Block a user