#!/usr/bin/env python
# -*- coding: utf-8 -*-
from django.conf import settings
from django.db import models
from django.utils import timezone
import logging
import traceback
import datetime
from django.utils.functional import cached_property
from talos.services.tag import TagService
from gm_serializer import fields
from gm_types.gaia import VIDEO_CODE_STATUS
from gm_types.mimas import (
    TRACTATE_STATUS,
    TRACTATE_PLATFORM,
    TRACTATE_CONTENT_LEVEL,
)
from data_sync.utils import to_epoch, tzlc
from gm_upload import ImgUrlField, IMG_TYPE
from talos.models.tractate.reply import TractateReply
from talos.models.tractate.favor import TractateFavor
from talos.models.tractate.vote import TractateVote
from talos.services.convert_service.user_convert_service import UserConvertService
from gm_types.gaia import (
    DOCTOR_TYPE,
)
from talos.cache.base import tractate_pv_cache, tractate_favor_count_cache, tractate_vote_count_cache
from utils.rpc import RPCMixin
from qa.models.answer import PageGoodClick


class UserManager(RPCMixin):
    def __call__(self, pk_list):
        """
        :param pk_list:
        :return:
        """
        return self.call_rpc('api/user/get_fundamental_info_by_user_ids', user_ids=pk_list)


class TagManager(RPCMixin):
    def __call__(self, pk_list):
        return self.call_rpc('api/tag/info_by_ids', tag_ids=pk_list)


