@@ -33,8 +33,8 @@ public enum ProjectProcessType { | |||||
PROJECT_RECORD_APPROVAL_PROCESS(8, "立项备案审批流程"), | PROJECT_RECORD_APPROVAL_PROCESS(8, "立项备案审批流程"), | ||||
XC_APPROVAL_PROCESS(9, "信创审批流程"), | XC_APPROVAL_PROCESS(9, "信创审批流程"), | ||||
SELF_TEST(10, "系统自测审批流程"), | SELF_TEST(10, "系统自测审批流程"), | ||||
ADAPTION(11, "适配改造审批流程"), | |||||
TEST_VALID(12, "测试验证审批流程"), | |||||
ADAPTION(11, "开工文件审批流程"), | |||||
TEST_VALID(12, "监理核实验证审批流程"), | |||||
COMPLIANCE_REVIEW(13, "合规性审查流程"), | COMPLIANCE_REVIEW(13, "合规性审查流程"), | ||||
PROJECT_REVIEW(14, "项目评审流程"), | PROJECT_REVIEW(14, "项目评审流程"), | ||||
PROJECT_STOPPED(15, "项目终止流程"), | PROJECT_STOPPED(15, "项目终止流程"), | ||||
@@ -55,7 +55,7 @@ public class SelfTestStateChangeAction { | |||||
@OnTransition(source = "SELF_TEST_INFO_FAILED", target = "SELF_TEST_INFO_AUDIT") | @OnTransition(source = "SELF_TEST_INFO_FAILED", target = "SELF_TEST_INFO_AUDIT") | ||||
public void RESUBMIT_SELF_TEST_INFO(Message<SelfTestStateChangeEvent> message) { | public void RESUBMIT_SELF_TEST_INFO(Message<SelfTestStateChangeEvent> message) { | ||||
Purchase purchase = getPurchaseInfo(message); | Purchase purchase = getPurchaseInfo(message); | ||||
purchase.setStatus(TenderSelfTestStatus.WITHOUT_SELF_TEST_INFO.getCode()); | |||||
purchase.setStatus(TenderSelfTestStatus.SELF_TEST_INFO_AUDIT.getCode()); | |||||
purchase.setSelfTestStatus(TenderSelfTestStatus.SELF_TEST_INFO_AUDIT.getCode()); | purchase.setSelfTestStatus(TenderSelfTestStatus.SELF_TEST_INFO_AUDIT.getCode()); | ||||
} | } | ||||
@@ -12,6 +12,7 @@ import com.hz.pm.api.external.model.dto.*; | |||||
import com.hz.pm.api.external.model.enumeration.MhDictType; | import com.hz.pm.api.external.model.enumeration.MhDictType; | ||||
import com.hz.pm.api.meeting.entity.req.MeetingIdReq; | import com.hz.pm.api.meeting.entity.req.MeetingIdReq; | ||||
import com.hz.pm.api.open.model.vo.MeetingExpertToMhDTO; | import com.hz.pm.api.open.model.vo.MeetingExpertToMhDTO; | ||||
import com.hz.pm.api.projectlib.model.dto.MhSystemReplaceInfoDTO; | |||||
import com.ningdatech.basic.exception.BizException; | import com.ningdatech.basic.exception.BizException; | ||||
import lombok.RequiredArgsConstructor; | import lombok.RequiredArgsConstructor; | ||||
import lombok.extern.slf4j.Slf4j; | import lombok.extern.slf4j.Slf4j; | ||||
@@ -62,6 +63,8 @@ public class MhApiClient { | |||||
private static final String PUSH_MEETING_EXPERTS_DATA = "/meeting/saveData"; | private static final String PUSH_MEETING_EXPERTS_DATA = "/meeting/saveData"; | ||||
private static final String CANCEL_MEETING_DATA = "/meeting/cancel"; | private static final String CANCEL_MEETING_DATA = "/meeting/cancel"; | ||||
private static final String SYSTEM_REPLACE_INFO = "/deep_design/dzSystem"; | |||||
/** | /** | ||||
* 信创符合性测评报告相关接口 | * 信创符合性测评报告相关接口 | ||||
*/ | */ | ||||
@@ -228,4 +231,23 @@ public class MhApiClient { | |||||
log.error("取消会议信息推送失败:{}", retBody); | log.error("取消会议信息推送失败:{}", retBody); | ||||
} | } | ||||
} | } | ||||
public List<MhSystemReplaceInfoDTO> querySystemReplaceInfos() { | |||||
String retBody; | |||||
if (!environmentUtil.isDevEnv()) { | |||||
String url = mhApiHost + SYSTEM_REPLACE_INFO; | |||||
retBody = HttpUtil.get(url); | |||||
} else { | |||||
retBody = new ClassPathResource("/response/ret-system-replace-info.json").readUtf8Str(); | |||||
} | |||||
MhRetDTO<List<MhSystemReplaceInfoDTO>> retObj = JSONUtil.toBean(retBody, | |||||
new TypeReference<MhRetDTO<List<MhSystemReplaceInfoDTO>>>() { | |||||
}, false); | |||||
if (retObj.isOk()) { | |||||
return retObj.getData(); | |||||
} | |||||
log.error("系统改造计划获取失败:{}", retBody); | |||||
throw BizException.wrap("系统改造计划获取失败"); | |||||
} | |||||
} | } |
@@ -475,6 +475,10 @@ public class PurchaseManage { | |||||
return null; | return null; | ||||
} | } | ||||
List<Purchase> purchases = purchaseService.list(query); | List<Purchase> purchases = purchaseService.list(query); | ||||
return adaptionProgressStatistics(purchases); | |||||
} | |||||
public AdaptionProgressStatVO adaptionProgressStatistics(List<Purchase> purchases) { | |||||
Map<ITenderStatus, Long> statusCountMap = CollUtils.groupCount(purchases, | Map<ITenderStatus, Long> statusCountMap = CollUtils.groupCount(purchases, | ||||
w -> { | w -> { | ||||
ITenderStatus status = TenderMainStatus.getNoNull(w.getStatus()); | ITenderStatus status = TenderMainStatus.getNoNull(w.getStatus()); | ||||
@@ -1,28 +1,18 @@ | |||||
package com.hz.pm.api.projectlib.controller; | package com.hz.pm.api.projectlib.controller; | ||||
import cn.hutool.core.map.MapUtil; | |||||
import cn.hutool.poi.excel.ExcelReader; | |||||
import cn.hutool.poi.excel.ExcelUtil; | |||||
import cn.hutool.poi.excel.ExcelWriter; | |||||
import cn.hutool.poi.excel.StyleSet; | |||||
import com.hz.pm.api.projectlib.manage.MhSystemReplaceManage; | import com.hz.pm.api.projectlib.manage.MhSystemReplaceManage; | ||||
import com.hz.pm.api.projectlib.model.dto.MhSystemBaseInfoDTO; | |||||
import com.hz.pm.api.projectlib.model.dto.MhSystemReplaceInfoVO; | |||||
import com.hz.pm.api.projectlib.model.req.MhSystemReplaceReq; | import com.hz.pm.api.projectlib.model.req.MhSystemReplaceReq; | ||||
import com.ningdatech.basic.model.PageVo; | import com.ningdatech.basic.model.PageVo; | ||||
import com.ningdatech.log.annotation.WebLog; | |||||
import io.swagger.annotations.Api; | import io.swagger.annotations.Api; | ||||
import io.swagger.annotations.ApiOperation; | import io.swagger.annotations.ApiOperation; | ||||
import lombok.RequiredArgsConstructor; | import lombok.RequiredArgsConstructor; | ||||
import org.apache.poi.ss.usermodel.CellStyle; | |||||
import org.springframework.security.access.prepost.PreAuthorize; | |||||
import org.springframework.web.bind.annotation.GetMapping; | import org.springframework.web.bind.annotation.GetMapping; | ||||
import org.springframework.web.bind.annotation.RequestMapping; | import org.springframework.web.bind.annotation.RequestMapping; | ||||
import org.springframework.web.bind.annotation.RestController; | import org.springframework.web.bind.annotation.RestController; | ||||
import java.io.File; | |||||
import java.time.LocalDateTime; | |||||
import java.util.List; | |||||
import java.util.Map; | |||||
import java.util.stream.Collectors; | |||||
/** | /** | ||||
* <p> | * <p> | ||||
* MhSystemReplaceController | * MhSystemReplaceController | ||||
@@ -41,34 +31,16 @@ public class MhSystemReplaceController { | |||||
@GetMapping("/page") | @GetMapping("/page") | ||||
@ApiOperation("列表查询") | @ApiOperation("列表查询") | ||||
public PageVo<MhSystemBaseInfoDTO> page(MhSystemReplaceReq req) { | |||||
public PageVo<MhSystemReplaceInfoVO> page(MhSystemReplaceReq req) { | |||||
return mhSystemReplaceManage.page(req); | return mhSystemReplaceManage.page(req); | ||||
} | } | ||||
public static void main(String[] args) { | |||||
ExcelReader reader = ExcelUtil.getReader("/Users/wendy/Desktop/信息系统.xlsx"); | |||||
List<Map<String, Object>> maps = reader.readAll(); | |||||
List<MhSystemBaseInfoDTO> collect = maps.stream().map(w -> { | |||||
MhSystemBaseInfoDTO dto = new MhSystemBaseInfoDTO(); | |||||
dto.setSourceName(MapUtil.getStr(w, "系统名称")); | |||||
dto.setTargetName(MapUtil.getStr(w, "替代后系统名称")); | |||||
dto.setBuildOrgName(MapUtil.getStr(w, "建设单位")); | |||||
dto.setBuildOrgCode(MapUtil.getLong(w, "建设单位ID")); | |||||
dto.setReplaceType(MapUtil.getStr(w, "改造方式")); | |||||
dto.setSystemNum(MapUtil.getInt(w, "集成系统数量", 1)); | |||||
dto.setPlanStartDate(MapUtil.getInt(w, "计划改造开始时间")); | |||||
dto.setPlanFinishDate(MapUtil.getInt(w, "计划完成时间")); | |||||
dto.setActualStartDate(MapUtil.get(w, "开始时间", LocalDateTime.class)); | |||||
dto.setActualFinishDate(MapUtil.get(w, "完成时间", LocalDateTime.class)); | |||||
return dto; | |||||
}).collect(Collectors.toList()); | |||||
try (ExcelWriter writer = ExcelUtil.getWriter()) { | |||||
writer.write(collect) | |||||
.flush(new File("/Users/wendy/Desktop/mh-system-replace.xlsx")) | |||||
.close(); | |||||
} | |||||
@GetMapping("/sync") | |||||
@ApiOperation("同步系统改造计划数据") | |||||
@WebLog("同步系统改造计划数据") | |||||
@PreAuthorize("hasAuthority('SUPER_ADMIN')") | |||||
public void syncMhSystemReplaceInfo() { | |||||
mhSystemReplaceManage.syncMhSystemReplaceInfo(); | |||||
} | } | ||||
} | } |
@@ -0,0 +1,74 @@ | |||||
package com.hz.pm.api.projectlib.entity; | |||||
import com.baomidou.mybatisplus.annotation.IdType; | |||||
import com.baomidou.mybatisplus.annotation.TableId; | |||||
import com.baomidou.mybatisplus.annotation.TableName; | |||||
import io.swagger.annotations.ApiModel; | |||||
import io.swagger.annotations.ApiModelProperty; | |||||
import lombok.Data; | |||||
import java.io.Serializable; | |||||
import java.math.BigDecimal; | |||||
import java.time.LocalDateTime; | |||||
/** | |||||
* <p> | |||||
* 信产系统改造计划 | |||||
* </p> | |||||
* | |||||
* @author WendyYang | |||||
* @since 2024-08-20 | |||||
*/ | |||||
@Data | |||||
@TableName("MH_SYSTEM_REPLACE_INFO") | |||||
@ApiModel(value = "MhSystemReplaceInfo对象") | |||||
public class MhSystemReplaceInfo implements Serializable { | |||||
private static final long serialVersionUID = 1L; | |||||
@TableId(type = IdType.INPUT) | |||||
private String id; | |||||
@ApiModelProperty("替代前系统名称") | |||||
private String sourceName; | |||||
@ApiModelProperty("是否涉密") | |||||
private String isSecret; | |||||
@ApiModelProperty("建设单位") | |||||
private String buildOrgName; | |||||
@ApiModelProperty("建设单位代码") | |||||
private Integer buildOrgCode; | |||||
@ApiModelProperty("系统数量") | |||||
private Integer systemNum; | |||||
@ApiModelProperty("替代方式") | |||||
private String replaceType; | |||||
@ApiModelProperty("改造费用") | |||||
private BigDecimal expectCost; | |||||
@ApiModelProperty("替代后系统名称") | |||||
private String targetName; | |||||
@ApiModelProperty("pid") | |||||
private String pid; | |||||
@ApiModelProperty("host") | |||||
private String host; | |||||
@ApiModelProperty("计划开始时间") | |||||
private Integer planStartDate; | |||||
@ApiModelProperty("计划完成时间") | |||||
private Integer planFinishDate; | |||||
@ApiModelProperty("实际完成时间") | |||||
private LocalDateTime actualFinishDate; | |||||
@ApiModelProperty("开始时间") | |||||
private LocalDateTime createOn; | |||||
} |
@@ -1,23 +1,25 @@ | |||||
package com.hz.pm.api.projectlib.manage; | package com.hz.pm.api.projectlib.manage; | ||||
import cn.hutool.core.bean.BeanUtil; | import cn.hutool.core.bean.BeanUtil; | ||||
import cn.hutool.core.io.resource.ClassPathResource; | |||||
import cn.hutool.core.collection.CollUtil; | |||||
import cn.hutool.core.util.StrUtil; | import cn.hutool.core.util.StrUtil; | ||||
import cn.hutool.poi.excel.ExcelReader; | |||||
import cn.hutool.poi.excel.ExcelUtil; | |||||
import com.hz.pm.api.projectlib.model.dto.MhSystemBaseInfoDTO; | |||||
import com.baomidou.mybatisplus.core.conditions.query.LambdaQueryWrapper; | |||||
import com.baomidou.mybatisplus.core.toolkit.Wrappers; | |||||
import com.baomidou.mybatisplus.extension.plugins.pagination.Page; | |||||
import com.hz.pm.api.external.MhApiClient; | |||||
import com.hz.pm.api.projectlib.entity.MhSystemReplaceInfo; | |||||
import com.hz.pm.api.projectlib.model.dto.MhSystemReplaceInfoDTO; | |||||
import com.hz.pm.api.projectlib.model.dto.MhSystemReplaceInfoVO; | |||||
import com.hz.pm.api.projectlib.model.req.MhSystemReplaceReq; | import com.hz.pm.api.projectlib.model.req.MhSystemReplaceReq; | ||||
import com.hz.pm.api.projectlib.service.IMhSystemReplaceInfoService; | |||||
import com.hz.pm.api.user.helper.MhUnitCache; | import com.hz.pm.api.user.helper.MhUnitCache; | ||||
import com.ningdatech.basic.model.PageVo; | import com.ningdatech.basic.model.PageVo; | ||||
import com.ningdatech.basic.util.CollUtils; | |||||
import lombok.RequiredArgsConstructor; | import lombok.RequiredArgsConstructor; | ||||
import org.springframework.stereotype.Component; | import org.springframework.stereotype.Component; | ||||
import org.springframework.transaction.annotation.Transactional; | |||||
import java.io.InputStream; | |||||
import java.util.Comparator; | |||||
import java.time.LocalDateTime; | |||||
import java.util.List; | import java.util.List; | ||||
import java.util.Map; | |||||
import java.util.Objects; | |||||
import java.util.stream.Collectors; | import java.util.stream.Collectors; | ||||
/** | /** | ||||
@@ -32,66 +34,71 @@ import java.util.stream.Collectors; | |||||
@RequiredArgsConstructor | @RequiredArgsConstructor | ||||
public class MhSystemReplaceManage { | public class MhSystemReplaceManage { | ||||
private final IMhSystemReplaceInfoService mhSystemReplaceInfoService; | |||||
private final MhUnitCache mhUnitCache; | private final MhUnitCache mhUnitCache; | ||||
private final MhApiClient mhApiClient; | |||||
public PageVo<MhSystemBaseInfoDTO> page(MhSystemReplaceReq req) { | |||||
ClassPathResource resource = new ClassPathResource("/response/mh-system-replace.xlsx"); | |||||
InputStream stream = resource.getStream(); | |||||
ExcelReader reader = ExcelUtil.getReader(stream); | |||||
List<Map<String, Object>> data = reader.readAll(); | |||||
List<MhSystemBaseInfoDTO> actualData = BeanUtil.copyToList(data, MhSystemBaseInfoDTO.class); | |||||
List<Long> filterOrgCodes; | |||||
if (req.getBuildOrgCode() != null) { | |||||
filterOrgCodes = mhUnitCache.getViewChildIdsRecursion(req.getBuildOrgCode()); | |||||
} else { | |||||
filterOrgCodes = null; | |||||
} | |||||
List<MhSystemBaseInfoDTO> filterData = actualData.stream().filter(w -> { | |||||
if (filterOrgCodes != null && !filterOrgCodes.contains(w.getBuildOrgCode())) { | |||||
return false; | |||||
} | |||||
if (req.getFinish() != null | |||||
&& !req.getFinish() == Objects.nonNull(w.getActualFinishDate())) { | |||||
return false; | |||||
} | |||||
if (StrUtil.isNotBlank(req.getReplaceType()) | |||||
&& !req.getReplaceType().equals(w.getReplaceType())) { | |||||
return false; | |||||
} | |||||
if (req.getPlanStartDateMin() != null | |||||
&& req.getPlanStartDateMax() != null | |||||
&& (w.getPlanStartDate() == null | |||||
|| !(w.getPlanStartDate() >= req.getPlanStartDateMin() | |||||
&& w.getPlanStartDate() <= req.getPlanStartDateMax()))) { | |||||
return false; | |||||
} | |||||
if (req.getPlanFinishDateMin() != null | |||||
&& req.getPlanFinishDateMax() != null | |||||
&& (w.getPlanFinishDate() == null | |||||
|| !(w.getPlanFinishDate() >= req.getPlanFinishDateMin() | |||||
&& w.getPlanFinishDate() <= req.getPlanFinishDateMax()))) { | |||||
return false; | |||||
} | |||||
if (StrUtil.isNotBlank(req.getSystemName()) | |||||
&& (!w.getSourceName().contains(req.getSystemName()) | |||||
|| !w.getTargetName().contains(req.getSystemName()))) { | |||||
return false; | |||||
} | |||||
@Transactional(rollbackFor = Exception.class) | |||||
public synchronized void syncMhSystemReplaceInfo() { | |||||
List<MhSystemReplaceInfoDTO> systemReplaceInfos = mhApiClient.querySystemReplaceInfos(); | |||||
mhSystemReplaceInfoService.remove(null); | |||||
if (CollUtil.isEmpty(systemReplaceInfos)) { | |||||
return; | |||||
} | |||||
LocalDateTime now = LocalDateTime.now(); | |||||
List<MhSystemReplaceInfo> newData = systemReplaceInfos.stream().map(w -> { | |||||
MhSystemReplaceInfo replaceInfo = new MhSystemReplaceInfo(); | |||||
replaceInfo.setActualFinishDate(w.getFinalTime()); | |||||
replaceInfo.setBuildOrgCode(w.getCreateUnit()); | |||||
replaceInfo.setBuildOrgName(w.getBuildUnit()); | |||||
replaceInfo.setExpectCost(w.getExpectCost()); | |||||
replaceInfo.setHost(w.getHost()); | |||||
replaceInfo.setId(w.getId()); | |||||
replaceInfo.setCreateOn(now); | |||||
replaceInfo.setIsSecret(w.getIsSecret()); | |||||
replaceInfo.setPid(w.getPid()); | |||||
replaceInfo.setPlanFinishDate(w.getExpectDate()); | |||||
replaceInfo.setPlanStartDate(w.getExpectStart()); | |||||
replaceInfo.setReplaceType(w.getAlternativeType()); | |||||
replaceInfo.setSourceName(w.getSystemName()); | |||||
replaceInfo.setSystemNum(1); | |||||
replaceInfo.setTargetName(w.getAlternativeName()); | |||||
return replaceInfo; | |||||
}).collect(Collectors.toList()); | |||||
mhSystemReplaceInfoService.saveBatch(newData); | |||||
} | |||||
if (StrUtil.isNotBlank(req.getBuildOrgName())) { | |||||
return w.getBuildOrgName().contains(req.getBuildOrgName()); | |||||
public PageVo<MhSystemReplaceInfoVO> page(MhSystemReplaceReq req) { | |||||
LambdaQueryWrapper<MhSystemReplaceInfo> query = Wrappers.lambdaQuery(MhSystemReplaceInfo.class) | |||||
.like(StrUtil.isNotBlank(req.getBuildOrgName()), MhSystemReplaceInfo::getBuildOrgName, req.getBuildOrgName()) | |||||
.and(StrUtil.isNotBlank(req.getSystemName()), q1 -> q1.like(MhSystemReplaceInfo::getSourceName, req.getSystemName()) | |||||
.or(q2 -> q2.like(MhSystemReplaceInfo::getTargetName, req.getSystemName()))) | |||||
.eq(StrUtil.isNotBlank(req.getReplaceType()), MhSystemReplaceInfo::getReplaceType, req.getReplaceType()) | |||||
.ge(req.getPlanFinishDateMin() != null, MhSystemReplaceInfo::getPlanFinishDate, req.getPlanFinishDateMin()) | |||||
.le(req.getPlanFinishDateMax() != null, MhSystemReplaceInfo::getPlanFinishDate, req.getPlanFinishDateMax()) | |||||
.ge(req.getPlanStartDateMin() != null, MhSystemReplaceInfo::getPlanStartDate, req.getPlanStartDateMin()) | |||||
.le(req.getPlanStartDateMax() != null, MhSystemReplaceInfo::getPlanStartDate, req.getPlanStartDateMax()); | |||||
if (req.getFinish() != null) { | |||||
if (Boolean.TRUE.equals(req.getFinish())) { | |||||
query.orderByDesc(MhSystemReplaceInfo::getActualFinishDate); | |||||
query.isNotNull(MhSystemReplaceInfo::getActualFinishDate); | |||||
} else { | |||||
query.orderByDesc(MhSystemReplaceInfo::getPlanFinishDate); | |||||
query.isNull(MhSystemReplaceInfo::getActualFinishDate); | |||||
} | } | ||||
return true; | |||||
}).collect(Collectors.toList()); | |||||
if (Boolean.TRUE.equals(req.getFinish())) { | |||||
filterData.sort(Comparator.comparing(MhSystemBaseInfoDTO::getActualFinishDate).reversed()); | |||||
} else { | } else { | ||||
filterData.sort(Comparator.comparing(MhSystemBaseInfoDTO::getPlanFinishDate).reversed()); | |||||
query.orderByDesc(MhSystemReplaceInfo::getPlanFinishDate); | |||||
} | |||||
if (req.getBuildOrgCode() != null) { | |||||
query.in(MhSystemReplaceInfo::getBuildOrgCode, mhUnitCache.getViewChildIdsRecursion(req.getBuildOrgCode())); | |||||
} | |||||
Page<MhSystemReplaceInfo> page = mhSystemReplaceInfoService.page(req.page(), query); | |||||
if (page.getTotal() == 0) { | |||||
return PageVo.empty(); | |||||
} | } | ||||
List<MhSystemBaseInfoDTO> pageData = CollUtils.page(filterData, req.getPageNumber(), req.getPageSize()); | |||||
return PageVo.of(pageData, filterData.size()); | |||||
List<MhSystemReplaceInfoVO> data = BeanUtil.copyToList(page.getRecords(), MhSystemReplaceInfoVO.class); | |||||
return PageVo.of(data, page.getTotal()); | |||||
} | } | ||||
} | } |
@@ -0,0 +1,16 @@ | |||||
package com.hz.pm.api.projectlib.mapper; | |||||
import com.hz.pm.api.projectlib.entity.MhSystemReplaceInfo; | |||||
import com.baomidou.mybatisplus.core.mapper.BaseMapper; | |||||
/** | |||||
* <p> | |||||
* Mapper 接口 | |||||
* </p> | |||||
* | |||||
* @author WendyYang | |||||
* @since 2024-08-20 | |||||
*/ | |||||
public interface MhSystemReplaceInfoMapper extends BaseMapper<MhSystemReplaceInfo> { | |||||
} |
@@ -0,0 +1,5 @@ | |||||
<?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.hz.pm.api.projectlib.mapper.MhSystemReplaceInfoMapper"> | |||||
</mapper> |
@@ -17,7 +17,7 @@ import java.time.LocalDateTime; | |||||
*/ | */ | ||||
@Data | @Data | ||||
@ApiModel("系统升级信息") | @ApiModel("系统升级信息") | ||||
public class MhSystemUpgradeInfoDTO { | |||||
public class MhSystemReplaceInfoDTO { | |||||
@ApiModelProperty("主键ID") | @ApiModelProperty("主键ID") | ||||
private String id; | private String id; |
@@ -15,7 +15,7 @@ import java.time.LocalDateTime; | |||||
* @since 13:35 2024/8/16 | * @since 13:35 2024/8/16 | ||||
*/ | */ | ||||
@Data | @Data | ||||
public class MhSystemBaseInfoDTO { | |||||
public class MhSystemReplaceInfoVO { | |||||
@ApiModelProperty("替代前系统名称") | @ApiModelProperty("替代前系统名称") | ||||
private String sourceName; | private String sourceName; |
@@ -35,8 +35,8 @@ public enum InstTypeEnum { | |||||
APPLY_BORROW(7, "申请借阅审批流程"), | APPLY_BORROW(7, "申请借阅审批流程"), | ||||
SELF_TEST(10, "系统自测审批流程"), | SELF_TEST(10, "系统自测审批流程"), | ||||
ADAPTION(11, "适配改造审批流程"), | |||||
TEST_VALID(12, "测试验证审批流程"), | |||||
ADAPTION(11, "开工文件审批流程"), | |||||
TEST_VALID(12, "监理核实验证审批流程"), | |||||
COMPLIANCE_REVIEW(13, "合规性审查流程"), | COMPLIANCE_REVIEW(13, "合规性审查流程"), | ||||
PROJECT_REVIEW(14, "项目评审流程"), | PROJECT_REVIEW(14, "项目评审流程"), | ||||
PROJECT_STOPPED(15, "项目终止流程"), | PROJECT_STOPPED(15, "项目终止流程"), | ||||
@@ -67,4 +67,8 @@ public enum TenderMainStatus implements ITenderStatus { | |||||
} | } | ||||
public static void main(String[] args) { | |||||
TENDER_STATUS_MAP.forEach((k, v) -> System.out.println(k + ":" + v)); | |||||
} | |||||
} | } |
@@ -0,0 +1,16 @@ | |||||
package com.hz.pm.api.projectlib.service; | |||||
import com.hz.pm.api.projectlib.entity.MhSystemReplaceInfo; | |||||
import com.baomidou.mybatisplus.extension.service.IService; | |||||
/** | |||||
* <p> | |||||
* 服务类 | |||||
* </p> | |||||
* | |||||
* @author WendyYang | |||||
* @since 2024-08-20 | |||||
*/ | |||||
public interface IMhSystemReplaceInfoService extends IService<MhSystemReplaceInfo> { | |||||
} |
@@ -0,0 +1,20 @@ | |||||
package com.hz.pm.api.projectlib.service.impl; | |||||
import com.hz.pm.api.projectlib.entity.MhSystemReplaceInfo; | |||||
import com.hz.pm.api.projectlib.mapper.MhSystemReplaceInfoMapper; | |||||
import com.hz.pm.api.projectlib.service.IMhSystemReplaceInfoService; | |||||
import com.baomidou.mybatisplus.extension.service.impl.ServiceImpl; | |||||
import org.springframework.stereotype.Service; | |||||
/** | |||||
* <p> | |||||
* 服务实现类 | |||||
* </p> | |||||
* | |||||
* @author WendyYang | |||||
* @since 2024-08-20 | |||||
*/ | |||||
@Service | |||||
public class MhSystemReplaceInfoServiceImpl extends ServiceImpl<MhSystemReplaceInfoMapper, MhSystemReplaceInfo> implements IMhSystemReplaceInfoService { | |||||
} |
@@ -0,0 +1,31 @@ | |||||
package com.hz.pm.api.scheduler.task; | |||||
import com.hz.pm.api.projectlib.manage.MhSystemReplaceManage; | |||||
import org.springframework.boot.autoconfigure.condition.ConditionalOnExpression; | |||||
import org.springframework.scheduling.annotation.Scheduled; | |||||
import org.springframework.stereotype.Component; | |||||
/** | |||||
* <p> | |||||
* MhSystemReplaceSyncTask | |||||
* </p> | |||||
*I | |||||
* @author WendyYang | |||||
* @since 20:53 2024/8/20 | |||||
*/ | |||||
@Component | |||||
@ConditionalOnExpression("${mh-system-replace-sync.open:true}") | |||||
public class MhSystemReplaceSyncTask { | |||||
private final MhSystemReplaceManage mhSystemReplaceManage; | |||||
public MhSystemReplaceSyncTask(MhSystemReplaceManage mhSystemReplaceManage) { | |||||
this.mhSystemReplaceManage = mhSystemReplaceManage; | |||||
} | |||||
@Scheduled(cron = "${mh-system-replace-sync.cron:0 0 1 * * ?}") | |||||
public void execute() { | |||||
mhSystemReplaceManage.syncMhSystemReplaceInfo(); | |||||
} | |||||
} |
@@ -13,8 +13,11 @@ import com.hz.pm.api.common.model.constant.BizConst; | |||||
import com.hz.pm.api.common.model.constant.ExistsSqlConst; | import com.hz.pm.api.common.model.constant.ExistsSqlConst; | ||||
import com.hz.pm.api.common.statemachine.event.*; | import com.hz.pm.api.common.statemachine.event.*; | ||||
import com.hz.pm.api.common.util.DecimalUtil; | import com.hz.pm.api.common.util.DecimalUtil; | ||||
import com.hz.pm.api.projectdeclared.manage.PurchaseManage; | |||||
import com.hz.pm.api.projectdeclared.model.entity.Contract; | import com.hz.pm.api.projectdeclared.model.entity.Contract; | ||||
import com.hz.pm.api.projectdeclared.model.entity.Purchase; | import com.hz.pm.api.projectdeclared.model.entity.Purchase; | ||||
import com.hz.pm.api.projectdeclared.model.enumerization.BidTypeEnum; | |||||
import com.hz.pm.api.projectdeclared.model.vo.AdaptionProgressStatVO; | |||||
import com.hz.pm.api.projectdeclared.service.IContractService; | import com.hz.pm.api.projectdeclared.service.IContractService; | ||||
import com.hz.pm.api.projectdeclared.service.IPurchaseService; | import com.hz.pm.api.projectdeclared.service.IPurchaseService; | ||||
import com.hz.pm.api.projectdeclared.utils.ProjectIdCodeCacheUtil; | import com.hz.pm.api.projectdeclared.utils.ProjectIdCodeCacheUtil; | ||||
@@ -70,6 +73,8 @@ import java.util.function.BiFunction; | |||||
import java.util.function.Predicate; | import java.util.function.Predicate; | ||||
import java.util.stream.Collectors; | import java.util.stream.Collectors; | ||||
import static com.hz.pm.api.workbench.model.vo.ProjectProcessStatVO.*; | |||||
/** | /** | ||||
* <p> | * <p> | ||||
* WorkbenchManage | * WorkbenchManage | ||||
@@ -96,6 +101,7 @@ public class WorkbenchManage { | |||||
private final MhUnitCache mhUnitCache; | private final MhUnitCache mhUnitCache; | ||||
private final IProjectGovSystemReplaceInfosService systemReplaceInfosService; | private final IProjectGovSystemReplaceInfosService systemReplaceInfosService; | ||||
private final IPurchaseStatusChangeService purchaseStatusChangeService; | private final IPurchaseStatusChangeService purchaseStatusChangeService; | ||||
private final PurchaseManage purchaseManage; | |||||
public WorkbenchVO getWorkbenchData(Integer year) { | public WorkbenchVO getWorkbenchData(Integer year) { | ||||
WorkbenchVO res = new WorkbenchVO(); | WorkbenchVO res = new WorkbenchVO(); | ||||
@@ -230,10 +236,10 @@ public class WorkbenchManage { | |||||
int sourceCount = 0; | int sourceCount = 0; | ||||
int targetCount = 0; | int targetCount = 0; | ||||
for (List<ProjectGovSystemReplaceInfos> currSystems : replaceGroupProject.values()) { | for (List<ProjectGovSystemReplaceInfos> currSystems : replaceGroupProject.values()) { | ||||
sourceCount += CollUtil.count(CollUtils.fieldSet(currSystems, ProjectGovSystemReplaceInfos::getSourceSystem), | |||||
isValidSystem::test); | |||||
targetCount += CollUtil.count(CollUtils.fieldSet(currSystems, ProjectGovSystemReplaceInfos::getTargetSystem), | |||||
isValidSystem::test); | |||||
sourceCount += CollUtil.count(CollUtils.fieldSet(currSystems, ProjectGovSystemReplaceInfos::getSourceSystem), | |||||
isValidSystem::test); | |||||
targetCount += CollUtil.count(CollUtils.fieldSet(currSystems, ProjectGovSystemReplaceInfos::getTargetSystem), | |||||
isValidSystem::test); | |||||
} | } | ||||
return SystemReplaceStatVO.builder() | return SystemReplaceStatVO.builder() | ||||
.sourceCount(sourceCount) | .sourceCount(sourceCount) | ||||
@@ -302,15 +308,19 @@ public class WorkbenchManage { | |||||
List<Long> allProjectIds = new ArrayList<>(); | List<Long> allProjectIds = new ArrayList<>(); | ||||
List<String> allProjectCodes = new ArrayList<>(); | List<String> allProjectCodes = new ArrayList<>(); | ||||
Map<String, Map<Long, Long>> purchaseEventMap = new HashMap<>(); | Map<String, Map<Long, Long>> purchaseEventMap = new HashMap<>(); | ||||
Map<Long, Long> projectPurchaseCountMap = new HashMap<>(); | |||||
Map<Long, List<Purchase>> projectPurchaseCountMap = new HashMap<>(); | |||||
BiFunction<AbstractStateChangeEvent, WorkbenchProcessNode, List<Long>> computeProjectIds = (event, node) -> { | BiFunction<AbstractStateChangeEvent, WorkbenchProcessNode, List<Long>> computeProjectIds = (event, node) -> { | ||||
Map<Long, Long> projBizMap = purchaseEventMap.getOrDefault(event.name(), Collections.emptyMap()); | Map<Long, Long> projBizMap = purchaseEventMap.getOrDefault(event.name(), Collections.emptyMap()); | ||||
if (node.equals(WorkbenchProcessNode.PROJECT_ADAPTION)) { | if (node.equals(WorkbenchProcessNode.PROJECT_ADAPTION)) { | ||||
return new ArrayList<>(projBizMap.keySet()); | |||||
return projectPurchaseCountMap.entrySet().stream().filter(w -> { | |||||
Long finishedBizCount = projBizMap.get(w.getKey()); | |||||
return finishedBizCount != null && finishedBizCount == CollUtil.count(w.getValue(), | |||||
x -> BidTypeEnum.BUILD_APP.eq(x.getBidType())); | |||||
}).map(Map.Entry::getKey).collect(Collectors.toList()); | |||||
} else { | } else { | ||||
return projectPurchaseCountMap.entrySet().stream().filter(w -> { | return projectPurchaseCountMap.entrySet().stream().filter(w -> { | ||||
Long finishedBizCount = projBizMap.get(w.getKey()); | Long finishedBizCount = projBizMap.get(w.getKey()); | ||||
return finishedBizCount != null && finishedBizCount.equals(w.getValue()); | |||||
return finishedBizCount != null && finishedBizCount == w.getValue().size(); | |||||
}).map(Map.Entry::getKey).collect(Collectors.toList()); | }).map(Map.Entry::getKey).collect(Collectors.toList()); | ||||
} | } | ||||
}; | }; | ||||
@@ -328,7 +338,7 @@ public class WorkbenchManage { | |||||
Map<String, List<ProjectStatusChange>> projectStatusChangeMap = new HashMap<>(); | Map<String, List<ProjectStatusChange>> projectStatusChangeMap = new HashMap<>(); | ||||
for (WorkbenchProcessNode node : WorkbenchProcessNode.ALL) { | for (WorkbenchProcessNode node : WorkbenchProcessNode.ALL) { | ||||
if (!projects.isEmpty()) { | if (!projects.isEmpty()) { | ||||
ProjectProcessStatVO currStat = ProjectProcessStatVO.builder() | |||||
ProjectProcessStatVO currStat = builder() | |||||
.stageName(node.getName()) | .stageName(node.getName()) | ||||
.stage(node) | .stage(node) | ||||
.build(); | .build(); | ||||
@@ -387,10 +397,10 @@ public class WorkbenchManage { | |||||
break; | break; | ||||
case PROJECT_PURCHASE: { | case PROJECT_PURCHASE: { | ||||
Wrapper<Purchase> purchaseQuery = Wrappers.lambdaQuery(Purchase.class) | Wrapper<Purchase> purchaseQuery = Wrappers.lambdaQuery(Purchase.class) | ||||
.select(Purchase::getId, Purchase::getProjectId) | |||||
.select(Purchase::getId, Purchase::getProjectId, Purchase::getBidType) | |||||
.in(Purchase::getProjectId, allProjectIds); | .in(Purchase::getProjectId, allProjectIds); | ||||
List<Purchase> purchases = purchaseService.list(purchaseQuery); | List<Purchase> purchases = purchaseService.list(purchaseQuery); | ||||
projectPurchaseCountMap.putAll(CollUtils.groupCount(purchases, Purchase::getProjectId)); | |||||
projectPurchaseCountMap.putAll(CollUtils.group(purchases, Purchase::getProjectId)); | |||||
currStat.setProjectCount(projectPurchaseCountMap.size()); | currStat.setProjectCount(projectPurchaseCountMap.size()); | ||||
Pair<Integer, Integer> systemReplaceCount = countReplaceSystemByProjectIds(projectPurchaseCountMap.keySet()); | Pair<Integer, Integer> systemReplaceCount = countReplaceSystemByProjectIds(projectPurchaseCountMap.keySet()); | ||||
currStat.setSourceCount(systemReplaceCount.getKey()); | currStat.setSourceCount(systemReplaceCount.getKey()); | ||||
@@ -407,7 +417,9 @@ public class WorkbenchManage { | |||||
TestValidStateChangeEvent.TEST_VALID_INFO_PASSED, | TestValidStateChangeEvent.TEST_VALID_INFO_PASSED, | ||||
TenderStateChangeEvent.SUBMIT_FIRST_INSPECTED_FILES, | TenderStateChangeEvent.SUBMIT_FIRST_INSPECTED_FILES, | ||||
XcfhxStateChangeEvent.XCFHX_APPLY_PASSED, | XcfhxStateChangeEvent.XCFHX_APPLY_PASSED, | ||||
TenderStateChangeEvent.FINALLY_INSPECTED_PASSED); | |||||
TenderStateChangeEvent.FINALLY_INSPECTED_PASSED, | |||||
TenderStateChangeEvent.SUBMIT_PURCHASE_ORG_CONFIRM, | |||||
TenderStateChangeEvent.SUBMIT_PURCHASE_CONSTRUCTION_INFO); | |||||
List<PurchaseStatusChange> purchaseChanges = purchaseStatusChangeService.list(pQuery); | List<PurchaseStatusChange> purchaseChanges = purchaseStatusChangeService.list(pQuery); | ||||
Map<String, Map<Long, Long>> purchaseEventMapTmp = purchaseChanges.stream() | Map<String, Map<Long, Long>> purchaseEventMapTmp = purchaseChanges.stream() | ||||
.collect(Collectors.groupingBy(PurchaseStatusChange::getEvent, | .collect(Collectors.groupingBy(PurchaseStatusChange::getEvent, | ||||
@@ -418,12 +430,22 @@ public class WorkbenchManage { | |||||
} | } | ||||
break; | break; | ||||
case PROJECT_ADAPTION: { | case PROJECT_ADAPTION: { | ||||
List<Long> projectIds = computeProjectIds.apply(AdaptStateChangeEvent.ADAPT_INFO_PASSED, node); | |||||
Pair<Integer, Integer> replaceSystemCount = countReplaceSystemByProjectIds(projectIds); | |||||
List<Long> projectIds = computeProjectIds.apply(TenderStateChangeEvent.SUBMIT_PURCHASE_ORG_CONFIRM, node); | |||||
currStat.setProjectCount(projectIds.size()); | currStat.setProjectCount(projectIds.size()); | ||||
Pair<Integer, Integer> replaceSystemCount = countReplaceSystemByProjectIds(projectIds); | |||||
currStat.setSourceCount(replaceSystemCount.getKey()); | currStat.setSourceCount(replaceSystemCount.getKey()); | ||||
currStat.setTargetCount(replaceSystemCount.getValue()); | currStat.setTargetCount(replaceSystemCount.getValue()); | ||||
List<String> projectCodes = CollUtils.convert(projectIds, ProjectIdCodeCacheUtil::get); | List<String> projectCodes = CollUtils.convert(projectIds, ProjectIdCodeCacheUtil::get); | ||||
Map<Long, Long> submitPurcahseRecordMap = purchaseEventMap.get(TenderStateChangeEvent.SUBMIT_PURCHASE_CONSTRUCTION_INFO.name()); | |||||
if (submitPurcahseRecordMap != null) { | |||||
List<Long> tmpProjectIds = submitPurcahseRecordMap.entrySet().stream() | |||||
.filter(w -> w.getValue() > 0) | |||||
.map(Map.Entry::getKey) | |||||
.collect(Collectors.toList()); | |||||
if (!tmpProjectIds.isEmpty()) { | |||||
currStat.setAdaptFinishStat(tenderAdaptStatistics(tmpProjectIds)); | |||||
} | |||||
} | |||||
currStat.setStoppedCount(stoppedProjectCount(projectStatusChangeMap, projectCodes)); | currStat.setStoppedCount(stoppedProjectCount(projectStatusChangeMap, projectCodes)); | ||||
} | } | ||||
break; | break; | ||||
@@ -456,6 +478,26 @@ public class WorkbenchManage { | |||||
return retData; | return retData; | ||||
} | } | ||||
private TenderAdaptFinishStatVO tenderAdaptStatistics(List<Long> projectIds) { | |||||
Wrapper<PurchaseStatusChange> purchaseQuery = Wrappers.lambdaQuery(PurchaseStatusChange.class) | |||||
.select(PurchaseStatusChange::getEvent, PurchaseStatusChange::getBidId) | |||||
.in(PurchaseStatusChange::getProjectId, projectIds) | |||||
.in(PurchaseStatusChange::getEvent, AdaptStateChangeEvent.SUBMIT_ADAPT_INFO, | |||||
SelfTestStateChangeEvent.SUBMIT_SELF_TEST_INFO, | |||||
TestValidStateChangeEvent.SUBMIT_TEST_VALID_INFO, | |||||
TenderStateChangeEvent.SUBMIT_PURCHASE_ORG_CONFIRM); | |||||
List<PurchaseStatusChange> statusChanges = purchaseStatusChangeService.list(purchaseQuery); | |||||
Map<String, Integer> eventMap = statusChanges.stream() | |||||
.collect(Collectors.groupingBy(PurchaseStatusChange::getEvent, | |||||
Collectors.collectingAndThen(Collectors.mapping(PurchaseStatusChange::getBidId, Collectors.toSet()), Set::size))); | |||||
TenderAdaptFinishStatVO stat = new TenderAdaptFinishStatVO(); | |||||
stat.setFinishTestValidCount(eventMap.getOrDefault(TestValidStateChangeEvent.SUBMIT_TEST_VALID_INFO.name(), 0)); | |||||
stat.setFinishAdaptionInfo(eventMap.getOrDefault(AdaptStateChangeEvent.SUBMIT_ADAPT_INFO.name(), 0)); | |||||
stat.setFinishOrgConfirmCount(eventMap.getOrDefault(TenderStateChangeEvent.SUBMIT_PURCHASE_ORG_CONFIRM.name(), 0)); | |||||
stat.setFinishSelfTestCount(eventMap.getOrDefault(SelfTestStateChangeEvent.SUBMIT_SELF_TEST_INFO.name(), 0)); | |||||
return stat; | |||||
} | |||||
private static int stoppedProjectCount(Map<String, List<ProjectStatusChange>> projectStatusChangeMap, List<String> projectCodes) { | private static int stoppedProjectCount(Map<String, List<ProjectStatusChange>> projectStatusChangeMap, List<String> projectCodes) { | ||||
return CollUtil.count(projectStatusChangeMap.entrySet(), | return CollUtil.count(projectStatusChangeMap.entrySet(), | ||||
w -> projectCodes.contains(w.getKey()) | w -> projectCodes.contains(w.getKey()) | ||||
@@ -39,4 +39,24 @@ public class ProjectProcessStatVO { | |||||
@ApiModelProperty("项目评审失败数量") | @ApiModelProperty("项目评审失败数量") | ||||
private Integer reviewFailedCount; | private Integer reviewFailedCount; | ||||
@ApiModelProperty("适配改造统计") | |||||
private TenderAdaptFinishStatVO adaptFinishStat; | |||||
@Data | |||||
public static class TenderAdaptFinishStatVO { | |||||
@ApiModelProperty("上传开工文件") | |||||
private Integer finishAdaptionInfo; | |||||
@ApiModelProperty("上传自测材料") | |||||
private Integer finishSelfTestCount; | |||||
@ApiModelProperty("上传测试验证材料") | |||||
private Integer finishTestValidCount; | |||||
@ApiModelProperty("单位确认") | |||||
private Integer finishOrgConfirmCount; | |||||
} | |||||
} | } |
@@ -210,4 +210,7 @@ web: | |||||
expert-invite: | expert-invite: | ||||
skip-send-call: true | skip-send-call: true | ||||
skip-send-sms: true | |||||
skip-send-sms: true | |||||
mh-system-replace-sync: | |||||
open: false |
@@ -55,7 +55,7 @@ public class CodeGen { | |||||
} | } | ||||
public static void main(String[] args) { | public static void main(String[] args) { | ||||
generate("WendyYang", "projectdeclared", PATH_YYD, "nd_project_change_history"); | |||||
generate("WendyYang", "projectlib", PATH_YYD, "mh_system_replace_info"); | |||||
} | } | ||||
} | } |