#! /usr/bin/env python3
# -*- coding:utf-8 -*-


import sys
import os
import time
import datetime
import logging
import traceback


# task任务执行
def injector(level):
    import django
    from django.db import close_old_connections
    from django.db.utils import OperationalError

    sys.path.insert(0, "../..")
    os.environ.setdefault('DJANGO_SETTINGS_MODULE', "apollo.settings")
    django.setup()
    from domain.injector import factory
    from domain.injector.value_object import TaskStatusValue
    from domain.injector.task_queue import TaskQueue
    from injector.models import TaskModel

    logger = logging.getLogger("django")
    queue = TaskQueue.get_queue(level)
    close_old_connections()
    for task_id, status in queue.items():
        # 执行注入流程
        if status in TaskStatusValue.pending():
            logger.info("task_id:{} status:{}".format(task_id, status))
            try:
                task = TaskModel.objects.filter(id=task_id).select_related("partner").first()
                partner = task.partner
                domain = factory.create_by_alias(partner.alias)
                status, flag = domain.injector(task)
                logger.info("执行注入:{} 状态:{}".format(task_id, status))
            except OperationalError:
                logger.error("OperationalError:{}".format("连接mysql报错"))
                break
            except Exception as e:
                logger.error("Exception:{} 任务{}执行报错,之后进行回收删除。".format(e, task_id))
                traceback.print_exc()
                status, flag = 0, 0
            if not flag:
                logger.error("队列中删除任务:{} 状态:{}".format(task_id, status))
                TaskQueue.delete(level, task_id)
            else:
                logger.error("队列中更新任务:{} 状态:{}".format(task_id, status))
                TaskQueue.update(level, task_id, status)

        # 删除回执失败的任务
        if status in TaskStatusValue.failed():
            TaskQueue.delete(level, task_id)


def batch_job(level):
    import django
    from django.db import close_old_connections
    from django.db.utils import OperationalError

    sys.path.insert(0, "../..")
    os.environ.setdefault('DJANGO_SETTINGS_MODULE', "apollo.settings")
    django.setup()
    from domain.injector import factory
    from domain.injector.value_object import TaskStatusValue
    from domain.injector.task_queue import TaskQueue
    from injector.models import TaskModel

    logger = logging.getLogger("django")
    queue = TaskQueue.get_queue(level)
    close_old_connections()
    for task_id, status in queue.items():
        # 执行注入流程
        if status in TaskStatusValue.pending():
            logger.info("task_id:{} status:{}".format(task_id, status))
            try:
                task = TaskModel.objects.filter(id=task_id).select_related("partner").first()
                partner = task.partner
                domain = factory.create_by_alias(partner.alias)
                if level == 20:
                    domain.remove(task)
                elif level == 21:
                    domain.update(task)
                logger.info("执行注入:{} 状态:{}".format(task_id, status))
            except OperationalError:
                logger.error("OperationalError:{}".format("连接mysql报错"))
                break
            except Exception as e:
                logger.error("Exception:{} 任务{}执行报错,之后进行回收删除。".format(e, task_id))
                traceback.print_exc()

            logger.error("队列中删除任务:{} 状态:{}".format(task_id, status))
            TaskQueue.delete(level, task_id)

        # 删除回执失败的任务
        if status in TaskStatusValue.failed():
            TaskQueue.delete(level, task_id)


# 注入循环
def main(tick):
    # 抢片 | 优先 | 普通
    cam_tick = 2
    lv1, lv2, lv3, lv6 = 8, 9, 10, 11
    lv4, lv5 = 20, 21
    while tick >= 1:
        if tick % cam_tick == 0:
            injector(lv1)
            injector(lv2)
            injector(lv3)
            injector(lv6)
            batch_job(lv4)
            batch_job(lv5)
        time.sleep(1)
        tick += 1


if __name__ == '__main__':
    main(1)
