99 changed files with 2511 additions and 214 deletions
@ -0,0 +1,92 @@ |
|||
package com.qs.serve.modules.bir.entity; |
|||
|
|||
import java.time.LocalDate; |
|||
import java.io.Serializable; |
|||
import java.math.BigDecimal; |
|||
import java.time.LocalDateTime; |
|||
|
|||
import com.baomidou.mybatisplus.annotation.*; |
|||
import com.fasterxml.jackson.annotation.JsonFormat; |
|||
import com.fasterxml.jackson.annotation.JsonIgnore; |
|||
import com.fasterxml.jackson.annotation.JsonProperty; |
|||
import lombok.Data; |
|||
import org.hibernate.validator.constraints.Length; |
|||
import org.springframework.format.annotation.DateTimeFormat; |
|||
|
|||
import javax.validation.constraints.NotNull; |
|||
import javax.validation.constraints.NotBlank; |
|||
|
|||
/** |
|||
* 实体类 |
|||
* @author YenHex |
|||
* @since 2024-06-05 |
|||
*/ |
|||
@Data |
|||
@TableName("bir_budget_target") |
|||
public class BirBudgetTarget implements Serializable { |
|||
|
|||
private static final long serialVersionUID = 1L; |
|||
|
|||
/** id */ |
|||
@TableId(type = IdType.AUTO) |
|||
private Long id; |
|||
|
|||
/** 搜索维度:0-客户;1-城市;2-省级经理;3-大区经理 */ |
|||
private Integer searchType; |
|||
|
|||
/** 年份 */ |
|||
private Integer yearNum; |
|||
|
|||
/** 季度 */ |
|||
private Integer quarterNum; |
|||
|
|||
/** 月份 */ |
|||
private Integer monthNum; |
|||
|
|||
/** 销售目标 */ |
|||
private BigDecimal targetAmt; |
|||
|
|||
/** 预算金额 */ |
|||
private BigDecimal budgetAmt; |
|||
|
|||
/** 实际发货 */ |
|||
private BigDecimal dispatchAmt; |
|||
|
|||
/** 去年同期发货 */ |
|||
private BigDecimal lastYearDispatchAmt; |
|||
|
|||
/** 城+省费用 */ |
|||
private BigDecimal provinceCityAmt; |
|||
|
|||
/** 城+省+区费用 */ |
|||
private BigDecimal provinceCityRegionAmt; |
|||
|
|||
/** 实际总费用 */ |
|||
private BigDecimal totalRealAmt; |
|||
|
|||
private String brandId; |
|||
|
|||
/** 品牌编码 */ |
|||
@Length(max = 255,message = "品牌编码长度不能超过255字") |
|||
private String brandCode; |
|||
|
|||
/** 品牌 */ |
|||
@Length(max = 255,message = "品牌长度不能超过255字") |
|||
private String brandName; |
|||
|
|||
/** 成本中心类型:saleRegion; bizRegion; costCenter; supplier */ |
|||
@Length(max = 255,message = "成本中心类型:saleRegion; bizRegion; costCenter; supplier长度不能超过255字") |
|||
private String centerType; |
|||
|
|||
private String centerId; |
|||
|
|||
/** 成本中心编码 */ |
|||
@Length(max = 255,message = "成本中心编码长度不能超过255字") |
|||
private String centerCode; |
|||
|
|||
/** 成本中心名 */ |
|||
@Length(max = 255,message = "成本中心名长度不能超过255字") |
|||
private String centerName; |
|||
|
|||
} |
|||
|
@ -0,0 +1,71 @@ |
|||
package com.qs.serve.modules.bir.entity.so; |
|||
|
|||
import com.fasterxml.jackson.annotation.JsonFormat; |
|||
import lombok.Data; |
|||
import org.springframework.format.annotation.DateTimeFormat; |
|||
|
|||
import java.time.LocalDate; |
|||
import java.time.LocalDateTime; |
|||
import java.util.List; |
|||
|
|||
/** |
|||
* @author YenHex |
|||
* @since 2024/6/4 |
|||
*/ |
|||
@Data |
|||
public class BirBudgetTargetSo { |
|||
|
|||
/** 搜索维度:0-客户;1-城市;2-省级经理;3-大区经理 */ |
|||
private Integer loadType; |
|||
|
|||
/** |
|||
* 开始时间 |
|||
*/ |
|||
@JsonFormat(pattern = "yyyy-MM-dd HH:mm:ss",timezone = "GMT+8") |
|||
@DateTimeFormat(pattern = "yyyy-MM-dd HH:mm:ss") |
|||
private LocalDateTime yearMonthStart; |
|||
@JsonFormat(pattern = "yyyy-MM-dd HH:mm:ss",timezone = "GMT+8") |
|||
@DateTimeFormat(pattern = "yyyy-MM-dd HH:mm:ss") |
|||
private LocalDateTime yearMonthEnd; |
|||
|
|||
/** |
|||
* 业务待定 |
|||
*/ |
|||
private String supplierId; |
|||
|
|||
/** |
|||
* 成本中心 |
|||
*/ |
|||
private List<CostInfo> centerList; |
|||
|
|||
/**品牌 */ |
|||
private List<String> brandIds; |
|||
|
|||
/** |
|||
* 减少xml条件 |
|||
*/ |
|||
private Integer selectCenterFlag; |
|||
|
|||
/**成本中心编码 */ |
|||
private List<String> centerIds; |
|||
|
|||
/**行政区域-成本中心编码 */ |
|||
private List<String> bizRegionIds; |
|||
|
|||
/**销售区域-成本中心编码 */ |
|||
private List<String> saleRegionIds; |
|||
|
|||
/**客户-成本中心编码 */ |
|||
private List<String> supplierIds; |
|||
|
|||
@Data |
|||
public static class CostInfo{ |
|||
/** |
|||
* center,saleRegion,bizRegion,supplier |
|||
*/ |
|||
private String costType; |
|||
|
|||
private String costId; |
|||
} |
|||
|
|||
} |
@ -0,0 +1,61 @@ |
|||
package com.qs.serve.modules.bir.entity.vo; |
|||
|
|||
import lombok.Data; |
|||
import org.hibernate.validator.constraints.Length; |
|||
|
|||
import java.math.BigDecimal; |
|||
|
|||
/** |
|||
* @author YenHex |
|||
* @since 2024/6/4 |
|||
*/ |
|||
@Data |
|||
public class BirBudgetTargetVo { |
|||
|
|||
/** 年份 */ |
|||
private Integer yearNum; |
|||
|
|||
/** 月份 */ |
|||
private Integer monthNum; |
|||
|
|||
/** 销售目标 */ |
|||
private BigDecimal targetAmt; |
|||
|
|||
/** 预算金额 */ |
|||
private BigDecimal budgetAmt; |
|||
|
|||
/** 实际发货 */ |
|||
private BigDecimal dispatchAmt; |
|||
|
|||
/** 实际总费用 */ |
|||
private BigDecimal totalRealAmt; |
|||
|
|||
/** 去年同期发货 */ |
|||
private BigDecimal lastYearDispatchAmt; |
|||
|
|||
/** 城+省费用 */ |
|||
private BigDecimal provinceCityAmt; |
|||
|
|||
/** 城+省+区费用 */ |
|||
private BigDecimal provinceCityRegionAmt; |
|||
|
|||
|
|||
/** 预算费用率 */ |
|||
private BigDecimal budgetRate; |
|||
|
|||
/** 发货达成率 */ |
|||
private BigDecimal dispatchRate; |
|||
|
|||
/** 同期成长率*/ |
|||
private BigDecimal lastYearGrowRate; |
|||
|
|||
/** 城+省费用率 */ |
|||
private BigDecimal provinceCityRate; |
|||
|
|||
/** 城+省+区费用率 */ |
|||
private BigDecimal provinceCityRegionRate; |
|||
|
|||
/** 实际总费用率 */ |
|||
private BigDecimal totalRealRate; |
|||
|
|||
} |
@ -0,0 +1,22 @@ |
|||
package com.qs.serve.modules.bir.mapper; |
|||
|
|||
import com.baomidou.mybatisplus.annotation.InterceptorIgnore; |
|||
import com.baomidou.mybatisplus.core.mapper.BaseMapper; |
|||
import com.qs.serve.modules.bir.entity.BirBudgetTarget; |
|||
import com.qs.serve.modules.bir.entity.so.BirBudgetTargetSo; |
|||
import org.apache.ibatis.annotations.Param; |
|||
|
|||
import java.util.List; |
|||
|
|||
/** |
|||
* Mapper |
|||
* @author YenHex |
|||
* @date 2024-06-04 |
|||
*/ |
|||
public interface BirBudgetTargetMapper extends BaseMapper<BirBudgetTarget> { |
|||
|
|||
@InterceptorIgnore(tenantLine = "1") |
|||
List<BirBudgetTarget> selectBirBudgetTargetList(@Param("query") BirBudgetTargetSo budgetTargetSo); |
|||
|
|||
} |
|||
|
@ -0,0 +1,20 @@ |
|||
package com.qs.serve.modules.bir.service; |
|||
|
|||
import com.baomidou.mybatisplus.extension.service.IService; |
|||
import com.qs.serve.modules.bir.entity.BirBudgetTarget; |
|||
import com.qs.serve.modules.bir.entity.so.BirBudgetTargetSo; |
|||
import com.qs.serve.modules.bir.entity.vo.BirBudgetTargetVo; |
|||
|
|||
import java.util.List; |
|||
|
|||
/** |
|||
* 服务接口 |
|||
* @author YenHex |
|||
* @date 2024-06-04 |
|||
*/ |
|||
public interface BirBudgetTargetService extends IService<BirBudgetTarget> { |
|||
|
|||
List<BirBudgetTargetVo> listVo(BirBudgetTargetSo query); |
|||
|
|||
} |
|||
|
@ -0,0 +1,116 @@ |
|||
package com.qs.serve.modules.bir.service.impl; |
|||
|
|||
import cn.hutool.core.collection.CollUtil; |
|||
import com.baomidou.mybatisplus.extension.service.impl.ServiceImpl; |
|||
import com.qs.serve.modules.bir.entity.so.BirBudgetTargetSo; |
|||
import com.qs.serve.modules.bir.entity.vo.BirBudgetTargetVo; |
|||
import lombok.AllArgsConstructor; |
|||
import lombok.extern.slf4j.Slf4j; |
|||
import org.springframework.stereotype.Service; |
|||
import com.qs.serve.modules.bir.entity.BirBudgetTarget; |
|||
import com.qs.serve.modules.bir.service.BirBudgetTargetService; |
|||
import com.qs.serve.modules.bir.mapper.BirBudgetTargetMapper; |
|||
|
|||
import java.math.BigDecimal; |
|||
import java.math.RoundingMode; |
|||
import java.time.LocalDate; |
|||
import java.time.LocalDateTime; |
|||
import java.time.temporal.TemporalAdjuster; |
|||
import java.time.temporal.TemporalAdjusters; |
|||
import java.util.ArrayList; |
|||
import java.util.List; |
|||
import java.util.Map; |
|||
import java.util.stream.Collectors; |
|||
|
|||
/** |
|||
* 服务实现类 |
|||
* @author YenHex |
|||
* @since 2024-06-04 |
|||
*/ |
|||
@Slf4j |
|||
@Service |
|||
@AllArgsConstructor |
|||
public class BirBudgetTargetServiceImpl extends ServiceImpl<BirBudgetTargetMapper,BirBudgetTarget> implements BirBudgetTargetService { |
|||
|
|||
@Override |
|||
public List<BirBudgetTargetVo> listVo(BirBudgetTargetSo query) { |
|||
query.setLoadType(query.getLoadType()+1); |
|||
LocalDateTime endMonth = query.getYearMonthEnd(); |
|||
LocalDateTime startMonth = query.getYearMonthStart(); |
|||
//格式化
|
|||
startMonth = startMonth.withDayOfMonth(1).toLocalDate().atTime(0,0,0); |
|||
endMonth = endMonth.with(TemporalAdjusters.lastDayOfMonth()).toLocalDate().atTime(23,59,59); |
|||
query.setYearMonthStart(startMonth); |
|||
query.setYearMonthEnd(endMonth); |
|||
query.setSelectCenterFlag(0); |
|||
if(CollUtil.isNotEmpty(query.getCenterList())){ |
|||
query.setSelectCenterFlag(1); |
|||
} |
|||
|
|||
List<BirBudgetTarget> birBudgetTargets = baseMapper.selectBirBudgetTargetList(query); |
|||
|
|||
Map<String,List<BirBudgetTarget>> listMap = birBudgetTargets.stream() |
|||
.collect(Collectors.groupingBy(obj->obj.getYearNum()+"_"+obj.getMonthNum())); |
|||
|
|||
List<BirBudgetTargetVo> budgetTargetVoList = new ArrayList<>(); |
|||
|
|||
|
|||
//12个月
|
|||
final int TOTAL_MONTH = 12; |
|||
for (int y = startMonth.getYear(); y <= endMonth.getYear(); y++) { |
|||
for (int m = 1; m <= TOTAL_MONTH; m++) { |
|||
//防止多空白行
|
|||
if(y == startMonth.getYear() && m < startMonth.getMonthValue()){ |
|||
continue; |
|||
} |
|||
if(y == endMonth.getYear() && m > endMonth.getMonthValue()){ |
|||
continue; |
|||
} |
|||
budgetTargetVoList.add(getBudgetTargetVo(listMap, m, y)); |
|||
} |
|||
} |
|||
return budgetTargetVoList; |
|||
} |
|||
|
|||
private BirBudgetTargetVo getBudgetTargetVo(Map<String, List<BirBudgetTarget>> listMap, int month, int year) { |
|||
List<BirBudgetTarget> mList = listMap.get(year +"_"+ month); |
|||
BirBudgetTargetVo targetVo = new BirBudgetTargetVo(); |
|||
targetVo.setYearNum(year); |
|||
targetVo.setMonthNum(month); |
|||
targetVo.setTargetAmt(BigDecimal.ZERO); |
|||
targetVo.setBudgetAmt(BigDecimal.ZERO); |
|||
targetVo.setDispatchAmt(BigDecimal.ZERO); |
|||
targetVo.setTotalRealAmt(BigDecimal.ZERO); |
|||
targetVo.setLastYearDispatchAmt(BigDecimal.ZERO); |
|||
targetVo.setProvinceCityAmt(BigDecimal.ZERO); |
|||
targetVo.setProvinceCityRegionAmt(BigDecimal.ZERO); |
|||
if(CollUtil.isNotEmpty(mList)){ |
|||
for (BirBudgetTarget target : mList) { |
|||
targetVo.setTargetAmt(targetVo.getTargetAmt().add(target.getTargetAmt())); |
|||
targetVo.setBudgetAmt(targetVo.getBudgetAmt().add(target.getBudgetAmt())); |
|||
targetVo.setDispatchAmt(targetVo.getDispatchAmt().add(target.getDispatchAmt())); |
|||
targetVo.setTotalRealAmt(targetVo.getTotalRealAmt().add(target.getTotalRealAmt())); |
|||
targetVo.setLastYearDispatchAmt(targetVo.getLastYearDispatchAmt().add(target.getLastYearDispatchAmt())); |
|||
targetVo.setProvinceCityAmt(targetVo.getProvinceCityAmt().add(target.getProvinceCityAmt())); |
|||
targetVo.setProvinceCityRegionAmt(targetVo.getProvinceCityRegionAmt().add(target.getProvinceCityRegionAmt())); |
|||
} |
|||
//预算费率 = 预算费用/销售目标
|
|||
targetVo.setBudgetRate(targetVo.getBudgetAmt().divide(targetVo.getTargetAmt(),2, RoundingMode.DOWN)); |
|||
//发货达成率 = 实际发货/销售目标
|
|||
targetVo.setDispatchRate(targetVo.getDispatchAmt().divide(targetVo.getTargetAmt(),2, RoundingMode.DOWN)); |
|||
//(当前发货-去年同期发货)/去年同期发货
|
|||
targetVo.setLastYearGrowRate( |
|||
targetVo.getDispatchAmt() |
|||
.subtract(targetVo.getLastYearDispatchAmt()) |
|||
.divide(targetVo.getLastYearDispatchAmt(),2, RoundingMode.DOWN) |
|||
); |
|||
//实际费用率=实际费用/实际发货
|
|||
targetVo.setProvinceCityRate(targetVo.getProvinceCityAmt().divide(targetVo.getDispatchAmt(),2, RoundingMode.DOWN)); |
|||
targetVo.setProvinceCityRegionRate(targetVo.getProvinceCityRate().divide(targetVo.getDispatchAmt(),2, RoundingMode.DOWN)); |
|||
targetVo.setTotalRealRate(targetVo.getTotalRealAmt().divide(targetVo.getDispatchAmt(),2, RoundingMode.DOWN)); |
|||
} |
|||
return targetVo; |
|||
} |
|||
|
|||
} |
|||
|
@ -0,0 +1,22 @@ |
|||
package com.qs.serve.modules.tbs.entity.dto; |
|||
|
|||
import lombok.Data; |
|||
|
|||
/** |
|||
* @author YenHex |
|||
* @since 2024/6/3 |
|||
*/ |
|||
@Data |
|||
public class TbsBudgetCheckingWithAmount { |
|||
|
|||
private String type; |
|||
private String tarId; |
|||
private String tarCode; |
|||
private String tarTitle; |
|||
private String totalAmount; |
|||
private String supplierCode; |
|||
private String supplierName; |
|||
private String userCode; |
|||
private String userName; |
|||
|
|||
} |
@ -0,0 +1,494 @@ |
|||
package com.qs.serve.modules.tbs.service; |
|||
|
|||
import com.baomidou.mybatisplus.core.conditions.query.LambdaQueryWrapper; |
|||
import com.baomidou.mybatisplus.core.conditions.query.QueryWrapper; |
|||
import com.qs.serve.common.util.CollectionUtil; |
|||
import com.qs.serve.common.util.CopierUtil; |
|||
import com.qs.serve.common.util.StringUtils; |
|||
import com.qs.serve.modules.tbs.entity.*; |
|||
import com.qs.serve.modules.tbs.mapper.*; |
|||
import com.qs.serve.modules.vtb.entity.VtbVerification; |
|||
import com.qs.serve.modules.vtb.entity.VtbVerificationSubject; |
|||
import com.qs.serve.modules.vtb.mapper.VtbVerificationMapper; |
|||
import com.qs.serve.modules.vtb.mapper.VtbVerificationSubjectMapper; |
|||
import lombok.AllArgsConstructor; |
|||
import lombok.extern.slf4j.Slf4j; |
|||
import org.jetbrains.annotations.NotNull; |
|||
import org.springframework.stereotype.Service; |
|||
|
|||
import java.math.BigDecimal; |
|||
import java.math.RoundingMode; |
|||
import java.util.ArrayList; |
|||
import java.util.HashMap; |
|||
import java.util.List; |
|||
import java.util.Map; |
|||
import java.util.stream.Collectors; |
|||
|
|||
/** |
|||
* @author YenHex |
|||
* @since 2024/5/25 |
|||
*/ |
|||
@Slf4j |
|||
@Service |
|||
@AllArgsConstructor |
|||
public class TbsActivityDebugApplicationService { |
|||
|
|||
private TbsActivityMapper activityMapper; |
|||
private TbsActivitySubjectService activitySubjectService; |
|||
private TbsActivitySubjectMapper activitySubjectMapper; |
|||
private TbsActivityCenterService activityCenterService; |
|||
private TbsActivityCenterGoodsService activityCenterGoodsService; |
|||
private TbsBudgetLogService budgetLogService; |
|||
private VtbVerificationMapper verificationMapper; |
|||
private TbsCostApplyMapper tbsCostApplyMapper; |
|||
|
|||
public String reset(Long activityId){ |
|||
|
|||
BigDecimal n100 = new BigDecimal("100"); |
|||
|
|||
QueryWrapper wrapper = new QueryWrapper(); |
|||
wrapper.eq("activity_id",activityId); |
|||
|
|||
TbsActivity activity = activityMapper.selectById(activityId); |
|||
|
|||
//TbsCostApply costApply = tbsCostApplyMapper.selectById(activity.getCostApplyId());
|
|||
// if(costApply.getPolicyItemId()!=null){
|
|||
// log.warn("随货折让不支持该方法");
|
|||
// return "随货折让不支持该方法";
|
|||
// }
|
|||
// //过滤 CA SHX YX06 PortalOfCostApplication.createCostProcess()
|
|||
// if(StringUtils.hasText(costApply.getBillNumber())||StringUtils.hasText(costApply.getDisCode())){
|
|||
// log.warn("方法仅支持普通订单");
|
|||
// return "方法仅支持普通订单";
|
|||
// }
|
|||
|
|||
BigDecimal checkeAmt = activity.getUsedAmount(); |
|||
if(activity.getReleaseFlag().equals(1)){ |
|||
checkeAmt = checkeAmt.add(activity.getReleaseAmount()); |
|||
} |
|||
if(checkeAmt.compareTo(activity.getTotalAmount())>0){ |
|||
log.warn("活动自身金额异常"); |
|||
return "活动自身金额异常"; |
|||
} |
|||
|
|||
Long unMatchNum = activitySubjectMapper.checkActAndSubjectAmt(activityId); |
|||
if(unMatchNum!=null&&unMatchNum>0){ |
|||
log.warn("活动科目金额异常"); |
|||
return "活动科目金额异常"; |
|||
} |
|||
|
|||
//校验核销金额,错误则不执行
|
|||
BigDecimal totalVerificationAmt = verificationMapper.getActivityVerificationAmt(activityId); |
|||
if(totalVerificationAmt==null){ |
|||
totalVerificationAmt = BigDecimal.ZERO; |
|||
} |
|||
if(activity.getUsedAmount().compareTo(BigDecimal.ZERO)!=0 |
|||
&&activity.getUsedAmount().compareTo(totalVerificationAmt)!=0){ |
|||
return "核销金额异常"; |
|||
} |
|||
|
|||
// subject是和activity的 申请金额和核销金额一致,不进行更新
|
|||
List<TbsActivitySubject> activitySubjectList = activitySubjectService.list(wrapper); |
|||
List<TbsActivityCenter> activityCenterList = activityCenterService.list(wrapper); |
|||
List<TbsActivityCenterGoods> activityCenterGoodsList = activityCenterGoodsService.list(wrapper); |
|||
|
|||
Map<Long,List<TbsActivityCenterGoods>> activityCenterGoodsListMap = activityCenterGoodsList.stream() |
|||
.collect(Collectors.groupingBy(TbsActivityCenterGoods::getSubjectId)); |
|||
|
|||
Map<Long,List<TbsActivityCenter>> activityCenterListMap = activityCenterList.stream() |
|||
.collect(Collectors.groupingBy(TbsActivityCenter::getSubjectId)); |
|||
|
|||
boolean updateSubject = false; |
|||
for (TbsActivitySubject activitySubject : activitySubjectList) { |
|||
Long subjectId = activitySubject.getSubjectId(); |
|||
List<TbsActivityCenter> subjectCenterList = activityCenterListMap.get(subjectId); |
|||
BigDecimal totalCenterRate = BigDecimal.ZERO; |
|||
BigDecimal totalCenterAmt = BigDecimal.ZERO; |
|||
BigDecimal totalCenterUsedAmt = BigDecimal.ZERO; |
|||
|
|||
BigDecimal subjectUsedAmt = activitySubject.getUsedAmount(); |
|||
BigDecimal subjectAmt = activitySubject.getAmount(); |
|||
for (TbsActivityCenter activityCenter : subjectCenterList) { |
|||
if(activityCenter.getCenterRate().compareTo(BigDecimal.ZERO)>=0){ |
|||
totalCenterRate = totalCenterRate.add(activityCenter.getCenterRate()); |
|||
} |
|||
if(activityCenter.getCenterAmount().compareTo(BigDecimal.ZERO)>=0){ |
|||
totalCenterAmt = totalCenterAmt.add(activityCenter.getCenterAmount()); |
|||
} |
|||
totalCenterUsedAmt = totalCenterUsedAmt.add(activityCenter.getUsedAmount()); |
|||
} |
|||
if(n100.compareTo(totalCenterRate)!=0){ |
|||
log.info("重新分配TbsActivityCenter的比例"); |
|||
BigDecimal centerRate = n100; |
|||
for (int i = 0; i < subjectCenterList.size(); i++) { |
|||
TbsActivityCenter activityCenter = subjectCenterList.get(i); |
|||
if(i+1 == subjectCenterList.size()){ |
|||
activityCenter.setCenterRate(centerRate); |
|||
}else { |
|||
if(activityCenter.getCenterRate().compareTo(BigDecimal.ZERO)<0){ |
|||
activityCenter.setCenterRate(BigDecimal.ZERO); |
|||
} |
|||
centerRate = centerRate.subtract(activityCenter.getCenterRate()); |
|||
} |
|||
} |
|||
} |
|||
|
|||
// 更新subject的已用金额
|
|||
if(subjectUsedAmt==null || totalCenterUsedAmt.compareTo(subjectUsedAmt)!=0){ |
|||
log.info("成本中心和科目已用金额不匹配"); |
|||
BigDecimal totalUsedOnCenter = BigDecimal.ZERO; |
|||
for (TbsActivityCenter center : activityCenterList) { |
|||
totalUsedOnCenter = totalUsedOnCenter.add(center.getUsedAmount()); |
|||
} |
|||
if(0 == totalUsedOnCenter.compareTo(activity.getUsedAmount())){ |
|||
log.info("通过center更新subject金额"); |
|||
subjectUsedAmt = BigDecimal.ZERO; |
|||
for (TbsActivityCenter center : subjectCenterList) { |
|||
subjectUsedAmt = subjectUsedAmt.add(center.getUsedAmount()); |
|||
} |
|||
activitySubject.setUsedAmount(subjectUsedAmt); |
|||
updateSubject = true; |
|||
}else if (activitySubjectList.size()==1){ |
|||
subjectUsedAmt = activity.getUsedAmount(); |
|||
activitySubject.setUsedAmount(subjectUsedAmt); |
|||
log.info("更新TbsActivityCenter的已用金额"); |
|||
BigDecimal totalCenterSubjectRate = BigDecimal.ZERO; |
|||
for (TbsActivityCenter center : subjectCenterList) { |
|||
totalCenterSubjectRate = totalCenterSubjectRate.add(center.getCenterRate()); |
|||
} |
|||
if(totalCenterSubjectRate.compareTo(n100)!=0){ |
|||
log.info("更新TbsActivityCenter的比率"); |
|||
BigDecimal avgRate = n100.divide(new BigDecimal(subjectCenterList.size()),2,RoundingMode.DOWN); |
|||
BigDecimal addRate = BigDecimal.ZERO; |
|||
for (int i = 0; i < subjectCenterList.size(); i++) { |
|||
TbsActivityCenter center = subjectCenterList.get(i); |
|||
if(i+1 == subjectCenterList.size()){ |
|||
center.setCenterRate(n100.subtract(addRate)); |
|||
}else { |
|||
center.setCenterRate(avgRate); |
|||
addRate = avgRate.add(avgRate); |
|||
} |
|||
} |
|||
} |
|||
BigDecimal totalUsed11 = BigDecimal.ZERO; |
|||
for (int i = 0; i < subjectCenterList.size(); i++) { |
|||
log.info("更新TbsActivityCenter的已用"); |
|||
TbsActivityCenter center = subjectCenterList.get(i); |
|||
if(i+1 == subjectCenterList.size()){ |
|||
center.setUsedAmount(subjectUsedAmt.subtract(totalUsed11)); |
|||
}else { |
|||
BigDecimal curAmt = subjectUsedAmt.multiply(center.getCenterRate()).divide(n100,2,RoundingMode.DOWN); |
|||
center.setUsedAmount(curAmt); |
|||
totalUsed11 = totalUsed11.add(curAmt); |
|||
} |
|||
} |
|||
}else { |
|||
log.info("成本中心和科目已用金额不匹配,而且活动金额也不匹配"); |
|||
return "成本中心和科目已用金额不匹配,而且活动金额也不匹配"; |
|||
} |
|||
} |
|||
|
|||
// 分配center的占用金额和已用金额
|
|||
if(totalCenterAmt.compareTo(activitySubject.getAmount())!=0){ |
|||
log.info("重新分配TbsActivityCenter的CenterAmount"); |
|||
BigDecimal centerAmt = subjectAmt; |
|||
BigDecimal centerUsedAmt = subjectUsedAmt; |
|||
for (int i = 0; i < subjectCenterList.size(); i++) { |
|||
TbsActivityCenter activityCenter = subjectCenterList.get(i); |
|||
if(i+1 == subjectCenterList.size()){ |
|||
activityCenter.setCenterAmount(centerAmt); |
|||
}else { |
|||
BigDecimal currAmt = subjectAmt |
|||
.multiply(activityCenter.getCenterRate()) |
|||
.divide(n100, 2,RoundingMode.DOWN); |
|||
centerAmt = centerAmt.subtract(currAmt); |
|||
activityCenter.setCenterAmount(currAmt); |
|||
} |
|||
//设置已用金额
|
|||
if(subjectAmt.compareTo(subjectUsedAmt)==0){ |
|||
activityCenter.setUsedAmount(activityCenter.getCenterAmount()); |
|||
}else { |
|||
if(i+1 == subjectCenterList.size()){ |
|||
activityCenter.setUsedAmount(centerUsedAmt); |
|||
}else { |
|||
BigDecimal currAmt = subjectUsedAmt |
|||
.multiply(activityCenter.getCenterRate()) |
|||
.divide(n100, 2,RoundingMode.DOWN); |
|||
centerUsedAmt = centerUsedAmt.subtract(currAmt); |
|||
activityCenter.setUsedAmount(centerAmt); |
|||
} |
|||
} |
|||
} |
|||
} |
|||
|
|||
List<TbsActivityCenterGoods> activityCenterGoodsListOfSubject = activityCenterGoodsListMap.get(subjectId); |
|||
|
|||
for (TbsActivityCenter center : subjectCenterList) { |
|||
List<TbsActivityCenterGoods> goodsList = activityCenterGoodsListOfSubject.stream() |
|||
.filter(a->a.getCenterId().equals(center.getCenterId())&&a.getCenterType().equals(center.getCenterType())) |
|||
.collect(Collectors.toList()); |
|||
if(goodsList.size()==0){ |
|||
if(subjectCenterList.size()==1 && activityCenterGoodsListOfSubject.size()==1){ |
|||
TbsActivityCenterGoods centerGoods = activityCenterGoodsListOfSubject.get(0); |
|||
centerGoods.setCenterType(center.getCenterType()); |
|||
centerGoods.setCenterId(center.getCenterId()); |
|||
centerGoods.setCenterName(center.getCenterName()); |
|||
goodsList = new ArrayList<>(); |
|||
goodsList.add(centerGoods); |
|||
}else { |
|||
log.error("商品数据缺失"); |
|||
return "商品数据缺失"; |
|||
} |
|||
} |
|||
final BigDecimal centerUsed = center.getUsedAmount(); |
|||
final BigDecimal centerAmt = center.getCenterAmount(); |
|||
|
|||
BigDecimal totalGoodRate = BigDecimal.ZERO; |
|||
for (TbsActivityCenterGoods goods : goodsList) { |
|||
BigDecimal rate = goods.getCenterGoodsRate(); |
|||
if(rate.compareTo(BigDecimal.ZERO)>0){ |
|||
totalGoodRate = totalGoodRate.add(rate); |
|||
} |
|||
} |
|||
//重新分配比率
|
|||
if(totalGoodRate.compareTo(n100)!=0){ |
|||
log.info("重新分配申请Rate"); |
|||
BigDecimal avgRate = n100.divide(new BigDecimal(goodsList.size()),2,RoundingMode.DOWN); |
|||
BigDecimal addRate = BigDecimal.ZERO; |
|||
for (int i = 0; i < goodsList.size(); i++) { |
|||
TbsActivityCenterGoods goods = goodsList.get(i); |
|||
if(i+1 == goodsList.size()){ |
|||
goods.setCenterGoodsRate(n100.subtract(addRate)); |
|||
}else { |
|||
goods.setCenterGoodsRate(avgRate); |
|||
addRate = addRate.add(avgRate); |
|||
} |
|||
} |
|||
} |
|||
|
|||
//分配申请金额
|
|||
BigDecimal centerAmt3 = centerAmt; |
|||
log.info("重新分配申请金额"); |
|||
for (int i = 0; i < goodsList.size(); i++) { |
|||
TbsActivityCenterGoods goods = goodsList.get(i); |
|||
if(i+1 == goodsList.size()){ |
|||
goods.setCenterGoodsAmount(centerAmt3); |
|||
}else { |
|||
BigDecimal currentAmt = centerAmt |
|||
.multiply(goods.getCenterGoodsRate()) |
|||
.divide(n100,2,RoundingMode.DOWN); |
|||
goods.setCenterGoodsAmount(currentAmt); |
|||
centerAmt3 = centerAmt3.subtract(currentAmt); |
|||
} |
|||
} |
|||
|
|||
//分配TbsActivityCenterGoods已用金额
|
|||
BigDecimal centerUsed2 = centerUsed; |
|||
log.info("重新分配已用金额"); |
|||
for (int i = 0; i < goodsList.size(); i++) { |
|||
TbsActivityCenterGoods goods = goodsList.get(i); |
|||
if(i+1 == goodsList.size()){ |
|||
goods.setUsedAmount(centerUsed2); |
|||
}else { |
|||
BigDecimal currentAmt = centerUsed |
|||
.multiply(goods.getCenterGoodsRate()) |
|||
.divide(n100,2,RoundingMode.DOWN); |
|||
goods.setUsedAmount(currentAmt); |
|||
centerUsed2 = centerUsed2.subtract(currentAmt); |
|||
} |
|||
} |
|||
} |
|||
|
|||
} |
|||
|
|||
//二次校验
|
|||
BigDecimal totalSubjectAmt = BigDecimal.ZERO; |
|||
BigDecimal totalSubjectUsedAmt = BigDecimal.ZERO; |
|||
BigDecimal totalAllCenterUsedAmt = BigDecimal.ZERO; |
|||
for (TbsActivitySubject activitySubject : activitySubjectList) { |
|||
Long subjectId = activitySubject.getSubjectId(); |
|||
List<TbsActivityCenter> subjectCenterList = activityCenterListMap.get(subjectId); |
|||
BigDecimal totalCenterRate = BigDecimal.ZERO; |
|||
BigDecimal totalCenterAmt = BigDecimal.ZERO; |
|||
BigDecimal totalCenterUsedAmt = BigDecimal.ZERO; |
|||
|
|||
BigDecimal subjectUsedAmt = activitySubject.getUsedAmount(); |
|||
BigDecimal subjectAmt = activitySubject.getAmount(); |
|||
totalSubjectAmt = totalSubjectAmt.add(subjectAmt); |
|||
totalSubjectUsedAmt = totalSubjectUsedAmt.add(activitySubject.getUsedAmount()); |
|||
|
|||
for (TbsActivityCenter activityCenter : subjectCenterList) { |
|||
totalCenterRate = totalCenterRate.add(activityCenter.getCenterRate()); |
|||
totalCenterAmt = totalCenterAmt.add(activityCenter.getCenterAmount()); |
|||
totalCenterUsedAmt = totalCenterUsedAmt.add(activityCenter.getUsedAmount()); |
|||
} |
|||
totalAllCenterUsedAmt = totalAllCenterUsedAmt.add(totalCenterUsedAmt); |
|||
if(totalCenterAmt.compareTo(subjectAmt)!=0){ |
|||
log.error("合计totalCenterAmt金额异常:{}",activityId); |
|||
return "合计totalCenterAmt金额异常"; |
|||
} |
|||
if(totalCenterUsedAmt.compareTo(subjectUsedAmt)!=0){ |
|||
log.error("合计totalCenterUsedAmt金额异常,将重新分配活动的成本中心金额:{}",activityId); |
|||
return "合计totalCenterUsedAmt金额异常"; |
|||
} |
|||
if(n100.compareTo(totalCenterRate)!=0){ |
|||
log.error("centerRate不为100:{}",activityId); |
|||
return "centerRate不为100"; |
|||
} |
|||
List<TbsActivityCenterGoods> activityCenterGoodsListOfSubject = activityCenterGoodsListMap.get(subjectId); |
|||
|
|||
for (TbsActivityCenter center : subjectCenterList) { |
|||
List<TbsActivityCenterGoods> goodsList = activityCenterGoodsListOfSubject.stream() |
|||
.filter(a->a.getCenterId().equals(center.getCenterId())&&a.getCenterType().equals(center.getCenterType())) |
|||
.collect(Collectors.toList()); |
|||
final BigDecimal centerUsed = center.getUsedAmount(); |
|||
final BigDecimal centerAmt = center.getCenterAmount(); |
|||
|
|||
BigDecimal totalGoodRate = BigDecimal.ZERO; |
|||
BigDecimal totalGoodUsed = BigDecimal.ZERO; |
|||
BigDecimal totalGoodAmt = BigDecimal.ZERO; |
|||
for (TbsActivityCenterGoods goods : goodsList) { |
|||
BigDecimal rate = goods.getCenterGoodsRate(); |
|||
totalGoodRate = totalGoodRate.add(rate); |
|||
totalGoodAmt = totalGoodAmt.add(goods.getCenterGoodsAmount()); |
|||
totalGoodUsed = totalGoodUsed.add(goods.getUsedAmount()); |
|||
} |
|||
//重新分配比率
|
|||
if(totalGoodRate.compareTo(n100)!=0){ |
|||
log.error("totalGoodRate不为100:{}",activityId); |
|||
return "totalGoodRate不为100"; |
|||
} |
|||
|
|||
if(totalGoodAmt.compareTo(centerAmt)!=0){ |
|||
log.error("totalGoodAmt:{}",activityId); |
|||
return "totalGoodAmt错误"; |
|||
} |
|||
if(totalGoodUsed.compareTo(centerUsed)!=0){ |
|||
log.error("totalGoodUsed:{}",activityId); |
|||
return "totalGoodUsed错误"; |
|||
} |
|||
} |
|||
|
|||
} |
|||
|
|||
if(activity.getUsedAmount().compareTo(totalSubjectUsedAmt)!=0){ |
|||
log.error("活动和totalSubjectUsedAmt匹对金额异常:{}",activityId); |
|||
return "活动和totalSubjectUsedAmt匹对金额异常"; |
|||
} |
|||
if(totalSubjectUsedAmt.compareTo(totalAllCenterUsedAmt)!=0){ |
|||
log.error("活动和totalAllCenterUsedAmt匹对金额异常:{}",activityId); |
|||
return "活动和totalAllCenterUsedAmt匹对金额异常"; |
|||
} |
|||
if(activity.getTotalAmount().compareTo(totalSubjectAmt)!=0){ |
|||
log.error("科目和活动的申请金额不匹配"); |
|||
return "科目和活动的申请金额不匹配"; |
|||
} |
|||
// 处理预算占用
|
|||
List<TbsBudgetLog> actBudgetLogs = budgetLogService.list(wrapper); |
|||
|
|||
List<TbsBudgetLog> applyLogs = actBudgetLogs.stream().filter(a-> a.getOptType()!=4).collect(Collectors.toList()); |
|||
|
|||
List<TbsBudgetLog> releaseLogs = actBudgetLogs.stream().filter(a-> a.getOptType()==4).collect(Collectors.toList()); |
|||
|
|||
BigDecimal applyAmt = totalBudgetLogAmount(applyLogs); |
|||
|
|||
BigDecimal releaseAmt = totalBudgetLogAmount(releaseLogs); |
|||
|
|||
//检查下占用预算和释放
|
|||
if(applyAmt.negate().compareTo(activity.getTotalAmount())!=0){ |
|||
log.info("历史预算占用金额异常"); |
|||
} |
|||
|
|||
if(activity.getReleaseAmount()!=null && releaseAmt.compareTo(activity.getReleaseAmount())!=0){ |
|||
log.info("历史预算释放金额异常"); |
|||
} |
|||
|
|||
List<TbsBudgetLog> newApplyLogList = new ArrayList<>(); |
|||
List<TbsBudgetLog> newReleaseLogList = new ArrayList<>(); |
|||
|
|||
for (TbsActivityCenterGoods goods : activityCenterGoodsList) { |
|||
|
|||
List<TbsBudgetLog> goodApplyLogs = actBudgetLogs.stream().filter(a-> |
|||
a.getSubjectId().equals(goods.getSubjectId()) |
|||
&&a.getCenterType().equals(goods.getCenterType()) |
|||
&&a.getCenterId().equals(goods.getCenterId()) |
|||
&&a.getOptType()!=4 |
|||
).collect(Collectors.toList()); |
|||
|
|||
List<TbsBudgetLog> goodReleaseLogs = actBudgetLogs.stream().filter(a-> |
|||
a.getSubjectId().equals(goods.getSubjectId()) |
|||
&&a.getCenterType().equals(goods.getCenterType()) |
|||
&&a.getCenterId().equals(goods.getCenterId()) |
|||
&&a.getOptType()==4 |
|||
).collect(Collectors.toList()); |
|||
|
|||
if(goodApplyLogs.size()==0 && goodReleaseLogs.size() ==0 |
|||
&&goods.getCenterGoodsAmount().equals(goods.getUsedAmount())){ |
|||
continue; |
|||
} |
|||
|
|||
if(goodApplyLogs.size()==0){ |
|||
return "缺失费用申请log"; |
|||
} |
|||
|
|||
// 新log
|
|||
TbsBudgetLog newApplyLog = CopierUtil.copy(goodApplyLogs.get(0),new TbsBudgetLog()); |
|||
newApplyLog.setId(null); |
|||
newApplyLog.setAmount(goods.getCenterGoodsAmount().negate()); |
|||
newApplyLog.setOptType(1); |
|||
newApplyLogList.add(newApplyLog); |
|||
|
|||
if(goodReleaseLogs.size()>0){ |
|||
TbsBudgetLog newReleaseLog = CopierUtil.copy(goodReleaseLogs.get(0),new TbsBudgetLog()); |
|||
newReleaseLog.setId(null); |
|||
newReleaseLog.setAmount(goods.getCenterGoodsAmount().subtract(goods.getUsedAmount())); |
|||
newReleaseLog.setOptType(4); |
|||
newReleaseLogList.add(newReleaseLog); |
|||
} |
|||
|
|||
} |
|||
|
|||
|
|||
BigDecimal newApplyAmt = totalBudgetLogAmount(newApplyLogList); |
|||
BigDecimal newReleaseAmt = totalBudgetLogAmount(newReleaseLogList); |
|||
|
|||
if(newApplyAmt.negate().compareTo(activity.getTotalAmount())!=0){ |
|||
log.error("预算占用金额异常"); |
|||
return "预算占用金额异常"; |
|||
} |
|||
|
|||
if(activity.getReleaseAmount()!=null && newReleaseAmt.compareTo(activity.getReleaseAmount())!=0){ |
|||
log.error("预算释放金额异常 activity{},.getReleaseAmount():{} newReleaseAmt:{}",activityId,activity.getReleaseAmount(),newReleaseAmt); |
|||
return "预算释放金额异常"; |
|||
} |
|||
|
|||
if(updateSubject){ |
|||
activitySubjectService.updateBatchById(activitySubjectList); |
|||
} |
|||
activityCenterService.updateBatchById(activityCenterList); |
|||
activityCenterGoodsService.updateBatchById(activityCenterGoodsList); |
|||
List<Long> logIds = actBudgetLogs.stream().map(a->a.getId()).collect(Collectors.toList()); |
|||
if(!newApplyLogList.isEmpty()){ |
|||
budgetLogService.saveBatch(newApplyLogList); |
|||
} |
|||
if(CollectionUtil.isNotEmpty(newReleaseLogList)){ |
|||
budgetLogService.saveBatch(newReleaseLogList); |
|||
} |
|||
if(CollectionUtil.isNotEmpty(logIds)){ |
|||
budgetLogService.removeBatchByIds(logIds); |
|||
} |
|||
return null; |
|||
} |
|||
|
|||
|
|||
private BigDecimal totalBudgetLogAmount(List<TbsBudgetLog> releaseLogs) { |
|||
BigDecimal amt = BigDecimal.ZERO; |
|||
if(releaseLogs!=null){ |
|||
for (TbsBudgetLog reLog : releaseLogs) { |
|||
amt = amt.add(reLog.getAmount()); |
|||
} |
|||
} |
|||
return amt; |
|||
} |
|||
|
|||
} |
@ -0,0 +1,206 @@ |
|||
package com.qs.serve.modules.tbs.service; |
|||
|
|||
import cn.hutool.core.collection.CollUtil; |
|||
import com.baomidou.mybatisplus.core.conditions.query.LambdaQueryWrapper; |
|||
import com.qs.serve.common.model.enums.BudgetLogOptFlag; |
|||
import com.qs.serve.common.util.CollectionUtil; |
|||
import com.qs.serve.modules.sys.entity.SysUser; |
|||
import com.qs.serve.modules.tbs.common.util.TbsBudgetLogBuildUtil; |
|||
import com.qs.serve.modules.tbs.entity.*; |
|||
import com.qs.serve.modules.vtb.common.VtbFundFlowType; |
|||
import com.qs.serve.modules.vtb.entity.VtbFundFlow; |
|||
import com.qs.serve.modules.vtb.mapper.VtbFundFlowMapper; |
|||
import com.qs.serve.modules.vtb.service.VtbFundFlowService; |
|||
import lombok.AllArgsConstructor; |
|||
import lombok.extern.slf4j.Slf4j; |
|||
import org.springframework.stereotype.Service; |
|||
|
|||
import java.math.BigDecimal; |
|||
import java.util.ArrayList; |
|||
import java.util.List; |
|||
import java.util.stream.Collectors; |
|||
|
|||
/** |
|||
* @author YenHex |
|||
* @since 2024/5/28 |
|||
*/ |
|||
@Slf4j |
|||
@Service |
|||
@AllArgsConstructor |
|||
public class TbsBudgetReleaseApplicationService { |
|||
|
|||
private final VtbFundFlowService fundFlowService; |
|||
private final VtbFundFlowMapper vtbFundFlowMapper; |
|||
private final TbsBudgetService budgetService; |
|||
private final TbsBudgetLogService budgetLogService; |
|||
private final TbsBudgetCostItemService budgetCostItemService; |
|||
private final TbsActivityService activityService; |
|||
private final TbsActivityCenterGoodsService activityCenterGoodsService; |
|||
private final TbsCostApplyService costApplyService; |
|||
private final TbsActivityPayConditionService activityPayConditionService; |
|||
private final TbsScheduleItemBudgetService tbsScheduleItemBudgetService; |
|||
|
|||
public void initHis(Long activityId){ |
|||
TbsBudget budget = budgetService.getById("1669"); |
|||
TbsScheduleItemBudget scheduleItemBudget = tbsScheduleItemBudgetService.getById("4896"); |
|||
TbsActivity activity = activityService.getById(activityId); |
|||
TbsCostApply costApply = costApplyService.getById(activity.getCostApplyId()); |
|||
SysUser sysUser = new SysUser(); |
|||
sysUser.setId("0"); |
|||
sysUser.setName("系统执行"); |
|||
sysUser.setCode("0"); |
|||
|
|||
List<TbsBudgetLog> budgetLogList = new ArrayList<>(); |
|||
List<TbsActivityCenterGoods> centerGoodsList = activityCenterGoodsService.listByActivityId(activityId); |
|||
for (TbsActivityCenterGoods centerGoods : centerGoodsList) { |
|||
BigDecimal amount = centerGoods.getCenterGoodsAmount(); |
|||
|
|||
TbsBudgetCostItem costItem = new TbsBudgetCostItem(); |
|||
costItem.setCenterGoodsCode(centerGoods.getCenterGoodsCode()); |
|||
costItem.setCostApplyId(centerGoods.getCostApplyId()); |
|||
costItem.setActivityId(centerGoods.getActivityId()); |
|||
costItem.setActivityCode(centerGoods.getActivityCode()); |
|||
costItem.setSupplierId(centerGoods.getSupplierId()); |
|||
costItem.setSupplierCode(centerGoods.getSupplierCode()); |
|||
costItem.setSupplierName(centerGoods.getSupplierName()); |
|||
costItem.setSubjectId(centerGoods.getSubjectId()); |
|||
costItem.setSubjectCode(centerGoods.getSubjectCode()); |
|||
costItem.setSubjectName(centerGoods.getSubjectName()); |
|||
costItem.setCenterType(centerGoods.getCenterType()); |
|||
costItem.setCenterId(centerGoods.getCenterId()); |
|||
costItem.setCenterCode(centerGoods.getCenterCode()); |
|||
costItem.setCenterName(centerGoods.getCenterName()); |
|||
costItem.setCenterAmount(centerGoods.getCenterAmount()); |
|||
costItem.setCenterRate(centerGoods.getCenterRate()); |
|||
costItem.setCenterGoodsAmount(centerGoods.getCenterGoodsAmount()); |
|||
costItem.setCenterGoodsRate(centerGoods.getCenterGoodsRate()); |
|||
costItem.setTargetType(centerGoods.getTargetType()); |
|||
costItem.setTargetId(centerGoods.getTargetId()); |
|||
costItem.setTargetCode(centerGoods.getTargetCode()); |
|||
costItem.setTargetName(centerGoods.getTargetName()); |
|||
costItem.setTargetLevelPathIds(centerGoods.getTargetLevelPathIds()); |
|||
costItem.setTargetLevelPathNames(centerGoods.getTargetLevelPathNames()); |
|||
costItem.setActStartDate(centerGoods.getActStartDate()); |
|||
costItem.setActEndDate(centerGoods.getActEndDate()); |
|||
costItem.setPreStartDate(centerGoods.getPreStartDate()); |
|||
costItem.setPreEndDate(centerGoods.getPreEndDate()); |
|||
costItem.setPreCheckDate(centerGoods.getPreCheckDate()); |
|||
costItem.setCenterGoodItemId(centerGoods.getId()); |
|||
|
|||
TbsBudgetLog budgetLog = TbsBudgetLogBuildUtil.buildTbsBudgetLog(BudgetLogOptFlag.State_1,sysUser,costApply,costItem ,budget,amount,activity); |
|||
budgetLog.setBudgetId(budget.getId()); |
|||
|
|||
budgetLog.setScheduleItemBudgetId(scheduleItemBudget.getId()); |
|||
budgetLog.setScheduleId(scheduleItemBudget.getScheduleId()); |
|||
budgetLog.setScheduleItemId(scheduleItemBudget.getScheduleItemId()); |
|||
budgetLog.setItemName(scheduleItemBudget.getItemName()); |
|||
|
|||
budgetLogList.add(budgetLog); |
|||
} |
|||
//移除历史记录
|
|||
budgetLogService.remove(new LambdaQueryWrapper<TbsBudgetLog>() |
|||
.eq(TbsBudgetLog::getCostApplyId,activity.getCostApplyId()) |
|||
.eq(TbsBudgetLog::getOptType, BudgetLogOptFlag.State_1.getCode()) |
|||
.eq(TbsBudgetLog::getActivityId,activity.getId())); |
|||
//重新保存
|
|||
if(CollectionUtil.isNotEmpty(budgetLogList)){ |
|||
budgetLogService.saveBatch(budgetLogList); |
|||
} |
|||
|
|||
} |
|||
|
|||
/** |
|||
* 依据剩余预算刷新释放金额 |
|||
*/ |
|||
public void check(Long actId){ |
|||
//校验活动的核销金额是否匹配,不匹配则中断
|
|||
//查询需要补偿释放的活动ID
|
|||
//List<Long> activityIds = vtbFundFlowMapper.listMissReleaseActivityId();
|
|||
Long[] activityIds = new Long[]{actId}; |
|||
for (Long activityId : activityIds) { |
|||
TbsActivity activity = activityService.getById(activityId); |
|||
TbsCostApply costApply = costApplyService.getById(activity.getCostApplyId()); |
|||
|
|||
//保存预算日志
|
|||
List<TbsActivityCenterGoods> centerGoodsList = activityCenterGoodsService.listByActivityId(activityId); |
|||
LambdaQueryWrapper<TbsBudgetCostItem> itemLqw = new LambdaQueryWrapper<>(); |
|||
itemLqw.eq(TbsBudgetCostItem::getActivityId,activityId); |
|||
List<TbsBudgetCostItem> budgetCostItemList = budgetCostItemService.list(itemLqw); |
|||
List<Long> budgetIds = budgetCostItemList.stream().map(TbsBudgetCostItem::getBudgetId).collect(Collectors.toList()); |
|||
if(CollUtil.isEmpty(budgetIds)){ |
|||
continue; |
|||
} |
|||
List<TbsBudget> budgetLIst = budgetService.listByIds(budgetIds); |
|||
List<TbsBudgetLog> budgetLogList = new ArrayList<>(); |
|||
for (TbsActivityCenterGoods centerGoods : centerGoodsList) { |
|||
if(centerGoods.getCenterGoodsAmount().compareTo(centerGoods.getUsedAmount())<1){ |
|||
continue; |
|||
} |
|||
TbsBudgetCostItem currCostItem = null; |
|||
TbsBudget currentBudget = null; |
|||
for (TbsBudgetCostItem costItem : budgetCostItemList) { |
|||
if(centerGoods.getId().equals(costItem.getCenterGoodItemId())){ |
|||
currCostItem = costItem; |
|||
break; |
|||
} |
|||
} |
|||
for (TbsBudget budget : budgetLIst) { |
|||
if (currCostItem.getBudgetId().equals(budget.getId())){ |
|||
currentBudget = budget; |
|||
} |
|||
} |
|||
BigDecimal amount = centerGoods.getCenterGoodsAmount().subtract(centerGoods.getUsedAmount()); |
|||
SysUser sysUser = new SysUser(); |
|||
sysUser.setId("0"); |
|||
sysUser.setName("系统执行"); |
|||
sysUser.setCode("0"); |
|||
TbsBudgetLog budgetLog = TbsBudgetLogBuildUtil.buildTbsBudgetLog(BudgetLogOptFlag.State_4,sysUser,costApply,currCostItem,currentBudget,amount,activity); |
|||
budgetLogList.add(budgetLog); |
|||
} |
|||
|
|||
//TODO 二次校验,释放金额是否一致
|
|||
|
|||
|
|||
//移除历史记录
|
|||
fundFlowService.remove( |
|||
new LambdaQueryWrapper<VtbFundFlow>() |
|||
.eq(VtbFundFlow::getFundType, VtbFundFlowType.Release) |
|||
.eq(VtbFundFlow::getCostApplyId,activity.getCostApplyId()) |
|||
.eq(VtbFundFlow::getActivityId,activity.getId()) |
|||
); |
|||
VtbFundFlow fundFlow = new VtbFundFlow(); |
|||
fundFlow.setFundType(VtbFundFlowType.Release); |
|||
fundFlow.setVerificationId(0L); |
|||
fundFlow.setCenterGoodsCode(activity.getActivityCode()+"_00"); |
|||
fundFlow.setCostApplyId(activity.getCostApplyId()); |
|||
fundFlow.setActivityId(activity.getId()); |
|||
fundFlow.setUsedAmount(activity.getReleaseAmount()); |
|||
fundFlow.setSupplierId(activity.getSupplierId()); |
|||
fundFlow.setSupplierCode(activity.getSupplierCode()); |
|||
fundFlow.setSupplierName(activity.getSupplierName()); |
|||
fundFlowService.save(fundFlow); |
|||
|
|||
//移除历史记录
|
|||
budgetLogService.remove(new LambdaQueryWrapper<TbsBudgetLog>() |
|||
.eq(TbsBudgetLog::getCostApplyId,activity.getCostApplyId()) |
|||
.eq(TbsBudgetLog::getOptType, BudgetLogOptFlag.State_4.getCode()) |
|||
.eq(TbsBudgetLog::getActivityId,activity.getId())); |
|||
|
|||
//更新付款条件状态
|
|||
LambdaQueryWrapper<TbsActivityPayCondition> updLqw = new LambdaQueryWrapper<>(); |
|||
updLqw.eq(TbsActivityPayCondition::getActivityId,activityId); |
|||
TbsActivityPayCondition payCondition = new TbsActivityPayCondition(); |
|||
payCondition.setFinishedFlag(1); |
|||
activityPayConditionService.update(payCondition,updLqw); |
|||
|
|||
//重新保存
|
|||
if(CollectionUtil.isNotEmpty(budgetLogList)){ |
|||
budgetLogService.saveBatch(budgetLogList); |
|||
} |
|||
|
|||
} |
|||
|
|||
|
|||
} |
|||
|
|||
} |
@ -0,0 +1,66 @@ |
|||
package com.qs.serve.modules.tbs.service; |
|||
|
|||
import cn.hutool.core.collection.CollUtil; |
|||
import com.baomidou.mybatisplus.core.conditions.query.LambdaQueryWrapper; |
|||
import com.baomidou.mybatisplus.core.conditions.update.LambdaUpdateWrapper; |
|||
import com.qs.serve.modules.tbs.common.TbsActivityState; |
|||
import com.qs.serve.modules.tbs.entity.TbsActivity; |
|||
import com.qs.serve.modules.tbs.entity.TbsActivityPayCondition; |
|||
import com.qs.serve.modules.tbs.entity.TbsCostApply; |
|||
import com.qs.serve.modules.tbs.mapper.TbsActivityPayConditionMapper; |
|||
import com.qs.serve.modules.vtb.service.VtbVerificationService; |
|||
import lombok.AllArgsConstructor; |
|||
import lombok.extern.slf4j.Slf4j; |
|||
import org.springframework.stereotype.Service; |
|||
|
|||
import java.util.List; |
|||
|
|||
/** |
|||
* @author YenHex |
|||
* @since 2024/5/28 |
|||
*/ |
|||
@Slf4j |
|||
@Service |
|||
@AllArgsConstructor |
|||
public class TbsCostContractApplication { |
|||
|
|||
private final TbsBudgetReleaseApplicationService tbsBudgetReleaseApplicationService; |
|||
private final TbsActivityPayConditionMapper activityPayConditionMapper; |
|||
private final TbsActivityPayConditionService activityPayConditionService; |
|||
private final TbsActivityService tbsActivityService; |
|||
private final TbsCostApplyService tbsCostApplyService; |
|||
private final VtbVerificationService verificationService; |
|||
|
|||
public void resetState(){ |
|||
//更新遗漏的已完成费用申请
|
|||
List<Long> costIds = activityPayConditionMapper.getFinishedCostId(); |
|||
if(CollUtil.isNotEmpty(costIds)){ |
|||
List<TbsCostApply> costApplyList = tbsCostApplyService.listByIds(costIds); |
|||
for (TbsCostApply costApply : costApplyList) { |
|||
costApply.setChargeState(3); |
|||
costApply.setCheckState(1); |
|||
} |
|||
tbsCostApplyService.updateBatchById(costApplyList); |
|||
//更新状态
|
|||
activityPayConditionService.update(new LambdaUpdateWrapper<TbsActivityPayCondition>() |
|||
.set(TbsActivityPayCondition::getFinishedFlag,1) |
|||
.in(TbsActivityPayCondition::getCostApplyId,costIds)); |
|||
List<TbsActivity> activityList = tbsActivityService.list(new LambdaQueryWrapper<TbsActivity>() |
|||
.in(TbsActivity::getCostApplyId,costIds)); |
|||
for (TbsActivity activity : activityList) { |
|||
if(activity.getUsedAmount().compareTo(activity.getTotalAmount())==0){ |
|||
activity.setActivityState(TbsActivityState.STATE_1_Finished); |
|||
}else { |
|||
//不进行直接释放,通过补充释放,最终一次性修复
|
|||
activity.setReleaseFlag(1); |
|||
activity.setReleaseAmount(activity.getTotalAmount().subtract(activity.getUsedAmount())); |
|||
activity.setActivityState(TbsActivityState.STATE_4_Release); |
|||
tbsBudgetReleaseApplicationService.check(activity.getId()); |
|||
} |
|||
} |
|||
tbsActivityService.updateBatchById(activityList); |
|||
} |
|||
|
|||
} |
|||
|
|||
} |
@ -0,0 +1,101 @@ |
|||
<?xml version="1.0" encoding="UTF-8" ?> |
|||
<!DOCTYPE mapper |
|||
PUBLIC "-//mybatis.org//DTD Mapper 3.0//EN" |
|||
"http://mybatis.org/dtd/mybatis-3-mapper.dtd"> |
|||
<mapper namespace="com.qs.serve.modules.bir.mapper.BirBudgetTargetMapper"> |
|||
|
|||
<resultMap id="birBudgetTargetMap" type="com.qs.serve.modules.bir.entity.BirBudgetTarget" > |
|||
<result property="id" column="id"/> |
|||
<result property="searchType" column="search_type"/> |
|||
<result property="yearNum" column="year_num"/> |
|||
<result property="quarterNum" column="quarter_num"/> |
|||
<result property="monthNum" column="month_num"/> |
|||
<result property="targetAmt" column="target_amt"/> |
|||
<result property="budgetAmt" column="budget_amt"/> |
|||
<result property="dispatchAmt" column="dispatch_amt"/> |
|||
<result property="lastYearDispatchAmt" column="last_year_dispatch_amt"/> |
|||
<result property="provinceCityAmt" column="province_city_amt"/> |
|||
<result property="provinceCityRegionAmt" column="province_city_region_amt"/> |
|||
<result property="totalRealAmt" column="total_real_amt"/> |
|||
<result property="brandId" column="brand_id"/> |
|||
<result property="brandCode" column="brand_code"/> |
|||
<result property="brandName" column="brand_name"/> |
|||
<result property="centerType" column="center_type"/> |
|||
<result property="centerId" column="center_id"/> |
|||
<result property="centerCode" column="center_code"/> |
|||
<result property="centerName" column="center_name"/> |
|||
</resultMap> |
|||
|
|||
<sql id="birBudgetTargetSql"> |
|||
bir_budget_target.`id`, |
|||
bir_budget_target.`search_type`, |
|||
bir_budget_target.`year_num`, |
|||
bir_budget_target.`quarter_num`, |
|||
bir_budget_target.`month_num`, |
|||
bir_budget_target.`target_amt`, |
|||
bir_budget_target.`budget_amt`, |
|||
bir_budget_target.`dispatch_amt`, |
|||
bir_budget_target.`last_year_dispatch_amt`, |
|||
bir_budget_target.`province_city_amt`, |
|||
bir_budget_target.`province_city_region_amt`, |
|||
bir_budget_target.`total_real_amt`, |
|||
bir_budget_target.`brand_id`, |
|||
bir_budget_target.`brand_code`, |
|||
bir_budget_target.`brand_name`, |
|||
bir_budget_target.`center_type`, |
|||
bir_budget_target.`center_id`, |
|||
bir_budget_target.`center_code`, |
|||
bir_budget_target.`center_name` </sql> |
|||
|
|||
<select id="selectBirBudgetTargetList" parameterType="com.qs.serve.modules.bir.entity.BirBudgetTarget" resultMap="birBudgetTargetMap"> |
|||
SELECT <include refid="birBudgetTargetSql"/> FROM `bir_budget_target` `bir_budget_target` |
|||
<where> |
|||
<if test="query.loadType != null"> and `bir_budget_target`.`search_type` = #{query.loadType}</if> |
|||
<if test="query.yearMonthStart != null"> and `bir_budget_target`.`row_date` >= #{query.yearMonthStart}</if> |
|||
<if test="query.yearMonthEnd != null"> and `bir_budget_target`.`row_date` <= #{query.yearMonthEnd}</if> |
|||
|
|||
<if test="query.brandIds!=null and query.brandIds.size > 0"> |
|||
and `bir_budget_target`.`brand_id` in |
|||
<foreach collection="query.brandIds" item="selectId" index="i" open="(" close=")" separator=","> |
|||
#{selectId} |
|||
</foreach> |
|||
</if> |
|||
|
|||
<if test="query.selectCenterFlag=1"> |
|||
and ( |
|||
1=0 |
|||
<if test="query.supplierIds!=null and query.supplierIds.size > 0"> |
|||
or (`bir_budget_target`.`center_type` = 'supplier' and `bir_budget_target`.center_id in |
|||
<foreach collection="query.supplierIds" item="selectId" index="i" open="(" close=")" separator=","> |
|||
#{selectId} |
|||
</foreach> |
|||
) |
|||
</if> |
|||
<if test="query.saleRegionIds!=null and query.saleRegionIds.size > 0"> |
|||
or (`bir_budget_target`.`center_type` = 'saleRegion' and `bir_budget_target`.center_id in |
|||
<foreach collection="query.saleRegionIds" item="selectId" index="i" open="(" close=")" separator=","> |
|||
#{selectId} |
|||
</foreach> |
|||
) |
|||
</if> |
|||
<if test="query.bizRegionIds!=null and query.bizRegionIds.size > 0"> |
|||
or (`bir_budget_target`.`center_type` = 'bizRegion' and `bir_budget_target`.center_id in |
|||
<foreach collection="query.bizRegionIds" item="selectId" index="i" open="(" close=")" separator=","> |
|||
#{selectId} |
|||
</foreach> |
|||
) |
|||
</if> |
|||
<if test="query.centerIds!=null and query.centerIds.size > 0"> |
|||
or (`bir_budget_target`.`center_type` = 'costCenter' and `bir_budget_target`.center_id in |
|||
<foreach collection="query.centerIds" item="selectId" index="i" open="(" close=")" separator=","> |
|||
#{selectId} |
|||
</foreach> |
|||
) |
|||
</if> |
|||
) |
|||
</if> |
|||
|
|||
</where> |
|||
</select> |
|||
|
|||
</mapper> |
Loading…
Reference in new issue