up
This commit is contained in:
@@ -228,6 +228,123 @@ func DeleteContrato(c *fiber.Ctx) error {
|
||||
return c.JSON(fiber.Map{"message": "Eliminado", "ok": true})
|
||||
}
|
||||
|
||||
// GetHistorialContrato devuelve la línea de tiempo de actividad de un contrato
|
||||
func GetHistorialContrato(c *fiber.Ctx) error {
|
||||
id, err := strconv.ParseUint(c.Params("id"), 10, 32)
|
||||
if err != nil {
|
||||
return c.Status(400).JSON(fiber.Map{"error": "ID inválido"})
|
||||
}
|
||||
contrato, err := models.GetContratoByID(uint(id))
|
||||
if err != nil {
|
||||
return c.Status(404).JSON(fiber.Map{"error": "No encontrado"})
|
||||
}
|
||||
|
||||
notifLogs, _ := models.GetLogsByContratoID(uint(id))
|
||||
pagoLogs, _ := models.GetDispatchLogsByContratoID(uint(id))
|
||||
|
||||
// Construir timeline unificado
|
||||
type Evento struct {
|
||||
Tipo string `json:"tipo"` // creacion | renovacion | notificacion | pago
|
||||
Icono string `json:"icono"`
|
||||
Titulo string `json:"titulo"`
|
||||
Detalle string `json:"detalle"`
|
||||
Estado string `json:"estado"` // ok | error | info
|
||||
FechaISO string `json:"fecha"`
|
||||
}
|
||||
|
||||
var timeline []Evento
|
||||
|
||||
// Evento: creación del contrato
|
||||
timeline = append(timeline, Evento{
|
||||
Tipo: "creacion",
|
||||
Icono: "document",
|
||||
Titulo: "Contrato creado",
|
||||
Detalle: "Inicio: " + contrato.FechaInicio.Format("02/01/2006") + " · Vence: " + contrato.FechaVencimiento.Format("02/01/2006"),
|
||||
Estado: "info",
|
||||
FechaISO: contrato.CreatedAt.Format(time.RFC3339),
|
||||
})
|
||||
|
||||
// Evento: renovaciones (updated_at con estado renovado — heurístico por estado)
|
||||
if contrato.Estado == "renovado" {
|
||||
timeline = append(timeline, Evento{
|
||||
Tipo: "renovacion",
|
||||
Icono: "refresh",
|
||||
Titulo: "Contrato renovado",
|
||||
Detalle: "Nuevo vencimiento: " + contrato.FechaVencimiento.Format("02/01/2006"),
|
||||
Estado: "ok",
|
||||
FechaISO: contrato.UpdatedAt.Format(time.RFC3339),
|
||||
})
|
||||
}
|
||||
|
||||
// Eventos: notificaciones enviadas
|
||||
for _, n := range notifLogs {
|
||||
estado := "ok"
|
||||
if n.Estado == "fallido" {
|
||||
estado = "error"
|
||||
} else if n.Estado == "pendiente" {
|
||||
estado = "info"
|
||||
}
|
||||
detalle := n.Asunto
|
||||
if n.Estado == "fallido" && n.ErrorMsg != "" {
|
||||
detalle += " · Error: " + n.ErrorMsg
|
||||
}
|
||||
reglaLabel := ""
|
||||
if n.Regla.ID > 0 {
|
||||
reglaLabel = " (" + n.Regla.Nombre + ")"
|
||||
}
|
||||
timeline = append(timeline, Evento{
|
||||
Tipo: "notificacion",
|
||||
Icono: "mail",
|
||||
Titulo: "Notificación enviada" + reglaLabel,
|
||||
Detalle: detalle,
|
||||
Estado: estado,
|
||||
FechaISO: n.CreatedAt.Format(time.RFC3339),
|
||||
})
|
||||
}
|
||||
|
||||
// Eventos: pagos / dispatches
|
||||
for _, p := range pagoLogs {
|
||||
estado := "ok"
|
||||
if p.Estado == "failed" {
|
||||
estado = "error"
|
||||
}
|
||||
detalle := p.Referencia
|
||||
if p.PayerEmail != "" {
|
||||
detalle += " · " + p.PayerEmail
|
||||
}
|
||||
if p.Fuente != "" {
|
||||
detalle += " · " + p.Fuente
|
||||
}
|
||||
timeline = append(timeline, Evento{
|
||||
Tipo: "pago",
|
||||
Icono: "currency",
|
||||
Titulo: "Pago recibido",
|
||||
Detalle: detalle,
|
||||
Estado: estado,
|
||||
FechaISO: p.CreatedAt.Format(time.RFC3339),
|
||||
})
|
||||
}
|
||||
|
||||
// Ordenar por fecha desc
|
||||
for i := 0; i < len(timeline)-1; i++ {
|
||||
for j := i + 1; j < len(timeline); j++ {
|
||||
if timeline[j].FechaISO > timeline[i].FechaISO {
|
||||
timeline[i], timeline[j] = timeline[j], timeline[i]
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
return c.JSON(fiber.Map{
|
||||
"contrato": fiber.Map{
|
||||
"id": contrato.ID,
|
||||
"cliente": contrato.Cliente.Nombre,
|
||||
"estado": contrato.Estado,
|
||||
},
|
||||
"timeline": timeline,
|
||||
"total": len(timeline),
|
||||
})
|
||||
}
|
||||
|
||||
func calcularFechaVencimiento(desde time.Time, periodicidad string) time.Time {
|
||||
switch periodicidad {
|
||||
case "mensual":
|
||||
|
||||
Reference in New Issue
Block a user