fix: Se crean endpoints para mostrar la informacion de peticiones y respuestas de los webservices, en el area del auditor del sistema.
This commit is contained in:
@@ -1,3 +1,6 @@
|
||||
import os
|
||||
from datetime import datetime
|
||||
from django.db import models
|
||||
from celery import shared_task, group
|
||||
from api.customs.models import ProcesamientoPedimento, Pedimento, Cove, EDocument
|
||||
from core.utils import xml_controller
|
||||
@@ -198,7 +201,7 @@ def auditar_coves(organizacion_id):
|
||||
pedimento,
|
||||
servicio=8,
|
||||
related_name='coves',
|
||||
variable='acuse_descargado',
|
||||
variable='cove_descargado',
|
||||
mensaje='COVE'
|
||||
)
|
||||
|
||||
@@ -247,7 +250,7 @@ def auditar_cove_por_pedimento(pedimento_id):
|
||||
pedimento,
|
||||
servicio=8,
|
||||
related_name='coves',
|
||||
variable='acuse_descargado',
|
||||
variable='cove_descargado',
|
||||
mensaje='COVE'
|
||||
)
|
||||
return {'success': True, 'pedimento_id': str(pedimento_id)}
|
||||
@@ -302,3 +305,154 @@ def auditar_acuse_por_pedimento(pedimento_id):
|
||||
except Exception as e:
|
||||
return {'success': False, 'error': str(e), 'pedimento_id': str(pedimento_id)}
|
||||
|
||||
@shared_task
|
||||
def auditar_pedimento_por_id(pedimento_id):
|
||||
"""
|
||||
Tarea para auditar un pedimento específico verificando todos sus documentos y datos.
|
||||
"""
|
||||
try:
|
||||
pedimento = Pedimento.objects.get(id=pedimento_id)
|
||||
resultado = {
|
||||
'pedimento_id': str(pedimento_id),
|
||||
'pedimento': pedimento.pedimento,
|
||||
'pedimento_app': pedimento.pedimento_app,
|
||||
'organizacion': str(pedimento.organizacion.id),
|
||||
'fecha_auditoria': datetime.now().isoformat(),
|
||||
'estado_general': 'EN_PROGRESO',
|
||||
'detalles': {}
|
||||
}
|
||||
|
||||
# 1. Verificar documentos XML
|
||||
from api.record.models import Document
|
||||
documentos_xml = Document.objects.filter(
|
||||
pedimento=pedimento,
|
||||
archivo__endswith='.xml'
|
||||
)
|
||||
|
||||
resultado['detalles']['documentos_xml'] = {
|
||||
'total': documentos_xml.count(),
|
||||
'archivos': []
|
||||
}
|
||||
|
||||
for doc in documentos_xml:
|
||||
try:
|
||||
xml_info = {
|
||||
'id': str(doc.id),
|
||||
'nombre': os.path.basename(doc.archivo.name),
|
||||
'tamanio': doc.size,
|
||||
'extension': doc.extension,
|
||||
'tipo': doc.document_type.descripcion if doc.document_type else 'Desconocido'
|
||||
}
|
||||
|
||||
# Verificar si el archivo existe físicamente
|
||||
if os.path.exists(doc.archivo.path):
|
||||
xml_info['existe_fisicamente'] = True
|
||||
# Intentar leer el XML
|
||||
try:
|
||||
with open(doc.archivo.path, 'r', encoding='utf-8') as f:
|
||||
content = f.read()
|
||||
xml_info['es_xml_valido'] = '<?xml' in content[:100]
|
||||
xml_info['tamanio_bytes'] = len(content)
|
||||
except Exception as e:
|
||||
xml_info['error_lectura'] = str(e)
|
||||
else:
|
||||
xml_info['existe_fisicamente'] = False
|
||||
|
||||
except Exception as e:
|
||||
xml_info['error'] = str(e)
|
||||
|
||||
resultado['detalles']['documentos_xml']['archivos'].append(xml_info)
|
||||
|
||||
# 2. Verificar si hay documentos asociados
|
||||
resultado['detalles']['documentos_totales'] = {
|
||||
'total': pedimento.documents.count(),
|
||||
'por_tipo': {}
|
||||
}
|
||||
|
||||
for doc_type in pedimento.documents.values('document_type__descripcion').annotate(total=models.Count('id')):
|
||||
tipo = doc_type['document_type__descripcion'] or 'Sin tipo'
|
||||
resultado['detalles']['documentos_totales']['por_tipo'][tipo] = doc_type['total']
|
||||
|
||||
# 3. Verificar COVEs
|
||||
resultado['detalles']['coves'] = {
|
||||
'total': pedimento.coves.count(),
|
||||
'descargados': pedimento.coves.filter(cove_descargado=True).count(),
|
||||
'con_acuse': pedimento.coves.filter(acuse_cove_descargado=True).count()
|
||||
}
|
||||
|
||||
# 4. Verificar EDocuments
|
||||
resultado['detalles']['edocuments'] = {
|
||||
'total': pedimento.documentos.count(),
|
||||
'descargados': pedimento.documentos.filter(edocument_descargado=True).count(),
|
||||
'con_acuse': pedimento.documentos.filter(acuse_descargado=True).count()
|
||||
}
|
||||
|
||||
# 5. Verificar procesamientos
|
||||
resultado['detalles']['procesamientos'] = {
|
||||
'total': pedimento.procesamientos.count(),
|
||||
'por_estado': {}
|
||||
}
|
||||
|
||||
for proc in pedimento.procesamientos.values('estado__estado').annotate(total=models.Count('id')):
|
||||
estado = proc['estado__estado'] or 'Sin estado'
|
||||
resultado['detalles']['procesamientos']['por_estado'][estado] = proc['total']
|
||||
|
||||
# 6. Verificar campos importantes del pedimento
|
||||
campos_revisados = {
|
||||
'numero_operacion': bool(pedimento.numero_operacion),
|
||||
'numero_partidas': bool(pedimento.numero_partidas),
|
||||
'importe_total': bool(pedimento.importe_total),
|
||||
'contribuyente': bool(pedimento.contribuyente),
|
||||
'tiene_remesas': pedimento.remesas,
|
||||
'partidas_creadas': pedimento.partidas.count() > 0,
|
||||
'fecha_pago': bool(pedimento.fecha_pago)
|
||||
}
|
||||
|
||||
resultado['detalles']['campos_pedimento'] = campos_revisados
|
||||
resultado['detalles']['campos_completos'] = sum(campos_revisados.values())
|
||||
resultado['detalles']['campos_totales'] = len(campos_revisados)
|
||||
|
||||
# 7. Determinar estado general
|
||||
campos_completos = resultado['detalles']['campos_completos']
|
||||
total_campos = resultado['detalles']['campos_totales']
|
||||
|
||||
if documentos_xml.count() == 0:
|
||||
resultado['estado_general'] = 'SIN_XML'
|
||||
resultado['mensaje'] = 'No se encontraron documentos XML'
|
||||
elif campos_completos == total_campos:
|
||||
resultado['estado_general'] = 'COMPLETO'
|
||||
resultado['mensaje'] = 'Pedimento completamente procesado'
|
||||
elif campos_completos >= total_campos * 0.7:
|
||||
resultado['estado_general'] = 'PARCIAL'
|
||||
resultado['mensaje'] = 'Pedimento parcialmente procesado'
|
||||
else:
|
||||
resultado['estado_general'] = 'INCOMPLETO'
|
||||
resultado['mensaje'] = 'Pedimento con información incompleta'
|
||||
|
||||
resultado['porcentaje_completitud'] = (campos_completos / total_campos) * 100 if total_campos > 0 else 0
|
||||
|
||||
# 8. Sugerencias
|
||||
sugerencias = []
|
||||
if not pedimento.numero_operacion:
|
||||
sugerencias.append("Falta el número de operación")
|
||||
if not pedimento.numero_partidas:
|
||||
sugerencias.append("Falta el número de partidas")
|
||||
if pedimento.numero_partidas and pedimento.numero_partidas > pedimento.partidas.count():
|
||||
sugerencias.append(f"Faltan partidas: {pedimento.numero_partidas - pedimento.partidas.count()} de {pedimento.numero_partidas}")
|
||||
if not pedimento.contribuyente:
|
||||
sugerencias.append("Falta el contribuyente asociado")
|
||||
|
||||
resultado['sugerencias'] = sugerencias
|
||||
|
||||
return resultado
|
||||
|
||||
except Pedimento.DoesNotExist:
|
||||
return {
|
||||
'error': f'Pedimento con ID {pedimento_id} no encontrado',
|
||||
'pedimento_id': str(pedimento_id)
|
||||
}
|
||||
except Exception as e:
|
||||
return {
|
||||
'error': f'Error auditar pedimento {pedimento_id}: {str(e)}',
|
||||
'pedimento_id': str(pedimento_id)
|
||||
}
|
||||
Reference in New Issue
Block a user