Merge branch 'feature/feeding-management-20250801'

This commit is contained in:
HashMap 2025-08-20 11:55:53 +08:00
commit 847055687b
6 changed files with 576 additions and 0 deletions

View File

@ -0,0 +1,219 @@
package com.zhyc.module.feed.controller;
import java.util.ArrayList;
import java.util.HashMap;
import java.util.List;
import java.util.Map;
import javax.servlet.http.HttpServletResponse;
import com.zhyc.module.feed.domain.SgFeedPlan;
import com.zhyc.module.feed.domain.SgFormulaManagement;
import com.zhyc.module.feed.service.ISgFeedPlanService;
import com.zhyc.module.feed.service.ISgFormulaManagementService;
import org.springframework.security.access.prepost.PreAuthorize;
import org.springframework.transaction.annotation.Transactional;
import org.springframework.web.bind.annotation.GetMapping;
import org.springframework.web.bind.annotation.PostMapping;
import org.springframework.web.bind.annotation.PutMapping;
import org.springframework.web.bind.annotation.DeleteMapping;
import org.springframework.web.bind.annotation.PathVariable;
import org.springframework.web.bind.annotation.RequestBody;
import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.bind.annotation.RestController;
import com.zhyc.common.annotation.Log;
import com.zhyc.common.core.controller.BaseController;
import com.zhyc.common.core.domain.AjaxResult;
import com.zhyc.common.enums.BusinessType;
import com.zhyc.module.feed.domain.SgFeedList;
import com.zhyc.module.feed.service.ISgFeedListService;
import com.zhyc.common.utils.poi.ExcelUtil;
import com.zhyc.common.core.page.TableDataInfo;
/**
* 配料清单Controller
*
* @author HashMap
* @date 2025-08-19
*/
@RestController
@RequestMapping("/feed/FeedList")
public class SgFeedListController extends BaseController {
private final ISgFeedListService sgFeedListService;
private final ISgFormulaManagementService sgFormulaManagementService;
private final ISgFeedPlanService sgFeedPlanService;
private final Map<String, SgFeedList> sgFeedListMap = new HashMap<>();
public SgFeedListController(ISgFeedListService sgFeedListService, ISgFormulaManagementService sgFormulaManagementService, ISgFeedPlanService sgFeedPlanService) {
this.sgFeedListService = sgFeedListService;
this.sgFormulaManagementService = sgFormulaManagementService;
this.sgFeedPlanService = sgFeedPlanService;
}
/**
* 查询配料清单列表
*/
@PreAuthorize("@ss.hasPermi('feed:FeedList:list')")
@GetMapping("/list")
@Transactional(rollbackFor = Exception.class)
public TableDataInfo list(SgFeedList sgFeedList) {
SyncFeedList();
startPage();
List<SgFeedList> list = sgFeedListService.selectSgFeedListList(sgFeedList);
// map 中已有的数据替换 list 中的元素
List<SgFeedList> replacedList = new ArrayList<>();
for (SgFeedList item : list) {
String key = item.getFormulaId() + "_" + item.getFormulaBatchId();
// 从缓存中取出完整对象
SgFeedList itemInCache = sgFeedListMap.getOrDefault(key, item);
// 将数据库查询的基本信息替换掉缓存中去除的内容 - 前端展示与修改需要
itemInCache.setId(item.getId());
itemInCache.setFormulaBatchId(item.getFormulaBatchId());
itemInCache.setFormulaId(item.getFormulaId());
itemInCache.setZookeeper(item.getZookeeper());
itemInCache.setDeployDate(item.getDeployDate());
// 替换为 map 中的对象
replacedList.add(itemInCache);
}
return getDataTable(replacedList);
}
/**
* 导出配料清单列表
*/
@PreAuthorize("@ss.hasPermi('feed:FeedList:export')")
@Log(title = "配料清单", businessType = BusinessType.EXPORT)
@PostMapping("/export")
public void export(HttpServletResponse response, SgFeedList sgFeedList) {
List<SgFeedList> list = sgFeedListService.selectSgFeedListList(sgFeedList);
ExcelUtil<SgFeedList> util = new ExcelUtil<>(SgFeedList.class);
util.exportExcel(response, list, "配料清单数据");
}
/**
* 获取配料清单详细信息
*/
@PreAuthorize("@ss.hasPermi('feed:FeedList:query')")
@GetMapping(value = "/{id}")
public AjaxResult getInfo(@PathVariable("id") Long id) {
return success(sgFeedListService.selectSgFeedListById(id));
}
/**
* 新增配料清单
*/
@PreAuthorize("@ss.hasPermi('feed:FeedList:add')")
@Log(title = "配料清单", businessType = BusinessType.INSERT)
@PostMapping
public AjaxResult add(@RequestBody SgFeedList sgFeedList) {
return toAjax(sgFeedListService.insertSgFeedList(sgFeedList));
}
/**
* 修改配料清单
*/
@PreAuthorize("@ss.hasPermi('feed:FeedList:edit')")
@Log(title = "配料清单", businessType = BusinessType.UPDATE)
@PutMapping
public AjaxResult edit(@RequestBody SgFeedList sgFeedList) {
return toAjax(sgFeedListService.updateSgFeedList(sgFeedList));
}
/**
* 删除配料清单
*/
@PreAuthorize("@ss.hasPermi('feed:FeedList:remove')")
@Log(title = "配料清单", businessType = BusinessType.DELETE)
@DeleteMapping("/{ids}")
@Transactional(rollbackFor = Exception.class)
public AjaxResult remove(@PathVariable Long[] ids) {
return toAjax(sgFeedListService.deleteSgFeedListByIds(ids));
}
public void SyncFeedList() {
// 清空旧缓存
sgFeedListMap.clear();
// 获取配方管理和现有配料清单内容
List<SgFormulaManagement> formulaManagementList = sgFormulaManagementService.selectSgFormulaManagementList(new SgFormulaManagement());
List<SgFeedList> feedLists = sgFeedListService.selectSgFeedListList(new SgFeedList());
// 将最新查询的配料清单加入缓存
for (SgFeedList sgFeedList : feedLists) {
sgFeedListMap.put(sgFeedList.getFormulaId() + "_" + sgFeedList.getFormulaBatchId(), sgFeedList);
}
// 与新的配方管理列表同步 - 如果配料清单没有对应数据则加入
for (SgFormulaManagement sgFormulaManagement : formulaManagementList) {
// 匹配 但忽略模板配方
if (sgFormulaManagement.getFormulaId() != null && sgFormulaManagement.getBatchId() != null && !sgFormulaManagement.getBatchId().equals("0")) {
// 查询当前配方管理项是否存在现有配料计划中 (不论是否存在都要设置,因为缓存被清空,存在则更新,不存在则插入)
boolean isExist = sgFeedListMap.containsKey(sgFormulaManagement.getFormulaId() + "_" + sgFormulaManagement.getBatchId());
// 标志位 : 如果当前配方不在饲喂计划中则不生成配量清单
boolean isPlan = true;
// 设置缓存对象具体值
SgFeedList sgFeedList = new SgFeedList();
sgFeedList.setFormulaId(sgFormulaManagement.getFormulaId());
sgFeedList.setFormulaBatchId(sgFormulaManagement.getBatchId());
sgFeedList.setFormulaList(sgFormulaManagement.getSgFormulaList());
sgFeedList.setRootFormula(sgFormulaManagement);
// 从饲喂计划列表中查出对应值(饲喂量需要计划中的比例计算)
SgFeedPlan rootPlanQuery = new SgFeedPlan();
rootPlanQuery.setFormulaId(sgFormulaManagement.getFormulaId());
rootPlanQuery.setBatchId(sgFormulaManagement.getBatchId());
List<SgFeedPlan> sgFeedPlans = sgFeedPlanService.selectSgFeedPlanList(rootPlanQuery);
// 为空则标识当前配方不在饲喂计划中
if (sgFeedPlans.isEmpty()) {
isPlan = false;
}
// rootPlan中存储的是该配方批号的总量
SgFeedPlan rootPlan = computePlanTotal(sgFeedPlans);
// 将计划实体对象设置到配料清单中
sgFeedList.setRootPlan(rootPlan);
// 完整的配料清单对象加入缓存
sgFeedListMap.put(sgFormulaManagement.getFormulaId() + "_" + sgFormulaManagement.getBatchId(), sgFeedList);
// 不存在则插入
if (!isExist && isPlan) {
sgFeedListService.insertSgFeedList(sgFeedList);
}
}
}
}
/**
* 计算某个配方某个批次的总和值
*
* @param sgFeedPlans 配方计划列表
* @return 各个值总和
*/
private static SgFeedPlan computePlanTotal(List<SgFeedPlan> sgFeedPlans) {
SgFeedPlan rootPlan = new SgFeedPlan();
if (!sgFeedPlans.isEmpty()) {
int sheepCountTotal = 0;
double sheepDailySize = 0.0;
double planFeedMorningSize = 0.0;
double planFeedNoonSize = 0.0;
double planFeedAfternoonSize = 0.0;
double planFeedTotalSize = 0.0;
for (SgFeedPlan sgFeedPlan : sgFeedPlans) {
sheepCountTotal += sgFeedPlan.getSheepCount();
sheepDailySize += sgFeedPlan.getPlanDailySize();
planFeedMorningSize += sgFeedPlan.getPlanMorningSize();
planFeedNoonSize += sgFeedPlan.getPlanNoonSize();
planFeedAfternoonSize += sgFeedPlan.getPlanAfternoonSize();
planFeedTotalSize += sgFeedPlan.getPlanFeedTotal();
}
rootPlan.setSheepCount(sheepCountTotal);
rootPlan.setPlanDailySize(sheepDailySize);
rootPlan.setPlanMorningSize(planFeedMorningSize);
rootPlan.setPlanNoonSize(planFeedNoonSize);
rootPlan.setPlanAfternoonSize(planFeedAfternoonSize);
rootPlan.setPlanFeedTotal(planFeedTotalSize);
}
return rootPlan;
}
}

