#!/usr/bin/env python3
# -*- coding: utf-8 -*-
import logging
import time

from django.db import transaction
from django.views import View

from Model.models import CompanyModel, UserModel, SerialNumberModel, CompanySerialModel
from Object.uidManageResponseObject import uidManageResponseObject
from Object.TokenObject import TokenObject
from Service.CommonService import CommonService
from Service.ModelService import ModelService


class CompanyView(View):

    def get(self, request, *arg, **kwargs):
        request.encoding = 'utf-8'
        request_dict = request.GET
        operation = kwargs.get('operation', None)
        return self.validate(request_dict, operation)

    def post(self, request, *arg, **kwargs):
        request.encoding = 'utf-8'
        request_dict = request.POST
        operation = kwargs.get('operation', None)
        return self.validate(request_dict, operation)

    def validate(self, request_dict, operation):

        token = TokenObject(request_dict.get('token', None))

        response = uidManageResponseObject()

        if token.code != 0:
            return response.json(token.code)

        if operation == 'create':
            return self.do_create(token.userID, request_dict, response)
        elif operation == 'update':
            return self.do_update(token.userID, request_dict, response)
        elif operation == 'delete':
            return self.do_delete(token.userID, request_dict, response)
        elif operation == 'list':
            return self.do_list(token.userID, request_dict, response)
        elif operation == 'createSerial':
            return self.do_create_serial(token.userID, request_dict, response)
        else:
            return response.json(404)

    def do_create(self, userID, request_dict, response):

        # perm = ModelService.check_perm_uid_manage(userID, 0)
        # if not perm:
        #     return response.json(309)

        name = request_dict.get('name', None)
        mark = request_dict.get('mark', None)

        if name and mark:
            now_time = int(time.time())
            company_qs = CompanyModel.objects.filter(mark=mark)
            if company_qs.exists():
                return response.json(174)

            secret = self.create_secret(mark)
            print(secret)

            company = CompanyModel(
                name=name,
                mark=mark,
                secret=secret,
                quantity=0,
                add_time=now_time,
                update_time=now_time
            )
            company.save()
            return response.json(0)
        else:
            return response.json(444)

    def do_update(self, userID, request_dict, response):

        # perm = ModelService.check_perm_uid_manage(userID, 0)
        # if not perm:
        #     return response.json(309)

        id = request_dict.get('id', None)

        if id:
            name = request_dict.get('name', None)
            quantity = request_dict.get('quantity', None)

            update = {}

            if name:
                update['name'] = name

            if quantity:
                update['quantity'] = quantity

            company_qs = CompanyModel.objects.filter(id=id)
            if company_qs.exists():
                company_qs.update(**update)
                return response.json(0)
            else:
                return response.json(173)

        else:
            return response.json(444)

    def do_delete(self, userID, request_dict, response):

        # perm = ModelService.check_perm_uid_manage(userID, 0)
        # if not perm:
        #     return response.json(309)

        id = request_dict.get('id', None)

        if id:
            CompanyModel.objects.filter(id=id).delete()
            return response.json(0)
        else:
            return response.json(444)

    @transaction.atomic
    def do_create_serial(self, userID, request_dict, response):
        # perm = ModelService.check_perm_uid_manage(userID, 0)
        # if not perm:
        #     return response.json(309)

        id = request_dict.get('id', None)
        quantity = request_dict.get('quantity', None)
        p2p = request_dict.get('p2p', None)
        if id and quantity:
            company_qs = CompanyModel.objects.filter(id=id)

            if not company_qs.exists():
                return response.json(444)
            p2p_sum_Serial = SerialNumberModel.objects.filter(p2p=p2p).count()
            p2p_sum_Serial_company = CompanySerialModel.objects.filter(p2p=p2p).count()
            p2p_sum_bind = p2p_sum_Serial - p2p_sum_Serial_company
            if int(quantity) > int(p2p_sum_bind):
                return response.json(10041)

            savePoint = transaction.savepoint()
            try:
                try:

                    company = company_qs[0]
                    # start = company.quantity
                    # start = int(start)
                    # end = start + int(quantity)
                    # serial_qs = SerialNumberModel.objects.filter(p2p=p2p)[start:end]
                    start_1 = p2p_sum_Serial_company
                    end_1 = int(start_1) + int(quantity)
                    serial_qs = SerialNumberModel.objects.filter(p2p=p2p)[start_1:end_1]
                    if serial_qs.exists():
                        data = []
                        now_time = int(time.time())
                        for item in serial_qs:
                            data.append(CompanySerialModel(
                                company_id=company.id,
                                serial_number=item.serial_number,
                                add_time=now_time,
                                update_time=now_time,
                                p2p=p2p
                            ))

                            if len(data) == 5000:
                                CompanySerialModel.objects.bulk_create(data)
                                data.clear()
                        if len(data) > 0:
                            CompanySerialModel.objects.bulk_create(data)
                            data.clear()

                        # company.quantity = company.quantity + end - start
                        company.quantity =CompanySerialModel.objects.filter(company_id=id).count()
                        company.save()
                        return response.json(0)
                    else:
                        return response.json(173)
                except Exception as e:
                    # print('--------------------------error 5000')
                    # print(repr(e))
                    if savePoint:
                        transaction.rollback(savePoint)
                    djangoLogger = logging.getLogger('django')
                    djangoLogger.exception(repr(e))
                    return response.json(176, str(e))
            except Exception as e:
                # print('--------------------------error 5001')
                # print(repr(e))
                djangoLogger = logging.getLogger('django')
                djangoLogger.exception(repr(e))
                return response.json(176, str(e))
        else:
            return response.json(444)

    def do_list(self, userID, request_dict, response):
        # perm = ModelService.check_perm_uid_manage(userID, 0)
        # if not perm:
        #     return response.json(309)

        page = request_dict.get('page', None)
        line = request_dict.get('limit', None)
        if page and line:
            page = int(page)
            line = int(line)

            start = (page - 1) * line
            end = start + line

            company_qs = CompanyModel.objects.filter()
            count = company_qs.count()

            company_qs = company_qs[start: end].values()
            print(company_qs)

            res = {
                'count': count,
                'data': list(company_qs)
            }
            return response.json(0, res)
        else:
            return response.json(444)

    def create_secret(self, mark):
        len1 = len(mark)
        secret = ''
        for i in range(len1):
            secret += CommonService.RandomStr(randomlength=1)
            secret += mark[i]

        print(mark)
        return CommonService.encode_data_without_salt(secret)
