# This file is part of Tryton.  The COPYRIGHT file at the top level of
# this repository contains the full copyright notices and license terms.
from trytond.model import fields
from trytond.pool import Pool, PoolMeta
from trytond.pyson import Bool, Eval, Id
from trytond.model import (ModelSQL, ModelView)
from decimal import getcontext, Decimal, ROUND_HALF_UP
from sql.aggregate import Count, Max, Min, Sum, Avg, BoolOr
from sql import Column, Literal
from sql.functions import CurrentTimestamp, DateTrunc
import datetime
import logging

logger = logging.getLogger(__name__)

class Lot(ModelSQL, ModelView):
    "Lot"
    __name__ = 'lot.lot'
    _rec_name = 'lot_name'
    
    line = fields.Many2One(
        'purchase.line', "Line", ondelete='CASCADE',
        )
    sale_line = fields.Many2One(
        'sale.line', "Line", ondelete='CASCADE',
        )
    lot_name = fields.Char("Lot")
    lot_qt = fields.Integer("Quantity",states={
           'readonly': Eval('lot_himself', True),
       },)
    lot_unit = fields.Many2One('product.uom', "Unit",required=True)
    lot_product = fields.Many2One('product.product', "Product")
    lot_type = fields.Selection([
        (None, ''),
        ('delivery', 'Delivery'),
        ('loss', 'Loss'),
        ('receive', 'Receive')
    ], 'Lot type',required=True)
    lot_status = fields.Selection([
        (None, ''),
        ('forecast', 'Forecast'),
        ('nom', 'Nom'),
        ('adjusted', 'Adjusted'),
        ('trade', 'Trade')
    ], 'Lot status',required=True)
    lot_quantity = fields.Numeric("Net Qt",digits='lot_unit',required=True)
    lot_unit_line = fields.Function(fields.Many2One('product.uom', "Unit",required=True),'get_unit')
    lot_premium = fields.Numeric("Prem/Disc", digits=(1,2))
    lot_premium_sale = fields.Numeric("Prem/Disc", digits=(1,2))
    lot_shipment = fields.Many2One('stock.shipment.in', "Shipment")
    lot_gross_quantity = fields.Numeric("Gross Qt",digits='lot_unit')
    lot_parent = fields.Many2One('purchase.lot',"Parent")
    lot_childs = fields.One2Many('purchase.lot','lot_parent',"Childs")
    lot_himself = fields.Many2One('purchase.lot',"Lot")
    lot_container = fields.Char("Container")
    lot_qt_hist = fields.One2Many('purchase.lot.qt','lot',"Qt history")

    lot_unit_line = fields.Function(fields.Many2One('product.uom', "Unit"),'get_unit')
    lot_price = fields.Function(fields.Numeric("Price", digits=(1,2)),'get_lot_price')
    lot_price_sale = fields.Function(fields.Numeric("Price", digits=(1,2)),'get_lot_sale_price')
    
    # lot_tu_net_qt = fields.Numeric("Net Takeup Qt")
    # lot_tu_gross_qt = fields.Numeric("Gross Takeup Qt")
    # lot_wr_net_qt = fields.Numeric("Net WR Qt")
    # lot_wr_gross_qt = fields.Numeric("Gross WR Qt")
    # lot_lr_net_qt = fields.Numeric("Net LR Qt")
    # lot_lr_gross_qt = fields.Numeric("Gross LR Qt")

    @classmethod
    def __setup__(cls):
        super(Lot, cls).__setup__()
        cls._order.insert(0, ('lot_shipment', 'ASC'))


    @classmethod
    def default_lot_unit(cls):
        return 2 #kg
    
    @classmethod
    def default_lot_qt(cls):
        return Decimal(0)
    
    @classmethod
    def default_lot_gross_quantity(cls):
        return Decimal(0)

    @classmethod
    def default_lot_status(cls):
        return 'trade'

    @classmethod
    def default_lot_type(cls):
        return 'receive'
    
    def get_unit(self,name):
        return 2 #kg

    def get_lot_price(self,name=None):
        price = Decimal(0)
        if self.line:
            l = Pool().get('purchase.line')(self.line)
            premium = Decimal(0)
            if self.lot_premium:
                premium = self.lot_premium
            price = premium + l.unit_price  
        return round(price,2)

    def get_lot_sale_price(self,name=None):
        price = Decimal(0)
        # if self.sale_line:
        #     l = Pool().get('sale.line')(self.sale_line)
        #     premium = Decimal(0)
        #     if self.lot_premium_sale:
        #         premium = self.lot_premium_sale
        #     price = premium + l.unit_price  
        return round(price,2)

    def get_sale_amount(self,name):
        round_context = getcontext()
        round_context.rounding = ROUND_HALF_UP
        price = self.get_lot_sale_price()
        # if price and not self.lot_wr_net_qt:
        #     return round(price * self.lot_quantity * Decimal(2.2046),2)
        # elif price and self.lot_wr_net_qt:
        #     return round(price * self.lot_wr_net_qt * Decimal(2.2046),2)
        return None

    def get_amount(self,name):
        round_context = getcontext()
        round_context.rounding = ROUND_HALF_UP
        price = self.get_lot_price()
        # if price and not self.lot_wr_net_qt:
        #     return round(price * self.lot_quantity * Decimal(2.2046),2)
        # elif price and self.lot_wr_net_qt:
        #     return round(price * self.lot_wr_net_qt * Decimal(2.2046),2)
        return None
    
    # @classmethod
    # def write(cls, *args):
    #     super().write(*args)
    #     lots = sum(args[::2], [])
    #     to_write = []
    #     for l in lots:
    #         lotnetqt = Decimal(0)
    #         lotgrossqt = Decimal(0)
    #         if l.lot_lr_net_qt and l.lot_lr_net_qt > 0 and l.lot_lr_net_qt != l.lot_quantity: 
    #             lotnetqt = l.lot_lr_net_qt
    #             lotgrossqt = l.lot_lr_gross_qt
    #         elif l.lot_wr_net_qt and not l.lot_lr_net_qt and l.lot_wr_net_qt > 0 and l.lot_wr_net_qt != l.lot_quantity:
    #             lotnetqt = l.lot_wr_net_qt
    #             lotgrossqt = l.lot_wr_gross_qt
    #         elif l.lot_tu_net_qt and not l.lot_lr_net_qt and not l.lot_wr_net_qt and l.lot_tu_net_qt > 0 and l.lot_tu_net_qt != l.lot_quantity:
    #             lotnetqt = l.lot_tu_net_qt
    #             lotgrossqt = l.lot_tu_gross_qt
    #         if lotnetqt:
    #             to_write.extend(([l], {
    #                                 'lot_quantity': lotnetqt,
    #                                 'lot_final_quantity': lotgrossqt,
    #                                 }))
    #     if to_write:
    #         cls.write(*to_write)

    # @classmethod
    # def create(cls, vlist):
    #     pool = Pool()
    #     vlist = [x.copy() for x in vlist]
    #     for values in vlist:
    #         parent = values.get('lot_parent')
    #         if parent:
    #             L = pool.get('position.lot')
    #             l = L(parent)
    #             balenw = round(Decimal((l.lot_quantity if l.lot_quantity else 0)/l.lot_bale),2)
    #             balegw = round(Decimal((l.lot_final_quantity if l.lot_final_quantity else 0)/l.lot_bale),2)
    #             balenwtu = round(Decimal((l.lot_tu_net_qt if l.lot_tu_net_qt else 0)/l.lot_bale),2)
    #             balegwtu = round(Decimal((l.lot_tu_gross_qt if l.lot_tu_gross_qt else 0)/l.lot_bale),2)
    #             balenwwr = round(Decimal((l.lot_wr_net_qt if l.lot_wr_net_qt else 0)/l.lot_bale),2)
    #             balegwwr = round(Decimal((l.lot_wr_gross_qt if l.lot_wr_gross_qt else 0)/l.lot_bale),2)
    #             balenwlr = round(Decimal((l.lot_lr_net_qt if l.lot_lr_net_qt else 0)/l.lot_bale),2)
    #             balegwlr = round(Decimal((l.lot_lr_gross_qt if l.lot_lr_gross_qt else 0)/l.lot_bale),2)
    #             nw = Decimal(int(values.get('lot_bale')) * balenw)
    #             gw = Decimal(int(values.get('lot_bale')) * balegw)
    #             nwtu = Decimal(int(values.get('lot_bale')) * balenwtu)
    #             gwtu = Decimal(int(values.get('lot_bale')) * balegwtu)
    #             nwwr = Decimal(int(values.get('lot_bale')) * balenwwr)
    #             gwwr = Decimal(int(values.get('lot_bale')) * balegwwr)
    #             nwlr = Decimal(int(values.get('lot_bale')) * balenwlr)
    #             gwlr = Decimal(int(values.get('lot_bale')) * balegwlr)
    #             l.lot_bale -= int(values.get('lot_bale'))
    #             if l.lot_quantity:
    #                 l.lot_quantity -= nw
    #             if l.lot_final_quantity:
    #                 l.lot_final_quantity -= gw
    #             if l.lot_tu_net_qt:
    #                 l.lot_tu_net_qt -= nwtu
    #             if l.lot_tu_gross_qt:
    #                 l.lot_tu_gross_qt -= gwtu
    #             if l.lot_wr_net_qt:
    #                 l.lot_wr_net_qt -= nwwr
    #             if l.lot_wr_gross_qt:
    #                 l.lot_wr_gross_qt -= gwwr
    #             if l.lot_lr_net_qt:
    #                 l.lot_lr_net_qt -= nwlr
    #             if l.lot_lr_gross_qt:
    #                 l.lot_lr_gross_qt -= gwlr
    #             values['lot_quantity'] = nw
    #             values['lot_final_quantity'] = gw
    #             values['lot_tu_net_qt'] = nwtu
    #             values['lot_tu_gross_qt'] = gwtu
    #             values['lot_wr_net_qt'] = nwwr
    #             values['lot_wr_gross_qt'] = gwwr
    #             values['lot_lr_net_qt'] = nwlr
    #             values['lot_lr_gross_qt'] = gwlr
    #             L.save([l]) 
            
    #     return super(Lot, cls).create(vlist)

    # @classmethod
    # def validate(cls, lots):
    #     super(Lot, cls).validate(lots)
    #     pool = Pool()
    #     Valuation = pool.get('valuation.valuation')
    #     Position = pool.get('trade.position')
    #     for lot in lots:
    #         L = pool.get('position.lot')
    #         if not lot.lot_himself:
    #             l = L(lot.id)
    #             l.lot_himself = lot.id
    #             L.save([l])
    #             if lot.lot_parent:
    #                 pa = L(lot.lot_parent)
    #                 l = L(lot.id)
    #                 l.position = pa.position
    #                 l.lot_quality = pa.lot_quality
    #                 l.lot_unit = pa.lot_unit
    #                 L.save([l])
            
    # @classmethod
    # def copy(cls, positions, default=None):
    #    if default is None:
    #        default = {}
    #    else:
    #        default = default.copy()
    #    return super(Lot, cls).copy(lots, default=default)
    
    # @classmethod
    # def delete(cls, lots):
    #     positions = []
    #     pool = Pool()
    #     LL = pool.get('position.lot')
    #     for lot in lots:
    #         positions.append(lot.position)
    #         if lot.lot_parent:
    #             pa = LL(lot.lot_parent)
    #             if pa:
    #                 pa.lot_bale += lot.lot_bale
    #                 pa.lot_quantity += lot.lot_quantity
    #                 pa.lot_final_quantity += lot.lot_final_quantity
    #                 if pa.lot_tu_net_qt:
    #                     pa.lot_tu_net_qt += lot.lot_tu_net_qt
    #                     pa.lot_tu_gross_qt += lot.lot_tu_gross_qt
    #                 if pa.lot_wr_net_qt:
    #                     pa.lot_wr_net_qt += lot.lot_wr_net_qt
    #                     pa.lot_wr_gross_qt += lot.lot_wr_gross_qt
    #                 if pa.lot_lr_net_qt:
    #                     pa.lot_lr_net_qt += lot.lot_lr_net_qt
    #                     pa.lot_lr_gross_qt += lot.lot_lr_gross_qt
    #                 LL.save([pa])
    #     super(Lot, cls).delete(lots)

class QtType(ModelSQL, ModelView):
    "Type"
    __name__ = 'lot.qt.type'
    name = fields.Char("Name")

class QtHist(ModelSQL, ModelView):
    "Quantities"
    __name__ = 'lot.qt'

    lot = fields.Many2One(
        'lot.lot', "Lot", ondelete='CASCADE',
        )
    quantity_type = fields.Many2One('lot.qt.type',"Type")
    quantity = fields.Numeric("Quantity")

    

