from gm_types.user_hierarchy import EventType
from gm_types.gaia import POINTS_TYPE

from .event_handler import *


class EventDispatcher(object):

    __slots__ = ('event_type', 'trigger_time', 'user_id', 'item_id', 'pre_payment')

    event_handler = {
        EventType.BINDPHONE: BindPhoneEventHandler,
        EventType.COMPLETEPORTRAIT: CompletePortraitEventHandler,
        EventType.CREATEOPERATIONTOPIC: CreateOpTopicEventHandler,
        EventType.CREATENONOPERATIONTOPIC: CreateNonOpTopicEventHandler,
        EventType.DIARYCOMMENTED: DiaryCommentedEventHandler,
        EventType.TOPICCOMMENTED: TopicCommentedEventHandler,
        EventType.OPERATIONDIARYBEEDEXCELENTFROMFINE: OpDiaryBeExFromFine,
        EventType.OPERATIONDIARYBEEDEXCELENTFROMOTHER: OpDiaryBeExFromOther,
        EventType.OPERATIONDIARYBEFINEFROMEX: OpDiaryBeFineFromEx,
        EventType.OPERATIONDIARYBEFINEFROMOTHER: OpDiaryEeFineFromOther,
        EventType.NONOPERATIONDIARYBEEXCELENTFROMFINE: NonOpDiaryBeExFromFine,
        EventType.NONOPERATIONDIARYBEEXCELENTFROMOTHER: NonOpDiaryBeExFromOther,
        EventType.NONOPERATIONDIARYBEFINEFROMEX: NonOpDiaryBeFineFromEx,
        EventType.NONOPERATIONDIARYBEFINEFROMOTHER: NonOpDiaryBeFineFromOther,
        EventType.COMMENTDIARY: CommentDiary,
        EventType.COMMENTTOPIC: CommentTopic,
        EventType.ANSWERRECOMMENDED: AnswerRecommended,
        EventType.QUESTIONRECOMMENDED: QuestionRecommended,
        EventType.TOPICISSPAM: TopicIsSpam,
        EventType.COMMENTISSPAM: CommentIsSpam,
        EventType.BUYSERVICE: BuyService,
        EventType.CHECKIN: CheckinHandler,
    }

    def dispatch(self, event_type, trigger_time, user_id, item_id, pre_payment):
        if event_type not in self.event_handler.keys():
            raise NotImplementedError

        return self.event_handler.get(event_type)(
            event_type,
            trigger_time,
            user_id,
            item_id,
            pre_payment,
        )



