< Summary

Information
Class: FAU.Logica.Calculators.DeficitCalculator
Assembly: FAU.Logica
File(s): /home/runner/work/Sistema.Liquidacion.BE/Sistema.Liquidacion.BE/FAU.Logica/Calculators/DeficitCalculator.cs
Line coverage
94%
Covered lines: 37
Uncovered lines: 2
Coverable lines: 39
Total lines: 86
Line coverage: 94.8%
Branch coverage
94%
Covered branches: 17
Total branches: 18
Branch coverage: 94.4%
Method coverage

Feature is only available for sponsors

Upgrade to PRO version

Metrics

MethodBranch coverage Crap Score Cyclomatic complexity Line coverage
.cctor()100%210%
AplicarAsync(...)94.44%181897.36%

File(s)

/home/runner/work/Sistema.Liquidacion.BE/Sistema.Liquidacion.BE/FAU.Logica/Calculators/DeficitCalculator.cs

#LineLine coverage
 1using System;
 2using System.Collections.Generic;
 3using System.Linq;
 4using System.Threading;
 5using System.Threading.Tasks;
 6using FAU.Logica.DTOs;
 7
 8namespace FAU.Logica.Calculators
 9{
 10    /// <summary>
 11    /// Calculador de déficit que aplica descuentos personales respetando el mínimo legal (35% del bruto).
 12    /// Implementación simple: ordena por PrioridadDeficit asc y aplica hasta agotar el disponible.
 13    /// </summary>
 14    public class DeficitCalculator : IDeficitCalculator
 15    {
 016        private const decimal PorcentajeRetencionMinima = 0.35M;
 17
 18        public Task<IEnumerable<DescuentoAplicacionResult>> AplicarAsync(
 19            decimal nominalBruto,
 20            decimal descuentosLegales,
 21            IEnumerable<DescuentoPersonalInput> descuentosConfirmados,
 22            CancellationToken ct = default)
 23        {
 1724            if (descuentosConfirmados == null)
 025                return Task.FromResult(Enumerable.Empty<DescuentoAplicacionResult>());
 26
 27            // Monto que debe quedar para el afiliado: 35% del nominal bruto
 1728            var minimo = Math.Round(nominalBruto * PorcentajeRetencionMinima, 2);
 29
 30            // Disponible para descuentos personales = nominalBruto - descuentosLegales - minimo
 1731            var disponibleTotal = Math.Round(nominalBruto - descuentosLegales - minimo, 2);
 32
 1733            var resultados = new List<DescuentoAplicacionResult>();
 34
 1735            if (disponibleTotal <= 0)
 36            {
 37                // No hay espacio para descuentos personales
 1338                foreach (var d in descuentosConfirmados.OrderBy(x => x.PrioridadDeficit))
 39                {
 340                    resultados.Add(new DescuentoAplicacionResult(
 341                        d.DescuentoPeriodoId,
 342                        d.PersonaId,
 343                        d.AcreedorId,
 344                        d.MontoSolicitado,
 345                        0m,
 346                        d.MontoSolicitado,
 347                        "deficit",
 348                        "No hay disponible según mínima retención (35%)"
 349                    ));
 50                }
 51
 252                return Task.FromResult<IEnumerable<DescuentoAplicacionResult>>(resultados);
 53            }
 54
 1555            decimal restante = disponibleTotal;
 56
 19557            foreach (var d in descuentosConfirmados.OrderBy(x => x.PrioridadDeficit))
 58            {
 4059                if (ct.IsCancellationRequested) break;
 60
 3861                var aplicar = Math.Min(d.MontoSolicitado, Math.Round(Math.Max(0, restante), 2));
 62
 3863                var estado = aplicar == d.MontoSolicitado ? "aplicado"
 3864                    : aplicar > 0 ? "parcial" : "deficit";
 65
 3866                var motivo = aplicar == 0 ? "deficit" : null;
 67
 3868                resultados.Add(new DescuentoAplicacionResult(
 3869                    d.DescuentoPeriodoId,
 3870                    d.PersonaId,
 3871                    d.AcreedorId,
 3872                    d.MontoSolicitado,
 3873                    aplicar,
 3874                    d.MontoSolicitado - aplicar,
 3875                    estado,
 3876                    motivo
 3877                ));
 78
 3879                restante -= aplicar;
 5980                if (restante <= 0) restante = 0;
 81            }
 82
 1583            return Task.FromResult<IEnumerable<DescuentoAplicacionResult>>(resultados);
 84        }
 85    }
 86}