package jnpf.limsController;
|
|
import jnpf.audit.sdk.annotation.AuditLog;
|
|
import com.baomidou.mybatisplus.core.conditions.query.LambdaQueryWrapper;
|
import com.baomidou.mybatisplus.core.conditions.update.LambdaUpdateWrapper;
|
import io.swagger.v3.oas.annotations.Operation;
|
import io.swagger.v3.oas.annotations.tags.Tag;
|
import jnpf.limsEntity.LimsLiuyangBiangengShenqingEntity;
|
import jnpf.limsEntity.LimsLiuyangJihuaBiangengShenqingEntity;
|
import jnpf.limsEntity.LimsLiuyangJihuaBiangengShenqingZixiangEntity;
|
import jnpf.limsEntity.LimsLiuyangJihuaCalculateParam;
|
import jnpf.limsEntity.LimsLiuyangJihuaCalculateResult;
|
import jnpf.limsEntity.LimsLiuyangJihuaBiangengCalculateParam;
|
import jnpf.limsEntity.LimsLiuyangJihuaEntity;
|
import jnpf.limsEntity.LimsLiuyangJihuaZixiangEntity;
|
import jnpf.limsEntity.LimsLiuyangJiluEntity;
|
import jnpf.limsEntity.LiuyangStatus;
|
import jnpf.limsEntity.LiuyangWendingxingZhouqiZixiangEntity;
|
import jnpf.limsEntity.LimsQingyandanEntity;
|
import jnpf.limsService.LiuyangWendingxingZhouqiZixiangService;
|
import jnpf.limsService.LimsLiuyangJihuaService;
|
import jnpf.limsService.LimsLiuyangJihuaZixiangService;
|
import jnpf.limsService.LimsLiuyangBiangengShenqingService;
|
import jnpf.limsService.LimsLiuyangJihuaBiangengShenqingService;
|
import jnpf.limsService.LimsLiuyangJihuaBiangengShenqingZixiangService;
|
import jnpf.limsService.LimsLiuyangJiluService;
|
import jnpf.limsService.LimsQingyandanService;
|
import jnpf.util.R;
|
import jnpf.util.RandomUtil;
|
import jnpf.util.UserProvider;
|
import lombok.extern.slf4j.Slf4j;
|
import org.springframework.beans.factory.annotation.Autowired;
|
import org.springframework.jdbc.core.JdbcTemplate;
|
import org.springframework.transaction.annotation.Transactional;
|
import org.springframework.web.bind.annotation.PostMapping;
|
import org.springframework.web.bind.annotation.RequestBody;
|
import org.springframework.web.bind.annotation.RequestMapping;
|
import org.springframework.web.bind.annotation.RestController;
|
|
import javax.sql.DataSource;
|
import java.math.BigDecimal;
|
import java.sql.Connection;
|
import java.sql.DatabaseMetaData;
|
import java.sql.PreparedStatement;
|
import java.sql.ResultSet;
|
import java.sql.SQLException;
|
import java.time.LocalDateTime;
|
import java.time.ZoneId;
|
import java.util.ArrayList;
|
import java.util.Arrays;
|
import java.util.Date;
|
import java.util.LinkedHashMap;
|
import java.util.LinkedHashSet;
|
import java.util.List;
|
import java.util.Map;
|
import java.util.Set;
|
import java.util.stream.Collectors;
|
|
@Slf4j
|
@Tag(name = "lims留样接口", description = "留样记录流程操作")
|
@RestController
|
@RequestMapping("/lims/biz")
|
public class LimsLiuyangController {
|
|
private static final String BIANGENG_ZIXIANG_TABLE = "lims_liuyang_jihua_biangeng_shenqing_zixiang";
|
private static final String LIUYANG_CHUKU_SHENQING_TABLE = "lims_liuyang_chuku_shenqing";
|
private static final String LIUYANG_CHUKU_SHENQING_ZIXIANG_TABLE = "lims_liuyang_chuku_shenqing_zixiang";
|
private static final String LIUYANG_CHUKU_TABLE = "lims_liuyang_chuku";
|
private static final String LIUYANG_XIAOHUI_SHENQING_TABLE = "lims_liuyang_xiaohui_shenqing";
|
private static final String LIUYANG_XIAOHUI_SHENQING_ZIXIANG_TABLE = "lims_liuyang_xiaohui_shenqing_zixiang";
|
private static final String BIZ_STATUS_DESTROYED = "destroyed";
|
private static final String BIZ_STATUS_DISABLED = "disabled";
|
|
private static final List<String> DEFAULT_BIANGENG_ZIXIANG_FIELDS = Arrays.asList(
|
"zhouqi",
|
"zhouqi_danwei",
|
"jihua_riqi",
|
"shifou_yiguancha",
|
"guancha_riqi",
|
"guancha_ren",
|
"guancha_shuliang",
|
"guancha_qingkuang",
|
"guancha_jieguo",
|
"beizhu"
|
);
|
|
@Autowired
|
private LimsLiuyangJiluService limsLiuyangJiluService;
|
|
@Autowired
|
private LimsQingyandanService limsQingyandanService;
|
|
@Autowired
|
private LiuyangWendingxingZhouqiZixiangService liuyangWendingxingZhouqiZixiangService;
|
|
@Autowired
|
private LimsLiuyangJihuaService limsLiuyangJihuaService;
|
|
@Autowired
|
private LimsLiuyangJihuaZixiangService limsLiuyangJihuaZixiangService;
|
|
@Autowired
|
private LimsLiuyangBiangengShenqingService limsLiuyangBiangengShenqingService;
|
|
@Autowired
|
private LimsLiuyangJihuaBiangengShenqingService limsLiuyangJihuaBiangengShenqingService;
|
|
@Autowired
|
private LimsLiuyangJihuaBiangengShenqingZixiangService limsLiuyangJihuaBiangengShenqingZixiangService;
|
|
@Autowired
|
private DataSource dataSource;
|
|
@Autowired
|
private JdbcTemplate jdbcTemplate;
|
|
/**
|
* 留样操作:
|
* submit -> 待审核,并把请验单 liuyang_jilu_id 关联到当前留样记录;
|
* reject -> 已退回,并清空请验单 liuyang_jilu_id;
|
* accept -> 已接收,并同步入库数量/单位为留样现存量;
|
* delete -> 按 JNPF 表单规范软删除留样记录。
|
*/
|
@Transactional(rollbackFor = Exception.class)
|
@Operation(summary = "留样操作(提交/拒绝/同意)")
|
@PostMapping("/liuyang/action")
|
@AuditLog(action = "LIUYANG_ACTION", label = "留样操作", bizType = "LIUYANG",
|
bizCodeExpr = "#result.success ? (#params['id'] ?: 'LIUYANG_ACTION') : ''", targetTable = "lims_liuyang_jilu",
|
targetIdExpr = "#params['id']", extraExpr = "{'action': #params['action']}",
|
diff = true, entityClass = LimsLiuyangJiluEntity.class)
|
public R<String> liuyangAction(@RequestBody Map<String, String> params) {
|
String action = params.get("action");
|
String id = params.get("id");
|
String flowId = firstNotBlank(params.get("flow_id"), params.get("flowId"));
|
String taskId = firstNotBlank(params.get("task_id"), params.get("taskId"));
|
String bizSign = params.get("biz_sign");
|
|
if (action == null || action.isEmpty()) {
|
return R.error("缺少 action");
|
}
|
if ((id == null || id.isEmpty()) && (flowId == null || flowId.isEmpty())) {
|
return R.error("缺少 flow_id");
|
}
|
|
LimsLiuyangJiluEntity liuyangJilu = findLiuyangJilu(id, flowId, taskId);
|
if (liuyangJilu == null) {
|
return R.error("留样记录数据不存在");
|
}
|
|
switch (action) {
|
case "submit":
|
updateLiuyangStatus(liuyangJilu, LiuyangStatus.PENDING_AUDIT, bizSign);
|
updateQingyandanLiuyangJiluId(liuyangJilu, liuyangJilu.getId());
|
return R.success("提交成功");
|
case "reject":
|
updateLiuyangStatus(liuyangJilu, LiuyangStatus.REJECTED, bizSign);
|
updateQingyandanLiuyangJiluId(liuyangJilu, null);
|
return R.success("拒绝成功");
|
case "accept":
|
receiveLiuyangJilu(liuyangJilu, bizSign);
|
return R.success("同意成功");
|
case "delete":
|
softDeleteLiuyangJilu(liuyangJilu, bizSign);
|
updateQingyandanLiuyangJiluId(liuyangJilu, null);
|
return R.success("删除成功");
|
default:
|
return R.error("不支持的操作: " + action);
|
}
|
}
|
|
/**
|
* 留样销毁流程操作:
|
* submit -> 销毁单号回写到留样记录;
|
* reject -> 清空留样记录销毁单号;
|
* accept -> shifou_pizhun=yes 时置为已销毁并禁用关联观察计划及子项,shifou_pizhun=no 时清空销毁单号。
|
*/
|
@Transactional(rollbackFor = Exception.class)
|
@Operation(summary = "留样销毁操作(提交/拒绝/同意)")
|
@PostMapping("/liuyang/xiaohui/action")
|
@AuditLog(action = "DESTROY_ACTION", label = "留样销毁操作", bizType = "LIUYANG",
|
bizCodeExpr = "#result.success ? (#params['id'] ?: 'LIUYANG_DESTROY') : ''", targetTable = "lims_liuyang_jilu",
|
targetIdExpr = "#params['id']", extraExpr = "{'action': #params['action']}",
|
diff = true, entityClass = LimsLiuyangJiluEntity.class)
|
public R<String> liuyangXiaohuiAction(@RequestBody Map<String, String> params) {
|
if (params == null) {
|
return R.error("请求参数不能为空");
|
}
|
String flowId = firstNotBlank(params.get("flow_id"), params.get("flowId"));
|
String taskId = firstNotBlank(params.get("task_id"), params.get("taskId"));
|
String action = params.get("action");
|
String shifouPizhun = firstNotBlank(params.get("shifou_pizhun"), params.get("shifouPizhun"));
|
|
if (isBlank(flowId)) {
|
return R.error("流程id(flow_id)不能为空");
|
}
|
if (isBlank(taskId)) {
|
return R.error("流程任务id(task_id)不能为空");
|
}
|
if (isBlank(action)) {
|
return R.error("缺少 action");
|
}
|
|
Map<String, Object> shenqing = findLiuyangXiaohuiShenqing(flowId, taskId);
|
if (shenqing == null || shenqing.isEmpty()) {
|
return R.error("留样销毁申请数据不存在");
|
}
|
String shenqingId = getString(shenqing, "f_id");
|
String xiaohuiDanhao = getString(shenqing, "xiaohui_danhao");
|
List<String> liuyangJiluIds = listLiuyangXiaohuiJiluIds(shenqingId);
|
if (liuyangJiluIds.isEmpty()) {
|
return R.error("留样销毁申请子项不能为空");
|
}
|
|
switch (action) {
|
case "submit":
|
if (isBlank(xiaohuiDanhao)) {
|
return R.error("销毁单号不能为空");
|
}
|
updateLiuyangXiaohuiDanhao(liuyangJiluIds, xiaohuiDanhao);
|
return R.success("提交成功");
|
case "reject":
|
updateLiuyangXiaohuiDanhao(liuyangJiluIds, null);
|
return R.success("拒绝成功");
|
case "accept":
|
if ("yes".equals(shifouPizhun)) {
|
acceptLiuyangXiaohui(liuyangJiluIds);
|
return R.success("同意成功");
|
}
|
if ("no".equals(shifouPizhun)) {
|
updateLiuyangXiaohuiDanhao(liuyangJiluIds, null);
|
return R.success("拒绝成功");
|
}
|
return R.error("是否批准(shifou_pizhun)不能为空,且必须为 yes 或 no");
|
default:
|
return R.error("不支持的操作: " + action);
|
}
|
}
|
|
/**
|
* 计算留样计划子项周期列表。
|
*/
|
@Operation(summary = "计算留样计划周期")
|
@PostMapping("/liuyang/jihua/calculate")
|
public R<List<LimsLiuyangJihuaCalculateResult>> calculateLiuyangJihua(@RequestBody LimsLiuyangJihuaCalculateParam param) {
|
if (param == null || isBlank(param.getLiuyangJiluId())) {
|
return R.error("留样记录主键不能为空");
|
}
|
if (isBlank(param.getLiuyangZhouqiId())) {
|
return R.error("留样周期主键不能为空");
|
}
|
|
LimsLiuyangJiluEntity liuyangJilu = limsLiuyangJiluService.getById(param.getLiuyangJiluId());
|
if (liuyangJilu == null || Integer.valueOf(1).equals(liuyangJilu.getDeleteMark())) {
|
return R.error("留样记录数据不存在");
|
}
|
if (liuyangJilu.getShouyangRiqi() == null) {
|
return R.error("留样记录收样日期不能为空");
|
}
|
|
List<LiuyangWendingxingZhouqiZixiangEntity> zhouqiList = listWendingxingZhouqiZixiang(param.getLiuyangZhouqiId());
|
if (zhouqiList.isEmpty()) {
|
return R.error("稳定性周期子项不能为空");
|
}
|
|
try {
|
List<LimsLiuyangJihuaCalculateResult> jihuaList = zhouqiList.stream()
|
.map(row -> buildJihuaZixiang(row, liuyangJilu.getShouyangRiqi()))
|
.collect(Collectors.toList());
|
return R.success("计算成功", jihuaList);
|
} catch (IllegalArgumentException e) {
|
return R.error(e.getMessage());
|
}
|
}
|
|
/**
|
* 计划变更时,按新的留样日期重新计算未观察计划,并保留已观察的原计划。
|
*/
|
@Operation(summary = "计算留样计划变更子项")
|
@PostMapping("/liuyang/jihua/biangeng/calculate")
|
public R<List<Map<String, Object>>> calculateLiuyangJihuaBiangeng(@RequestBody LimsLiuyangJihuaBiangengCalculateParam param) {
|
if (param == null || isBlank(param.getLiuyangJihuaId())) {
|
return R.error("留样观察计划主键不能为空");
|
}
|
if (isBlank(param.getLiuyangZhouqiId())) {
|
return R.error("留样周期主键不能为空");
|
}
|
if (param.getLiuyangRiqi() == null) {
|
return R.error("留样日期不能为空");
|
}
|
|
List<LiuyangWendingxingZhouqiZixiangEntity> zhouqiList = listWendingxingZhouqiZixiang(param.getLiuyangZhouqiId());
|
if (zhouqiList.isEmpty()) {
|
return R.error("稳定性周期子项不能为空");
|
}
|
|
try {
|
List<String> responseFields = getBiangengZixiangBusinessFields();
|
List<Map<String, Object>> result = new ArrayList<>();
|
|
List<LimsLiuyangJihuaZixiangEntity> observedList = listObservedJihuaZixiang(param.getLiuyangJihuaId());
|
Set<String> observedZhouqiKeys = observedList.stream()
|
.map(row -> buildZhouqiKey(row.getZhouqi(), row.getZhouqiDanwei()))
|
.collect(Collectors.toSet());
|
observedList.stream()
|
.map(row -> buildBiangengRow(row, responseFields))
|
.forEach(result::add);
|
|
zhouqiList.stream()
|
.filter(row -> !observedZhouqiKeys.contains(buildZhouqiKey(row.getZhouqi(), row.getZhouqiDanwei())))
|
.map(row -> buildBiangengRow(row, param.getLiuyangRiqi(), responseFields))
|
.forEach(result::add);
|
|
return R.success("计算成功", result);
|
} catch (IllegalArgumentException e) {
|
return R.error(e.getMessage());
|
}
|
}
|
|
/**
|
* 提交留样观察计划:启用计划,并关联回留样记录。
|
*/
|
@Transactional(rollbackFor = Exception.class)
|
@Operation(summary = "提交留样观察计划")
|
@PostMapping("/liuyang/jihua/submit")
|
@AuditLog(action = "PLAN_SUBMIT", label = "提交留样观察计划", bizType = "LIUYANG",
|
bizCodeExpr = "#result.success ? 'LIUYANG_PLAN' : ''", targetTable = "lims_liuyang_jihua",
|
targetIdExpr = "#formData['id'] ?: #formData['f_id']", diff = true,
|
entityClass = LimsLiuyangJihuaEntity.class)
|
public R<String> submitLiuyangJihua(@RequestBody Map<String, Object> formData) {
|
String jihuaId = getFormId(formData);
|
if (isBlank(jihuaId)) {
|
return R.error("留样观察计划主键不能为空");
|
}
|
|
LimsLiuyangJihuaEntity jihua = limsLiuyangJihuaService.getById(jihuaId);
|
if (jihua == null || Integer.valueOf(1).equals(jihua.getDeleteMark())) {
|
return R.error("留样观察计划数据不存在");
|
}
|
if (isBlank(jihua.getLiuyangJiluId())) {
|
return R.error("留样观察计划未关联留样记录");
|
}
|
|
LimsLiuyangJihuaEntity jihuaUpdate = new LimsLiuyangJihuaEntity();
|
jihuaUpdate.setId(jihua.getId());
|
jihuaUpdate.setBizStatus("enabled");
|
limsLiuyangJihuaService.updateById(jihuaUpdate);
|
jihua.setBizStatus("enabled");
|
|
syncJihuaInfoToZixiang(jihua);
|
|
LimsLiuyangJiluEntity jiluUpdate = new LimsLiuyangJiluEntity();
|
jiluUpdate.setId(jihua.getLiuyangJiluId());
|
jiluUpdate.setLiuyangJihuaId(jihua.getId());
|
limsLiuyangJiluService.updateById(jiluUpdate);
|
|
return R.success("提交成功");
|
}
|
|
/**
|
* 留样观察计划变更:将变更申请同步到实际留样观察计划。
|
*/
|
@Transactional(rollbackFor = Exception.class)
|
@Operation(summary = "留样观察计划变更")
|
@PostMapping("/liuyang/jihua/biangeng/action")
|
@AuditLog(action = "PLAN_CHANGE", label = "留样观察计划变更", bizType = "LIUYANG",
|
bizCodeExpr = "#result.success ? (#params['id'] ?: 'LIUYANG_PLAN_CHANGE') : ''", targetTable = "lims_liuyang_jihua",
|
targetIdExpr = "T(jnpf.limsService.support.LimsAuditTargetIds).liuyangJihuaByChangeFlow(" +
|
"#params['flow_id'] ?: #params['flowId'], #params['task_id'] ?: #params['taskId'])",
|
extraExpr = "{'action': #params['action']}", diff = true,
|
entityClass = LimsLiuyangJihuaEntity.class)
|
public R<String> liuyangJihuaBiangengAction(@RequestBody Map<String, String> params) {
|
if (params == null) {
|
return R.error("请求参数不能为空");
|
}
|
String flowId = firstNotBlank(params.get("flow_id"), params.get("flowId"));
|
String taskId = firstNotBlank(params.get("task_id"), params.get("taskId"));
|
|
if (isBlank(flowId)) {
|
return R.error("流程id(flow_id)不能为空");
|
}
|
if (isBlank(taskId)) {
|
return R.error("流程任务id(task_id)不能为空");
|
}
|
|
LimsLiuyangJihuaBiangengShenqingEntity shenqing = findJihuaBiangengShenqing(flowId, taskId);
|
if (shenqing == null) {
|
return R.error("留样观察计划变更申请数据不存在");
|
}
|
if (isBlank(shenqing.getLiuyangJihuaId())) {
|
return R.error("变更申请未关联留样观察计划");
|
}
|
|
LimsLiuyangJihuaEntity jihua = limsLiuyangJihuaService.getById(shenqing.getLiuyangJihuaId());
|
if (jihua == null || Integer.valueOf(1).equals(jihua.getDeleteMark())) {
|
return R.error("留样观察计划数据不存在");
|
}
|
|
updateJihuaByBiangeng(shenqing);
|
softDeleteUnobservedJihuaZixiang(shenqing.getLiuyangJihuaId());
|
syncBiangengZixiangToJihuaZixiang(jihua, shenqing);
|
|
return R.success("变更成功");
|
}
|
|
/**
|
* 留样数量变更:将变更申请的入库数量/单位同步到留样记录。
|
* 仅当留样记录未出库(入库数量 == 留样现存量)时允许变更。
|
*/
|
@Transactional(rollbackFor = Exception.class)
|
@Operation(summary = "留样数量变更")
|
@PostMapping("/liuyang/biangeng/action")
|
@AuditLog(action = "QUANTITY_CHANGE", label = "留样数量变更", bizType = "LIUYANG",
|
bizCodeExpr = "#result.success ? #params['liuyang_jilu_id'] : ''",
|
targetTable = "lims_liuyang_jilu", targetIdExpr = "#params['liuyang_jilu_id']",
|
diff = true, entityClass = LimsLiuyangJiluEntity.class)
|
public R<String> liuyangBiangengAction(@RequestBody Map<String, String> params) {
|
String liuyangJiluId = params.get("liuyang_jilu_id");
|
String biangengShenqingId = params.get("biangeng_shenqing_id");
|
|
if (isBlank(liuyangJiluId)) {
|
return R.error("留样记录主键不能为空");
|
}
|
if (isBlank(biangengShenqingId)) {
|
return R.error("变更申请主键不能为空");
|
}
|
|
LimsLiuyangJiluEntity jilu = findById(liuyangJiluId);
|
if (jilu == null) {
|
return R.error("留样记录数据不存在");
|
}
|
|
LimsLiuyangBiangengShenqingEntity shenqing = findBiangengShenqing(biangengShenqingId);
|
if (shenqing == null) {
|
return R.error("变更申请数据不存在");
|
}
|
|
if (!equalsNullable(jilu.getRukuShuliang(), jilu.getLiuyangXiancunliang())) {
|
return R.error("该留样样品已出库,无法变更数量");
|
}
|
|
LimsLiuyangJiluEntity jiluUpdate = new LimsLiuyangJiluEntity();
|
jiluUpdate.setId(jilu.getId());
|
jiluUpdate.setRukuShuliang(shenqing.getRukuShuliang());
|
jiluUpdate.setLiuyangXiancunliang(shenqing.getRukuShuliang());
|
jiluUpdate.setDanwei(shenqing.getDanwei());
|
jiluUpdate.setLiuyangXiancunliangDanwei(shenqing.getDanwei());
|
limsLiuyangJiluService.updateById(jiluUpdate);
|
|
syncBiangengToJihua(liuyangJiluId, shenqing);
|
|
return R.success("变更成功");
|
}
|
|
/**
|
* 留样出库验证:审批前校验申请出库数量不能大于留样现存量。
|
*/
|
@Operation(summary = "留样出库验证")
|
@PostMapping("/liuyang/chuku/validate")
|
public R<String> validateLiuyangChuku(@RequestBody Map<String, String> params) {
|
if (params == null) {
|
return R.error("请求参数不能为空");
|
}
|
String flowId = params.get("flow_id");
|
String taskId = params.get("task_id");
|
if (isBlank(flowId)) {
|
return R.error("流程id(flow_id)不能为空");
|
}
|
if (isBlank(taskId)) {
|
return R.error("流程任务id(task_id)不能为空");
|
}
|
|
try {
|
String shenqingId = findLiuyangChukuShenqingId(flowId, taskId);
|
if (isBlank(shenqingId)) {
|
return R.error("留样出库申请数据不存在");
|
}
|
|
List<Map<String, String>> zixiangList = listLiuyangChukuShenqingZixiang(shenqingId);
|
for (Map<String, String> zixiang : zixiangList) {
|
String liuyangJiluId = zixiang.get("liuyang_jilu_id");
|
LimsLiuyangJiluEntity jilu = isBlank(liuyangJiluId) ? null : findById(liuyangJiluId);
|
if (jilu == null) {
|
return R.error(buildChukuStockErrorMessage(zixiang));
|
}
|
|
BigDecimal chukuShuliang = parseDecimal(zixiang.get("chuku_shuliang"));
|
BigDecimal xiancunliang = parseDecimal(jilu.getLiuyangXiancunliang());
|
if (chukuShuliang == null || xiancunliang == null || chukuShuliang.compareTo(xiancunliang) > 0) {
|
return R.error(buildChukuStockErrorMessage(zixiang, jilu));
|
}
|
}
|
return R.success("验证通过");
|
} catch (SQLException e) {
|
log.error("留样出库验证失败:flowId={}, taskId={}", flowId, taskId, e);
|
return R.error("留样出库验证失败");
|
}
|
}
|
|
/**
|
* 留样出库:按申请子项扣减留样现存量,同步观察计划现存量,并写出库记录。
|
*/
|
@Transactional(rollbackFor = Exception.class)
|
@Operation(summary = "留样出库")
|
@PostMapping("/liuyang/chuku/action")
|
@AuditLog(action = "OUTBOUND", label = "留样出库", bizType = "LIUYANG",
|
bizCodeExpr = "#result.success ? #params['liuyang_jilu_id'] : ''",
|
targetTable = "lims_liuyang_jilu", targetIdExpr = "#params['liuyang_jilu_id']",
|
diff = true, entityClass = LimsLiuyangJiluEntity.class)
|
public R<String> liuyangChukuAction(@RequestBody Map<String, String> params) {
|
if (params == null) {
|
return R.error("请求参数不能为空");
|
}
|
String flowId = params.get("flow_id");
|
String taskId = params.get("task_id");
|
if (isBlank(flowId)) {
|
return R.error("流程id(flow_id)不能为空");
|
}
|
if (isBlank(taskId)) {
|
return R.error("流程任务id(task_id)不能为空");
|
}
|
|
Map<String, Object> shenqing = findLiuyangChukuShenqing(flowId, taskId);
|
if (shenqing == null || shenqing.isEmpty()) {
|
return R.error("留样出库申请数据不存在");
|
}
|
String shenqingId = getString(shenqing, "f_id");
|
List<Map<String, Object>> zixiangList = listLiuyangChukuShenqingZixiangRows(shenqingId);
|
if (zixiangList.isEmpty()) {
|
return R.error("留样出库申请子项不能为空");
|
}
|
|
for (Map<String, Object> zixiang : zixiangList) {
|
String liuyangJiluId = getString(zixiang, "liuyang_jilu_id");
|
LimsLiuyangJiluEntity jilu = isBlank(liuyangJiluId) ? null : findById(liuyangJiluId);
|
if (jilu == null) {
|
return R.error(buildChukuStockErrorMessage(zixiang));
|
}
|
|
BigDecimal chukuShuliang = parseDecimal(getString(zixiang, "chuku_shuliang"));
|
BigDecimal oldXiancunliang = parseDecimal(jilu.getLiuyangXiancunliang());
|
if (chukuShuliang == null || oldXiancunliang == null || chukuShuliang.compareTo(oldXiancunliang) > 0) {
|
return R.error(buildChukuStockErrorMessage(zixiang, jilu));
|
}
|
|
BigDecimal newXiancunliang = oldXiancunliang.subtract(chukuShuliang);
|
String newXiancunliangText = toPlainString(newXiancunliang);
|
|
LimsLiuyangJiluEntity jiluUpdate = new LimsLiuyangJiluEntity();
|
jiluUpdate.setId(jilu.getId());
|
jiluUpdate.setLiuyangXiancunliang(newXiancunliangText);
|
limsLiuyangJiluService.updateById(jiluUpdate);
|
|
syncChukuLiuyangXiancunliangToJihua(jilu.getId(), newXiancunliangText);
|
insertLiuyangChukuRecord(shenqing, zixiang, jilu, oldXiancunliang);
|
}
|
|
return R.success("出库成功");
|
}
|
|
private Map<String, Object> findLiuyangChukuShenqing(String flowId, String taskId) {
|
String sql = "select * from " + LIUYANG_CHUKU_SHENQING_TABLE
|
+ " where f_flow_id = ? and f_flow_task_id = ?"
|
+ " and (f_delete_mark is null or f_delete_mark <> 1)"
|
+ " limit 1";
|
List<Map<String, Object>> list = jdbcTemplate.queryForList(sql, flowId, taskId);
|
return list.isEmpty() ? null : list.get(0);
|
}
|
|
private List<Map<String, Object>> listLiuyangChukuShenqingZixiangRows(String shenqingId) {
|
String sql = "select * from " + LIUYANG_CHUKU_SHENQING_ZIXIANG_TABLE
|
+ " where f_foreign_id = ?"
|
+ " and (f_delete_mark is null or f_delete_mark <> 1)";
|
return jdbcTemplate.queryForList(sql, shenqingId);
|
}
|
|
private void syncChukuLiuyangXiancunliangToJihua(String liuyangJiluId, String liuyangXiancunliang) {
|
LambdaUpdateWrapper<LimsLiuyangJihuaEntity> wrapper = new LambdaUpdateWrapper<>();
|
wrapper.eq(LimsLiuyangJihuaEntity::getLiuyangJiluId, liuyangJiluId)
|
.and(w -> w.isNull(LimsLiuyangJihuaEntity::getDeleteMark)
|
.or()
|
.ne(LimsLiuyangJihuaEntity::getDeleteMark, 1))
|
.set(LimsLiuyangJihuaEntity::getLiuyangXiancunliang, liuyangXiancunliang);
|
limsLiuyangJihuaService.update(wrapper);
|
}
|
|
private void insertLiuyangChukuRecord(Map<String, Object> shenqing,
|
Map<String, Object> zixiang,
|
LimsLiuyangJiluEntity jilu,
|
BigDecimal oldXiancunliang) {
|
String sql = "insert into " + LIUYANG_CHUKU_TABLE
|
+ " (f_id, f_foreign_id, f_tenant_id, chuku_shenqing_id,"
|
+ " yangpin_mingcheng, yangpin_bianma, guige, pihao,"
|
+ " liuyang_xiancunliang, chuku_shuliang, danwei, yongtu,"
|
+ " shenqing_ren, shenqing_riqi, fafang_ren, shenhe_ren, shenhe_riqi, fafang_riqi)"
|
+ " values (?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?)";
|
String shenqingId = getString(shenqing, "f_id");
|
jdbcTemplate.update(sql,
|
RandomUtil.uuId(),
|
jilu.getId(),
|
firstNotBlank(getString(zixiang, "f_tenant_id"), getString(shenqing, "f_tenant_id")),
|
shenqingId,
|
firstNotBlank(getString(zixiang, "yangpin_mingcheng"), jilu.getYangpinMingcheng()),
|
firstNotBlank(getString(zixiang, "yangpin_bianma"), jilu.getYangpinBianma()),
|
firstNotBlank(getString(zixiang, "guige"), jilu.getGuige()),
|
firstNotBlank(getString(zixiang, "pihao"), jilu.getPihao()),
|
toPlainString(oldXiancunliang),
|
parseDecimal(getString(zixiang, "chuku_shuliang")),
|
firstNotBlank(getString(zixiang, "danwei"), jilu.getDanwei()),
|
firstNotBlank(getString(zixiang, "yongtu"), getString(shenqing, "yongtu")),
|
getObject(shenqing, "shenqing_ren"),
|
getObject(shenqing, "shenqing_riqi"),
|
getObject(shenqing, "fafang_ren"),
|
getObject(shenqing, "shenhe_ren"),
|
getObject(shenqing, "shenhe_riqi"),
|
getObject(shenqing, "fafang_riqi"));
|
}
|
|
private Map<String, Object> findLiuyangXiaohuiShenqing(String flowId, String taskId) {
|
String sql = "select * from " + LIUYANG_XIAOHUI_SHENQING_TABLE
|
+ " where f_flow_id = ? and f_flow_task_id = ?"
|
+ " and (f_delete_mark is null or f_delete_mark <> 1)"
|
+ " limit 1";
|
List<Map<String, Object>> list = jdbcTemplate.queryForList(sql, flowId, taskId);
|
return list.isEmpty() ? null : list.get(0);
|
}
|
|
private List<String> listLiuyangXiaohuiJiluIds(String shenqingId) {
|
String sql = "select distinct liuyang_jilu_id from " + LIUYANG_XIAOHUI_SHENQING_ZIXIANG_TABLE
|
+ " where f_foreign_id = ?"
|
+ " and liuyang_jilu_id is not null and liuyang_jilu_id <> ''"
|
+ " and (f_delete_mark is null or f_delete_mark <> 1)";
|
return jdbcTemplate.queryForList(sql, shenqingId).stream()
|
.map(row -> getString(row, "liuyang_jilu_id"))
|
.filter(value -> !isBlank(value))
|
.distinct()
|
.collect(Collectors.toList());
|
}
|
|
private void updateLiuyangXiaohuiDanhao(List<String> liuyangJiluIds, String xiaohuiDanhao) {
|
LambdaUpdateWrapper<LimsLiuyangJiluEntity> wrapper = new LambdaUpdateWrapper<>();
|
wrapper.in(LimsLiuyangJiluEntity::getId, liuyangJiluIds)
|
.and(w -> w.isNull(LimsLiuyangJiluEntity::getDeleteMark)
|
.or()
|
.ne(LimsLiuyangJiluEntity::getDeleteMark, 1))
|
.set(LimsLiuyangJiluEntity::getXiaohuiDanhao, xiaohuiDanhao);
|
limsLiuyangJiluService.update(wrapper);
|
}
|
|
private void acceptLiuyangXiaohui(List<String> liuyangJiluIds) {
|
LambdaUpdateWrapper<LimsLiuyangJiluEntity> jiluUpdate = new LambdaUpdateWrapper<>();
|
jiluUpdate.in(LimsLiuyangJiluEntity::getId, liuyangJiluIds)
|
.and(w -> w.isNull(LimsLiuyangJiluEntity::getDeleteMark)
|
.or()
|
.ne(LimsLiuyangJiluEntity::getDeleteMark, 1))
|
.set(LimsLiuyangJiluEntity::getBizStatus, BIZ_STATUS_DESTROYED);
|
limsLiuyangJiluService.update(jiluUpdate);
|
|
List<String> jihuaIds = listLiuyangJihuaIdsByJiluIds(liuyangJiluIds);
|
|
LambdaUpdateWrapper<LimsLiuyangJihuaEntity> jihuaUpdate = new LambdaUpdateWrapper<>();
|
jihuaUpdate.in(LimsLiuyangJihuaEntity::getLiuyangJiluId, liuyangJiluIds)
|
.and(w -> w.isNull(LimsLiuyangJihuaEntity::getDeleteMark)
|
.or()
|
.ne(LimsLiuyangJihuaEntity::getDeleteMark, 1))
|
.set(LimsLiuyangJihuaEntity::getBizStatus, BIZ_STATUS_DISABLED);
|
limsLiuyangJihuaService.update(jihuaUpdate);
|
|
if (!jihuaIds.isEmpty()) {
|
LambdaUpdateWrapper<LimsLiuyangJihuaZixiangEntity> zixiangUpdate = new LambdaUpdateWrapper<>();
|
zixiangUpdate.in(LimsLiuyangJihuaZixiangEntity::getForeignId, jihuaIds)
|
.and(w -> w.isNull(LimsLiuyangJihuaZixiangEntity::getDeleteMark)
|
.or()
|
.ne(LimsLiuyangJihuaZixiangEntity::getDeleteMark, 1))
|
.set(LimsLiuyangJihuaZixiangEntity::getBizStatus, BIZ_STATUS_DISABLED);
|
limsLiuyangJihuaZixiangService.update(zixiangUpdate);
|
}
|
}
|
|
private List<String> listLiuyangJihuaIdsByJiluIds(List<String> liuyangJiluIds) {
|
LambdaQueryWrapper<LimsLiuyangJihuaEntity> query = new LambdaQueryWrapper<>();
|
query.in(LimsLiuyangJihuaEntity::getLiuyangJiluId, liuyangJiluIds)
|
.and(w -> w.isNull(LimsLiuyangJihuaEntity::getDeleteMark)
|
.or()
|
.ne(LimsLiuyangJihuaEntity::getDeleteMark, 1));
|
return limsLiuyangJihuaService.list(query).stream()
|
.map(LimsLiuyangJihuaEntity::getId)
|
.filter(value -> !isBlank(value))
|
.distinct()
|
.collect(Collectors.toList());
|
}
|
|
private String findLiuyangChukuShenqingId(String flowId, String taskId) throws SQLException {
|
String sql = "select f_id from " + LIUYANG_CHUKU_SHENQING_TABLE
|
+ " where f_flow_id = ? and f_flow_task_id = ?"
|
+ " and (f_delete_mark is null or f_delete_mark <> 1)"
|
+ " limit 1";
|
try (Connection connection = dataSource.getConnection();
|
PreparedStatement statement = connection.prepareStatement(sql)) {
|
statement.setString(1, flowId);
|
statement.setString(2, taskId);
|
try (ResultSet resultSet = statement.executeQuery()) {
|
return resultSet.next() ? resultSet.getString("f_id") : null;
|
}
|
}
|
}
|
|
private List<Map<String, String>> listLiuyangChukuShenqingZixiang(String shenqingId) throws SQLException {
|
String sql = "select liuyang_jilu_id, chuku_shuliang, yangpin_mingcheng, pihao from "
|
+ LIUYANG_CHUKU_SHENQING_ZIXIANG_TABLE
|
+ " where f_foreign_id = ?"
|
+ " and (f_delete_mark is null or f_delete_mark <> 1)";
|
List<Map<String, String>> list = new ArrayList<>();
|
try (Connection connection = dataSource.getConnection();
|
PreparedStatement statement = connection.prepareStatement(sql)) {
|
statement.setString(1, shenqingId);
|
try (ResultSet resultSet = statement.executeQuery()) {
|
while (resultSet.next()) {
|
Map<String, String> row = new LinkedHashMap<>();
|
row.put("liuyang_jilu_id", resultSet.getString("liuyang_jilu_id"));
|
row.put("chuku_shuliang", resultSet.getString("chuku_shuliang"));
|
row.put("yangpin_mingcheng", resultSet.getString("yangpin_mingcheng"));
|
row.put("pihao", resultSet.getString("pihao"));
|
list.add(row);
|
}
|
}
|
}
|
return list;
|
}
|
|
private String buildChukuStockErrorMessage(Map<String, ?> zixiang) {
|
return buildChukuStockErrorMessage(zixiang, null);
|
}
|
|
private String buildChukuStockErrorMessage(Map<String, ?> zixiang, LimsLiuyangJiluEntity jilu) {
|
String yangpinMingcheng = firstNotBlank(getString(zixiang, "yangpin_mingcheng"), jilu == null ? null : jilu.getYangpinMingcheng());
|
String pihao = firstNotBlank(getString(zixiang, "pihao"), jilu == null ? null : jilu.getPihao());
|
return trimToEmpty(yangpinMingcheng) + "批次" + trimToEmpty(pihao) + "库存不足,不满足出库条件";
|
}
|
|
private BigDecimal parseDecimal(String value) {
|
if (isBlank(value)) {
|
return null;
|
}
|
try {
|
return new BigDecimal(value.trim());
|
} catch (NumberFormatException e) {
|
return null;
|
}
|
}
|
|
private String firstNotBlank(String first, String second) {
|
return isBlank(first) ? second : first;
|
}
|
|
private String trimToEmpty(String value) {
|
return value == null ? "" : value.trim();
|
}
|
|
private String getString(Map<String, ?> row, String key) {
|
if (row == null || key == null) {
|
return null;
|
}
|
Object value = row.get(key);
|
return value == null ? null : String.valueOf(value);
|
}
|
|
private Object getObject(Map<String, ?> row, String key) {
|
if (row == null || key == null) {
|
return null;
|
}
|
return row.get(key);
|
}
|
|
private String toPlainString(BigDecimal value) {
|
return value == null ? null : value.stripTrailingZeros().toPlainString();
|
}
|
|
private void syncBiangengToJihua(String liuyangJiluId, LimsLiuyangBiangengShenqingEntity shenqing) {
|
LambdaUpdateWrapper<LimsLiuyangJihuaEntity> wrapper = new LambdaUpdateWrapper<>();
|
wrapper.eq(LimsLiuyangJihuaEntity::getLiuyangJiluId, liuyangJiluId)
|
.and(w -> w.isNull(LimsLiuyangJihuaEntity::getDeleteMark)
|
.or()
|
.ne(LimsLiuyangJihuaEntity::getDeleteMark, 1))
|
.set(LimsLiuyangJihuaEntity::getRukuShuliang, shenqing.getRukuShuliang())
|
.set(LimsLiuyangJihuaEntity::getLiuyangXiancunliang, shenqing.getRukuShuliang())
|
.set(LimsLiuyangJihuaEntity::getDanwei, shenqing.getDanwei())
|
.set(LimsLiuyangJihuaEntity::getLiuyangXiancunliangDanwei, shenqing.getDanwei());
|
limsLiuyangJihuaService.update(wrapper);
|
}
|
|
private LimsLiuyangBiangengShenqingEntity findBiangengShenqing(String id) {
|
LambdaQueryWrapper<LimsLiuyangBiangengShenqingEntity> query = new LambdaQueryWrapper<>();
|
query.eq(LimsLiuyangBiangengShenqingEntity::getId, id)
|
.and(w -> w.isNull(LimsLiuyangBiangengShenqingEntity::getDeleteMark)
|
.or()
|
.ne(LimsLiuyangBiangengShenqingEntity::getDeleteMark, 1));
|
query.last("limit 1");
|
return limsLiuyangBiangengShenqingService.getOne(query, false);
|
}
|
|
private LimsLiuyangJihuaBiangengShenqingEntity findJihuaBiangengShenqing(String flowId, String taskId) {
|
LambdaQueryWrapper<LimsLiuyangJihuaBiangengShenqingEntity> query = new LambdaQueryWrapper<>();
|
query.eq(LimsLiuyangJihuaBiangengShenqingEntity::getFlowId, flowId)
|
.eq(LimsLiuyangJihuaBiangengShenqingEntity::getFlowTaskId, taskId)
|
.and(w -> w.isNull(LimsLiuyangJihuaBiangengShenqingEntity::getDeleteMark)
|
.or()
|
.ne(LimsLiuyangJihuaBiangengShenqingEntity::getDeleteMark, 1));
|
query.last("limit 1");
|
return limsLiuyangJihuaBiangengShenqingService.getOne(query, false);
|
}
|
|
private void updateJihuaByBiangeng(LimsLiuyangJihuaBiangengShenqingEntity shenqing) {
|
LimsLiuyangJihuaEntity update = new LimsLiuyangJihuaEntity();
|
update.setId(shenqing.getLiuyangJihuaId());
|
update.setLiuyangRiqi(shenqing.getLiuyangRiqi());
|
update.setLiuyangZhouqiId(shenqing.getLiuyangZhouqiId());
|
limsLiuyangJihuaService.updateById(update);
|
}
|
|
private void softDeleteUnobservedJihuaZixiang(String jihuaId) {
|
LambdaUpdateWrapper<LimsLiuyangJihuaZixiangEntity> wrapper = new LambdaUpdateWrapper<>();
|
wrapper.eq(LimsLiuyangJihuaZixiangEntity::getForeignId, jihuaId)
|
.and(w -> w.isNull(LimsLiuyangJihuaZixiangEntity::getShifouYiguancha)
|
.or()
|
.ne(LimsLiuyangJihuaZixiangEntity::getShifouYiguancha, "yes"))
|
.and(w -> w.isNull(LimsLiuyangJihuaZixiangEntity::getDeleteMark)
|
.or()
|
.ne(LimsLiuyangJihuaZixiangEntity::getDeleteMark, 1))
|
.set(LimsLiuyangJihuaZixiangEntity::getDeleteMark, 1)
|
.set(LimsLiuyangJihuaZixiangEntity::getDeleteTime, new Date())
|
.set(LimsLiuyangJihuaZixiangEntity::getDeleteUserId, UserProvider.getUser().getUserId());
|
limsLiuyangJihuaZixiangService.update(wrapper);
|
}
|
|
private void syncBiangengZixiangToJihuaZixiang(LimsLiuyangJihuaEntity jihua, LimsLiuyangJihuaBiangengShenqingEntity shenqing) {
|
List<LimsLiuyangJihuaBiangengShenqingZixiangEntity> shenqingZixiangList = listUnobservedJihuaBiangengZixiang(shenqing.getId());
|
if (shenqingZixiangList.isEmpty()) {
|
return;
|
}
|
|
List<LimsLiuyangJihuaZixiangEntity> jihuaZixiangList = shenqingZixiangList.stream()
|
.map(row -> buildJihuaZixiangFromBiangeng(jihua, shenqing, row))
|
.collect(Collectors.toList());
|
limsLiuyangJihuaZixiangService.saveBatch(jihuaZixiangList);
|
}
|
|
private List<LimsLiuyangJihuaBiangengShenqingZixiangEntity> listUnobservedJihuaBiangengZixiang(String shenqingId) {
|
LambdaQueryWrapper<LimsLiuyangJihuaBiangengShenqingZixiangEntity> query = new LambdaQueryWrapper<>();
|
query.eq(LimsLiuyangJihuaBiangengShenqingZixiangEntity::getForeignId, shenqingId)
|
.and(w -> w.isNull(LimsLiuyangJihuaBiangengShenqingZixiangEntity::getShifouYiguancha)
|
.or()
|
.ne(LimsLiuyangJihuaBiangengShenqingZixiangEntity::getShifouYiguancha, "yes"))
|
.and(w -> w.isNull(LimsLiuyangJihuaBiangengShenqingZixiangEntity::getDeleteMark)
|
.or()
|
.ne(LimsLiuyangJihuaBiangengShenqingZixiangEntity::getDeleteMark, 1))
|
.orderByAsc(LimsLiuyangJihuaBiangengShenqingZixiangEntity::getJihuaRiqi);
|
return limsLiuyangJihuaBiangengShenqingZixiangService.list(query);
|
}
|
|
private LimsLiuyangJihuaZixiangEntity buildJihuaZixiangFromBiangeng(
|
LimsLiuyangJihuaEntity jihua,
|
LimsLiuyangJihuaBiangengShenqingEntity shenqing,
|
LimsLiuyangJihuaBiangengShenqingZixiangEntity shenqingZixiang) {
|
LimsLiuyangJihuaZixiangEntity zixiang = new LimsLiuyangJihuaZixiangEntity();
|
zixiang.setId(RandomUtil.uuId());
|
zixiang.setForeignId(jihua.getId());
|
zixiang.setZhouqi(shenqingZixiang.getZhouqi());
|
zixiang.setZhouqiDanwei(shenqingZixiang.getZhouqiDanwei());
|
zixiang.setJihuaRiqi(shenqingZixiang.getJihuaRiqi());
|
zixiang.setGuanchaRiqi(shenqingZixiang.getGuanchaRiqi());
|
zixiang.setGuanchaRen(shenqingZixiang.getGuanchaRen());
|
zixiang.setGuanchaShuliang(shenqingZixiang.getGuanchaShuliang());
|
zixiang.setGuanchaQingkuang(shenqingZixiang.getGuanchaQingkuang());
|
zixiang.setGuanchaJieguo(shenqingZixiang.getGuanchaJieguo());
|
zixiang.setShifouYiguancha(shenqingZixiang.getShifouYiguancha());
|
zixiang.setBeizhu(shenqingZixiang.getBeizhu());
|
zixiang.setBizType(jihua.getBizType());
|
zixiang.setYangpinMingcheng(jihua.getYangpinMingcheng());
|
zixiang.setYangpinBianma(jihua.getYangpinBianma());
|
zixiang.setGuige(jihua.getGuige());
|
zixiang.setPihao(jihua.getPihao());
|
zixiang.setShengchanRiqi(jihua.getShengchanRiqi());
|
zixiang.setYouxiaoqi(jihua.getYouxiaoqi());
|
zixiang.setLiuyangRiqi(shenqing.getLiuyangRiqi());
|
zixiang.setGuanchaShuliangDanwei(jihua.getDanwei());
|
zixiang.setBizStatus(jihua.getBizStatus());
|
return zixiang;
|
}
|
|
private boolean equalsNullable(String a, String b) {
|
if (a == null && b == null) {
|
return true;
|
}
|
if (a == null || b == null) {
|
return false;
|
}
|
return a.trim().equals(b.trim());
|
}
|
|
private String getFormId(Map<String, Object> formData) {
|
if (formData == null) {
|
return null;
|
}
|
Object id = formData.get("f_id");
|
if (id == null) {
|
id = formData.get("id");
|
}
|
return id == null ? null : String.valueOf(id);
|
}
|
|
private void syncJihuaInfoToZixiang(LimsLiuyangJihuaEntity jihua) {
|
LambdaUpdateWrapper<LimsLiuyangJihuaZixiangEntity> wrapper = new LambdaUpdateWrapper<>();
|
wrapper.eq(LimsLiuyangJihuaZixiangEntity::getForeignId, jihua.getId())
|
.and(w -> w.isNull(LimsLiuyangJihuaZixiangEntity::getDeleteMark)
|
.or()
|
.ne(LimsLiuyangJihuaZixiangEntity::getDeleteMark, 1))
|
// 提交计划时,将主表样品信息冗余到周期子项,便于后续观察列表独立展示。
|
.set(LimsLiuyangJihuaZixiangEntity::getBizType, jihua.getBizType())
|
.set(LimsLiuyangJihuaZixiangEntity::getYangpinMingcheng, jihua.getYangpinMingcheng())
|
.set(LimsLiuyangJihuaZixiangEntity::getYangpinBianma, jihua.getYangpinBianma())
|
.set(LimsLiuyangJihuaZixiangEntity::getGuige, jihua.getGuige())
|
.set(LimsLiuyangJihuaZixiangEntity::getPihao, jihua.getPihao())
|
.set(LimsLiuyangJihuaZixiangEntity::getShengchanRiqi, jihua.getShengchanRiqi())
|
.set(LimsLiuyangJihuaZixiangEntity::getYouxiaoqi, jihua.getYouxiaoqi())
|
.set(LimsLiuyangJihuaZixiangEntity::getLiuyangRiqi, jihua.getLiuyangRiqi())
|
.set(LimsLiuyangJihuaZixiangEntity::getGuanchaShuliangDanwei, jihua.getDanwei())
|
.set(LimsLiuyangJihuaZixiangEntity::getBizStatus, jihua.getBizStatus());
|
limsLiuyangJihuaZixiangService.update(wrapper);
|
}
|
|
private LimsLiuyangJiluEntity findLiuyangJilu(String id, String flowId, String taskId) {
|
if (id != null && !id.isEmpty()) {
|
return findById(id);
|
}
|
return findByFlow(flowId, taskId);
|
}
|
|
private LimsLiuyangJiluEntity findById(String id) {
|
LambdaQueryWrapper<LimsLiuyangJiluEntity> query = new LambdaQueryWrapper<>();
|
query.eq(LimsLiuyangJiluEntity::getId, id)
|
.and(w -> w.isNull(LimsLiuyangJiluEntity::getDeleteMark)
|
.or()
|
.ne(LimsLiuyangJiluEntity::getDeleteMark, 1));
|
query.last("limit 1");
|
return limsLiuyangJiluService.getOne(query, false);
|
}
|
|
private LimsLiuyangJiluEntity findByFlow(String flowId, String taskId) {
|
LambdaQueryWrapper<LimsLiuyangJiluEntity> query = new LambdaQueryWrapper<>();
|
query.eq(LimsLiuyangJiluEntity::getFlowId, flowId)
|
.and(w -> w.isNull(LimsLiuyangJiluEntity::getDeleteMark)
|
.or()
|
.ne(LimsLiuyangJiluEntity::getDeleteMark, 1));
|
if (taskId != null && !taskId.isEmpty()) {
|
query.eq(LimsLiuyangJiluEntity::getFlowTaskId, taskId);
|
}
|
query.last("limit 1");
|
return limsLiuyangJiluService.getOne(query, false);
|
}
|
|
private List<LiuyangWendingxingZhouqiZixiangEntity> listWendingxingZhouqiZixiang(String zhouqiId) {
|
LambdaQueryWrapper<LiuyangWendingxingZhouqiZixiangEntity> query = new LambdaQueryWrapper<>();
|
query.eq(LiuyangWendingxingZhouqiZixiangEntity::getForeignId, zhouqiId)
|
.and(w -> w.isNull(LiuyangWendingxingZhouqiZixiangEntity::getDeleteMark)
|
.or()
|
.ne(LiuyangWendingxingZhouqiZixiangEntity::getDeleteMark, 1))
|
.orderByAsc(LiuyangWendingxingZhouqiZixiangEntity::getZhouqi);
|
return liuyangWendingxingZhouqiZixiangService.list(query);
|
}
|
|
private List<LimsLiuyangJihuaZixiangEntity> listObservedJihuaZixiang(String jihuaId) {
|
LambdaQueryWrapper<LimsLiuyangJihuaZixiangEntity> query = new LambdaQueryWrapper<>();
|
query.eq(LimsLiuyangJihuaZixiangEntity::getForeignId, jihuaId)
|
.eq(LimsLiuyangJihuaZixiangEntity::getShifouYiguancha, "yes")
|
.and(w -> w.isNull(LimsLiuyangJihuaZixiangEntity::getDeleteMark)
|
.or()
|
.ne(LimsLiuyangJihuaZixiangEntity::getDeleteMark, 1))
|
.orderByAsc(LimsLiuyangJihuaZixiangEntity::getJihuaRiqi);
|
return limsLiuyangJihuaZixiangService.list(query);
|
}
|
|
private LimsLiuyangJihuaCalculateResult buildJihuaZixiang(LiuyangWendingxingZhouqiZixiangEntity zhouqi, Date shouyangRiqi) {
|
if (zhouqi.getZhouqi() == null) {
|
throw new IllegalArgumentException("周期不能为空");
|
}
|
if (isBlank(zhouqi.getZhouqiDanwei())) {
|
throw new IllegalArgumentException("周期单位不能为空");
|
}
|
|
LimsLiuyangJihuaCalculateResult item = new LimsLiuyangJihuaCalculateResult();
|
item.setZhouqi(zhouqi.getZhouqi());
|
item.setZhouqiDanwei(zhouqi.getZhouqiDanwei());
|
item.setJihuaRiqi(calculateJihuaRiqi(shouyangRiqi, zhouqi.getZhouqi(), zhouqi.getZhouqiDanwei()));
|
item.setGuanchaRiqi(null);
|
item.setShifouYiguancha("no");
|
return item;
|
}
|
|
private Map<String, Object> buildBiangengRow(LimsLiuyangJihuaZixiangEntity jihuaZixiang, List<String> responseFields) {
|
Map<String, Object> row = newEmptyBiangengRow(responseFields);
|
putIfPresent(row, "zhouqi", jihuaZixiang.getZhouqi());
|
putIfPresent(row, "zhouqi_danwei", jihuaZixiang.getZhouqiDanwei());
|
putIfPresent(row, "jihua_riqi", jihuaZixiang.getJihuaRiqi());
|
putIfPresent(row, "shifou_yiguancha", jihuaZixiang.getShifouYiguancha());
|
putIfPresent(row, "guancha_riqi", jihuaZixiang.getGuanchaRiqi());
|
putIfPresent(row, "guancha_ren", jihuaZixiang.getGuanchaRen());
|
putIfPresent(row, "guancha_shuliang", jihuaZixiang.getGuanchaShuliang());
|
putIfPresent(row, "guancha_qingkuang", jihuaZixiang.getGuanchaQingkuang());
|
putIfPresent(row, "guancha_jieguo", jihuaZixiang.getGuanchaJieguo());
|
putIfPresent(row, "beizhu", jihuaZixiang.getBeizhu());
|
return row;
|
}
|
|
private Map<String, Object> buildBiangengRow(LiuyangWendingxingZhouqiZixiangEntity zhouqi, Date liuyangRiqi, List<String> responseFields) {
|
if (zhouqi.getZhouqi() == null) {
|
throw new IllegalArgumentException("周期不能为空");
|
}
|
if (isBlank(zhouqi.getZhouqiDanwei())) {
|
throw new IllegalArgumentException("周期单位不能为空");
|
}
|
|
Map<String, Object> row = newEmptyBiangengRow(responseFields);
|
putIfPresent(row, "zhouqi", zhouqi.getZhouqi());
|
putIfPresent(row, "zhouqi_danwei", zhouqi.getZhouqiDanwei());
|
putIfPresent(row, "jihua_riqi", calculateJihuaRiqi(liuyangRiqi, zhouqi.getZhouqi(), zhouqi.getZhouqiDanwei()));
|
putIfPresent(row, "shifou_yiguancha", "no");
|
return row;
|
}
|
|
private Map<String, Object> newEmptyBiangengRow(List<String> responseFields) {
|
Map<String, Object> row = new LinkedHashMap<>();
|
for (String field : responseFields) {
|
row.put(field, null);
|
}
|
return row;
|
}
|
|
private void putIfPresent(Map<String, Object> row, String field, Object value) {
|
if (row.containsKey(field)) {
|
row.put(field, value);
|
}
|
}
|
|
private String buildZhouqiKey(BigDecimal zhouqi, String zhouqiDanwei) {
|
if (zhouqi == null || isBlank(zhouqiDanwei)) {
|
return "";
|
}
|
return zhouqi.stripTrailingZeros().toPlainString() + "|" + zhouqiDanwei.trim();
|
}
|
|
private List<String> getBiangengZixiangBusinessFields() {
|
Set<String> fields = new LinkedHashSet<>();
|
try (Connection connection = dataSource.getConnection()) {
|
DatabaseMetaData metaData = connection.getMetaData();
|
readBusinessColumns(fields, metaData, connection.getCatalog(), connection.getSchema(), BIANGENG_ZIXIANG_TABLE);
|
if (fields.isEmpty()) {
|
readBusinessColumns(fields, metaData, connection.getCatalog(), connection.getSchema(), BIANGENG_ZIXIANG_TABLE.toUpperCase());
|
}
|
} catch (Exception e) {
|
log.warn("读取{}字段失败,使用默认字段", BIANGENG_ZIXIANG_TABLE, e);
|
}
|
if (fields.isEmpty()) {
|
fields.addAll(DEFAULT_BIANGENG_ZIXIANG_FIELDS);
|
}
|
return new ArrayList<>(fields);
|
}
|
|
private void readBusinessColumns(Set<String> fields, DatabaseMetaData metaData, String catalog, String schema, String tableName) throws SQLException {
|
try (ResultSet columns = metaData.getColumns(catalog, schema, tableName, null)) {
|
while (columns.next()) {
|
String columnName = columns.getString("COLUMN_NAME");
|
if (!isBlank(columnName) && !columnName.toLowerCase().startsWith("f_")) {
|
fields.add(columnName);
|
}
|
}
|
}
|
}
|
|
private Date calculateJihuaRiqi(Date shouyangRiqi, BigDecimal zhouqi, String zhouqiDanwei) {
|
int amount = toIntegerZhouqi(zhouqi);
|
LocalDateTime baseTime = LocalDateTime.ofInstant(shouyangRiqi.toInstant(), ZoneId.systemDefault());
|
LocalDateTime jihuaTime;
|
switch (zhouqiDanwei.trim()) {
|
case "day":
|
case "天":
|
jihuaTime = baseTime.plusDays(amount);
|
break;
|
case "week":
|
case "周":
|
jihuaTime = baseTime.plusWeeks(amount);
|
break;
|
case "month":
|
case "月":
|
jihuaTime = baseTime.plusMonths(amount);
|
break;
|
case "quarter":
|
case "季":
|
jihuaTime = baseTime.plusMonths(amount * 3L);
|
break;
|
case "year":
|
case "年":
|
jihuaTime = baseTime.plusYears(amount);
|
break;
|
default:
|
throw new IllegalArgumentException("不支持的周期单位:" + zhouqiDanwei);
|
}
|
return Date.from(jihuaTime.atZone(ZoneId.systemDefault()).toInstant());
|
}
|
|
private int toIntegerZhouqi(BigDecimal zhouqi) {
|
try {
|
return zhouqi.stripTrailingZeros().intValueExact();
|
} catch (ArithmeticException e) {
|
throw new IllegalArgumentException("周期必须为整数:" + zhouqi);
|
}
|
}
|
|
private void updateLiuyangStatus(LimsLiuyangJiluEntity liuyangJilu, LiuyangStatus status, String bizSign) {
|
LimsLiuyangJiluEntity update = new LimsLiuyangJiluEntity();
|
update.setId(liuyangJilu.getId());
|
update.setBizStatus(status.getCode());
|
if (bizSign != null && !bizSign.isEmpty()) {
|
update.setBizSign(bizSign);
|
}
|
limsLiuyangJiluService.updateById(update);
|
}
|
|
private void receiveLiuyangJilu(LimsLiuyangJiluEntity liuyangJilu, String bizSign) {
|
LimsLiuyangJiluEntity update = new LimsLiuyangJiluEntity();
|
update.setId(liuyangJilu.getId());
|
update.setBizStatus(LiuyangStatus.RECEIVED.getCode());
|
update.setLiuyangXiancunliang(liuyangJilu.getRukuShuliang());
|
update.setLiuyangXiancunliangDanwei(liuyangJilu.getDanwei());
|
if (bizSign != null && !bizSign.isEmpty()) {
|
update.setBizSign(bizSign);
|
}
|
limsLiuyangJiluService.updateById(update);
|
}
|
|
private void softDeleteLiuyangJilu(LimsLiuyangJiluEntity liuyangJilu, String bizSign) {
|
LimsLiuyangJiluEntity update = new LimsLiuyangJiluEntity();
|
update.setId(liuyangJilu.getId());
|
update.setDeleteMark(1);
|
update.setDeleteTime(new Date());
|
update.setDeleteUserId(UserProvider.getUser().getUserId());
|
if (bizSign != null && !bizSign.isEmpty()) {
|
update.setBizSign(bizSign);
|
}
|
limsLiuyangJiluService.updateById(update);
|
}
|
|
private void updateQingyandanLiuyangJiluId(LimsLiuyangJiluEntity liuyangJilu, String liuyangJiluId) {
|
String qingyandanId = liuyangJilu.getQingyandanId();
|
if (qingyandanId == null || qingyandanId.isEmpty()) {
|
return;
|
}
|
|
LimsQingyandanEntity qingyandan = limsQingyandanService.getById(qingyandanId);
|
if (qingyandan == null) {
|
return;
|
}
|
|
LambdaUpdateWrapper<LimsQingyandanEntity> updateWrapper = new LambdaUpdateWrapper<>();
|
updateWrapper.eq(LimsQingyandanEntity::getId, qingyandan.getId())
|
.set(LimsQingyandanEntity::getLiuyangJiluId, liuyangJiluId);
|
limsQingyandanService.update(updateWrapper);
|
}
|
|
private boolean isBlank(String value) {
|
return value == null || value.trim().isEmpty();
|
}
|
}
|