public async Task <Result <GetSalaryConfigResponse> > Handle(GetSalaryConfigRequest request, CancellationToken cancellationToken) { var salaryConfig = await _salaryConfigRepository.GetAsync(); return(salaryConfig.Map(x => new GetSalaryConfigResponse( salarySetting: new SalarySettingResponse( id: x.Id, commonMinimumWage: x.CommonMinimumWage, regionalMinimumWage: x.RegionalMinimumWage, coefficientSocialCare: x.CoefficientSocialCare, employerSocialInsuranceRate: x.EmployerSocialInsuranceRate, employeeSocialInsuranceRate: x.EmployeeSocialInsuranceRate, employerHealthCareInsuranceRate: x.EmployerHealthCareInsuranceRate, employeeHealthCareInsuranceRate: x.EmployeeHealthCareInsuranceRate, employeeUnemploymentInsuranceRate: x.EmployeeUnemploymentInsuranceRate, employerUnemploymentInsuranceRate: x.EmployerUnemploymentInsuranceRate, foreignEmployerSocialInsuranceRate: x.ForeignEmployerSocialInsuranceRate, foreignEmployeeSocialInsuranceRate: x.ForeignEmployeeSocialInsuranceRate, foreignHealthCareInsuranceEmployeeRate: x.ForeignEmployeeHealthCareInsuranceRate, foreignHealthCareInsuranceEmployerRate: x.ForeignEmployerHealthCareInsuranceRate, foreignUnemploymentInsuranceEmployeeRate: x.ForeignEmployeeUnemploymentInsuranceRate, foreignUnemploymentInsuranceEmployerRate: x.ForeignEmployerUnemploymentInsuranceRate, employeeUnionFeeRate: x.EmployeeUnionFeeRate, employerUnionFeeRate: x.EmployerUnionFeeRate, maximumUnionFeeRate: x.MaximumUnionFeeRate, defaultProbationTaxRate: x.DefaultProbationTaxRate, isInsurancePaidFullSalary: x.IsInsurancePaidFullSalary, insurancePaidAmount: x.InsurancePaidAmount, personalDeduction: x.PersonalDeduction, dependantDeduction: x.DependantDeduction, currency: x.CommonMinimumWage.Currency, minimumNonWorkingDay: x.MinimumNonWorkingDay), progressiveTaxRates: x.ProgressiveTaxRateLookUpTable.AsReadOnlyCollection() .Select(x => new ProgressiveTaxRateResponse( lowerBound: x.LowerBound, upperBound: x.UpperBound, taxRateLevel: x.ProgressiveTaxRateLevel, rate: x.Rate)).ToList() ))); }
public async Task <Result <PreviewEmpMonthlySalaryResponse> > Handle( PreviewEmpMonthlySalaryRequest request, CancellationToken cancellationToken) { // get calculated salary var calculatedSalaries = await _salaryRepo.GetAsync(request.Key, request.YearMonth); if (calculatedSalaries.Failure) { return(calculatedSalaries.Error); } if (calculatedSalaries.Data.Length > 0) { return(Result <PreviewEmpMonthlySalaryResponse> .Ok(new PreviewEmpMonthlySalaryResponse( calculatedSalaries.Data.Select(x => new PreviewEmpMonthlySalary( fullname: x.Fullname, email: x.Email, employeeType: x.EmployeeType, position: x.Position, numberOfDependants: x.NumberOfDependants, standardWorkingDays: x.StandardWorkingDays, actualWorkingDays: x.ActualWorkingDays, grossContractSalary: x.GrossContractSalary, insuranceSalary: x.InsuranceSalary, actualGrossSalary: x.ActualGrossSalary, taxableIncome: x.TaxableIncome, totalMonthlyIncome: x.TotalMonthlyIncome, employeeSocialInsurance: x.EmployeeSocialInsurance, employeeHealthcareInsurance: x.EmployeeHealthcareInsurance, employeeUnemploymentInsurance: x.EmployeeUnemploymentInsurance, employeeUnionFee: x.EmployeeUnionFee, employerSocialInsurance: x.EmployerSocialInsurance, employerHealthcareInsurance: x.EmployerHealthcareInsurance, employerUnemploymentInsurance: x.EmployerUnemploymentInsurance, employerUnionFee: x.EmployerUnionFee, personalDeduction: x.PersonalDeduction, dependantDeduction: x.DependantDeduction, assessableIncome: x.AssessableIncome, netIncome: x.NetIncome, pit: x.PIT, totalSalaryCost: x.TotalSalaryCost, paymentAdvance: x.PaymentAdvance, taxableAllowances: x.TaxableAllowances, nonTaxableAllowances: x.NonTaxableAllowances.Select(x => x.Amount.Value).Sum(), netPayment: x.NetPayment, adjustmentAddition: x.AdjustmentAddition, adjustmentDeduction: x.AdjustmentDeduction)).OrderBy(x => x.Fullname).ToArray()))); } var salaryConfig = await _configRepo.GetAsync(); var recordsRepo = await _recordRepo.GetAsync(request.YearMonth, request.Key); var profilesRepo = await _profileRepo.GetAsync(request.YearMonth); var records = salaryConfig.Map(() => profilesRepo).Map(() => recordsRepo) .Map(x => recordsRepo.Data.records.Where(y => profilesRepo.Data.Any(z => y.Email == z.Email)).ToList()); var result = await records.Map(x => MapModelToCalculateSalary(x, profilesRepo.Data, recordsRepo.Data.standardWorkingDays)) .Map(x => Main.GeneratePayRollRecord(x.ToArray(), salaryConfig.Data)) // add new month records if there is no current month records. .ExecuteAsync(x => _recordRepo.SaveAsync(records.Data, request.YearMonth, request.Key, recordsRepo.Data.standardWorkingDays)) // save calculated salary to db .ExecuteAsync(x => _salaryRepo.SaveAsync(x, request.Key, request.YearMonth)); return(result.Map(x => new PreviewEmpMonthlySalaryResponse( x.Select(y => new PreviewEmpMonthlySalary( fullname: y.Fullname, email: y.Email, employeeType: y.EmployeeType, position: y.Position, numberOfDependants: y.NumberOfDependants, standardWorkingDays: y.StandardWorkingDays, actualWorkingDays: y.ActualWorkingDays, grossContractSalary: y.GrossContractSalary, insuranceSalary: y.InsuranceSalary, actualGrossSalary: y.ActualGrossSalary, taxableIncome: y.TaxableIncome, totalMonthlyIncome: y.TotalMonthlyIncome, employeeSocialInsurance: y.EmployeeSocialInsurance, employeeHealthcareInsurance: y.EmployeeHealthcareInsurance, employeeUnemploymentInsurance: y.EmployeeUnemploymentInsurance, employeeUnionFee: y.EmployeeUnionFee, employerSocialInsurance: y.EmployerSocialInsurance, employerHealthcareInsurance: y.EmployerHealthcareInsurance, employerUnemploymentInsurance: y.EmployerUnemploymentInsurance, employerUnionFee: y.EmployerUnionFee, personalDeduction: y.PersonalDeduction, dependantDeduction: y.DependantDeduction, assessableIncome: y.AssessableIncome, netIncome: y.NetIncome, pit: y.PIT, totalSalaryCost: y.TotalSalaryCost, paymentAdvance: y.PaymentAdvance, taxableAllowances: y.TaxableAllowances, nonTaxableAllowances: y.NonTaxableAllowances.Select(z => z.Amount.Value).Sum(), netPayment: y.NetPayment, adjustmentAddition: y.AdjustmentAddition, adjustmentDeduction: y.AdjustmentDeduction)).ToArray()))); }
public async Task <Result <ExportEmpMonthlySalaryResponse> > Handle(ExportEmpMonthlySalaryRequest request, CancellationToken cancellationToken) { var salaryConfig = await _salaryConfigRepo.GetAsync(); var previewResult = await _mediator.Send(new PreviewEmpMonthlySalaryRequest { Key = request.Key, YearMonth = request.YearMonth }); try { return(await salaryConfig.Map(() => previewResult).Map(x => { var salaries = x.Salaries.GroupBy(x => x.Email).Select((y, index) => { var salary = y.FirstOrDefault(); return new ExportEmpMonthlySalary { No = $"{index + 1}", Fullname = salary.Fullname, Email = salary.Email, EmployeeType = y.Count() == 2 ? $"{EmployeeTypeEnum.Probation}/{EmployeeTypeEnum.Permanent}" : salary.EmployeeType, Position = salary.Position, StandardWorkingDays = salary.StandardWorkingDays, ActualWorkingDays = y.Sum(z => z.ActualWorkingDays), GrossContractSalary = salary.GrossContractSalary, InsuranceSalary = salary.InsuranceSalary, ActualGrossSalary = y.Sum(z => z.ActualGrossSalary), NonTaxableAllowances = y.Sum(z => z.NonTaxableAllowances), Taxable13MonthSalary = y.Sum(z => z.Taxable13MonthSalary), TaxableAnnualLeave = y.Sum(z => z.TaxableAnnualLeave), TaxableOthers = y.Sum(z => z.TaxableOthers), TotalMonthlyIncome = y.Sum(z => z.TotalMonthlyIncome), TaxableIncome = y.Sum(z => z.TaxableIncome), EmployeeSocialInsurance = y.Sum(z => z.EmployeeSocialInsurance), EmployeeHealthcareInsurance = y.Sum(z => z.EmployeeHealthcareInsurance), EmployeeUnemploymentInsurance = y.Sum(z => z.EmployeeUnemploymentInsurance), EmployeeUnionFee = y.Sum(z => z.EmployeeUnionFee), EmployerSocialInsurance = y.Sum(z => z.EmployerSocialInsurance), EmployerHealthcareInsurance = y.Sum(z => z.EmployerHealthcareInsurance), EmployerUnemploymentInsurance = y.Sum(z => z.EmployerUnemploymentInsurance), EmployerUnionFee = y.Sum(z => z.EmployerUnionFee), PersonalDeduction = salary.PersonalDeduction, NumberOfDependants = salary.NumberOfDependants, DependantDeduction = salary.DependantDeduction, AssessableIncome = y.Sum(z => z.AssessableIncome), NetIncome = y.Sum(z => z.NetIncome), PIT = y.Sum(z => z.PIT), TotalSalaryCost = y.Sum(z => z.TotalSalaryCost), PaymentAdvance = salary.PaymentAdvance, AdjustmentDeduction = salary.AdjustmentDeduction, AdjustmentAddition = salary.AdjustmentAddition, NetPayment = y.Sum(z => z.NetPayment), }; }).ToList(); salaries.Add(new ExportEmpMonthlySalary { No = "Grand Total", StandardWorkingDays = salaries.Sum(y => y.StandardWorkingDays), ActualWorkingDays = salaries.Sum(y => y.ActualWorkingDays), GrossContractSalary = salaries.Sum(y => y.GrossContractSalary), InsuranceSalary = salaries.Sum(y => y.InsuranceSalary), ActualGrossSalary = salaries.Sum(y => y.ActualGrossSalary), NonTaxableAllowances = salaries.Sum(y => y.NonTaxableAllowances), Taxable13MonthSalary = salaries.Sum(y => y.Taxable13MonthSalary), TaxableAnnualLeave = salaries.Sum(y => y.TaxableAnnualLeave), TaxableOthers = salaries.Sum(y => y.TaxableOthers), TotalMonthlyIncome = salaries.Sum(y => y.TotalMonthlyIncome), TaxableIncome = salaries.Sum(y => y.TaxableIncome), EmployeeSocialInsurance = salaries.Sum(y => y.EmployeeSocialInsurance), EmployeeHealthcareInsurance = salaries.Sum(y => y.EmployeeHealthcareInsurance), EmployeeUnemploymentInsurance = salaries.Sum(y => y.EmployeeUnemploymentInsurance), EmployeeUnionFee = salaries.Sum(y => y.EmployeeUnionFee), EmployerSocialInsurance = salaries.Sum(y => y.EmployerSocialInsurance), EmployerHealthcareInsurance = salaries.Sum(y => y.EmployerHealthcareInsurance), EmployerUnemploymentInsurance = salaries.Sum(y => y.EmployerUnemploymentInsurance), EmployerUnionFee = salaries.Sum(y => y.EmployerUnionFee), PersonalDeduction = salaries.Sum(y => y.PersonalDeduction), NumberOfDependants = salaries.Sum(y => y.NumberOfDependants), DependantDeduction = salaries.Sum(y => y.DependantDeduction), AssessableIncome = salaries.Sum(y => y.AssessableIncome), NetIncome = salaries.Sum(y => y.NetIncome), PIT = salaries.Sum(y => y.PIT), TotalSalaryCost = salaries.Sum(y => y.TotalSalaryCost), PaymentAdvance = salaries.Sum(y => y.PaymentAdvance), AdjustmentDeduction = salaries.Sum(y => y.AdjustmentDeduction), AdjustmentAddition = salaries.Sum(y => y.AdjustmentAddition), NetPayment = salaries.Sum(y => y.NetPayment) }); return salaries; }) .MapAsync(x => _fileHelper.CreateCsvByteArrayAsync(x, salaryConfig.Data, request.YearMonth)) .MapAsync(x => new ExportEmpMonthlySalaryResponse { CsvSalaries = x })); } catch (CsvHelperException ex) { _logger.LogError(ex, Errors.ExportEmpMonthlySalary.ExportWriteCSVError.Message); return(Errors.ExportEmpMonthlySalary.ExportWriteCSVError); } }