using AutoMapper; using AutoMapper.QueryableExtensions; using IRaCIS.Application.ExpressionExtend; using IRaCIS.Application.Interfaces; using IRaCIS.Application.ViewModels.Pay; using IRaCIS.Core.Application.Contracts.RequestAndResponse; using IRaCIS.Core.Domain.Share; using IRaCIS.Infra.Data.ExpressionExtend; using System; using System.Collections.Generic; using System.Linq; using System.Linq.Expressions; using IRaCIS.Core.Domain.Interfaces; using IRaCIS.Core.Domain.Models; namespace IRaCIS.Application.Services.Pay { public class PaymentAdjustmentService : IPaymentAdjustmentService { private readonly IPaymentAdjustmentRepository _payAdjustmentRepository; private readonly IDoctorRepository _doctorRepository; private readonly IExchangeRateRepository _exchangeRateRepository; private readonly IPaymentRepository _paymentRepository; private readonly IMapper _mapper; public PaymentAdjustmentService(IPaymentAdjustmentRepository costAdjustmentRepository, IDoctorRepository doctorRepository, IExchangeRateRepository exchangeRateRepository, IPaymentRepository paymentRepository, IMapper mapper) { _payAdjustmentRepository = costAdjustmentRepository; _doctorRepository = doctorRepository; _exchangeRateRepository = exchangeRateRepository; _paymentRepository = paymentRepository; _mapper = mapper; } public IResponseOutput AddOrUpdatePaymentAdjustment(PaymentAdjustmentCommand addOrUpdateModel, Guid optUseId) { var yearMonthDate = new DateTime(addOrUpdateModel.YearMonth.Year, addOrUpdateModel.YearMonth.Month, 1); var yearMonth = addOrUpdateModel.YearMonth.ToString("yyyy-MM"); var payment = _paymentRepository.FindSingleOrDefault(u => u.DoctorId == addOrUpdateModel.ReviewerId && u.YearMonth == yearMonth); //判断付费表中是否有记录 if (payment == null) { //没有 添加仅有的调整费用记录 payment = new Payment { DoctorId = addOrUpdateModel.ReviewerId, YearMonth = yearMonth, YearMonthDate = yearMonthDate, PaymentCNY = 0, PaymentUSD = 0, AdjustmentCNY = 0, AdjustmentUSD = 0 }; _paymentRepository.Add(payment); _paymentRepository.SaveChanges(); } else { if (payment.IsLock) { return ResponseOutput.NotOk("Doctor payment has confirmed lock"); } } var exchangeRate = _exchangeRateRepository.GetAll().FirstOrDefault(t => t.YearMonth == yearMonth); if (addOrUpdateModel.Id == Guid.Empty || addOrUpdateModel.Id == null) { var costAdjustment = _mapper.Map(addOrUpdateModel); //视图模型和领域模型没对应 重新赋值 costAdjustment.ExchangeRate = exchangeRate?.Rate ?? 0; costAdjustment.AdjustmentCNY = addOrUpdateModel.AdjustPaymentUSD * (exchangeRate?.Rate ?? 0) ; costAdjustment.AdjustmentUSD = addOrUpdateModel.AdjustPaymentUSD; _payAdjustmentRepository.Add(costAdjustment); //添加的时候,每个月调整汇总费用 需要加上本次调整的费用 payment.AdjustmentCNY += costAdjustment.AdjustmentCNY; payment.AdjustmentUSD += costAdjustment.AdjustmentUSD; _paymentRepository.Update(payment); if (_payAdjustmentRepository.SaveChanges()) { return ResponseOutput.Ok(costAdjustment.Id.ToString()); } else { return ResponseOutput.NotOk(StaticData.AddFailed); } } else { // 更新的时候,先查出来,更新前的调整费用数据 var paymentAdjust = _payAdjustmentRepository.FindSingleOrDefault(t => t.Id == addOrUpdateModel.Id); _mapper.Map(addOrUpdateModel, paymentAdjust); paymentAdjust.ExchangeRate = exchangeRate?.Rate ?? 0; paymentAdjust.AdjustmentUSD = addOrUpdateModel.AdjustPaymentUSD; paymentAdjust.AdjustmentCNY = addOrUpdateModel.AdjustPaymentUSD * (exchangeRate?.Rate ?? 0); _payAdjustmentRepository.Update(paymentAdjust); var success = _payAdjustmentRepository.SaveChanges(); if (success) { var adjustmentList = _payAdjustmentRepository.Find(u=> u.ReviewerId == addOrUpdateModel.ReviewerId && u.YearMonth == yearMonth).ToList(); payment.AdjustmentCNY = adjustmentList.Sum(t => t.AdjustmentCNY); payment.AdjustmentUSD = adjustmentList.Sum(t => t.AdjustmentUSD); _paymentRepository.Update(payment); _paymentRepository.SaveChanges(); } //查询得到历史汇总 return ResponseOutput.Result(success, success ? string.Empty : StaticData.UpdateFailed); #region 逻辑存在错误 问题待查 //// 更新的时候,先查出来,更新前的调整费用数据 //var paymentAdjust = _payAdjustmentRepository.FindSingleOrDefault(t => t.Id == addOrUpdateModel.Id); ////减去数据库本条记录的值 //payment.AdjustmentCNY = -paymentAdjust.AdjustmentCNY; //payment.AdjustmentUSD = -paymentAdjust.AdjustmentUSD; //_mapper.Map(addOrUpdateModel, paymentAdjust); //paymentAdjust.ExchangeRate = exchangeRate?.Rate ?? 0; //paymentAdjust.AdjustmentUSD = addOrUpdateModel.AdjustPaymentUSD; //paymentAdjust.AdjustmentCNY = addOrUpdateModel.AdjustPaymentUSD * (exchangeRate?.Rate ?? 0); //_payAdjustmentRepository.Update(paymentAdjust); ////查询得到历史汇总 //var adjustment = _payAdjustmentRepository.Find(u => u.ReviewerId == addOrUpdateModel.ReviewerId && u.YearMonth == yearMonth) // .GroupBy(u => new { u.ReviewerId, u.YearMonth }).Select(g => new // { // AdjustCNY = g.Sum(t => t.AdjustmentCNY), // AdjustUSD = g.Sum(t => t.AdjustmentUSD) // }).FirstOrDefault(); ////最终的值 等于历史汇总 减去更新前的加上当前更新的值 //payment.AdjustmentCNY += (adjustment.AdjustCNY + paymentAdjust.AdjustmentCNY); //payment.AdjustmentUSD += (adjustment.AdjustUSD + paymentAdjust.AdjustmentUSD); //_paymentRepository.Update(payment); //var success = _payAdjustmentRepository.SaveChanges(); //return ResponseOutput.Result(success, success ? string.Empty : StaticData.UpdateFailed); #endregion } } public IResponseOutput DeleteCostAdjustment(Guid id) { var adjustPayment = _payAdjustmentRepository.FindSingleOrDefault(u => u.Id == id); var monthPay = _paymentRepository.GetAll().FirstOrDefault(t => t.DoctorId == adjustPayment.ReviewerId && t.YearMonth == adjustPayment.YearMonth); _payAdjustmentRepository.Delete(new PaymentAdjustment() { Id = id }); var success = _payAdjustmentRepository.SaveChanges(); if (success) { var adjustmentList= _payAdjustmentRepository.Find(u => u.ReviewerId == adjustPayment.ReviewerId && u.YearMonth == adjustPayment.YearMonth).ToList(); monthPay.AdjustmentCNY = adjustmentList.Sum(t=>t.AdjustmentCNY); monthPay.AdjustmentUSD = adjustmentList.Sum(t=>t.AdjustmentUSD); _paymentRepository.Update(monthPay); _paymentRepository.SaveChanges(); } return ResponseOutput.Result(success); } public PageOutput GetPaymentAdjustmentList(PaymentAdjustmentQueryDTO queryParam) { var beginYearMonth = queryParam.BeginMonth.AddDays(1 - queryParam.BeginMonth.Day); var endYearMonth = queryParam.EndMonth.AddDays(1 - queryParam.EndMonth.Day).AddMonths(1).AddDays(-1); Expression> trialLambda = x => true; var trialCode = queryParam.TrialCode.Trim(); if (!string.IsNullOrWhiteSpace(trialCode)) { trialLambda = trialLambda.And(u => u.Code.Contains(trialCode)); } Expression> doctorLambda = x => true; var reviewer = queryParam.Reviewer.Trim(); if (!string.IsNullOrWhiteSpace(reviewer)) { doctorLambda = doctorLambda.And(u => u.ChineseName.Contains(reviewer) || u.FirstName.Contains(reviewer) || u.LastName.Contains(reviewer) || u.Code.Contains(reviewer)); } var costAdjustmentQueryable = from costAdjustment in _payAdjustmentRepository.GetAll() .Where(t => t.YearMonthDate >= beginYearMonth && t.YearMonthDate <= endYearMonth) join doctor in _doctorRepository.GetAll().Where(doctorLambda) on costAdjustment.ReviewerId equals doctor.Id select new PaymentAdjustmentDetailDTO() { AdjustPaymentCNY = costAdjustment.AdjustmentCNY, AdjustPaymentUSD = costAdjustment.AdjustmentUSD, IsLock = costAdjustment.IsLock, Id = costAdjustment.Id, YearMonth = costAdjustment.YearMonth, YearMonthDate = costAdjustment.YearMonthDate, Note = costAdjustment.Note, ReviewerId = costAdjustment.ReviewerId, ReviewerCode = doctor.Code, FirstName = doctor.FirstName, LastName = doctor.LastName, ChineseName = doctor.ChineseName }; var propName = string.IsNullOrWhiteSpace(queryParam.SortField) ? "YearMonthDate" : queryParam.SortField; costAdjustmentQueryable = queryParam.Asc ? costAdjustmentQueryable.OrderBy(propName) : costAdjustmentQueryable.OrderByDescending(propName); var count = costAdjustmentQueryable.Count(); costAdjustmentQueryable = costAdjustmentQueryable.Skip((queryParam.PageIndex - 1) * queryParam.PageSize) .Take(queryParam.PageSize); var list = costAdjustmentQueryable.ToList(); return new PageOutput(queryParam.PageIndex, queryParam.PageSize, count, list); } public List GetReviewerSelectList() { return _doctorRepository.GetAll().Where(t => t.CooperateStatus == (int)ContractorStatus.Cooperation && t.ResumeStatus == (int)ResumeStatus.Pass).ProjectTo(_mapper.ConfigurationProvider).ToList(); } public void CalculateCNY(string yearMonth, decimal rate) { //如果是double 不会保留两位小数 _payAdjustmentRepository.Update(u => u.YearMonth == yearMonth && !u.IsLock, t => new PaymentAdjustment { AdjustmentCNY = t.AdjustmentUSD * rate, ExchangeRate = rate, UpdateTime = DateTime.Now }); var adjustList = _payAdjustmentRepository.GetAll().Where(u => u.YearMonth == yearMonth && !u.IsLock).ToList(); var needUpdatePayment= adjustList.GroupBy(t => t.ReviewerId).Select(g => new { ReviewerId = g.Key, AdjustCNY = g.Sum(t => t.AdjustmentCNY), AdjustUSD = g.Sum(t => t.AdjustmentUSD) }); foreach (var reviewer in needUpdatePayment) { _paymentRepository.Update(u => u.YearMonth == yearMonth && !u.IsLock && u.DoctorId == reviewer.ReviewerId, t => new Payment() { AdjustmentUSD = reviewer.AdjustUSD, AdjustmentCNY = reviewer.AdjustCNY }); } } } }