import logging from celery import shared_task, group from api.customs.models import ProcesamientoPedimento, Pedimento, Cove, EDocument from core.utils import xml_controller from core.redis_events import publish_task_event from api.customs.tasks.auditoria import _crear_notificacion_auditoria from api.customs.tasks.microservice import ( procesar_cove_individual, procesar_acuse_individual, procesar_acuse_cove_individual, procesar_edoc_individual, procesar_partida_individual, procesar_remesa_individual, ) @shared_task def crear_procesamiento_remesa(pedimento_id): import logging logger = logging.getLogger('api.customs.async_operations') pedimento = Pedimento.objects.get(id=pedimento_id) logger.info(f"[TAREA] crear_procesamiento_remesa para pedimento {pedimento_id}") if pedimento.remesas: existe = ProcesamientoPedimento.objects.filter( pedimento=pedimento, servicio_id=5, organizacion=pedimento.organizacion, estado_id__in=[1, 2, 3, 4] ).exists() if not existe: logger.info(f"[TAREA] ProcesamientoPedimento remesa creado para pedimento {pedimento_id}") ProcesamientoPedimento.objects.create( pedimento=pedimento, estado_id=1, servicio_id=5, organizacion=pedimento.organizacion ) procesar_remesa_individual.apply_async(args=[str(pedimento.id), str(pedimento.organizacion.id)]) @shared_task def crear_procesamiento_partida(pedimento_id): import logging logger = logging.getLogger('api.customs.async_operations') pedimento = Pedimento.objects.get(id=pedimento_id) logger.info(f"[TAREA] crear_procesamiento_partida para pedimento {pedimento_id}") existe = ProcesamientoPedimento.objects.filter( pedimento=pedimento, servicio_id=4, organizacion=pedimento.organizacion, estado_id__in=[1, 2, 3, 4] ).exists() if not existe: logger.info(f"[TAREA] ProcesamientoPedimento partida creado para pedimento {pedimento_id}") ProcesamientoPedimento.objects.create( pedimento=pedimento, estado_id=1, servicio_id=4, organizacion=pedimento.organizacion ) procesar_partida_individual.apply_async(args=[str(pedimento.id), str(pedimento.organizacion.id)]) @shared_task def crear_procesamiento_cove(pedimento_id): import logging logger = logging.getLogger('api.customs.async_operations') pedimento = Pedimento.objects.get(id=pedimento_id) logger.info(f"[TAREA] crear_procesamiento_cove para pedimento {pedimento_id}") if pedimento.coves.exists(): existe = ProcesamientoPedimento.objects.filter( pedimento=pedimento, servicio_id=8, organizacion=pedimento.organizacion, estado_id__in=[1, 2, 3, 4] ).exists() if not existe: logger.info(f"[TAREA] ProcesamientoPedimento cove creado para pedimento {pedimento_id}") ProcesamientoPedimento.objects.create( pedimento=pedimento, estado_id=1, servicio_id=8, organizacion=pedimento.organizacion ) procesar_cove_individual.apply_async(args=[str(pedimento.id), str(pedimento.organizacion.id)]) @shared_task def crear_procesamiento_acuse(pedimento_id): import logging logger = logging.getLogger('api.customs.async_operations') pedimento = Pedimento.objects.get(id=pedimento_id) logger.info(f"[TAREA] crear_procesamiento_acuse para pedimento {pedimento_id}") if pedimento.documentos.exists(): existe = ProcesamientoPedimento.objects.filter( pedimento=pedimento, servicio_id=6, organizacion=pedimento.organizacion, estado_id__in=[1, 2, 3, 4] ).exists() if not existe: logger.info(f"[TAREA] ProcesamientoPedimento acuse creado para pedimento {pedimento_id}") ProcesamientoPedimento.objects.create( pedimento=pedimento, estado_id=1, servicio_id=6, organizacion=pedimento.organizacion ) procesar_acuse_individual.apply_async(args=[str(pedimento.id), str(pedimento.organizacion.id)]) @shared_task def crear_procesamiento_acuse_cove(pedimento_id): import logging logger = logging.getLogger('api.customs.async_operations') pedimento = Pedimento.objects.get(id=pedimento_id) logger.info(f"[TAREA] crear_procesamiento_acuse_cove para pedimento {pedimento_id}") if pedimento.coves.exists(): existe = ProcesamientoPedimento.objects.filter( pedimento=pedimento, servicio_id=9, organizacion=pedimento.organizacion, estado_id__in=[1, 2, 3, 4] ).exists() if not existe: logger.info(f"[TAREA] ProcesamientoPedimento acuse_cove creado para pedimento {pedimento_id}") ProcesamientoPedimento.objects.create( pedimento=pedimento, estado_id=1, servicio_id=9, organizacion=pedimento.organizacion ) procesar_acuse_cove_individual.apply_async(args=[str(pedimento.id), str(pedimento.organizacion.id)]) @shared_task def crear_procesamiento_edocument(pedimento_id): import logging logger = logging.getLogger('api.customs.async_operations') pedimento = Pedimento.objects.get(id=pedimento_id) logger.info(f"[TAREA] crear_procesamiento_edocument para pedimento {pedimento_id}") if pedimento.documentos.exists(): existe = ProcesamientoPedimento.objects.filter( pedimento=pedimento, servicio_id=7, organizacion=pedimento.organizacion, estado_id__in=[1, 2, 3, 4] ).exists() if not existe: logger.info(f"[TAREA] ProcesamientoPedimento edocument creado para pedimento {pedimento_id}") ProcesamientoPedimento.objects.create( pedimento=pedimento, estado_id=1, servicio_id=7, organizacion=pedimento.organizacion ) procesar_edoc_individual.apply_async(args=[str(pedimento.id), str(pedimento.organizacion.id)]) @shared_task def crear_procesamiento_pedimento_completo(organizacion_id): import logging logger = logging.getLogger('api.customs.async_operations') pedimentos = Pedimento.objects.filter(organizacion_id=organizacion_id) for pedimento in pedimentos: logger.info(f"[TAREA] crear_procesamiento_pedimento_completo para pedimento {pedimento.id}") existe = ProcesamientoPedimento.objects.filter( pedimento=pedimento, servicio_id=3, # ID del servicio de Pedimento Completo organizacion=pedimento.organizacion, estado_id__in=[1, 2, 3, 4] ).exists() if not existe: logger.info(f"[TAREA] ProcesamientoPedimento pedimento_completo creado para pedimento {pedimento.id}") ProcesamientoPedimento.objects.create( pedimento=pedimento, estado_id=1, # Estado "pendiente" servicio_id=3, organizacion=pedimento.organizacion ) @shared_task def crear_servicios(organizacion_id): pedimentos = Pedimento.objects.filter(organizacion=organizacion_id) for pedimento in pedimentos: crear_procesamiento_remesa.apply_async(args=[str(pedimento.id)]) crear_procesamiento_partida.apply_async(args=[str(pedimento.id)]) crear_procesamiento_cove.apply_async(args=[str(pedimento.id)]) crear_procesamiento_acuse.apply_async(args=[str(pedimento.id)]) crear_procesamiento_acuse_cove.apply_async(args=[str(pedimento.id)]) crear_procesamiento_edocument.apply_async(args=[str(pedimento.id)]) @shared_task(bind=True) def auditar_pedimentos(self, organizacion_id, user_id=None): _logger = logging.getLogger('api.customs.async_operations') task_id = self.request.id pedimentos = Pedimento.objects.filter(organizacion_id=organizacion_id) total_pedimentos = pedimentos.count() publish_task_event(task_id, "processing", f"Auditando pedimentos: {total_pedimentos} pedimentos", progress=0) procesados = 0 sin_xml = 0 errores = [] for idx, pedimento in enumerate(pedimentos): pc = pedimento.documents.filter(document_type__id=2).first() if pc: try: with open(f'./media/{pc.archivo}', 'r') as f: xml_content = f.read() xml_data = xml_controller.extract_data(xml_content) pedimento.numero_operacion = xml_data.get('numero_operacion') pedimento.curp_apoderado = xml_data.get('curp_apoderado') pedimento.agente_aduanal = xml_data.get('agente_aduanal') pedimento.numero_partidas = xml_data.get('numero_partidas') pedimento.remesas = xml_data.get('remesas') pedimento.tipo_operacion__id = xml_data.get('tipo_operacion') pedimento.fecha_pago = xml_data.get('fecha_pago') pedimento.pedimento_app = xml_data.get('fecha_pago')[2:4] + "-" + pedimento.aduana[:2] + "-" + pedimento.patente + "-" + pedimento.pedimentodd for edoc in xml_data.get('identificadores_ed', []): EDocument.objects.get_or_create( pedimento=pedimento, organizacion=pedimento.organizacion, clave=edoc.get('clave'), descripcion=edoc.get('descripcion'), numero_edocument=edoc.get('complemento1') ) from django.db import IntegrityError try: for cove in xml_data.get('coves', []): try: Cove.objects.get_or_create( pedimento=pedimento, organizacion=pedimento.organizacion, numero_cove=cove ) except IntegrityError: # Si ya existe por unique, recupera el objeto existente Cove.objects.get(numero_cove=cove) except: pass procesados += 1 except Exception as e: errores.append({'pedimento_id': str(pedimento.id), 'error': str(e)}) _logger.error(f"Error auditando pedimento {pedimento.id}: {e}") else: sin_xml += 1 if total_pedimentos > 0 and (idx + 1) % 10 == 0: pct = int(((idx + 1) / total_pedimentos) * 100) publish_task_event(task_id, "processing", f"Auditando pedimentos: {idx + 1}/{total_pedimentos}", progress=pct) resultado = { 'organizacion_id': str(organizacion_id), 'auditoria': 'pedimentos', 'total_pedimentos': total_pedimentos, 'procesados': procesados, 'sin_xml': sin_xml, 'con_errores': len(errores), 'detalle_errores': errores, } publish_task_event(task_id, "completed", "Auditoría de pedimentos completada", resultado=resultado, progress=100) if user_id: _crear_notificacion_auditoria(user_id, task_id, "Pedimentos", resultado) return resultado @shared_task def crear_todos_los_servicios(): from organization.models import Organizacion organizaciones = Organizacion.objects.all() for org in organizaciones: crear_procesamiento_pedimento_completo.apply_async(args=[str(org.id)]) crear_servicios.apply_async(args=[str(org.id)])