123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354 |
- package data
- import (
- "context"
- "sort"
- "time"
- "go-common/app/interface/main/creative/model/data"
- "go-common/app/interface/main/creative/model/tag"
- "go-common/library/ecode"
- "go-common/library/log"
- )
- func beginningOfDay(t time.Time) time.Time {
- d := time.Duration(-t.Hour()) * time.Hour
- return t.Truncate(time.Hour).Add(d)
- }
- func getTuesday(now time.Time) time.Time {
- t := beginningOfDay(now)
- weekday := int(t.Weekday())
- if weekday == 0 {
- weekday = 7
- }
- d := time.Duration(-weekday+2) * 24 * time.Hour
- return t.Truncate(time.Hour).Add(d)
- }
- func getSunday(now time.Time) time.Time {
- t := beginningOfDay(now)
- weekday := int(t.Weekday())
- if weekday == 0 {
- return t
- }
- d := time.Duration(7-weekday) * 24 * time.Hour
- return t.Truncate(time.Hour).Add(d)
- }
- func getDate() (sd string) {
- t := time.Now()
- td := getTuesday(t).Add(12 * time.Hour)
- if t.Before(td) { //当前时间在本周二12点之前,则取上上周日的数据,否则取上周日的数据
- sd = getSunday(t.AddDate(0, 0, -14)).Format("20060102")
- } else {
- sd = getSunday(t.AddDate(0, 0, -7)).Format("20060102")
- }
- log.Info("current time (%s) tuesday (%s) sunday (%s)", t.Format("2006-01-02 15:04:05"), td, sd)
- return
- }
- // NewStat get stat from hbase.
- func (s *Service) NewStat(c context.Context, mid int64, ip string) (r *data.Stat, err error) {
- hbaseDate1 := time.Now().AddDate(0, 0, -1).Add(-12 * time.Hour).Format("20060102")
- hbaseDate2 := time.Now().AddDate(0, 0, -2).Add(-12 * time.Hour).Format("20060102")
- var r1, r2 *data.UpBaseStat
- if r1, err = s.data.UpStat(c, mid, hbaseDate1); err != nil || r1 == nil {
- log.Error("s.data.NewStat error(%v) mid(%d) r1(%v) ip(%s)", err, mid, r1, ip)
- err = ecode.CreativeDataErr
- return
- }
- if r2, err = s.data.UpStat(c, mid, hbaseDate2); err != nil || r2 == nil {
- log.Error("s.data.NewStat error(%v) mid(%d) r2(%v) ip(%s)", err, mid, r2, ip)
- err = ecode.CreativeDataErr
- return
- }
- r = &data.Stat{}
- if r1 != nil {
- r.Play = r1.View
- r.Dm = r1.Dm
- r.Comment = r1.Reply
- r.Fan = r1.Fans
- r.Fav = r1.Fav
- r.Like = r1.Like
- r.Share = r1.Share
- r.Coin = r1.Coin
- r.Elec = r1.Elec
- }
- log.Info("s.data.UpStat hbaseDate1(%+v) mid(%d)", r1, mid)
- if r2 != nil {
- r.PlayLast = r2.View
- r.DmLast = r2.Dm
- r.CommentLast = r2.Reply
- r.FanLast = r2.Fans
- r.FavLast = r2.Fav
- r.LikeLast = r2.Like
- r.ShareLast = r2.Share
- r.CoinLast = r2.Coin
- r.ElecLast = r2.Elec
- }
- log.Info("s.data.UpStat hbaseDate2 (%+v) mid(%d)", r2, mid)
- pfl, err := s.acc.ProfileWithStat(c, mid)
- if err != nil {
- return
- }
- r.Fan = int64(pfl.Follower)
- return
- }
- // ViewerBase get up viewer base data.
- func (s *Service) ViewerBase(c context.Context, mid int64) (res map[string]*data.ViewerBase, err error) {
- dt := getDate()
- // try cache
- if res, _ = s.data.ViewerBaseCache(c, mid, dt); res != nil {
- s.pCacheHit.Incr("viewer_base_cache")
- return
- }
- // from data source
- if res, err = s.data.ViewerBase(c, mid, dt); len(res) != 0 {
- s.pCacheMiss.Incr("viewer_base_cache")
- s.data.AddCache(func() {
- s.data.AddViewerBaseCache(context.Background(), mid, dt, res)
- })
- }
- return
- }
- // ViewerArea get up viewer area data.
- func (s *Service) ViewerArea(c context.Context, mid int64) (res map[string]map[string]int64, err error) {
- dt := getDate()
- // try cache
- if res, _ = s.data.ViewerAreaCache(c, mid, dt); res != nil {
- s.pCacheHit.Incr("viewer_area_cache")
- return
- }
- // from data source
- if res, err = s.data.ViewerArea(c, mid, dt); len(res) != 0 {
- s.pCacheMiss.Incr("viewer_area_cache")
- s.data.AddCache(func() {
- s.data.AddViewerAreaCache(context.Background(), mid, dt, res)
- })
- }
- return
- }
- // CacheTrend get trend from mc.
- func (s *Service) CacheTrend(c context.Context, mid int64) (res map[string]*data.ViewerTrend, err error) {
- dt := getDate()
- // try cache
- if res, err = s.data.TrendCache(c, mid, dt); err != nil {
- log.Error("trend s.data.TrendCache err(%v)", err)
- return
- }
- if len(res) != 0 {
- s.pCacheHit.Incr("trend_cache")
- return
- }
- // from data source
- if res, err = s.viewerTrend(c, mid, dt); err != nil {
- return
- }
- s.pCacheMiss.Incr("trend_cache")
- if len(res) != 0 {
- s.data.AddCache(func() {
- s.data.AddTrendCache(context.Background(), mid, dt, res)
- })
- }
- return
- }
- // ViewerTrend get up viewer trend data.
- func (s *Service) viewerTrend(c context.Context, mid int64, dt string) (res map[string]*data.ViewerTrend, err error) {
- ut, err := s.data.ViewerTrend(c, mid, dt)
- if err != nil || ut == nil {
- log.Error("trend s.data.ViewerTrend err(%v)", err)
- return
- }
- f := []string{"fan", "not_fan"}
- skeys := make([]int, 0) //for tag sort.
- tgs := make([]int64, 0) // for request tag name.
- res = make(map[string]*data.ViewerTrend)
- for _, fk := range f {
- td := ut[fk]
- vt := &data.ViewerTrend{}
- if td == nil {
- vt.Ty = nil
- vt.Tag = nil
- res[fk] = vt
- continue
- }
- tg := make(map[int]string) //return tag map to user.
- ty := make(map[string]int64) //return type map to user.
- //deal type for type name.
- if td.Ty != nil {
- for k, v := range td.Ty {
- ke := int16(k)
- if t, ok := s.p.TypeMapCache[ke]; ok {
- ty[t.Name] = v
- }
- }
- } else {
- ty = nil
- }
- // deal tag for tag name.
- if td.Tag != nil {
- for k, v := range td.Tag {
- tgs = append(tgs, v)
- skeys = append(skeys, k)
- }
- var tlist []*tag.Meta
- if tlist, err = s.dtag.TagList(c, tgs); err != nil {
- log.Error("trend s.dtag.TagList err(%v)", err)
- }
- tNameMap := make(map[int64]string)
- for _, v := range tlist {
- tNameMap[v.TagID] = v.TagName
- }
- for _, k := range skeys {
- if _, ok := tNameMap[td.Tag[k]]; ok {
- tg[k] = tNameMap[td.Tag[k]]
- }
- }
- } else {
- tg = nil
- }
- vt.Ty = ty
- vt.Tag = tg
- res[fk] = vt
- }
- return
- }
- // RelationFansDay get up viewer trend data.
- func (s *Service) RelationFansDay(c context.Context, mid int64) (res map[string]map[string]int, err error) {
- dt := time.Now().AddDate(0, 0, -1).Add(-12 * time.Hour).Format("20060102")
- // try cache
- if res, _ = s.data.RelationFansDayCache(c, mid, dt); res != nil {
- s.pCacheHit.Incr("relation_fans_day_cache")
- return
- }
- // from data source
- if res, err = s.data.RelationFansDay(c, mid); len(res) != 0 {
- s.pCacheMiss.Incr("relation_fans_day_cache")
- s.data.AddCache(func() {
- s.data.AddRelationFansDayCache(context.Background(), mid, dt, res)
- })
- }
- return
- }
- // RelationFansHistory get relation history data by month.
- func (s *Service) RelationFansHistory(c context.Context, mid int64, month string) (res map[string]map[string]int, err error) {
- if res, err = s.data.RelationFansHistory(c, mid, month); err != nil {
- log.Error("s.data.RelationFansHistory err(%v)", err)
- }
- return
- }
- // RelationFansMonth get up viewer trend data.
- func (s *Service) RelationFansMonth(c context.Context, mid int64) (res map[string]map[string]int, err error) {
- dt := time.Now().AddDate(0, 0, -1).Add(-12 * time.Hour).Format("20060102")
- // try cache
- if res, _ = s.data.RelationFansMonthCache(c, mid, dt); res != nil {
- s.pCacheHit.Incr("relation_fans_month_cache")
- return
- }
- // from data source
- if res, err = s.data.RelationFansMonth(c, mid); len(res) != 0 {
- s.pCacheMiss.Incr("relation_fans_month_cache")
- s.data.AddCache(func() {
- s.data.AddRelationFansMonthCache(context.Background(), mid, dt, res)
- })
- }
- return
- }
- // ViewerActionHour get up viewer action hour data.
- func (s *Service) ViewerActionHour(c context.Context, mid int64) (res map[string]*data.ViewerActionHour, err error) {
- dt := getDate()
- // try cache
- if res, _ = s.data.ViewerActionHourCache(c, mid, dt); res != nil {
- s.pCacheHit.Incr("viewer_action_hour_cache")
- return
- }
- // from data source
- if res, err = s.data.ViewerActionHour(c, mid, dt); len(res) != 0 {
- s.data.AddCache(func() {
- s.pCacheMiss.Incr("viewer_action_hour_cache")
- s.data.AddViewerActionHourCache(context.Background(), mid, dt, res)
- })
- }
- return
- }
- // UpIncr for Play/Dm/Reply/Fav/Share/Elec/Coin incr.
- func (s *Service) UpIncr(c context.Context, mid int64, ty int8, ip string) (res map[string]*data.ViewerIncr, err error) {
- tyStr, _ := data.IncrTy(ty)
- res = make(map[string]*data.ViewerIncr)
- daytime := time.Now().AddDate(0, 0, -1).Add(-12 * time.Hour)
- datekey := daytime.Format("20060102")
- dt := daytime.Format("20060102")
- vic, _ := s.data.ViewerIncrCache(c, mid, tyStr, dt)
- if vic != nil {
- s.pCacheHit.Incr("viewer_incr_cache")
- res[datekey] = vic
- log.Info("s.data.ViewerIncrCache mid(%d) cache(%v) err(%v)", mid, vic, err)
- return
- }
- incr, _ := s.data.UpIncr(c, mid, ty, dt)
- if incr == nil {
- res[datekey] = nil
- log.Info("s.data.UpIncr mid(%d) incr(%v) err(%v)", incr, err)
- return
- }
- tyRank := make(map[string]int) //return type map to user.
- for k, v := range incr.Rank {
- ke := int16(k)
- if t, ok := s.p.TypeMapCache[ke]; ok {
- tyRank[t.Name] = v
- }
- }
- sortK := make([]int, 0, len(incr.TopAIDList))
- aids := make([]int64, 0, len(incr.TopAIDList))
- for k, v := range incr.TopAIDList {
- aids = append(aids, v)
- sortK = append(sortK, k)
- }
- avm, _ := s.p.BatchArchives(c, mid, aids, ip)
- if len(avm) == 0 {
- return
- }
- sort.Ints(sortK)
- arcs := make([]*data.ArcInc, 0, len(avm))
- for _, k := range sortK {
- if aid, ok := incr.TopAIDList[k]; ok {
- if av, ok := avm[aid]; ok {
- al := &data.ArcInc{}
- al.AID = av.Archive.Aid
- al.PTime = av.Archive.PTime
- al.Title = av.Archive.Title
- al.DayTime = daytime.Unix()
- if _, ok := incr.TopIncrList[k]; ok {
- al.Incr = incr.TopIncrList[k]
- }
- arcs = append(arcs, al)
- }
- }
- }
- vi := &data.ViewerIncr{}
- vi.Arcs = arcs
- vi.TotalIncr = incr.Incr
- if len(tyRank) == 0 {
- vi.TyRank = nil
- } else {
- vi.TyRank = tyRank
- }
- res[datekey] = vi
- // insert cache. NOTE: sync reason?
- s.data.AddCache(func() {
- s.pCacheMiss.Incr("viewer_incr_cache")
- s.data.AddViewerIncrCache(context.Background(), mid, tyStr, dt, vi)
- })
- return
- }
|