View File

@ -0,0 +1,67 @@
package com.zhyc.module.feed.domain;
import java.util.Date;
import java.util.List;
import com.fasterxml.jackson.annotation.JsonFormat;
import lombok.Getter;
import lombok.Setter;
import org.apache.commons.lang3.builder.ToStringBuilder;
import org.apache.commons.lang3.builder.ToStringStyle;
import com.zhyc.common.annotation.Excel;
import com.zhyc.common.core.domain.BaseEntity;
/**
* 配料清单对象 sg_feed_list
*
* @author HashMap
* @date 2025-08-19
*/
@Setter
@Getter
public class SgFeedList extends BaseEntity
{
private static final long serialVersionUID = 1L;
/** 序号 */
private Long id;
/** 配方编号 */
@Excel(name = "配方编号")
private String formulaId;
/** 配方批号 */
@Excel(name = "配方批号")
private String formulaBatchId;
/** 饲草班人员 */
@Excel(name = "饲草班人员")
private String zookeeper;
/** 配料日期 */
@JsonFormat(pattern = "yyyy-MM-dd")
@Excel(name = "配料日期", width = 30, dateFormat = "yyyy-MM-dd")
private Date deployDate;
private SgFormulaManagement rootFormula;
private SgFeedPlan rootPlan;
private Double morningTotal;
private Double noonTotal;
private Double afternoonTotal;
private List<SgFormulaList> formulaList;
@Override
public String toString() {
return new ToStringBuilder(this,ToStringStyle.MULTI_LINE_STYLE)
.append("id", getId())
.append("formulaId", getFormulaId())
.append("formulaBatchId", getFormulaBatchId())
.append("zookeeper", getZookeeper())
.append("deployDate", getDeployDate())
.toString();
}
}

