151 lines
		
	
	
		
			6.8 KiB
		
	
	
	
		
			Python
		
	
	
	
			
		
		
	
	
			151 lines
		
	
	
		
			6.8 KiB
		
	
	
	
		
			Python
		
	
	
	
from itertools import count
 | 
						|
from rest_framework.exceptions import ValidationError
 | 
						|
from apps.inm.models import FIFOItemProduct, IProduct, Inventory, MaterialBatch, FIFO, FIFOItem, WareHouse
 | 
						|
from apps.mtm.models import Material
 | 
						|
from apps.sam.models import SalePack, SaleProduct
 | 
						|
from django.db.models import Count
 | 
						|
from django.db.models.aggregates import Sum
 | 
						|
import logging
 | 
						|
 | 
						|
from apps.wpm.services import WpmService
 | 
						|
logger = logging.getLogger('log')
 | 
						|
 | 
						|
class InmService:
 | 
						|
    @classmethod
 | 
						|
    def update_inm(cls, instance:FIFO, type:int=1):
 | 
						|
        """
 | 
						|
        更新库存(正反)
 | 
						|
        """
 | 
						|
        if instance.type in [FIFO.FIFO_TYPE_PUR_IN, 
 | 
						|
            FIFO.FIFO_TYPE_DO_IN, FIFO.FIFO_TYPE_OTHER_IN]: # 采购入库, 生产入库, 其他入库
 | 
						|
            # 更新相关表
 | 
						|
            for i in FIFOItem.objects.filter(fifo=instance):
 | 
						|
                material = i.material
 | 
						|
                warehouse = i.warehouse
 | 
						|
 | 
						|
                o2, _ = MaterialBatch.objects.get_or_create(material=material, warehouse=warehouse, batch=i.batch,\
 | 
						|
                    defaults={'material':material, 'warehouse':warehouse, 'count':0, 'batch':i.batch})
 | 
						|
                o2.count = o2.count + i.count
 | 
						|
                if o2.expiration_date is None:
 | 
						|
                    o2.expiration_date = i.expiration_date
 | 
						|
                o2.save()
 | 
						|
 | 
						|
                iv, _= Inventory.objects.get_or_create(material=material, warehouse=warehouse, \
 | 
						|
                    defaults={'material':material, 'warehouse':warehouse, 'count':0})
 | 
						|
                iv.count = MaterialBatch.objects.filter(material=material, 
 | 
						|
                        warehouse=warehouse).aggregate(total=Sum('count')).get('total', 0)
 | 
						|
                iv.save()
 | 
						|
 | 
						|
                material.count = MaterialBatch.objects.filter(material=material).aggregate(total=Sum('count')).get('total', 0)
 | 
						|
                material.save()
 | 
						|
        
 | 
						|
                # 创建IProduct
 | 
						|
                ips2 = []
 | 
						|
                for m in FIFOItemProduct.objects.filter(fifoitem=i):
 | 
						|
                    ip = {}
 | 
						|
                    ip['warehouse'] = warehouse
 | 
						|
                    ip['batch'] = i.batch
 | 
						|
                    wp = m.wproduct
 | 
						|
                    ip['wproduct'] = wp
 | 
						|
                    ip['number'] = m.number
 | 
						|
                    ip['material'] = m.material
 | 
						|
                    ips2.append(IProduct(**ip))
 | 
						|
                IProduct.objects.bulk_create(ips2)
 | 
						|
 | 
						|
                # 如果是采购入库更新采购订单表
 | 
						|
                if instance.type == FIFO.FIFO_TYPE_PUR_IN:
 | 
						|
                    pu_order_item = i.pu_order_item
 | 
						|
                    delivered_count = pu_order_item.delivered_count + i.count
 | 
						|
                    if delivered_count > pu_order_item.count:
 | 
						|
                        raise ValidationError('超出采购订单所需量')
 | 
						|
                    pu_order_item.delivered_count = delivered_count
 | 
						|
                    pu_order_item.save()
 | 
						|
 | 
						|
        elif instance.type in [FIFO.FIFO_TYPE_DO_OUT, FIFO.FIFO_TYPE_SALE_OUT, FIFO.FIFO_TYPE_OTHER_OUT]: # 生产领料 销售出库
 | 
						|
            # 更新相关表
 | 
						|
            for i in FIFOItem.objects.filter(fifo=instance):
 | 
						|
                material = i.material
 | 
						|
                warehouse = i.warehouse
 | 
						|
                mb = MaterialBatch.objects.get(material=material, warehouse=warehouse, batch=i.batch)
 | 
						|
                temp_count = mb.count - i.count
 | 
						|
                if temp_count < 0:
 | 
						|
                    raise ValidationError('批次库存不足,操作失败')
 | 
						|
                mb.count = temp_count
 | 
						|
                mb.save()
 | 
						|
 | 
						|
                iv = Inventory.objects.get(material=material, warehouse=warehouse)
 | 
						|
                iv.count = MaterialBatch.objects.filter(material=material, 
 | 
						|
                    warehouse=warehouse).aggregate(total=Sum('count')).get('total', 0)
 | 
						|
                iv.save()
 | 
						|
 | 
						|
                material.count = MaterialBatch.objects.filter(material=
 | 
						|
                    material).aggregate(total=Sum('count')).get('total', 0)
 | 
						|
                material.save()
 | 
						|
 | 
						|
                # 删除IProduct
 | 
						|
                if instance.type == FIFO.FIFO_TYPE_DO_OUT:
 | 
						|
                    # 生产领料的情况直接从IProduct中删除
 | 
						|
                    numbers = FIFOItemProduct.objects.filter(fifoitem=i).values_list('number', flat=True)
 | 
						|
                    IProduct.objects.filter(number__in=numbers).delete()
 | 
						|
                # 销售的话已经处理了
 | 
						|
                # elif instance.type == FIFO.FIFO_TYPE_SALE_OUT:
 | 
						|
                #     ips = FIFOItemProduct.objects.filter(fifoitem=i).values_list('iproduct', flat=True)
 | 
						|
                #     IProduct.objects.filter(id__in=ips).update(state=IProduct.SALED)
 | 
						|
 | 
						|
    @classmethod
 | 
						|
    def sale_out_audit(cls, fifo:FIFO):
 | 
						|
        sale = fifo.sale
 | 
						|
        saleps = SaleProduct.objects.filter(sale=sale, packnum__isnull=True, remark__isnull=True)
 | 
						|
        if saleps.exists():
 | 
						|
            raise ValidationError('存在未装箱的产品')
 | 
						|
        # 创建出库条目
 | 
						|
        ips = IProduct.objects.filter(sale_iproduct__sale=sale, 
 | 
						|
                sale_iproduct__packnum__isnull=False)
 | 
						|
        ips.update(state=IProduct.SALED)
 | 
						|
        items = ips.values('warehouse', 'material', 'batch').annotate(total=Count('id'))
 | 
						|
        for i in items:
 | 
						|
            warehouse = WareHouse.objects.get(id=i['warehouse'])
 | 
						|
            material = Material.objects.get(id=i['material'])
 | 
						|
            fifoitem = FIFOItem()
 | 
						|
            fifoitem.need_test = False
 | 
						|
            fifoitem.warehouse = warehouse
 | 
						|
            fifoitem.material = material
 | 
						|
            fifoitem.count = i['total']
 | 
						|
            fifoitem.batch = i['batch']
 | 
						|
            fifoitem.fifo = fifo
 | 
						|
            fifoitem.save()
 | 
						|
            items_p = ips.filter(warehouse=warehouse, batch=i['batch'])
 | 
						|
            ipxs = []
 | 
						|
            for i in items_p:       
 | 
						|
                # 创建出库明细半成品
 | 
						|
                ip = {}
 | 
						|
                ip['fifoitem'] = fifoitem
 | 
						|
                ip['number'] = i.number
 | 
						|
                ip['material'] = i.material
 | 
						|
                ip['iproduct'] = i
 | 
						|
                ipxs.append(FIFOItemProduct(**ip))
 | 
						|
            FIFOItemProduct.objects.bulk_create(ipxs)
 | 
						|
 | 
						|
        # 装箱附件处理
 | 
						|
        # ml = SalePack.objects.filter(sale_product__iproduct = ips
 | 
						|
        # ).values('packitem__material').annotate(count=Sum('count'))
 | 
						|
        # for i in ml:
 | 
						|
        #     material = Material.objects.get(id=i['material'])
 | 
						|
 | 
						|
        
 | 
						|
        # 更新动态产品表情况
 | 
						|
        from apps.wpm.models import WProduct
 | 
						|
        wps = WProduct.objects.filter(id__in=ips.values_list('wproduct', flat=True))
 | 
						|
        wps.update(
 | 
						|
            act_state=WProduct.WPR_ACT_STATE_SELLED)
 | 
						|
        WpmService.add_wproducts_flow_log(instances=wps, change_str='selled')
 | 
						|
        
 | 
						|
        # 变更销售记录实际发货数
 | 
						|
        sale.count_real = ips.count()
 | 
						|
        sale.save()
 | 
						|
        # 变更订单状态
 | 
						|
        order = sale.order
 | 
						|
        if order:
 | 
						|
            order.delivered_count = IProduct.objects.filter(sale_iproduct__sale__order=order
 | 
						|
                , sale_iproduct__packnum__isnull=False).count()
 | 
						|
            order.save() |