package logic

import (
	"app.yhyue.com/moapp/jybase/redis"
	"context"
	IC "jyBXBase/rpc/init"
	"jyBXBase/rpc/model"
	"log"
	"sort"
	"time"

	"jyBXBase/rpc/internal/svc"
	"jyBXBase/rpc/type/bxbase"

	"github.com/zeromicro/go-zero/core/logx"
)

type NewestBiddingLogic struct {
	ctx    context.Context
	svcCtx *svc.ServiceContext
	logx.Logger
}

func NewNewestBiddingLogic(ctx context.Context, svcCtx *svc.ServiceContext) *NewestBiddingLogic {
	return &NewestBiddingLogic{
		ctx:    ctx,
		svcCtx: svcCtx,
		Logger: logx.WithContext(ctx),
	}
}

type newSet struct {
	status      int
	redisKey    string
	redisStatus int
	query       string
}

// 首页最新招标信息
func (l *NewestBiddingLogic) NewestBidding(in *bxbase.NewestBiddingReq) (*bxbase.NewsetBiddingResp, error) {
	t := time.Now()
	//  status : 0 -不存缓存 1-未登录用户 2-用户自己的key 3-登录用户最新标讯
	r, n := func(in *bxbase.NewestBiddingReq) (*bxbase.NewsetBiddingResp, *newSet) {
		var res = &bxbase.NewsetBiddingResp{
			Data: &bxbase.NewsetBidding{
				List: []*bxbase.NewestList{},
			},
		}
		/* 1. 未登录用户 查未登录缓存 返回  没有缓存 查最新标讯存未登录返回
		   2. 登录用户 查count count=1 查用户缓存   缓存没数据查用户推送
		                     count =0 查最新标讯缓存 缓存没数据查最新标讯存登录缓存 显示引导用户设置关键词
		*/
		// 未登录用户
		if in.UserId == "" {
			// 没数据查最新数据返回
			//未登录用户访问全部信息类型 需要过滤掉 拟建和采购意向
			subtype := `"预告","公告","结果","其它"`
			query := model.NewestQuery("", "", subtype)
			res.Data.ShowTip = 1
			redisKey, _ := model.GetRedisKeyTimeout(model.StatusNoLogin, in.PositionId)
			list, err := model.GetNewsCache(redisKey)
			if err == nil && list != nil && len(list) > 0 { // 缓存有数据可以直接返回
				res.Data.List = list
				res.Data.Count = int64(len(list))
				return res, &newSet{model.StatusCache, redisKey, model.StatusNoLogin, query}
			}
			noLoginTime := time.Now()
			list = model.NewestES(query)
			res.Data.List = list
			res.Data.Count = int64(len(list))
			log.Println("未登录获es取数据耗时：", time.Since(noLoginTime).Seconds())
			return res, &newSet{model.StatusNoLogin, redisKey, model.StatusNoLogin, query}
		}

		// 登录用户
		roleNewestInfo, flag := model.GetRoleNewestInfoService(in.AppId, in.MgoUserId, in.NewUserId, in.AccountId, in.EntId, in.EntUserId, in.PositionType, in.PositionId)
		res.Data.SubFlag = flag
		// 查count判断
		existData := roleNewestInfo.GetPushHistoryCount()
		if existData > 0 { // 存在推送 查推送缓存  缓存没有数据则查 推送数据
			res.Data.ShowTip = 1 // count>0说明存在数据不用显示引导用户设置关键词
			// 查缓存
			redisKey, _ := model.GetRedisKeyTimeout(model.StatusLoginUser, in.PositionId)
			list, err := model.GetNewsCache(redisKey)
			if err == nil && list != nil && len(list) > 0 {
				res.Data.List = list
				res.Data.Count = int64(len(list))
				return res, &newSet{model.StatusCache, redisKey, model.StatusLoginUser, ""}
			}
			//  查推送
			subscribeTime := time.Now()
			list = roleNewestInfo.GetPushHistory()
			log.Println("获取订阅数据耗时：", time.Since(subscribeTime).Seconds())
			if list != nil && len(list) > 0 {
				res.Data.List = list
				res.Data.Count = int64(len(list))
				return res, &newSet{model.StatusLoginUser, redisKey, model.StatusLoginUser, ""}
			}
		}
		// 等0则说明推送里面没有数据 所以去查最新标讯信息缓存 返回  缓存没有则查最新标讯信息 存到缓存里面
		res.Data.ShowTip = 2 // 显示
		//  查最新标讯
		query := model.NewestQuery("", "", "")
		// 查缓存
		redisKey, _ := model.GetRedisKeyTimeout(model.StatusLogin, in.PositionId)
		list, err := model.GetNewsCache(redisKey)
		if err == nil && list != nil && len(list) > 0 {
			res.Data.List = list
			res.Data.Count = int64(len(list))
			return res, &newSet{model.StatusCache, redisKey, model.StatusLogin, query}
		}
		esTime := time.Now()
		list = model.NewestES(query)
		log.Println("获取es数据耗时：", time.Since(esTime).Seconds())
		res.Data.List = list
		res.Data.Count = int64(len(list))
		return res, &newSet{model.StatusLogin, redisKey, model.StatusLogin, query}
	}(in)
	if r.Data.Count == 0 {
		return r, nil
	}
	// status : 0 -拿到的是缓存 不用再处理也不用存缓存 1-存到未登录用户 2-存到用户自己的key 3-存到登录用户最新标讯
	var sortRedis = func(r *bxbase.NewsetBiddingResp, status int, positionId int64) {
		//排序
		sort.Slice(r.Data.List, func(i, j int) bool {
			return r.Data.List[i].PublishTime > r.Data.List[j].PublishTime
		})
		redisKey, timeout := model.GetRedisKeyTimeout(status, positionId)
		go model.PutNewsCache(redisKey, timeout, r.Data.List)
	}
	if n.status != model.StatusCache {
		go sortRedis(r, n.status, in.PositionId)
	} else {
		//获取最新数据 --  延长缓存时间
		go func(n *newSet, in *bxbase.NewestBiddingReq) {
			if n.redisKey != "" {
				//剩余时间 在 IC.C.NewsTimeOut 之内
				if ttl := redis.GetTTL("new", n.redisKey); ttl-IC.C.NewsTimeOut < 0 {
					var res = &bxbase.NewsetBiddingResp{
						Data: &bxbase.NewsetBidding{
							List: []*bxbase.NewestList{},
						},
					}
					switch n.redisStatus {
					case model.StatusLoginUser:
						// 登录用户
						roleNewestInfo, _ := model.GetRoleNewestInfoService(in.AppId, in.MgoUserId, in.NewUserId, in.AccountId, in.EntId, in.EntUserId, in.PositionType, in.PositionId)
						//  查推送
						res.Data.List = roleNewestInfo.GetPushHistory()
					default:
						res.Data.List = model.NewestES(n.query)
					}
					go sortRedis(res, n.redisStatus, in.PositionId)
				}
			}
		}(n, in)
	}

	model.MakeCollection(in.UserId, r.Data.List)
	log.Println("接口耗时：", time.Since(t).Seconds())
	return r, nil
}