View File

@ -0,0 +1,63 @@
package com.zhyc.module.feed.mapper;
import java.util.List;
import com.zhyc.module.feed.domain.SgFeedList;
import org.apache.ibatis.annotations.Mapper;
/**
* 配料清单Mapper接口
*
* @author HashMap
* @date 2025-08-19
*/
@Mapper
public interface SgFeedListMapper
{
/**
* 查询配料清单
*
* @param id 配料清单主键
* @return 配料清单
*/
SgFeedList selectSgFeedListById(Long id);
/**
* 查询配料清单列表
*
* @param sgFeedList 配料清单
* @return 配料清单集合
*/
List<SgFeedList> selectSgFeedListList(SgFeedList sgFeedList);
/**
* 新增配料清单
*
* @param sgFeedList 配料清单
* @return 结果
*/
int insertSgFeedList(SgFeedList sgFeedList);
/**
* 修改配料清单
*
* @param sgFeedList 配料清单
* @return 结果
*/
int updateSgFeedList(SgFeedList sgFeedList);
/**
* 删除配料清单
*
* @param id 配料清单主键
* @return 结果
*/
int deleteSgFeedListById(Long id);
/**
* 批量删除配料清单
*
* @param ids 需要删除的数据主键集合
* @return 结果
*/
int deleteSgFeedListByIds(Long[] ids);
}

