#!/usr/bin/env python
# -*- coding: utf-8 -*-
# @Time    : 2020-03-07 10:51
# @Author  : Lemon
# @File    : views.py
# @Software: PyCharm
import datetime
import json

from apscheduler.schedulers.tornado import TornadoScheduler

import tornado.web
import hashlib

from __sdk import Yes, database

later_seconds = lambda s: datetime.datetime.now() + datetime.timedelta(seconds=s)


class BaseHandler(tornado.web.RequestHandler):
    def write_json(self, data):
        self.write(json.dumps(data, ensure_ascii=False))


class IndexHandler(tornado.web.RequestHandler):

    def print(self):
        print('ok')
        return 'ok'

    def get(self):
        self.write("test")


class UploadHandler(tornado.web.RequestHandler):
    def __init__(self, application, request, **kwargs):
        super().__init__(application, request, **kwargs)
        from apscheduler.executors.pool import ThreadPoolExecutor
        from apscheduler import events
        executors = {
            'default': ThreadPoolExecutor(20),
        }
        job_defaults = {
            'coalesce': False,
            'max_instances': 3
        }
        self.scheduler = TornadoScheduler(executors=executors, job_defaults=job_defaults)
        self.scheduler.add_listener(self.executed, events.EVENT_JOB_EXECUTED)
        self.scheduler.start()

    def md5(self, byte):
        m = hashlib.md5()
        m.update(byte)
        return m.hexdigest()

    def post(self):
        if self.request.files:
            file = self.request.files['file'][0]
        else:
            return self.write('请上传文件')

        remark = str(self.request.body_arguments['remark'][0], 'utf-8')
        file_md5 = self.md5(file.body)
        file_name = file.filename
        table_prefix = file_md5[:16]
        need_wxid = self.request.body_arguments['need_wxid'][0]
        res = Yes.Create('cj_table_config', {
            'file_md5': file_md5,
            'file_name': file_name,
            'remark': remark,
            'table_prefix': table_prefix,
            'need_wxid': int(need_wxid)
        })
        self.write(res['data'])
        try:
            assert res['ret'] == 200 and res['data']['err_code'] == 0
            id = res['data']['id']
            self.scheduler.add_job(database.insert_data,
                                   id=f'upload_{id}',
                                   args=[id, file.body, table_prefix, int(need_wxid)],
                                   next_run_time=later_seconds(3))
        except:
            print(res)

    def executed(self, event):
        text, id = event.job_id.split('_')
        if text == 'upload':
            print('继续完成上传后的操作:', id)


class QueryHandler(BaseHandler):

    def get(self, *args, **kwargs):
        self.write(database.query_list())

    def post(self, *args, **kwargs):
        params = json.loads(self.request.body)
        id = params['id']
        msg = database.query_id_progress(id=id)
        self.write_json({'code': 200, "msg": msg})


class UpdateHandler(BaseHandler):

    def post(self, *args, **kwargs):
        params = json.loads(self.request.body)
        id = params['id']
        info = database.get_current_info(id)
        if info and '完成' in info['status']:
            current_code = int(info['code'])
            if current_code == -1:
                self.write_json({'code': 201, "msg": 'id找不到'})
            elif current_code == 1:
                self.write_json({'code': 201, "msg": '已经在任务清单了'})
            elif current_code == 2:
                self.write_json({'code': 201, "msg": '该任务已经完成了'})
            elif current_code == 0:
                database.update_code(id, 1)
                self.write_json({'code': 200, "msg": '加入成功,请等待结果'})
            else:
                self.write_json({'code': 201, "msg": f'未知状态:{current_code},联系开发人员'})
        else:
            self.write_json({'code': 201, "msg": '状态不对,无法加入'})


class DownloadHandler(BaseHandler):
    def get(self, *args, **kwargs):
        id = self.get_argument('id')
        table_prefix = database.get_table_prefix(id)
        io = database.get_table_data(id)
        if io:
            self.set_header('Content-Type', 'application/octet-stream')
            self.set_header('Content-Disposition', 'attachment; filename=%s.xls' % table_prefix)
            while True:
                byte = io.read(1024)
                if not byte:
                    break
                self.write(byte)
            self.finish()
        else:
            self.write('<script>alert("找不到数据");</script>')


class DeleteHandler(BaseHandler):
    def post(self, *args, **kwargs):
        params = json.loads(self.request.body)
        id = params['id']
        password = params['password']
        if password == '[email protected]':
            database.delete_from_id(id)
            self.write_json({'code': 200, 'msg': '删除成功'})
        else:
            self.write_json({'code': 201, 'msg': '拒绝操作'})