package com.fzzy.igds.timer; import com.fzzy.igds.constant.Constant; import com.fzzy.igds.data.IgdsBaseParam; import com.fzzy.igds.domain.*; import com.fzzy.igds.service.*; import com.fzzy.igds.utils.ContextUtil; import com.fzzy.igds.utils.DateUtil; import lombok.extern.slf4j.Slf4j; import org.apache.commons.lang3.time.DateFormatUtils; import org.apache.commons.lang3.time.DateUtils; import org.springframework.stereotype.Service; import javax.annotation.Resource; import java.time.LocalDate; import java.util.*; /** * @Description 库存定时统计入口:通过框架定时任务调用,默认每天凌晨1点执行,统计昨天的库存信息 * @Author CZT * @Date 2026/1/14 10:42 */ @Slf4j @Service public class JobDepotStoreService { @Resource private CoreDeptService deptService; @Resource private InoutRecordService inoutRecordService; @Resource private InoutStockChangeService stockChangeService; @Resource private InoutLossOverService lossOverService; @Resource private DepotStoreService depotStoreService; @Resource private DepotService depotService; public void timer() { doExe(); } /** * 开始执行库存统计 */ public void doExe() { Date time = DateUtil.getNewByDay(new Date(), -1); log.info("===============系统定时统计库存信息==============="); //获取所有的库区信息 List listDept = deptService.listDept(null, ContextUtil.getCompanyId(), null); if (null == listDept || listDept.isEmpty()) { log.info("-----未获取到库区,不执行库存定时统计-----"); return; } Date startTime = null; //出入库最早时间 for (Dept dept : listDept) { startTime = getStartTime(time, dept); if (null == startTime) { log.info("-----{}在{}未有库存相关数量更新,不执行库存统计-----", dept.getKqmc(), DateFormatUtils.format(time, "yyyy-MM-dd")); continue; } //多天循环统计 sumMoreDepotStore(startTime, time, dept); } } /** * 多天循环遍历统计库存信息 * * @param startTime * @param endTime * @param dept */ public void sumMoreDepotStore(Date startTime, Date endTime, Dept dept) { log.info("-----统计库存信息,库区={},时间={}--->{}-----", dept.getKqmc(), DateFormatUtils.format(startTime, "yyyy-MM-dd"), DateFormatUtils.format(endTime, "yyyy-MM-dd")); //获取两个时间相差的天数 LocalDate startDate = LocalDate.parse(DateFormatUtils.format(startTime, "yyyy-MM-dd")); LocalDate endDate = LocalDate.parse(DateFormatUtils.format(endTime, "yyyy-MM-dd")); //从最早天开始循环统计库存到当前天 while (!startDate.isAfter(endDate)) { //统计库区库存 sumDepotStore(startTime, dept); //对应时间加1天 startTime = DateUtils.addDays(startTime, 1); //将日期加1天 startDate = startDate.plusDays(1); } } /** * 根据时间,统计更新当天的库存信息 * * @param time * @param dept */ public void sumDepotStore(Date time, Dept dept) { //更改为当天的23点50分 time = DateUtils.addMinutes(DateUtil.getNextZero(time), -10); log.info("-----统计库存信息,库区={},时间={}-----", dept.getKqmc(), DateFormatUtils.format(time, "yyyy-MM-dd")); //设置参数 IgdsBaseParam param = new IgdsBaseParam(); param.setStart(DateUtil.getCurZero(time)); param.setEnd(DateUtil.getNextZero(time)); param.setDeptId(dept.getId()); //用于存放数量变动的仓库 Set set = new HashSet<>(); //统计仓库的数量 Map map1 = new HashMap<>(); Map map2 = new HashMap<>(); Map map3 = new HashMap<>(); boolean inTag = false; boolean outTag = false; //获取出入库信息统计仓库数量 List inoutRecords = inoutRecordService.getCompleteInoutByTime("complete_time", param); if (null != inoutRecords && !inoutRecords.isEmpty()) { for (InoutRecord inoutRecord : inoutRecords) { set.add(inoutRecord.getDepotId()); map1.putIfAbsent(inoutRecord.getDepotId(), 0.0); //统计数量 if (Constant.TYPE_IN.equals(inoutRecord.getType())) { inTag = true; map1.put(inoutRecord.getDepotId(), map1.get(inoutRecord.getDepotId()) + inoutRecord.getRecordWeight()); } if (Constant.TYPE_OUT.equals(inoutRecord.getType())) { outTag = true; map1.put(inoutRecord.getDepotId(), map1.get(inoutRecord.getDepotId()) - inoutRecord.getRecordWeight()); } } } //获取倒仓信息统计仓库数量 List stockChanges = stockChangeService.getDataByTime("change_date", param); if (null != stockChanges && !stockChanges.isEmpty()) { for (InoutStockChange stockChange : stockChanges) { set.add(stockChange.getDepotIdIn()); set.add(stockChange.getDepotIdOut()); map2.putIfAbsent(stockChange.getDepotIdIn(), 0.0); map2.putIfAbsent(stockChange.getDepotIdOut(), 0.0); //统计数量 map2.put(stockChange.getDepotIdIn(), map2.get(stockChange.getDepotIdIn()) + stockChange.getNumber()); map2.put(stockChange.getDepotIdOut(), map2.get(stockChange.getDepotIdOut()) - stockChange.getNumber()); } } //获取损益信息统计仓库数量 List lossOvers = lossOverService.getDataByTime("loss_time", param); if (null != lossOvers && !lossOvers.isEmpty()) { for (InoutLossOver lossOver : lossOvers) { set.add(lossOver.getDepotId()); map3.putIfAbsent(lossOver.getDepotId(), 0.0); //统计数量 if (Constant.TYPE_LOSS.equals(lossOver.getType())) { map1.put(lossOver.getDepotId(), map1.get(lossOver.getDepotId()) - lossOver.getAmount()); } if (Constant.TYPE_OVER.equals(lossOver.getType())) { map1.put(lossOver.getDepotId(), map1.get(lossOver.getDepotId()) + lossOver.getAmount()); } } } Double sum = 0.0; Depot depot; for (String s : set) { sum = 0.0; if (null != map1.get(s)) { sum += map1.get(s); } if (null != map2.get(s)) { sum += map2.get(s); } if (null != map3.get(s)) { sum += map3.get(s); } //获取上一条数据 DepotStore lastData = depotStoreService.getLastData(s, time); if (null == lastData) { lastData = new DepotStore(); //主键ID规则:yyyyMMddHHmm_仓库编码 lastData.setId(DateFormatUtils.format(time, "yyyyMMddHHmm") + "_" + s); lastData.setCompanyId(dept.getCompanyId()); lastData.setDeptId(dept.getId()); lastData.setDepotId(s); lastData.setStorageReal(0.0); lastData.setUpdateTime(time); lastData.setUpdateBy("系统定时统计"); if (inTag) { //设置入库时间 lastData.setStoreDate(time); } if (outTag) { //设置出库时间 lastData.setOutDate(time); } //获取仓库信息 depot = depotService.getCacheDepot(dept.getCompanyId(), s); if (null != depot) { lastData.setDepotStatus(depot.getDepotStatus()); lastData.setFoodVariety(depot.getFoodVariety()); lastData.setFoodLevel(depot.getFoodLevel()); lastData.setFoodLocation(depot.getFoodLocation()); lastData.setFoodLocationId(depot.getFoodLocationId()); lastData.setFoodType(depot.getFoodType()); lastData.setFoodYear(depot.getFoodYear()); } } lastData.setStorageReal(lastData.getStorageReal() + sum); lastData.setCreateTime(new Date()); //设置为最新时间,其他系统可以通过此时间查询数据是否有更新修改,同步到省平台接口。 lastData.setCreateBy("系统定时统计"); lastData.setRemark("系统统计" + DateFormatUtils.format(time, "yyyy-MM-dd") + "日库存"); depotStoreService.updateAndSave(lastData); } } /** * 根据时间,统计更新当天的库存信息 * * @param dept */ public Date getStartTime(Date time, Dept dept) { Date startTime = time; //出入库最早时间 Date time1 = null; //出入库最早时间 Date time2 = null; //倒仓最早时间 Date time3 = null; //损益最早时间 //获取当天有更新的出入库信息 IgdsBaseParam param = new IgdsBaseParam(); param.setStart(DateUtil.getCurZero(time)); param.setEnd(DateUtil.getNextZero(time)); //获取当天有更新的出入库信息 param.setDeptId(dept.getId()); List inoutRecords = inoutRecordService.getCompleteInoutByTime("update_time", param); if (null != inoutRecords && !inoutRecords.isEmpty()) { time1 = inoutRecords.get(0).getCompleteTime(); } //获取当天有更新的倒仓数据 List stockChanges = stockChangeService.getDataByTime("update_time", param); if (null != stockChanges && !stockChanges.isEmpty()) { time2 = stockChanges.get(0).getChangeDate(); } //获取当天有更新的损益数据 List lossOvers = lossOverService.getDataByTime("update_time", param); if (null != lossOvers && !lossOvers.isEmpty()) { time3 = lossOvers.get(0).getLossTime(); } if (null == time1 && null == time2 && null == time3) { return null; } if (null != time1 && time1.before(startTime)) { startTime = time1; } if (null != time2 && time2.before(startTime)) { startTime = time2; } if (null != time3 && time3.before(startTime)) { startTime = time3; } return startTime; } }