Files
2026-04-20 14:47:24 -05:00

164 lines
7.6 KiB
C#

using System;
using System.Collections.Generic;
using System.Linq;
using LCU.API.Collections.RepoApi.Domain.FloorPricing;
using LCU.API.Collections.RepoApi.Domain.FloorPricing.Strategies;
using LCU.API.Collections.RepoApi.Exceptions;
using LCU.Shared.Collections.RepoApiLib.Models;
using LCU.Shared.Collections.RepoApiLib.WebServices.NADA;
using Serilog;
namespace LCU.API.Collections.RepoApi.Services
{
public class FloorPricingService : IFloorPricingService
{
private readonly IFloorPricingStrategyFactory _floorFloorPricingStrategyFactory;
private readonly IImsAutoFileDataService _imsAutoFileDataService;
private readonly IVehicleFloorPricingParametersService _vehicleFloorPricingParametersService;
private readonly ICollateralValueService _collateralValueService;
public FloorPricingService(
IFloorPricingStrategyFactory floorFloorPricingStrategyFactory,
IVehicleFloorPricingParametersService vehicleFloorPricingParametersService,
IImsAutoFileDataService imsAutoFileDataService,
ICollateralValueService collateralValueService)
{
_floorFloorPricingStrategyFactory = floorFloorPricingStrategyFactory;
_vehicleFloorPricingParametersService = vehicleFloorPricingParametersService;
_imsAutoFileDataService = imsAutoFileDataService;
_collateralValueService = collateralValueService;
}
public FloorPriceCalculationResultSet DetermineFloorPrice(int auctionAssignmentId)
{
CollateralValuation collateralValuation = new CollateralValuation { };
ImsAutoFileData imsAutoFileData = new ImsAutoFileData { };
var floorPricingParams = _vehicleFloorPricingParametersService.ListAll().GetAwaiter().GetResult();
try
{
imsAutoFileData = _imsAutoFileDataService.GetByAuctionAssignmentId(auctionAssignmentId).GetAwaiter().GetResult();
collateralValuation = GetCollateralValuation(imsAutoFileData.VIN, imsAutoFileData.StatedMileage ?? 0, 0);
}
catch (Exception ex)
{
Log.Error(ex, $"Error when trying to Determine Floor Price for auctionAssignment with id: ${auctionAssignmentId}");
}
FloorPriceCalculationParams fpcParams = new FloorPriceCalculationParams()
{
VehicleFloorPricingParameters = floorPricingParams,
ImsAutoFileData = imsAutoFileData,
CollateralValuation = collateralValuation
};
var prices = GetCalculatedFloorPrices(fpcParams);
var price = SelectBestFloorPrice(prices);
var floorPriceValuesUsed = PopulateFloorPriceValuesUsed(auctionAssignmentId, fpcParams, prices, price);
FloorPriceCalculationResultSet strategicResultSet = new FloorPriceCalculationResultSet { };
strategicResultSet.AllResults = prices;
strategicResultSet.PrimaryResult = price;
strategicResultSet.FloorPriceValuesUsed = floorPriceValuesUsed;
return strategicResultSet;
}
public CollateralValuation GetCollateralValuation(string VIN, int StatedMileage, int vehichleTypeKey)
{
CollateralValuation collateralValuation = new CollateralValuation { };
try
{
collateralValuation = _collateralValueService.GetCollateralValue(VIN, StatedMileage, vehichleTypeKey);
}
catch (Exception ex)
{
if (ex.Message.Contains("license"))
{
Log.Error(ex, "Your collateral value service license may be invalid/expired, please notify the collections department administration.");
}
Log.Error(ex, "NADA ERROR when getting Collateral Value");
}
return collateralValuation;
}
public IReadOnlyCollection<FloorPriceCalculationResult> GetCalculatedFloorPrices(FloorPriceCalculationParams fpcParams)
{
IReadOnlyCollection<IFloorPricingStrategy> strategies =
_floorFloorPricingStrategyFactory.GetFloorPricingStrategies();
List<FloorPriceCalculationResult> calculationResults = new List<FloorPriceCalculationResult>();
foreach (var floorPricingStrategy in strategies)
{
calculationResults.Add(floorPricingStrategy.CalculateFloorPrice(fpcParams));
}
return calculationResults;
}
public FloorPriceCalculationResult SelectBestFloorPrice(IReadOnlyCollection<FloorPriceCalculationResult> results)
{
var successWeight = -1;
FloorPriceCalculationResult successResult = null;
foreach (var result in results)
{
if (result.ResultWeight > successWeight && result.Success)
{
successWeight = result.ResultWeight;
successResult = result;
}
}
if (successResult == null)
{
return new FloorPriceCalculationResult()
{
ResultWeight = -1,
Success = false,
StrategyName = "Manual",
FloorPrice = -1
};
}
return successResult;
}
public FloorPriceValuesUsed PopulateFloorPriceValuesUsed(int auctionAssignmentId, FloorPriceCalculationParams fpcParams, IReadOnlyCollection<FloorPriceCalculationResult> prices,
FloorPriceCalculationResult bestPrice)
{
var result = new FloorPriceValuesUsed
{
AuctionAssignmentId = auctionAssignmentId,
RepoId = fpcParams.ImsAutoFileData.RepoId,
CollateralValuation = fpcParams.CollateralValuation
};
result.AuctionGuideBookPrice = fpcParams.ImsAutoFileData.AuctionGuideBookPrice;
var autoImsResult = prices.FirstOrDefault(x => x.StrategyName.Equals(typeof(AutoImsSuggestedValue).FullName));
result.WasAuctionGuideBookPriceUsed = autoImsResult != null && autoImsResult.Success && autoImsResult.FloorPrice == bestPrice.FloorPrice;
var nadaMmrResult = prices.FirstOrDefault(x => x.StrategyName.Equals(typeof(NadaMmrConditionValue).FullName));
result.MMRNationalAdjustedPrice = fpcParams.ImsAutoFileData.MMRNationalAdjustedPrice;
result.MMRRegionalAdjustedPrice = fpcParams.ImsAutoFileData.MMRRegionalAdjustedPrice;
result.NADALowAdjustedAuctionValue = fpcParams.CollateralValuation.LowAdjustedAuctionValue;
result.NADAAverageAdjustedAuctionValue = fpcParams.CollateralValuation.AverageAdjustedAuctionValue;
result.NADAHighAdjustedAuctionValue = fpcParams.CollateralValuation.HighAdjustedAuctionValue;
result.Condition = fpcParams.ImsAutoFileData.ApprovedVehicleGrade ?? fpcParams.ImsAutoFileData.VehicleGrade;
if (result.Condition == null || result.Condition <= 0)
{
return result;
}
var vfpParams = Enumerable.First(Enumerable.Where(fpcParams.VehicleFloorPricingParameters,
x => result.Condition >= x.LowCondition && result.Condition <= x.HighCondition));
result.LowParam = vfpParams.LowCondition;
result.HighParam = vfpParams.HighCondition;
result.PercentageOf = vfpParams.PercentageOf;
var hasMmrPrice = fpcParams.ImsAutoFileData.MMRNationalAdjustedPrice != null || fpcParams.ImsAutoFileData.MMRRegionalAdjustedPrice != null;
result.WasAuctionGuideBookPriceUsed = autoImsResult != null && autoImsResult.Success && autoImsResult.StrategyName == bestPrice.StrategyName || (!hasMmrPrice && autoImsResult.FloorPrice > 0);
result.WasMMRNationalAdjustedPriceUsed = nadaMmrResult != null && nadaMmrResult.Success && vfpParams.MMRAdjustedValue.ToLower().StartsWith("national") && hasMmrPrice;
result.WasMMRRegionalAdjustedPriceUsed = nadaMmrResult != null && nadaMmrResult.Success && vfpParams.MMRAdjustedValue.ToLower().StartsWith("regional") && hasMmrPrice;
result.WasNADALowAdjustedAuctionValueUsed = nadaMmrResult != null && nadaMmrResult.Success && vfpParams.NADAFirstValue.ToLower().StartsWith("low") || vfpParams.NADASecondValue.ToLower().StartsWith("low");
result.WasNADAAverageAdjustedAuctionValueUsed = nadaMmrResult != null && nadaMmrResult.Success && vfpParams.NADAFirstValue.ToLower().StartsWith("avg") || vfpParams.NADASecondValue.ToLower().StartsWith("avg");
result.WasNADAHighAdjustedAuctionValueUsed = nadaMmrResult != null && nadaMmrResult.Success && vfpParams.NADAFirstValue.ToLower().StartsWith("high") || vfpParams.NADASecondValue.ToLower().StartsWith("high");
return result;
}
}
}