441 lines
10 KiB
Go
441 lines
10 KiB
Go
|
package newcomer
|
|||
|
|
|||
|
import (
|
|||
|
"context"
|
|||
|
"time"
|
|||
|
|
|||
|
"go-common/app/interface/main/creative/conf"
|
|||
|
"go-common/app/interface/main/creative/dao/academy"
|
|||
|
"go-common/app/interface/main/creative/dao/account"
|
|||
|
"go-common/app/interface/main/creative/dao/archive"
|
|||
|
"go-common/app/interface/main/creative/dao/article"
|
|||
|
"go-common/app/interface/main/creative/dao/data"
|
|||
|
"go-common/app/interface/main/creative/dao/medal"
|
|||
|
"go-common/app/interface/main/creative/dao/newcomer"
|
|||
|
"go-common/app/interface/main/creative/dao/order"
|
|||
|
"go-common/app/interface/main/creative/dao/watermark"
|
|||
|
ncMDL "go-common/app/interface/main/creative/model/newcomer"
|
|||
|
"go-common/app/interface/main/creative/service"
|
|||
|
"go-common/library/conf/env"
|
|||
|
"go-common/library/log"
|
|||
|
"go-common/library/net/metadata"
|
|||
|
"go-common/library/queue/databus/report"
|
|||
|
"sync"
|
|||
|
)
|
|||
|
|
|||
|
//Service struct
|
|||
|
type Service struct {
|
|||
|
c *conf.Config
|
|||
|
newc *newcomer.Dao
|
|||
|
arc *archive.Dao
|
|||
|
art *article.Dao
|
|||
|
acc *account.Dao
|
|||
|
data *data.Dao
|
|||
|
aca *academy.Dao
|
|||
|
wm *watermark.Dao
|
|||
|
medal *medal.Dao
|
|||
|
order *order.Dao
|
|||
|
//reward
|
|||
|
RewardCache []*ncMDL.Reward
|
|||
|
RewardMapCache map[int64]*ncMDL.Reward
|
|||
|
RewardTyPIDMapCache map[int8]int64 //存储奖励 类型-分类id对应关系
|
|||
|
RewardPIDTyMapCache map[int64]int8 //存储奖励 分类id-类型对应关系
|
|||
|
//task
|
|||
|
TaskCache []*ncMDL.Task
|
|||
|
TaskMapCache map[int64]*ncMDL.Task
|
|||
|
TaskTypeMapCache map[int8][]*ncMDL.Task
|
|||
|
TaskRewardMapCache map[int64][]*ncMDL.TaskRewardEntity
|
|||
|
//taskgroup-reward
|
|||
|
TaskGroupRewardMapCache map[int64][]*ncMDL.TaskGroupReward
|
|||
|
//gift-reward
|
|||
|
GiftRewardMapCache map[int8][]*ncMDL.GiftReward
|
|||
|
//initiative check task
|
|||
|
checkTaskChan chan int64
|
|||
|
checkTaskQueue []int64
|
|||
|
checkTaskDone chan struct{}
|
|||
|
// task-group
|
|||
|
TaskGroupCache []*ncMDL.TaskGroupEntity
|
|||
|
TaskGroupMapCache map[int64]*ncMDL.TaskGroupEntity
|
|||
|
}
|
|||
|
|
|||
|
//New get service
|
|||
|
func New(c *conf.Config, rpcdaos *service.RPCDaos) *Service {
|
|||
|
s := &Service{
|
|||
|
c: c,
|
|||
|
newc: newcomer.New(c),
|
|||
|
arc: rpcdaos.Arc,
|
|||
|
art: rpcdaos.Art,
|
|||
|
acc: rpcdaos.Acc,
|
|||
|
data: data.New(c),
|
|||
|
aca: academy.New(c),
|
|||
|
wm: watermark.New(c),
|
|||
|
medal: medal.New(c),
|
|||
|
order: order.New(c),
|
|||
|
checkTaskChan: make(chan int64, 1000),
|
|||
|
checkTaskQueue: make([]int64, 0, 1000),
|
|||
|
checkTaskDone: make(chan struct{}),
|
|||
|
}
|
|||
|
|
|||
|
s.loadRewards()
|
|||
|
s.loadTasks()
|
|||
|
s.loadTaskGroupRewards()
|
|||
|
s.loadGiftRewards()
|
|||
|
s.loadTaskRewards()
|
|||
|
s.loadTaskGroups()
|
|||
|
go s.loadProc()
|
|||
|
go s.checkTaskStateByMid()
|
|||
|
|
|||
|
return s
|
|||
|
}
|
|||
|
|
|||
|
// Ping service
|
|||
|
func (s *Service) Ping(c context.Context) (err error) {
|
|||
|
if err = s.newc.Ping(c); err != nil {
|
|||
|
log.Error("s.newc.Ping err(%v)", err)
|
|||
|
}
|
|||
|
return
|
|||
|
}
|
|||
|
|
|||
|
// Close dao
|
|||
|
func (s *Service) Close() {
|
|||
|
s.newc.Close()
|
|||
|
s.checkTaskDone <- struct{}{}
|
|||
|
}
|
|||
|
|
|||
|
// loadproc
|
|||
|
func (s *Service) loadProc() {
|
|||
|
for {
|
|||
|
time.Sleep(3 * time.Minute)
|
|||
|
s.loadRewards()
|
|||
|
s.loadTasks()
|
|||
|
s.loadTaskGroupRewards()
|
|||
|
s.loadGiftRewards()
|
|||
|
s.loadTaskRewards()
|
|||
|
s.loadTaskGroups()
|
|||
|
}
|
|||
|
}
|
|||
|
|
|||
|
//load tags
|
|||
|
func (s *Service) loadRewards() {
|
|||
|
res, err := s.newc.Rewards(context.Background())
|
|||
|
if err != nil {
|
|||
|
log.Error("s.newc.Rewards error(%v)", err)
|
|||
|
return
|
|||
|
}
|
|||
|
if len(res) == 0 {
|
|||
|
return
|
|||
|
}
|
|||
|
s.RewardCache = res
|
|||
|
tempRewardMapCache := make(map[int64]*ncMDL.Reward)
|
|||
|
tempRewardTyPIDMapCache := make(map[int8]int64)
|
|||
|
tempRewardPIDTyMapCache := make(map[int64]int8)
|
|||
|
for _, v := range res {
|
|||
|
tempRewardMapCache[v.ID] = v
|
|||
|
if v.ParentID == 0 {
|
|||
|
tempRewardTyPIDMapCache[v.Type] = v.ID
|
|||
|
tempRewardPIDTyMapCache[v.ID] = v.Type
|
|||
|
}
|
|||
|
}
|
|||
|
s.RewardMapCache = tempRewardMapCache
|
|||
|
s.RewardTyPIDMapCache = tempRewardTyPIDMapCache
|
|||
|
s.RewardPIDTyMapCache = tempRewardPIDTyMapCache
|
|||
|
|
|||
|
}
|
|||
|
|
|||
|
//load tags
|
|||
|
func (s *Service) loadTasks() {
|
|||
|
res, err := s.newc.Tasks(context.Background())
|
|||
|
if err != nil {
|
|||
|
log.Error("s.newc.Tasks error(%v)", err)
|
|||
|
return
|
|||
|
}
|
|||
|
if len(res) == 0 {
|
|||
|
return
|
|||
|
}
|
|||
|
s.TaskCache = res
|
|||
|
|
|||
|
temp := make(map[int64]*ncMDL.Task)
|
|||
|
tempMap := make(map[int8][]*ncMDL.Task)
|
|||
|
for _, v := range res {
|
|||
|
temp[v.ID] = v
|
|||
|
switch v.Type {
|
|||
|
case ncMDL.NewcomerTaskType:
|
|||
|
tempMap[ncMDL.NewcomerTaskType] = append(tempMap[ncMDL.NewcomerTaskType], v)
|
|||
|
case ncMDL.AdvancedTaskType:
|
|||
|
tempMap[ncMDL.AdvancedTaskType] = append(tempMap[ncMDL.AdvancedTaskType], v)
|
|||
|
case ncMDL.MonthTaskType:
|
|||
|
tempMap[ncMDL.MonthTaskType] = append(tempMap[ncMDL.MonthTaskType], v)
|
|||
|
}
|
|||
|
}
|
|||
|
s.TaskMapCache = temp
|
|||
|
// 默认分类包含:新手与进阶任务
|
|||
|
tempMap[ncMDL.DefualtTaskType] = append(tempMap[ncMDL.DefualtTaskType], tempMap[ncMDL.NewcomerTaskType]...)
|
|||
|
tempMap[ncMDL.DefualtTaskType] = append(tempMap[ncMDL.DefualtTaskType], tempMap[ncMDL.AdvancedTaskType]...)
|
|||
|
s.TaskTypeMapCache = tempMap
|
|||
|
}
|
|||
|
|
|||
|
// SendRewardReceiveLog for reward receive.
|
|||
|
func (s *Service) SendRewardReceiveLog(c context.Context, mid int64) (err error) {
|
|||
|
if env.DeployEnv == env.DeployEnvDev {
|
|||
|
return
|
|||
|
}
|
|||
|
uInfo := &report.UserInfo{
|
|||
|
Business: 141, //创作中心奖励领取行为日志业务ID
|
|||
|
Mid: mid,
|
|||
|
Type: 0, //0-激励计划奖品领取
|
|||
|
Oid: mid,
|
|||
|
Platform: "激励计划",
|
|||
|
Ctime: time.Now(),
|
|||
|
Action: "incentive_plan_reward_receive", //激励计划奖品领取
|
|||
|
Index: []interface{}{mid},
|
|||
|
IP: metadata.String(c, metadata.RemoteIP),
|
|||
|
}
|
|||
|
report.User(uInfo)
|
|||
|
log.Info("s.SendRewardReceiveLog mid(%d)|uInfo(%+v)", mid, uInfo)
|
|||
|
return
|
|||
|
}
|
|||
|
|
|||
|
// SendPendantReceiveLog for reward receive.
|
|||
|
func (s *Service) SendPendantReceiveLog(c context.Context, mid int64) (err error) {
|
|||
|
if env.DeployEnv == env.DeployEnvDev {
|
|||
|
return
|
|||
|
}
|
|||
|
uInfo := &report.UserInfo{
|
|||
|
Business: 141, //创作中心奖励领取行为日志业务ID
|
|||
|
Mid: mid,
|
|||
|
Type: 1, //1-头像挂件奖品领取
|
|||
|
Oid: mid,
|
|||
|
Platform: "头像挂件",
|
|||
|
Ctime: time.Now(),
|
|||
|
Action: "pendant_reward_receive", //头像挂件奖品领取
|
|||
|
Index: []interface{}{mid},
|
|||
|
IP: metadata.String(c, metadata.RemoteIP),
|
|||
|
}
|
|||
|
report.User(uInfo)
|
|||
|
log.Info("s.SendPendantReceiveLog mid(%d)|uInfo(%+v)", mid, uInfo)
|
|||
|
return
|
|||
|
}
|
|||
|
|
|||
|
//load gift-reward
|
|||
|
func (s *Service) loadGiftRewards() {
|
|||
|
res, err := s.newc.AllGiftRewards(context.Background())
|
|||
|
if err != nil {
|
|||
|
log.Error("s.newc.AllGiftRewards error(%v)", err)
|
|||
|
return
|
|||
|
}
|
|||
|
if len(res) == 0 {
|
|||
|
return
|
|||
|
}
|
|||
|
s.GiftRewardMapCache = res
|
|||
|
}
|
|||
|
|
|||
|
//load taskgroup-reward
|
|||
|
func (s *Service) loadTaskGroupRewards() {
|
|||
|
res, err := s.newc.AllTaskGroupRewards(context.Background())
|
|||
|
if err != nil {
|
|||
|
log.Error("s.newc.AllTaskGroupRewards error(%v)", err)
|
|||
|
return
|
|||
|
}
|
|||
|
if len(res) == 0 {
|
|||
|
return
|
|||
|
}
|
|||
|
s.TaskGroupRewardMapCache = res
|
|||
|
}
|
|||
|
|
|||
|
// checkTaskStateByMid read bindMid to check task state
|
|||
|
func (s *Service) checkTaskStateByMid() {
|
|||
|
ticker := time.NewTicker(time.Millisecond * 100)
|
|||
|
defer ticker.Stop()
|
|||
|
for {
|
|||
|
select {
|
|||
|
case id := <-s.checkTaskChan:
|
|||
|
s.checkTaskQueue = append(s.checkTaskQueue, id)
|
|||
|
case <-ticker.C:
|
|||
|
if len(s.checkTaskQueue) > 0 {
|
|||
|
mid := s.checkTaskQueue[0]
|
|||
|
s.checkTaskQueue = s.checkTaskQueue[1:]
|
|||
|
s.DriveStateByUser(context.Background(), mid)
|
|||
|
}
|
|||
|
case <-s.checkTaskDone:
|
|||
|
log.Info("checkTaskStateByMid close")
|
|||
|
return
|
|||
|
}
|
|||
|
}
|
|||
|
}
|
|||
|
|
|||
|
// putCheckTask put mid to checkTaskQueue
|
|||
|
func (s *Service) putCheckTaskState(mid int64) {
|
|||
|
var wg sync.WaitGroup
|
|||
|
wg.Add(1)
|
|||
|
go func() {
|
|||
|
s.checkTaskChan <- mid
|
|||
|
wg.Done()
|
|||
|
}()
|
|||
|
wg.Wait()
|
|||
|
}
|
|||
|
|
|||
|
//load task-group
|
|||
|
func (s *Service) loadTaskGroups() {
|
|||
|
res, err := s.newc.TaskGroups(context.Background())
|
|||
|
if err != nil {
|
|||
|
log.Error("s.newc.TaskGroups error(%v)", err)
|
|||
|
return
|
|||
|
}
|
|||
|
if len(res) == 0 {
|
|||
|
return
|
|||
|
}
|
|||
|
s.TaskGroupCache = res
|
|||
|
|
|||
|
temp := make(map[int64]*ncMDL.TaskGroupEntity)
|
|||
|
for _, v := range res {
|
|||
|
temp[v.ID] = v
|
|||
|
}
|
|||
|
s.TaskGroupMapCache = temp
|
|||
|
}
|
|||
|
|
|||
|
//load task-group
|
|||
|
func (s *Service) loadTaskRewards() {
|
|||
|
res, err := s.newc.TaskRewards(context.Background())
|
|||
|
if err != nil {
|
|||
|
log.Error("s.newc.TaskRewards error(%v)", err)
|
|||
|
return
|
|||
|
}
|
|||
|
if len(res) == 0 {
|
|||
|
return
|
|||
|
}
|
|||
|
s.TaskRewardMapCache = res
|
|||
|
}
|
|||
|
|
|||
|
// getRewardsByTaskType get rewards by taskType
|
|||
|
func (s *Service) getRewardsByTaskType(taskType int8) (res []*ncMDL.Reward) {
|
|||
|
res = make([]*ncMDL.Reward, 0)
|
|||
|
gifts, ok := s.GiftRewardMapCache[taskType]
|
|||
|
if !ok || len(gifts) == 0 {
|
|||
|
return
|
|||
|
}
|
|||
|
for _, v := range gifts {
|
|||
|
if v == nil {
|
|||
|
continue
|
|||
|
}
|
|||
|
r, ok := s.RewardMapCache[v.RewardID]
|
|||
|
if !ok {
|
|||
|
continue
|
|||
|
}
|
|||
|
|
|||
|
res = append(res, r)
|
|||
|
}
|
|||
|
return
|
|||
|
}
|
|||
|
|
|||
|
// getRewardsByGroupID get reward by groupID
|
|||
|
func (s *Service) getRewardsByGroupID(groupID int64) []*ncMDL.Reward {
|
|||
|
rewards := make([]*ncMDL.Reward, 0)
|
|||
|
rs, ok := s.TaskGroupRewardMapCache[groupID]
|
|||
|
if !ok || len(rs) == 0 {
|
|||
|
log.Error("getRewardsByGroupID reward not exist groupID(%d)", groupID)
|
|||
|
return rewards
|
|||
|
}
|
|||
|
|
|||
|
for _, r := range rs {
|
|||
|
if r == nil {
|
|||
|
continue
|
|||
|
}
|
|||
|
if rr, ok := s.RewardMapCache[r.RewardID]; ok {
|
|||
|
rewards = append(rewards, rr)
|
|||
|
}
|
|||
|
}
|
|||
|
return rewards
|
|||
|
}
|
|||
|
|
|||
|
// getTaskByGroupID get tasks by groupID
|
|||
|
func (s *Service) getTasksByGroupID(groupID int64) (res []*ncMDL.Task) {
|
|||
|
res = make([]*ncMDL.Task, 0)
|
|||
|
for _, task := range s.TaskCache {
|
|||
|
if task == nil {
|
|||
|
continue
|
|||
|
}
|
|||
|
if _, ok := s.TaskGroupMapCache[task.GroupID]; !ok {
|
|||
|
continue
|
|||
|
}
|
|||
|
if task.GroupID == groupID && task.State == ncMDL.NormalState {
|
|||
|
res = append(res, task)
|
|||
|
}
|
|||
|
}
|
|||
|
return
|
|||
|
}
|
|||
|
|
|||
|
// getTaskByType get tasks by type
|
|||
|
func (s *Service) getTasksByType(ty int8) (res []*ncMDL.Task) {
|
|||
|
res = make([]*ncMDL.Task, 0)
|
|||
|
for _, task := range s.TaskCache {
|
|||
|
if task == nil {
|
|||
|
continue
|
|||
|
}
|
|||
|
if _, ok := s.TaskGroupMapCache[task.GroupID]; !ok {
|
|||
|
continue
|
|||
|
}
|
|||
|
if task.Type == ty && task.State == ncMDL.NormalState {
|
|||
|
res = append(res, task)
|
|||
|
}
|
|||
|
}
|
|||
|
return
|
|||
|
}
|
|||
|
|
|||
|
// getTasksInfo get tasks info by type
|
|||
|
func (s *Service) getTasksInfoByType(ts []*ncMDL.Task, ty int8) (res []*ncMDL.Task) {
|
|||
|
tsMap := make(map[int64]*ncMDL.Task)
|
|||
|
for _, t := range ts {
|
|||
|
if t == nil {
|
|||
|
continue
|
|||
|
}
|
|||
|
tsMap[t.ID] = t
|
|||
|
}
|
|||
|
|
|||
|
tasks, ok := s.TaskTypeMapCache[ty]
|
|||
|
if !ok || len(tasks) == 0 {
|
|||
|
return
|
|||
|
}
|
|||
|
|
|||
|
res = make([]*ncMDL.Task, 0, len(tasks))
|
|||
|
for _, v := range tasks {
|
|||
|
if v == nil || v.State != 0 { //-1-删除;0-正常;1-隐藏
|
|||
|
continue
|
|||
|
}
|
|||
|
if _, ok := s.TaskGroupMapCache[v.GroupID]; !ok { // check taskGroup
|
|||
|
continue
|
|||
|
}
|
|||
|
|
|||
|
task := *v
|
|||
|
t, ok := tsMap[v.ID]
|
|||
|
if !ok {
|
|||
|
task.CompleteSate = ncMDL.TaskIncomplete
|
|||
|
} else {
|
|||
|
task.CompleteSate = t.CompleteSate
|
|||
|
}
|
|||
|
res = append(res, &task)
|
|||
|
}
|
|||
|
|
|||
|
return
|
|||
|
}
|
|||
|
|
|||
|
// isHiddenTaskType check taskType is hidden
|
|||
|
func (s *Service) isHiddenTaskType(ty int8) bool {
|
|||
|
tasks, ok := s.TaskTypeMapCache[ty]
|
|||
|
if !ok || len(tasks) == 0 {
|
|||
|
return true
|
|||
|
}
|
|||
|
for _, t := range tasks {
|
|||
|
if t == nil {
|
|||
|
continue
|
|||
|
}
|
|||
|
_, ok := s.TaskGroupMapCache[t.GroupID]
|
|||
|
if !ok {
|
|||
|
continue
|
|||
|
}
|
|||
|
if t.State == 0 {
|
|||
|
return false
|
|||
|
}
|
|||
|
}
|
|||
|
return true
|
|||
|
}
|