package services import ( "fmt" "time" "github.com/sujit-baniya/fiber-boilerplate/pkg/models" ) // GenerarDocumentoContrato produce el PDF de un contrato ya existente a partir de // la plantilla activa tipo 'contrato' (cláusulas estándar) + los datos del contrato // (cliente, servicios, vigencia, valor). Es la implementación única que comparten // el endpoint POST /api/v2/contratos/:id/generar-documento y la tool crear_contrato. func GenerarDocumentoContrato(contratoID uint, generadoPor string) (*models.DocumentoGenerado, error) { contrato, err := models.GetContratoByID(contratoID) if err != nil { return nil, fmt.Errorf("contrato no encontrado: %w", err) } datos := DatosBaseDocumento(map[string]interface{}{ "Contrato": contrato, "Cliente": contrato.Cliente, "Servicios": contrato.Servicios, "FechaInicio": contrato.FechaInicio.Format("02/01/2006"), "FechaVencimiento": contrato.FechaVencimiento.Format("02/01/2006"), "PrecioAcordado": contrato.PrecioAcordado, "Moneda": contrato.Moneda, "Notas": contrato.Notas, }) doc, _, err := GenerarDocumento("contrato", datos, &contrato.ClienteID, nil, generadoPor) return doc, err } // CrearContratoConDocumento crea el registro de contrato y de una vez genera su PDF // con cláusulas estándar, para el flujo "cliente, tipo de servicio, duración" que // describe la automatización con IA (Telegram / chat propio / Claude directo). func CrearContratoConDocumento(clienteID uint, servicioIDs []uint, duracionMeses int, precioAcordado float64, moneda, notas, generadoPor string) (*models.Contrato, *models.DocumentoGenerado, error) { if clienteID == 0 { return nil, nil, fmt.Errorf("cliente_id requerido") } if len(servicioIDs) == 0 { return nil, nil, fmt.Errorf("servicio_ids requerido (al menos un servicio)") } if duracionMeses <= 0 { duracionMeses = 12 } if moneda == "" { moneda = "COP" } inicio := time.Now() vencimiento := inicio.AddDate(0, duracionMeses, 0) c := models.Contrato{ ClienteID: clienteID, FechaInicio: inicio, FechaVencimiento: vencimiento, PrecioAcordado: precioAcordado, Moneda: moneda, Estado: "activo", Notas: notas, } if err := models.CreateContrato(c, servicioIDs, nil, nil, nil); err != nil { return nil, nil, fmt.Errorf("no se pudo crear el contrato: %w", err) } // Recargar con Cliente/Servicios precargados (CreateContrato no los devuelve). creado, err := models.GetUltimoContratoByCliente(clienteID) if err != nil { return nil, nil, fmt.Errorf("contrato creado pero no se pudo recargar: %w", err) } doc, err := GenerarDocumentoContrato(creado.ID, generadoPor) if err != nil { return creado, nil, err } return creado, doc, nil }