class Tractate(models.Model):
    """
    短文（新帖子）
    """

    class Meta:
        verbose_name = u'新帖子'
        db_table = 'api_tractate'
        app_label = 'talos'

    # user = fields.MagicField(type=int, manager=UserManager, ttl=60 * 5, db_column="user_id")
    user_id = models.IntegerField(verbose_name="用户id", db_index=True)
    content = models.TextField(verbose_name=u'正文描述', default="")
    is_online = models.BooleanField(verbose_name=u"是否在线", default=True)
    status = models.CharField(verbose_name=u"审核状态", max_length=12,
                              choices=TRACTATE_STATUS, default=TRACTATE_STATUS.UNAUDITED)
    platform = models.CharField(verbose_name=u"数据来源", max_length=12, choices=TRACTATE_PLATFORM)
    content_level = models.CharField(verbose_name=u"内容等级", max_length=12,
                                     choices=TRACTATE_CONTENT_LEVEL, default=TRACTATE_CONTENT_LEVEL.NULL)
    is_excellent = models.BooleanField(verbose_name=u"加精", default=False)
    create_time = models.DateTimeField(verbose_name="创建时间", default=timezone.now)
    last_modified = models.DateTimeField(verbose_name=u'最后修改时间', auto_now=True)
    audit_time = models.DateTimeField(verbose_name=u'最近一次的审核时间', null=True, default=None)
    user_del = models.BooleanField(verbose_name=u"用户是否删除", default=False)

    low_quality = models.IntegerField(default=0, verbose_name=u'低质量反馈数量', blank=True, null=False)
    low_quality_deal = models.BooleanField(default=False, verbose_name=u'低质量反馈是否处理', blank=True)

    platform_id = models.CharField(verbose_name=u"数据来源id", max_length=125, db_index=True)

    @property
    def view_amount(self):
        """
        浏览量
        :return:
        """
        return int(tractate_pv_cache.get(str(self.id)) or 0)

    @property
    def vote_amount(self):
        """
        点赞数
        :return:
        """
        return int(tractate_vote_count_cache.get(str(self.id)) or 0)

    @cached_property
    def reply_amount(self):
        """
        评论数
        :return:
        """
        try:
            extra = TractateExtra.objects.get(tractate_id=self.id)
        except TractateExtra.DoesNotExist:
            return 0
        return extra.reply_count

    @property
    def favor_amount(self):
        """
        收藏数
        :return:
        """

        return int(tractate_favor_count_cache.get(str(self.id)) or 0)

    @property
    def get_tractate_score(self):
        """
        帖子分数
        :return:
        """
        try:
            results = list(
                TractateScore.objects.filter(tractate_id=self.id, type="user").values_list("tractate_score", flat=True))
            _score = results and results[0] or 0
            return _score
        except:
            logging.error("catch exception,err_msg:%s" % traceback.format_exc())
            return 0

    @property
    def get_good_click_tractate_score(self):
        """
        帖子加上godd_click分数
        :return:
        """
        try:
            results = list(
                TractateScore.objects.filter(tractate_id=self.id, type="user").values_list("new_score", flat=True))
            good_click_score = results and results[0] or 0
            return good_click_score
        except:
            logging.error("catch exception,err_msg:%s" % traceback.format_exc())
            return 0

    @property
    def get_goodclick(self):
        try:
            results = list(
                PageGoodClick.objects.filter(business_id=self.id, page_name="user_post_detail")
                    .order_by('-create_date').values_list("avg_new_gc", flat=True))
            good_click_score = results and results[0] or 0
            return good_click_score
        except:
            logging.error("catch exception,err_msg:%s" % traceback.format_exc())
            return 0

    @property
    def get_tag_list(self):
        """
        帖子关联标签
        :return:
        """
        try:
            tag_id_list = list(TractateTag.objects.filter(tractate_id=self.id).values_list("tag_id", flat=True))
            return tag_id_list
        except:
            logging.error("catch exception,err_msg:%s" % traceback.format_exc())
            return []

    @property
    def get_fresh_tag_list(self):
        """
        帖子关联标签
        :return:
        """
        try:
            tag_id_list = list(TractateNewTag.objects.filter(tractate_id=self.id).values_list("tag_id", flat=True))
            return tag_id_list
        except:
            logging.error("catch exception,err_msg:%s" % traceback.format_exc())
            return []

    @property
    def get_is_video(self):
        """
        判断该帖子是否有视频
        :return:
        """
        try:
            bol = TractateVideo.objects.filter(tractate_id=self.id, is_online=True)
            if len(bol):
                return True
            else:
                return False
        except:
            logging.error("catch exception,err_msg:%s" % traceback.format_exc())

    # 获取贴子标签和名称
    def get_tag(self, tag_list):

        try:
            association_tags_id_list = list()

            tag_list = TagService._get_by_ids_from_cache_type(tag_list)

            for item in tag_list:
                association_tags_id_list.append(
                    {"id": item.id, "tag_name": item.name, "recommend_type": item.recommend_type,
                     "tag_type": item.tag_type})

            return association_tags_id_list

        except:
            logging.error("catch exception,err_msg:%s" % traceback.format_exc())
            return []

    def get_tag_names(self, tag_list):

        try:

            association_tags_id_list = list()

            tag_list = TagService._get_by_ids_from_cache_type(tag_list)
            for item in tag_list:
                if int(item.recommend_type) != 5 or int(item.tag_type) != 11:
                    association_tags_id_list.append(item.name)
            return association_tags_id_list

        except:
            logging.error("catch exception,err_msg:%s" % traceback.format_exc())
            return []

    def get_fresh_tag_names(self, new_tag_ids):

        try:
            from talos.services import AgileTagService
            tag_name_list = list()
            agile_tag_info_dic = AgileTagService.get_agile_tags_by_agile_tag_ids(new_tag_ids)
            for item in new_tag_ids:
                data = agile_tag_info_dic.get(item, None)
                tag_name_list.append(data.name)

            return tag_name_list
        except:
            logging.error("catch exception,err_msg:%s" % traceback.format_exc())
            return []

    def get_tag_names_content(self, tag_list):
        try:

            association_tags_id_list = list()

            tag_list = TagService._get_by_ids_from_cache_type(tag_list)

            for item in tag_list:
                if int(item.recommend_type) == 5 and int(item.tag_type) == 11:
                    association_tags_id_list.append(item.name)

            return association_tags_id_list

        except:
            logging.error("catch exception,err_msg:%s" % traceback.format_exc())
            return []

    def get_hot_score(self):
        try:
            now = datetime.datetime.now()
            three_day = datetime.datetime.now() - datetime.timedelta(days=60)
            yesterday_begin_time = "%s-%s-%s 00:00:00" % (three_day.year, three_day.month, three_day.day)
            # 点赞数+3评论数+5收藏数
            # 获得点赞数
            vote_num = TractateVote.objects.filter(tractate_id=self.id, create_time__gte=yesterday_begin_time,
                                                   create_time__lte=now, is_online=True).count()
            # 获得评论数
            reply_num = TractateReply.objects.filter(tractate_id=self.id, create_time__gte=yesterday_begin_time,
                                                     create_time__lte=now, is_online=True).count()
            # 获得收藏数
            click_num = TractateFavor.objects.filter(tractate_id=self.id, create_time__gte=yesterday_begin_time,
                                                     create_time__lte=now, is_deleted=False).count()

            return int(vote_num) + 3 * int(reply_num) + 5 * int(click_num)

        except:
            logging.error("catch exception,err_msg:%s" % traceback.format_exc())
            return 0

    def get_tractate_last_any_reply_time(self):
        try:
            result = TractateReply.objects.filter(tractate_id=self.id).values_list("create_time", flat=True).order_by(
                "-create_time").first()

            return result

        except:
            logging.error("catch exception,err_msg:%s" % traceback.format_exc())
            return ''

    def get_user_info_office(self):
        try:
            is_office = 0
            result = UserConvertService.get_user_info_by_user_id(self.user_id)
            if result.get("doctor_id") and result.get("doctor_type") == DOCTOR_TYPE.OFFICER:
                is_office = 1

            return is_office

        except:
            logging.error("catch exception,err_msg:%s" % traceback.format_exc())
            return 0


class TractateExtra(models.Model):
    """
    新帖子 数据相关
    """

    class Meta:
        verbose_name = u'新帖子其他数据表'
        db_table = 'api_tractate_extra'
        app_label = 'talos'

    tractate_id = models.IntegerField(verbose_name="新帖子id", unique=True)
    reply_count = models.IntegerField(verbose_name="所有评论数", default=0)
    vote_count = models.IntegerField(verbose_name="点赞数", default=0)
    favor_count = models.IntegerField(verbose_name="收藏数", default=0)


