管理端按用户查询开启通讯录/相册/媒体拉取;服务端写入路径自动压图;新增 /v1/sign 与 /v1/energy。 Co-authored-by: Cursor <cursoragent@cursor.com>
81 lines
2.2 KiB
Go
81 lines
2.2 KiB
Go
package logic
|
|
|
|
import (
|
|
"context"
|
|
"errors"
|
|
|
|
"spark-server/internal/module/energy/entity"
|
|
"spark-server/internal/pkg/errs"
|
|
"spark-server/internal/pkg/reqctx"
|
|
"spark-server/internal/pkg/validate"
|
|
)
|
|
|
|
// MakeupQuery is eligibility for a past day.
|
|
type MakeupQuery struct {
|
|
CanReSign bool `json:"can_resign"`
|
|
NeedWatchVideoCount int `json:"need_watch_video_count"`
|
|
Date int `json:"date"`
|
|
}
|
|
|
|
// MakeupInput performs makeup for a past day.
|
|
type MakeupInput struct {
|
|
Date int `json:"date" validate:"required,gt=19700101" label:"field.date" errmsg:"required:validate.required;gt:validate.required"`
|
|
}
|
|
|
|
// MakeupCheck returns whether the user may makeup the given YYYYMMDD day.
|
|
func (s *Service) MakeupCheck(ctx context.Context, userID int64, date int) (*MakeupQuery, error) {
|
|
if !s.ready() || userID <= 0 {
|
|
return nil, errs.ErrUnauthorized
|
|
}
|
|
out := &MakeupQuery{Date: date, NeedWatchVideoCount: 0}
|
|
ok, err := s.canMakeup(ctx, userID, date)
|
|
if err != nil {
|
|
return nil, err
|
|
}
|
|
out.CanReSign = ok
|
|
return out, nil
|
|
}
|
|
|
|
// Makeup credits a missed past day (no rewarded-video gate in v1).
|
|
func (s *Service) Makeup(ctx context.Context, userID int64, in *MakeupInput) (*CheckInResult, error) {
|
|
if !s.ready() || userID <= 0 {
|
|
return nil, errs.ErrUnauthorized
|
|
}
|
|
if in == nil {
|
|
return nil, errs.ErrInvalidArgument
|
|
}
|
|
if err := validate.StructLang(reqctx.Lang(ctx), in); err != nil {
|
|
return nil, err
|
|
}
|
|
ok, err := s.canMakeup(ctx, userID, in.Date)
|
|
if err != nil {
|
|
return nil, err
|
|
}
|
|
if !ok {
|
|
return nil, errs.ErrForbidden
|
|
}
|
|
return s.signDay(ctx, userID, in.Date, entity.KindMakeup, "补签奖励")
|
|
}
|
|
|
|
func (s *Service) canMakeup(ctx context.Context, userID int64, date int) (bool, error) {
|
|
if _, ok := parseDayKey(date); !ok {
|
|
return false, errs.ErrInvalidArgument
|
|
}
|
|
today := dayKeyOf(s.now())
|
|
if date >= today {
|
|
return false, nil
|
|
}
|
|
// Only allow makeup within the current calendar month.
|
|
ty, tm := today/10000, (today/100)%100
|
|
dy, dm := date/10000, (date/100)%100
|
|
if ty != dy || tm != dm {
|
|
return false, nil
|
|
}
|
|
if _, err := s.repo.GetSign(ctx, userID, date); err == nil {
|
|
return false, nil
|
|
} else if err != nil && !errors.Is(err, errs.ErrNotFound) {
|
|
return false, err
|
|
}
|
|
return true, nil
|
|
}
|