View File

@ -0,0 +1,61 @@
package com.zhyc.module.feed.service;
import java.util.List;
import com.zhyc.module.feed.domain.SgFeedList;
/**
* 配料清单Service接口
*
* @author HashMap
* @date 2025-08-19
*/
public interface ISgFeedListService
{
/**
* 查询配料清单
*
* @param id 配料清单主键
* @return 配料清单
*/
SgFeedList selectSgFeedListById(Long id);
/**
* 查询配料清单列表
*
* @param sgFeedList 配料清单
* @return 配料清单集合
*/
List<SgFeedList> selectSgFeedListList(SgFeedList sgFeedList);
/**
* 新增配料清单
*
* @param sgFeedList 配料清单
* @return 结果
*/
int insertSgFeedList(SgFeedList sgFeedList);
/**
* 修改配料清单
*
* @param sgFeedList 配料清单
* @return 结果
*/
int updateSgFeedList(SgFeedList sgFeedList);
/**
* 批量删除配料清单
*
* @param ids 需要删除的配料清单主键集合
* @return 结果
*/
int deleteSgFeedListByIds(Long[] ids);
/**
* 删除配料清单信息
*
* @param id 配料清单主键
* @return 结果
*/
int deleteSgFeedListById(Long id);
}

View File

@ -0,0 +1,96 @@
package com.zhyc.module.feed.service.impl;
import java.util.List;
import org.springframework.stereotype.Service;
import com.zhyc.module.feed.mapper.SgFeedListMapper;
import com.zhyc.module.feed.domain.SgFeedList;
import com.zhyc.module.feed.service.ISgFeedListService;
/**
* 配料清单Service业务层处理
*
* @author HashMap
* @date 2025-08-19
*/
@Service
public class SgFeedListServiceImpl implements ISgFeedListService
{
private final SgFeedListMapper sgFeedListMapper;
public SgFeedListServiceImpl(SgFeedListMapper sgFeedListMapper) {
this.sgFeedListMapper = sgFeedListMapper;
}
/**
* 查询配料清单
*
* @param id 配料清单主键
* @return 配料清单
*/
@Override
public SgFeedList selectSgFeedListById(Long id)
{
return sgFeedListMapper.selectSgFeedListById(id);
}
/**
* 查询配料清单列表
*
* @param sgFeedList 配料清单
* @return 配料清单
*/
@Override
public List<SgFeedList> selectSgFeedListList(SgFeedList sgFeedList)
{
return sgFeedListMapper.selectSgFeedListList(sgFeedList);
}
/**
* 新增配料清单
*
* @param sgFeedList 配料清单
* @return 结果
*/
@Override
public int insertSgFeedList(SgFeedList sgFeedList)
{
return sgFeedListMapper.insertSgFeedList(sgFeedList);
}
/**
* 修改配料清单
*
* @param sgFeedList 配料清单
* @return 结果
*/
@Override
public int updateSgFeedList(SgFeedList sgFeedList)
{
return sgFeedListMapper.updateSgFeedList(sgFeedList);
}
/**
* 批量删除配料清单
*
* @param ids 需要删除的配料清单主键
* @return 结果
*/
@Override
public int deleteSgFeedListByIds(Long[] ids)
{
return sgFeedListMapper.deleteSgFeedListByIds(ids);
}
/**
* 删除配料清单信息
*
* @param id 配料清单主键
* @return 结果
*/
@Override
public int deleteSgFeedListById(Long id)
{
return sgFeedListMapper.deleteSgFeedListById(id);
}
}