class TractateTag(models.Model):
    """
    新帖子 标签相关
    """

    class Meta:
        verbose_name = u'新帖子标签相关'
        db_table = 'api_tractate_tag'
        app_label = 'talos'

    tractate_id = models.IntegerField(verbose_name="新帖子id", db_index=True)
    # tag = fields.MagicField(type=int, manager=TagManager, ttl=60 * 60 * 24, db_column="tag_id")
    tag_id = models.IntegerField(verbose_name="标签id", db_index=True)
    create_time = models.DateTimeField(verbose_name=u'创建时间', default=timezone.now)
    update_time = models.DateTimeField(verbose_name=u'更新时间', auto_now=True)


class TractateNewTag(models.Model):
    """
    新帖子 标签相关
    """

    class Meta:
        verbose_name = u'新帖子标签相关'
        db_table = 'api_tractate_new_tag'
        app_label = 'talos'

    tractate_id = models.IntegerField(verbose_name="新帖子id", db_index=True)
    tag_id = models.IntegerField(verbose_name="新标签id", db_index=True)
    create_time = models.DateTimeField(verbose_name=u'创建时间', default=timezone.now)
    update_time = models.DateTimeField(verbose_name=u'更新时间', auto_now=True)


class TractateImages(models.Model):
    """
    新帖子 图片相关
    默认第一张图片为封面图，故未设置 is_cover 字段
    """

    class Meta:
        verbose_name = u'新帖子图片相关'
        db_table = 'api_tractate_images'
        app_label = 'talos'

    tractate_id = models.IntegerField(verbose_name="新帖子id", db_index=True)
    image_url = ImgUrlField(img_type=IMG_TYPE.TOPICIMAGE, max_length=300, verbose_name=u'图片地址')
    width = models.IntegerField(verbose_name="图片宽度", default=0)
    height = models.IntegerField(verbose_name="图片高度", default=0)
    create_time = models.DateTimeField(verbose_name=u'创建时间', default=timezone.now)
    update_time = models.DateTimeField(verbose_name=u'更新时间', auto_now=True)


class TractateVideo(models.Model):
    """
    新帖子 视频相关
    """

    class Meta:
        verbose_name = u'新帖子视频相关'
        db_table = 'api_tractate_video'
        app_label = 'talos'

    tractate_id = models.IntegerField(verbose_name="新帖子id", db_index=True)
    video_cover_url = models.CharField(max_length=300, verbose_name="视频封面图地址", default="")
    width = models.IntegerField(verbose_name="视频封面图片宽度", default=0)
    height = models.IntegerField(verbose_name="视频封面图片高度", default=0)
    raw_video_url = models.CharField(max_length=128, verbose_name=u"视频地址")
    water_video_url = models.CharField(max_length=128, verbose_name=u"带图片水印的视频地址", default="")
    persistent_id = models.CharField(max_length=128, verbose_name=u'七牛视频处理id', default="")
    persistent_status = models.IntegerField(verbose_name=u"七牛状态",
                                            choices=VIDEO_CODE_STATUS, default=VIDEO_CODE_STATUS.NOSTART)
    is_online = models.BooleanField(verbose_name=u"是否在线", default=True)

    persistent_clip_id = models.CharField(max_length=128, verbose_name=u'七牛视频截取处理id', default="")
    persistent_clip_status = models.IntegerField(default=VIDEO_CODE_STATUS.NOSTART, verbose_name=u"七牛截取状态",
                                                 db_index=True)
    intercept_video_url = models.CharField(max_length=128, verbose_name=u"截取的视频地址", default="")
    webp_url = models.CharField(max_length=128, verbose_name=u'webp图片地址', default="")

    create_time = models.DateTimeField(verbose_name=u'创建时间', default=timezone.now)
    update_time = models.DateTimeField(verbose_name=u'更新时间', auto_now=True)

    @classmethod
    def cleaned_video_url(cls, video_url):
        return video_url.replace(settings.VIDEO_HOST, '')


class TractateScore(models.Model):
    """
    新帖子 排序分
    """

    class Meta:
        verbose_name = u'新帖子视频相关'
        db_table = 'api_tractate_score'
        app_label = 'doris'

    tractate_id = models.IntegerField(verbose_name="新帖子id")
    mean = models.FloatField(verbose_name="平均分")
    tractate_score = models.FloatField(verbose_name="新帖子分数", default=mean)
    new_score = models.FloatField(verbose_name="新帖子分数", default=mean)
    type = models.TextField(verbose_name="新帖子类型")


class TractateRelationService(models.Model):
    """
    帖子关联美购
    """
    class Meta:
        verbose_name = u'帖子关联美购信息'
        db_table = 'api_tractate_service'
        app_label = 'talos'

    tractate_id = models.IntegerField(verbose_name="新帖子id")
    service_id = models.IntegerField(verbose_name="美购id")
    from_order = models.BooleanField(verbose_name="作者是否通过订单关联这个美购", default=False)
