153 lines
		
	
	
		
			8.8 KiB
		
	
	
	
		
			C#
		
	
	
	
	
	
			
		
		
	
	
			153 lines
		
	
	
		
			8.8 KiB
		
	
	
	
		
			C#
		
	
	
	
	
	
| using Dapper;
 | |
| using GestionIntegral.Api.Models.Contables;
 | |
| using Microsoft.Extensions.Logging;
 | |
| using System;
 | |
| using System.Collections.Generic;
 | |
| using System.Data;
 | |
| using System.Linq;
 | |
| using System.Text;
 | |
| using System.Threading.Tasks;
 | |
| 
 | |
| namespace GestionIntegral.Api.Data.Repositories.Contables
 | |
| {
 | |
|     public class NotaCreditoDebitoRepository : INotaCreditoDebitoRepository
 | |
|     {
 | |
|         private readonly DbConnectionFactory _cf;
 | |
|         private readonly ILogger<NotaCreditoDebitoRepository> _log;
 | |
| 
 | |
|         public NotaCreditoDebitoRepository(DbConnectionFactory cf, ILogger<NotaCreditoDebitoRepository> log)
 | |
|         {
 | |
|             _cf = cf;
 | |
|             _log = log;
 | |
|         }
 | |
| 
 | |
|         private string SelectQueryBase() => @"
 | |
|             SELECT 
 | |
|                 Id_Nota AS IdNota, Destino, Id_Destino AS IdDestino, Referencia, Tipo, Fecha, 
 | |
|                 Monto, Observaciones, Id_Empresa AS IdEmpresa
 | |
|             FROM dbo.cue_CreditosDebitos";
 | |
| 
 | |
|         public async Task<IEnumerable<NotaCreditoDebito>> GetAllAsync(
 | |
|             DateTime? fechaDesde, DateTime? fechaHasta,
 | |
|             string? destino, int? idDestino, int? idEmpresa, string? tipoNota)
 | |
|         {
 | |
|             var sqlBuilder = new StringBuilder(SelectQueryBase());
 | |
|             sqlBuilder.Append(" WHERE 1=1");
 | |
|             var parameters = new DynamicParameters();
 | |
| 
 | |
|             if (fechaDesde.HasValue) { sqlBuilder.Append(" AND Fecha >= @FechaDesdeParam"); parameters.Add("FechaDesdeParam", fechaDesde.Value.Date); }
 | |
|             if (fechaHasta.HasValue) { sqlBuilder.Append(" AND Fecha <= @FechaHastaParam"); parameters.Add("FechaHastaParam", fechaHasta.Value.Date); }
 | |
|             if (!string.IsNullOrWhiteSpace(destino)) { sqlBuilder.Append(" AND Destino = @DestinoParam"); parameters.Add("DestinoParam", destino); }
 | |
|             if (idDestino.HasValue) { sqlBuilder.Append(" AND Id_Destino = @IdDestinoParam"); parameters.Add("IdDestinoParam", idDestino.Value); }
 | |
|             if (idEmpresa.HasValue) { sqlBuilder.Append(" AND Id_Empresa = @IdEmpresaParam"); parameters.Add("IdEmpresaParam", idEmpresa.Value); }
 | |
|             if (!string.IsNullOrWhiteSpace(tipoNota)) { sqlBuilder.Append(" AND Tipo = @TipoParam"); parameters.Add("TipoParam", tipoNota); }
 | |
|             
 | |
|             sqlBuilder.Append(" ORDER BY Fecha DESC, Id_Nota DESC;");
 | |
| 
 | |
|             try
 | |
|             {
 | |
|                 using var connection = _cf.CreateConnection();
 | |
|                 return await connection.QueryAsync<NotaCreditoDebito>(sqlBuilder.ToString(), parameters);
 | |
|             }
 | |
|             catch (Exception ex)
 | |
|             {
 | |
|                 _log.LogError(ex, "Error al obtener todas las Notas de Crédito/Débito.");
 | |
|                 return Enumerable.Empty<NotaCreditoDebito>();
 | |
|             }
 | |
|         }
 | |
| 
 | |
|         public async Task<NotaCreditoDebito?> GetByIdAsync(int idNota)
 | |
|         {
 | |
|             var sql = SelectQueryBase() + " WHERE Id_Nota = @IdNotaParam";
 | |
|             try
 | |
|             {
 | |
|                 using var connection = _cf.CreateConnection();
 | |
|                 return await connection.QuerySingleOrDefaultAsync<NotaCreditoDebito>(sql, new { IdNotaParam = idNota });
 | |
|             }
 | |
|             catch (Exception ex)
 | |
|             {
 | |
|                 _log.LogError(ex, "Error al obtener Nota C/D por ID: {IdNota}", idNota);
 | |
|                 return null;
 | |
|             }
 | |
|         }
 | |
| 
 | |
|         public async Task<NotaCreditoDebito?> CreateAsync(NotaCreditoDebito nuevaNota, int idUsuario, IDbTransaction transaction)
 | |
|         {
 | |
|             const string sqlInsert = @"
 | |
|                 INSERT INTO dbo.cue_CreditosDebitos (Destino, Id_Destino, Referencia, Tipo, Fecha, Monto, Observaciones, Id_Empresa)
 | |
|                 OUTPUT INSERTED.Id_Nota AS IdNota, INSERTED.Destino, INSERTED.Id_Destino AS IdDestino, INSERTED.Referencia, 
 | |
|                        INSERTED.Tipo, INSERTED.Fecha, INSERTED.Monto, INSERTED.Observaciones, INSERTED.Id_Empresa AS IdEmpresa
 | |
|                 VALUES (@Destino, @IdDestino, @Referencia, @Tipo, @Fecha, @Monto, @Observaciones, @IdEmpresa);";
 | |
|             const string sqlHistorico = @"
 | |
|                 INSERT INTO dbo.cue_CreditosDebitos_H 
 | |
|                     (Id_Nota, Destino, Id_Destino, Referencia, Tipo, Fecha, Monto, Observaciones, Id_Empresa, Id_Usuario, FechaMod, TipoMod)
 | |
|                 VALUES (@IdNotaHist, @DestinoHist, @IdDestinoHist, @ReferenciaHist, @TipoHist, @FechaHist, @MontoHist, @ObservacionesHist, @IdEmpresaHist, @IdUsuarioHist, @FechaModHist, @TipoModHist);";
 | |
| 
 | |
|             var inserted = await transaction.Connection!.QuerySingleAsync<NotaCreditoDebito>(sqlInsert, nuevaNota, transaction);
 | |
|             if (inserted == null || inserted.IdNota == 0) throw new DataException("Error al crear la nota o ID no generado.");
 | |
| 
 | |
|             await transaction.Connection!.ExecuteAsync(sqlHistorico, new {
 | |
|                 IdNotaHist = inserted.IdNota, DestinoHist = inserted.Destino, IdDestinoHist = inserted.IdDestino,
 | |
|                 ReferenciaHist = inserted.Referencia, TipoHist = inserted.Tipo, FechaHist = inserted.Fecha, MontoHist = inserted.Monto,
 | |
|                 ObservacionesHist = inserted.Observaciones, IdEmpresaHist = inserted.IdEmpresa,
 | |
|                 IdUsuarioHist = idUsuario, FechaModHist = DateTime.Now, TipoModHist = "Creada"
 | |
|             }, transaction);
 | |
|             return inserted;
 | |
|         }
 | |
| 
 | |
|         public async Task<bool> UpdateAsync(NotaCreditoDebito notaAActualizar, int idUsuario, IDbTransaction transaction)
 | |
|         {
 | |
|             var actual = await transaction.Connection!.QuerySingleOrDefaultAsync<NotaCreditoDebito>(
 | |
|                 SelectQueryBase() + " WHERE Id_Nota = @IdNotaParam",
 | |
|                 new { IdNotaParam = notaAActualizar.IdNota }, transaction);
 | |
|             if (actual == null) throw new KeyNotFoundException("Nota de Crédito/Débito no encontrada.");
 | |
| 
 | |
|             // Solo se permite actualizar Monto y Observaciones
 | |
|             const string sqlUpdate = @"
 | |
|                 UPDATE dbo.cue_CreditosDebitos SET
 | |
|                     Monto = @Monto, Observaciones = @Observaciones
 | |
|                 WHERE Id_Nota = @IdNota;";
 | |
|              const string sqlHistorico = @"
 | |
|                 INSERT INTO dbo.cue_CreditosDebitos_H 
 | |
|                     (Id_Nota, Destino, Id_Destino, Referencia, Tipo, Fecha, Monto, Observaciones, Id_Empresa, Id_Usuario, FechaMod, TipoMod)
 | |
|                 VALUES (@IdNotaHist, @DestinoHist, @IdDestinoHist, @ReferenciaHist, @TipoHist, @FechaHist, @MontoHist, @ObservacionesHist, @IdEmpresaHist, @IdUsuarioHist, @FechaModHist, @TipoModHist);";
 | |
|             
 | |
|             await transaction.Connection!.ExecuteAsync(sqlHistorico, new {
 | |
|                 IdNotaHist = actual.IdNota, DestinoHist = actual.Destino, IdDestinoHist = actual.IdDestino, ReferenciaHist = actual.Referencia,
 | |
|                 TipoHist = actual.Tipo, FechaHist = actual.Fecha, MontoHist = actual.Monto, // Valor ANTERIOR
 | |
|                 ObservacionesHist = actual.Observaciones, IdEmpresaHist = actual.IdEmpresa, // Valor ANTERIOR
 | |
|                 IdUsuarioHist = idUsuario, FechaModHist = DateTime.Now, TipoModHist = "Actualizada"
 | |
|             }, transaction);
 | |
| 
 | |
|             var rowsAffected = await transaction.Connection!.ExecuteAsync(sqlUpdate, new {
 | |
|                 notaAActualizar.Monto,
 | |
|                 notaAActualizar.Observaciones,
 | |
|                 notaAActualizar.IdNota
 | |
|             } , transaction);
 | |
|             return rowsAffected == 1;
 | |
|         }
 | |
| 
 | |
|         public async Task<bool> DeleteAsync(int idNota, int idUsuario, IDbTransaction transaction)
 | |
|         {
 | |
|             var actual = await transaction.Connection!.QuerySingleOrDefaultAsync<NotaCreditoDebito>(
 | |
|                SelectQueryBase() + " WHERE Id_Nota = @IdNotaParam",
 | |
|                new { IdNotaParam = idNota }, transaction);
 | |
|             if (actual == null) throw new KeyNotFoundException("Nota de Crédito/Débito no encontrada para eliminar.");
 | |
| 
 | |
|             const string sqlDelete = "DELETE FROM dbo.cue_CreditosDebitos WHERE Id_Nota = @IdNotaParam";
 | |
|             const string sqlHistorico = @"
 | |
|                  INSERT INTO dbo.cue_CreditosDebitos_H 
 | |
|                     (Id_Nota, Destino, Id_Destino, Referencia, Tipo, Fecha, Monto, Observaciones, Id_Empresa, Id_Usuario, FechaMod, TipoMod)
 | |
|                 VALUES (@IdNotaHist, @DestinoHist, @IdDestinoHist, @ReferenciaHist, @TipoHist, @FechaHist, @MontoHist, @ObservacionesHist, @IdEmpresaHist, @IdUsuarioHist, @FechaModHist, @TipoModHist);";
 | |
| 
 | |
|             await transaction.Connection!.ExecuteAsync(sqlHistorico, new {
 | |
|                 IdNotaHist = actual.IdNota, DestinoHist = actual.Destino, IdDestinoHist = actual.IdDestino, ReferenciaHist = actual.Referencia,
 | |
|                 TipoHist = actual.Tipo, FechaHist = actual.Fecha, MontoHist = actual.Monto, ObservacionesHist = actual.Observaciones, IdEmpresaHist = actual.IdEmpresa,
 | |
|                 IdUsuarioHist = idUsuario, FechaModHist = DateTime.Now, TipoModHist = "Eliminada"
 | |
|             }, transaction);
 | |
| 
 | |
|             var rowsAffected = await transaction.Connection!.ExecuteAsync(sqlDelete, new { IdNotaParam = idNota }, transaction);
 | |
|             return rowsAffected == 1;
 | |
|         }
 | |
|     }
 | |
| } |