Fix Consulta de Bancas

- Se elimina la iteración sobre las secciones para la consulta de bancas.
This commit is contained in:
2025-10-18 19:31:41 -03:00
parent 705683861c
commit 2b7fb927e2
2 changed files with 14 additions and 50 deletions

View File

@@ -109,45 +109,35 @@ public class CriticalDataWorker : BackgroundService
.Where(c => c.Nombre.Contains("SENADORES") || c.Nombre.Contains("DIPUTADOS")) .Where(c => c.Nombre.Contains("SENADORES") || c.Nombre.Contains("DIPUTADOS"))
.ToListAsync(stoppingToken); .ToListAsync(stoppingToken);
// --- MODIFICACIÓN 1: Obtener todos los ámbitos en una sola consulta ---
var ambitosASondear = await dbContext.AmbitosGeograficos var ambitosASondear = await dbContext.AmbitosGeograficos
.AsNoTracking() .AsNoTracking()
.Where(a => (a.NivelId == 10 || a.NivelId == 20) && a.DistritoId != null) .Where(a => a.NivelId == 10 && a.DistritoId != null)
.ToListAsync(stoppingToken); .ToListAsync(stoppingToken);
var provincia = ambitosASondear.FirstOrDefault(a => a.NivelId == 10); if (!categoriasDeBancas.Any() || !ambitosASondear.Any())
var seccionesElectorales = ambitosASondear.Where(a => a.NivelId == 20).ToList();
if (!categoriasDeBancas.Any() || provincia == null)
{ {
_logger.LogWarning("No se encontraron categorías de bancas o el ámbito provincial en la BD. Omitiendo sondeo de bancas."); _logger.LogWarning("No se encontraron categorías de bancas o ámbitos provinciales en la BD. Omitiendo sondeo de bancas.");
return; return;
} }
_logger.LogInformation("Iniciando sondeo de Bancas a nivel Provincial y para {count} Secciones Electorales...", seccionesElectorales.Count); _logger.LogInformation("Iniciando sondeo de Bancas a nivel Provincial para {count} provincias...", ambitosASondear.Count);
var todasLasProyecciones = new List<ProyeccionBanca>(); var todasLasProyecciones = new List<ProyeccionBanca>();
bool hasReceivedAnyNewData = false; bool hasReceivedAnyNewData = false;
// --- MODIFICACIÓN 2: Usar un diccionario para no buscar repetidamente en la BD ---
var agrupacionesEnDb = await dbContext.AgrupacionesPoliticas.ToDictionaryAsync(a => a.Id, a => a, stoppingToken); var agrupacionesEnDb = await dbContext.AgrupacionesPoliticas.ToDictionaryAsync(a => a.Id, a => a, stoppingToken);
// Bucle combinado para todos los ámbitos
foreach (var ambito in ambitosASondear) foreach (var ambito in ambitosASondear)
{ {
if (stoppingToken.IsCancellationRequested) break; if (stoppingToken.IsCancellationRequested) break;
foreach (var categoria in categoriasDeBancas) foreach (var categoria in categoriasDeBancas)
{ {
if (stoppingToken.IsCancellationRequested) break; if (stoppingToken.IsCancellationRequested) break;
// Llamada a la API (lógica adaptada para ambos niveles)
var repartoBancasDto = await _apiService.GetBancasAsync(authToken, ambito.DistritoId!, ambito.SeccionProvincialId, categoria.Id); var repartoBancasDto = await _apiService.GetBancasAsync(authToken, ambito.DistritoId!, ambito.SeccionProvincialId, categoria.Id);
if (repartoBancasDto?.RepartoBancas is { Count: > 0 } bancas) if (repartoBancasDto?.RepartoBancas is { Count: > 0 } bancas)
{ {
hasReceivedAnyNewData = true; hasReceivedAnyNewData = true;
DateTime fechaTotalizacion; DateTime fechaTotalizacion;
if (!DateTime.TryParse(repartoBancasDto.FechaTotalizacion, out var parsedDate)) if (!DateTime.TryParse(repartoBancasDto.FechaTotalizacion, out var parsedDate))
{ {
@@ -161,20 +151,17 @@ public class CriticalDataWorker : BackgroundService
foreach (var banca in bancas) foreach (var banca in bancas)
{ {
// --- MODIFICACIÓN 3: Lógica de "Upsert" para Agrupaciones ---
if (!agrupacionesEnDb.ContainsKey(banca.IdAgrupacion)) if (!agrupacionesEnDb.ContainsKey(banca.IdAgrupacion))
{ {
_logger.LogWarning("Agrupación con ID {AgrupacionId} ('{Nombre}') no encontrada. Creándola desde los datos de bancas.", banca.IdAgrupacion, banca.NombreAgrupacion); _logger.LogWarning("Agrupación con ID {AgrupacionId} ('{Nombre}') no encontrada. Creándola desde los datos de bancas.", banca.IdAgrupacion, banca.NombreAgrupacion);
var nuevaAgrupacion = new AgrupacionPolitica var nuevaAgrupacion = new AgrupacionPolitica
{ {
Id = banca.IdAgrupacion, Id = banca.IdAgrupacion,
Nombre = banca.NombreAgrupacion, Nombre = banca.NombreAgrupacion,
IdTelegrama = banca.IdAgrupacionTelegrama ?? string.Empty IdTelegrama = banca.IdAgrupacionTelegrama ?? string.Empty
}; };
await dbContext.AgrupacionesPoliticas.AddAsync(nuevaAgrupacion, stoppingToken); await dbContext.AgrupacionesPoliticas.AddAsync(nuevaAgrupacion, stoppingToken);
agrupacionesEnDb.Add(nuevaAgrupacion.Id, nuevaAgrupacion); // Añadir al diccionario para no volver a crearla agrupacionesEnDb.Add(nuevaAgrupacion.Id, nuevaAgrupacion);
} }
todasLasProyecciones.Add(new ProyeccionBanca todasLasProyecciones.Add(new ProyeccionBanca
@@ -195,16 +182,11 @@ public class CriticalDataWorker : BackgroundService
{ {
_logger.LogInformation("Se recibieron datos válidos de bancas. Procediendo a actualizar la base de datos..."); _logger.LogInformation("Se recibieron datos válidos de bancas. Procediendo a actualizar la base de datos...");
await using var transaction = await dbContext.Database.BeginTransactionAsync(stoppingToken); await using var transaction = await dbContext.Database.BeginTransactionAsync(stoppingToken);
await dbContext.SaveChangesAsync(stoppingToken); // Guardar nuevas agrupaciones si las hay
// Si se crearon nuevas agrupaciones, se guardarán aquí primero. await dbContext.Database.ExecuteSqlRawAsync("DELETE FROM ProyeccionesBancas WHERE EleccionId = {0}", EleccionId, stoppingToken); // CORRECCIÓN: Borrar solo para la elección actual
await dbContext.SaveChangesAsync(stoppingToken);
// Luego, procedemos con las proyecciones.
await dbContext.Database.ExecuteSqlRawAsync("DELETE FROM ProyeccionesBancas", stoppingToken);
await dbContext.ProyeccionesBancas.AddRangeAsync(todasLasProyecciones, stoppingToken); await dbContext.ProyeccionesBancas.AddRangeAsync(todasLasProyecciones, stoppingToken);
await dbContext.SaveChangesAsync(stoppingToken); await dbContext.SaveChangesAsync(stoppingToken);
await transaction.CommitAsync(stoppingToken); await transaction.CommitAsync(stoppingToken);
_logger.LogInformation("La tabla de proyecciones ha sido actualizada con {count} registros.", todasLasProyecciones.Count); _logger.LogInformation("La tabla de proyecciones ha sido actualizada con {count} registros.", todasLasProyecciones.Count);
} }
else else

View File

@@ -572,45 +572,35 @@ public class LowPriorityDataWorker : BackgroundService
.Where(c => c.Nombre.Contains("SENADORES") || c.Nombre.Contains("DIPUTADOS")) .Where(c => c.Nombre.Contains("SENADORES") || c.Nombre.Contains("DIPUTADOS"))
.ToListAsync(stoppingToken); .ToListAsync(stoppingToken);
// --- MODIFICACIÓN 1: Obtener todos los ámbitos en una sola consulta ---
var ambitosASondear = await dbContext.AmbitosGeograficos var ambitosASondear = await dbContext.AmbitosGeograficos
.AsNoTracking() .AsNoTracking()
.Where(a => (a.NivelId == 10 || a.NivelId == 20) && a.DistritoId != null) .Where(a => a.NivelId == 10 && a.DistritoId != null)
.ToListAsync(stoppingToken); .ToListAsync(stoppingToken);
var provincia = ambitosASondear.FirstOrDefault(a => a.NivelId == 10); if (!categoriasDeBancas.Any() || !ambitosASondear.Any())
var seccionesElectorales = ambitosASondear.Where(a => a.NivelId == 20).ToList();
if (!categoriasDeBancas.Any() || provincia == null)
{ {
_logger.LogWarning("No se encontraron categorías de bancas o el ámbito provincial en la BD. Omitiendo sondeo de bancas."); _logger.LogWarning("No se encontraron categorías de bancas o ámbitos provinciales en la BD. Omitiendo sondeo de bancas.");
return; return;
} }
_logger.LogInformation("Iniciando sondeo de Bancas a nivel Provincial y para {count} Secciones Electorales...", seccionesElectorales.Count); _logger.LogInformation("Iniciando sondeo de Bancas a nivel Provincial para {count} provincias...", ambitosASondear.Count);
var todasLasProyecciones = new List<ProyeccionBanca>(); var todasLasProyecciones = new List<ProyeccionBanca>();
bool hasReceivedAnyNewData = false; bool hasReceivedAnyNewData = false;
// --- MODIFICACIÓN 2: Usar un diccionario para no buscar repetidamente en la BD ---
var agrupacionesEnDb = await dbContext.AgrupacionesPoliticas.ToDictionaryAsync(a => a.Id, a => a, stoppingToken); var agrupacionesEnDb = await dbContext.AgrupacionesPoliticas.ToDictionaryAsync(a => a.Id, a => a, stoppingToken);
// Bucle combinado para todos los ámbitos
foreach (var ambito in ambitosASondear) foreach (var ambito in ambitosASondear)
{ {
if (stoppingToken.IsCancellationRequested) break; if (stoppingToken.IsCancellationRequested) break;
foreach (var categoria in categoriasDeBancas) foreach (var categoria in categoriasDeBancas)
{ {
if (stoppingToken.IsCancellationRequested) break; if (stoppingToken.IsCancellationRequested) break;
// Llamada a la API (lógica adaptada para ambos niveles)
var repartoBancasDto = await _apiService.GetBancasAsync(authToken, ambito.DistritoId!, ambito.SeccionProvincialId, categoria.Id); var repartoBancasDto = await _apiService.GetBancasAsync(authToken, ambito.DistritoId!, ambito.SeccionProvincialId, categoria.Id);
if (repartoBancasDto?.RepartoBancas is { Count: > 0 } bancas) if (repartoBancasDto?.RepartoBancas is { Count: > 0 } bancas)
{ {
hasReceivedAnyNewData = true; hasReceivedAnyNewData = true;
DateTime fechaTotalizacion; DateTime fechaTotalizacion;
if (!DateTime.TryParse(repartoBancasDto.FechaTotalizacion, out var parsedDate)) if (!DateTime.TryParse(repartoBancasDto.FechaTotalizacion, out var parsedDate))
{ {
@@ -624,20 +614,17 @@ public class LowPriorityDataWorker : BackgroundService
foreach (var banca in bancas) foreach (var banca in bancas)
{ {
// --- MODIFICACIÓN 3: Lógica de "Upsert" para Agrupaciones ---
if (!agrupacionesEnDb.ContainsKey(banca.IdAgrupacion)) if (!agrupacionesEnDb.ContainsKey(banca.IdAgrupacion))
{ {
_logger.LogWarning("Agrupación con ID {AgrupacionId} ('{Nombre}') no encontrada. Creándola desde los datos de bancas.", banca.IdAgrupacion, banca.NombreAgrupacion); _logger.LogWarning("Agrupación con ID {AgrupacionId} ('{Nombre}') no encontrada. Creándola desde los datos de bancas.", banca.IdAgrupacion, banca.NombreAgrupacion);
var nuevaAgrupacion = new AgrupacionPolitica var nuevaAgrupacion = new AgrupacionPolitica
{ {
Id = banca.IdAgrupacion, Id = banca.IdAgrupacion,
Nombre = banca.NombreAgrupacion, Nombre = banca.NombreAgrupacion,
IdTelegrama = banca.IdAgrupacionTelegrama ?? string.Empty IdTelegrama = banca.IdAgrupacionTelegrama ?? string.Empty
}; };
await dbContext.AgrupacionesPoliticas.AddAsync(nuevaAgrupacion, stoppingToken); await dbContext.AgrupacionesPoliticas.AddAsync(nuevaAgrupacion, stoppingToken);
agrupacionesEnDb.Add(nuevaAgrupacion.Id, nuevaAgrupacion); // Añadir al diccionario para no volver a crearla agrupacionesEnDb.Add(nuevaAgrupacion.Id, nuevaAgrupacion);
} }
todasLasProyecciones.Add(new ProyeccionBanca todasLasProyecciones.Add(new ProyeccionBanca
@@ -658,16 +645,11 @@ public class LowPriorityDataWorker : BackgroundService
{ {
_logger.LogInformation("Se recibieron datos válidos de bancas. Procediendo a actualizar la base de datos..."); _logger.LogInformation("Se recibieron datos válidos de bancas. Procediendo a actualizar la base de datos...");
await using var transaction = await dbContext.Database.BeginTransactionAsync(stoppingToken); await using var transaction = await dbContext.Database.BeginTransactionAsync(stoppingToken);
await dbContext.SaveChangesAsync(stoppingToken); // Guardar nuevas agrupaciones si las hay
// Si se crearon nuevas agrupaciones, se guardarán aquí primero. await dbContext.Database.ExecuteSqlRawAsync("DELETE FROM ProyeccionesBancas WHERE EleccionId = {0}", EleccionId, stoppingToken); // CORRECCIÓN: Borrar solo para la elección actual
await dbContext.SaveChangesAsync(stoppingToken);
// Luego, procedemos con las proyecciones.
await dbContext.Database.ExecuteSqlRawAsync("DELETE FROM ProyeccionesBancas", stoppingToken);
await dbContext.ProyeccionesBancas.AddRangeAsync(todasLasProyecciones, stoppingToken); await dbContext.ProyeccionesBancas.AddRangeAsync(todasLasProyecciones, stoppingToken);
await dbContext.SaveChangesAsync(stoppingToken); await dbContext.SaveChangesAsync(stoppingToken);
await transaction.CommitAsync(stoppingToken); await transaction.CommitAsync(stoppingToken);
_logger.LogInformation("La tabla de proyecciones ha sido actualizada con {count} registros.", todasLasProyecciones.Count); _logger.LogInformation("La tabla de proyecciones ha sido actualizada con {count} registros.", todasLasProyecciones.Count);
} }
else else