class TaskEvent(object):
    # http://wiki.wanmeizhensuo.com/pages/viewpage.action?pageId=4430289
    POINT_KEY, POINT_MULTI_KEY = 'point', 'point_multi'
    GROWTH_KEY, GROWTH_MULTI_KEY = 'growth', 'growth_multi'
    MATCHED_POINT_TYPE = 'point_type'   # 对应的增加美分和成长值的类型
    MATCHED_POINT_TYPE_MULTI, GROWTH_TYPE_MULTI = 'point_type_multi', 'growth_type_multi'  # 对应的增加美分和成长值的类型, 多次
    is_max_limit = True  # 所加的值是否算在每日上限中
    muitl_times = 6

    event_handler = {
        EventType.COMMENT_OTHER: {
            POINT_KEY: 5, GROWTH_KEY: 5,
            MATCHED_POINT_TYPE: POINTS_TYPE.REPLY_OTHERS,

            POINT_MULTI_KEY: 30, GROWTH_MULTI_KEY: 20,
            MATCHED_POINT_TYPE_MULTI: POINTS_TYPE.REPLY_OTHERS_MULTI_TIMES,
            GROWTH_TYPE_MULTI: EventType.COMMENT_OTHER_MULTI_TIMES
        },
        EventType.ANSWER_QUESTION: {
            POINT_KEY: 20, GROWTH_KEY: 30, MATCHED_POINT_TYPE: POINTS_TYPE.ANSWER_QUESTION,
            POINT_MULTI_KEY: 30, GROWTH_MULTI_KEY: 30,
            MATCHED_POINT_TYPE_MULTI: POINTS_TYPE.ANSWER_MULTI_TIMES,
            GROWTH_TYPE_MULTI: EventType.ANSWER_MULTI_TIMES
        },
        # EventType.BUYSERVICE: {POINT_KEY: 30, GROWTH_KEY: 5, MATCHED_POINT_TYPE: POINTS_TYPE.BUY_SERVICE},
        EventType.CREATE_TOPIC: {POINT_KEY: 30, GROWTH_KEY: 50, MATCHED_POINT_TYPE: POINTS_TYPE.PUBLISH_TOPIC},  # 7.6.20 发表术后日记帖，此版本后不区分手术类或非手术类
        EventType.CHECKIN: {POINT_KEY: 300, GROWTH_KEY: 5, MATCHED_POINT_TYPE: POINTS_TYPE.SIGN_IN},  # 签到美分根据天数累计加值，签到这里的值只做展示！！！
        EventType.VOTE_MULTI_TIMES: {POINT_MULTI_KEY: 20, GROWTH_MULTI_KEY: 20, MATCHED_POINT_TYPE: POINTS_TYPE.VOTE_MULTI_TIMES},
        EventType.FOLLOW_MULTI_TIMES: {POINT_MULTI_KEY: 30, GROWTH_MULTI_KEY: 20, MATCHED_POINT_TYPE: POINTS_TYPE.FOLLOW_MULTI_TIMES},
        EventType.DIARY_TOBE_EXCELLENT: {POINT_KEY: 50, GROWTH_KEY: 20, MATCHED_POINT_TYPE: POINTS_TYPE.CHOSEN_DIARY},
        EventType.ANSWERRECOMMENDED: {POINT_KEY: 50, GROWTH_KEY: 30, MATCHED_POINT_TYPE: POINTS_TYPE.ANSWER_RECOMMEND},
        EventType.BINDPHONE: {POINT_KEY: 50, GROWTH_KEY: 10, MATCHED_POINT_TYPE: POINTS_TYPE.BIND_PHONE},
        EventType.COMPLETEPORTRAIT: {POINT_KEY: 25, GROWTH_KEY: 10, MATCHED_POINT_TYPE: POINTS_TYPE.EDIT_PROFILE},
        EventType.UPDATE_NICKNAME: {POINT_KEY: 25, GROWTH_KEY: 10, MATCHED_POINT_TYPE: POINTS_TYPE.UPDATE_NICKNAME},
    }


    def get_reveal_data(self, event_type, operate_count, user_id):
        value_dict = self.event_handler.get(event_type)
        if operate_count == self.muitl_times:
            re_data = {'point_value': value_dict.get(self.POINT_MULTI_KEY), 'growth_value': value_dict.get(self.GROWTH_MULTI_KEY)}
        else:
            re_data = {'point_value': value_dict.get(self.POINT_KEY), 'growth_value': value_dict.get(self.GROWTH_KEY)}

        if event_type == EventType.CHECKIN:
            # 只展示成长值
            re_data = self._checkin_extra_limit(user_id,  event_type, operate_count)

        return re_data

    def get(self, user_id, event_type, operate_count):
        if event_type == EventType.CHECKIN:
            re_data = self._checkin_extra_limit(user_id, event_type, operate_count)
        else:
            value_dict = self.event_handler.get(event_type)
            if operate_count == self.muitl_times:
                if (self.POINT_MULTI_KEY in value_dict) and (self.GROWTH_MULTI_KEY in value_dict):
                    re_data = {'point_value': value_dict.get(self.POINT_MULTI_KEY), 'growth_value': value_dict.get(self.GROWTH_MULTI_KEY)}
                else:
                    re_data = {'point_value': value_dict.get(self.POINT_KEY), 'growth_value': value_dict.get(self.GROWTH_KEY)}
            else:
                re_data = {'point_value': value_dict.get(self.POINT_KEY), 'growth_value': value_dict.get(self.GROWTH_KEY)}

        return re_data

    def get_diff_type_task(self, task_type):
        # 前端区域任务区分展示用
        if task_type == 'uni':
            # 每日任务
            return [EventType.CHECKIN, EventType.COMMENT_OTHER, EventType.ANSWER_QUESTION,
                    EventType.CREATE_TOPIC]
                    # EventType.BUYSERVICE, EventType.CREATE_TOPIC]
        else:
            # 成长任务
            return [EventType.COMMENT_OTHER, EventType.VOTE_MULTI_TIMES,
                    EventType.FOLLOW_MULTI_TIMES, EventType.ANSWER_QUESTION]

    def get_matched_real_type(self, event_type, operate_time):
        type_dict = {'point_type': '', 'growth_type': ''}
        if self.event_handler.get(event_type):
            if operate_time == self.muitl_times:
                if self.MATCHED_POINT_TYPE_MULTI in self.event_handler.get(event_type):
                    type_dict['point_type'] = self.event_handler.get(event_type)[self.MATCHED_POINT_TYPE_MULTI]
                    type_dict['growth_type'] = self.event_handler.get(event_type)[self.GROWTH_TYPE_MULTI]
                else:
                    type_dict['point_type'] = self.event_handler.get(event_type)[self.MATCHED_POINT_TYPE]
                    type_dict['growth_type'] = event_type
            else:
                type_dict['point_type'] = self.event_handler.get(event_type)[self.MATCHED_POINT_TYPE]
                type_dict['growth_type'] = event_type

        return type_dict

    def _checkin_extra_limit(self, user_id, event_type, operate_count):
        self.is_max_limit = False
        if operate_count == 1:
            value_list = [2, 5, 5, 2, 2]
            current_month = datetime.date.today().month
            days = UserEventLog.objects.filter(
                user_id=user_id,
                event_type=event_type,
                trigger_time__month=current_month,
            ).values_list('trigger_time', flat=True)
            days = [d.day for d in days]

            current_day = datetime.date.today().day
            days = [(lambda i: 1 if i in days else 0)(i) for i in range(current_day)]
            _sum = 0

            for i in reversed(days):
                if i == 1:
                    _sum += 1
                else:
                    break

            return {'point_value': 0, 'growth_value': value_list[_sum % 5]}

        return {'point_value': 0, 'growth_value': 0}