View File

@ -0,0 +1,70 @@
<?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.zhyc.module.feed.mapper.SgFeedListMapper">
<resultMap type="SgFeedList" id="SgFeedListResult">
<result property="id" column="id" />
<result property="formulaId" column="formula_id" />
<result property="formulaBatchId" column="formula_batch_id" />
<result property="zookeeper" column="zookeeper" />
<result property="deployDate" column="deploy_date" />
</resultMap>
<sql id="selectSgFeedListVo">
select id, formula_id, formula_batch_id, zookeeper, deploy_date from sg_feed_list
</sql>
<select id="selectSgFeedListList" parameterType="SgFeedList" resultMap="SgFeedListResult">
<include refid="selectSgFeedListVo"/>
<where>
<if test="formulaId != null and formulaId != ''"> and formula_id = #{formulaId}</if>
<if test="zookeeper != null and zookeeper != ''"> and zookeeper = #{zookeeper}</if>
<if test="deployDate != null "> and deploy_date = #{deployDate}</if>
</where>
</select>
<select id="selectSgFeedListById" parameterType="Long" resultMap="SgFeedListResult">
<include refid="selectSgFeedListVo"/>
where id = #{id}
</select>
<insert id="insertSgFeedList" parameterType="SgFeedList" useGeneratedKeys="true" keyProperty="id">
insert into sg_feed_list
<trim prefix="(" suffix=")" suffixOverrides=",">
<if test="formulaId != null">formula_id,</if>
<if test="formulaBatchId != null">formula_batch_id,</if>
<if test="zookeeper != null">zookeeper,</if>
<if test="deployDate != null">deploy_date,</if>
</trim>
<trim prefix="values (" suffix=")" suffixOverrides=",">
<if test="formulaId != null">#{formulaId},</if>
<if test="formulaBatchId != null">#{formulaBatchId},</if>
<if test="zookeeper != null">#{zookeeper},</if>
<if test="deployDate != null">#{deployDate},</if>
</trim>
</insert>
<update id="updateSgFeedList" parameterType="SgFeedList">
update sg_feed_list
<trim prefix="SET" suffixOverrides=",">
<if test="formulaId != null">formula_id = #{formulaId},</if>
<if test="formulaBatchId != null">formula_batch_id = #{formulaBatchId},</if>
<if test="zookeeper != null">zookeeper = #{zookeeper},</if>
<if test="deployDate != null">deploy_date = #{deployDate},</if>
</trim>
where id = #{id}
</update>
<delete id="deleteSgFeedListById" parameterType="Long">
delete from sg_feed_list where id = #{id}
</delete>
<delete id="deleteSgFeedListByIds" parameterType="String">
delete from sg_feed_list where id in
<foreach item="id" collection="array" open="(" separator="," close=")">
#{id}
</foreach>
</delete>
</mapper>