Merge remote-tracking branch 'origin/dev-tmp1' into dev-tmp1
commit
ef8e8a5450
|
|
@ -5,6 +5,7 @@ import io.swagger.annotations.ApiOperation;
|
|||
import io.swagger.annotations.ApiParam;
|
||||
import org.qinan.safetyeval.client.api.OrgPersonnelApi;
|
||||
import org.qinan.safetyeval.client.co.OrgPersonnelCO;
|
||||
import org.qinan.safetyeval.client.co.OrgPersonnelDeptCountCO;
|
||||
import org.qinan.safetyeval.client.co.OrgPersonnelImportResultCO;
|
||||
import org.qinan.safetyeval.client.co.QualFilingPersonnelInfoCO;
|
||||
import org.qinan.safetyeval.client.dto.*;
|
||||
|
|
@ -95,4 +96,10 @@ public class OrgPersonnelController {
|
|||
public SingleResponse<List<OrgPersonnelCO>> getOrgPersonnel() {
|
||||
return orgPersonnelApi.getOrgPersonnel();
|
||||
}
|
||||
|
||||
@ApiOperation("按部门批量统计人员数量")
|
||||
@GetMapping("/deptPersonCount")
|
||||
public SingleResponse<List<OrgPersonnelDeptCountCO>> deptPersonCount() {
|
||||
return orgPersonnelApi.deptPersonCount();
|
||||
}
|
||||
}
|
||||
|
|
|
|||
|
|
@ -34,6 +34,7 @@ import org.qinan.safetyeval.infrastructure.adapter.auth.AuthUserContextAdapter;
|
|||
import org.qinan.safetyeval.infrastructure.adapter.gbs.GbsUserFacadeClient;
|
||||
import org.qinan.safetyeval.infrastructure.convertor.OrgPersonnelCertConvertor;
|
||||
import org.qinan.safetyeval.infrastructure.dataobject.OrgPersonnelDO;
|
||||
import org.qinan.safetyeval.infrastructure.dataobject.OrgPersonnelDeptCountDO;
|
||||
import org.qinan.safetyeval.infrastructure.mapper.OrgPersonnelMapper;
|
||||
import org.qinan.safetyeval.infrastructure.mapper.QualFilingPersonnelCertMapper;
|
||||
import org.qinan.safetyeval.infrastructure.support.UserOrgIdResolver;
|
||||
|
|
@ -459,6 +460,22 @@ public class OrgPersonnelExecutor implements OrgPersonnelApi {
|
|||
return SingleResponse.success(orgPersonnelCOS);
|
||||
}
|
||||
|
||||
@Override
|
||||
public SingleResponse<List<OrgPersonnelDeptCountCO>> deptPersonCount() {
|
||||
Long orgId = ThreadLocalUserInfoAdapter.getOrgId();
|
||||
List<OrgPersonnelDeptCountDO> rows = orgPersonnelMapper.countPersonGroupByDept(orgId);
|
||||
if (CollectionUtils.isEmpty(rows)) {
|
||||
return SingleResponse.success(Collections.emptyList());
|
||||
}
|
||||
List<OrgPersonnelDeptCountCO> list = rows.stream().map(row -> {
|
||||
OrgPersonnelDeptCountCO co = new OrgPersonnelDeptCountCO();
|
||||
co.setDeptId(row.getDeptId() != null ? String.valueOf(row.getDeptId()) : null);
|
||||
co.setPersonCount(row.getPersonCount() != null ? row.getPersonCount() : 0);
|
||||
return co;
|
||||
}).collect(Collectors.toList());
|
||||
return SingleResponse.success(list);
|
||||
}
|
||||
|
||||
@Override
|
||||
public SingleResponse<Void> professionalCapabilityProofMaterialUpdate(ProfessionalCapabilityProofMaterialUpdateCmd cmd) {
|
||||
orgPersonnelMapper.update(new LambdaUpdateWrapper<OrgPersonnelDO>()
|
||||
|
|
|
|||
|
|
@ -1,6 +1,7 @@
|
|||
package org.qinan.safetyeval.client.api;
|
||||
|
||||
import org.qinan.safetyeval.client.co.OrgPersonnelCO;
|
||||
import org.qinan.safetyeval.client.co.OrgPersonnelDeptCountCO;
|
||||
import org.qinan.safetyeval.client.co.OrgPersonnelImportResultCO;
|
||||
import org.qinan.safetyeval.client.co.QualFilingPersonnelInfoCO;
|
||||
import org.qinan.safetyeval.client.dto.*;
|
||||
|
|
@ -51,6 +52,10 @@ public interface OrgPersonnelApi {
|
|||
|
||||
SingleResponse<List<OrgPersonnelCO>> getOrgPersonnel();
|
||||
|
||||
/**
|
||||
* 按部门批量统计人员数量(直接归属,一次返回)。
|
||||
*/
|
||||
SingleResponse<List<OrgPersonnelDeptCountCO>> deptPersonCount();
|
||||
|
||||
SingleResponse<Void> professionalCapabilityProofMaterialUpdate(ProfessionalCapabilityProofMaterialUpdateCmd cmd);
|
||||
}
|
||||
|
|
|
|||
|
|
@ -0,0 +1,19 @@
|
|||
package org.qinan.safetyeval.client.co;
|
||||
|
||||
import io.swagger.annotations.ApiModelProperty;
|
||||
import lombok.Data;
|
||||
|
||||
/**
|
||||
* 部门人员数量统计 CO
|
||||
*
|
||||
* @author safety-eval
|
||||
*/
|
||||
@Data
|
||||
public class OrgPersonnelDeptCountCO {
|
||||
|
||||
@ApiModelProperty(value = "部门ID")
|
||||
private String deptId;
|
||||
|
||||
@ApiModelProperty(value = "人员数量(直接归属该部门)")
|
||||
private Integer personCount;
|
||||
}
|
||||
|
|
@ -14,6 +14,7 @@ public enum ErrorCode {
|
|||
DATA_NOT_EXIST("01-02-101", "数据不存在"),
|
||||
// ---- 部门 ----
|
||||
ORG_DEPARTMENT_NOT_FOUND("01-02-001", "部门不存在"),
|
||||
ORG_DEPARTMENT_HAS_PERSONNEL("01-02-002", "该部门(含子部门)下存在人员,无法删除"),
|
||||
|
||||
// ---- 装备信息 ----
|
||||
ORG_EQUIPMENT_NOT_FOUND("01-03-001", "装备信息不存在"),
|
||||
|
|
@ -54,6 +55,7 @@ public enum ErrorCode {
|
|||
ORG_POSITION_NOT_FOUND("01-08-001", "岗位不存在"),
|
||||
ORG_POSITION_GBS_ROLE_REQUIRED("01-08-002", "岗位关联GBS角色编码不能为空"),
|
||||
ORG_POSITION_GBS_ROLE_SYNC_ERROR("01-08-003", "岗位关联人员GBS角色同步失败"),
|
||||
ORG_POSITION_HAS_PERSONNEL("01-08-004", "该岗位下存在人员,无法删除"),
|
||||
|
||||
// ---- 机构资质证书 ----
|
||||
ORG_QUALIFICATION_NOT_FOUND("01-09-001", "机构资质证书不存在"),
|
||||
|
|
|
|||
|
|
@ -30,4 +30,9 @@ public interface OrgDepartmentGateway {
|
|||
* 按机构ID + 部门名称集合批量精确查询未删除部门(用于导入名称解析)。
|
||||
*/
|
||||
List<OrgDepartmentEntity> listByOrgIdAndNames(Long orgId, Collection<String> deptNames);
|
||||
|
||||
/**
|
||||
* 查询部门自身及所有未删除子部门 ID(含自身)。
|
||||
*/
|
||||
List<Long> listSelfAndDescendantIds(Long deptId);
|
||||
}
|
||||
|
|
|
|||
|
|
@ -47,4 +47,14 @@ public interface OrgPersonnelGateway {
|
|||
* 按主键批量查询未删除人员(WPS 用户展示等)。
|
||||
*/
|
||||
java.util.List<OrgPersonnelEntity> listByIds(Collection<Long> ids);
|
||||
|
||||
/**
|
||||
* 指定部门集合下是否存在未删除人员(直接归属)。
|
||||
*/
|
||||
boolean existsByDeptIds(Collection<Long> deptIds);
|
||||
|
||||
/**
|
||||
* 指定岗位下是否存在未删除人员。
|
||||
*/
|
||||
boolean existsByPostId(Long postId);
|
||||
}
|
||||
|
|
|
|||
|
|
@ -4,6 +4,7 @@ import org.qinan.safetyeval.domain.entity.OrgDepartmentEntity;
|
|||
import org.qinan.safetyeval.domain.exception.BizException;
|
||||
import org.qinan.safetyeval.domain.exception.ErrorCode;
|
||||
import org.qinan.safetyeval.domain.gateway.OrgDepartmentGateway;
|
||||
import org.qinan.safetyeval.domain.gateway.OrgPersonnelGateway;
|
||||
import org.qinan.safetyeval.domain.query.OrgDepartmentQuery;
|
||||
import org.qinan.safetyeval.domain.query.PageResult;
|
||||
|
||||
|
|
@ -23,6 +24,9 @@ public class OrgDepartmentDomainService {
|
|||
@Resource
|
||||
private OrgDepartmentGateway orgDepartmentGateway;
|
||||
|
||||
@Resource
|
||||
private OrgPersonnelGateway orgPersonnelGateway;
|
||||
|
||||
public OrgDepartmentEntity add(OrgDepartmentEntity entity) {
|
||||
return orgDepartmentGateway.save(entity);
|
||||
}
|
||||
|
|
@ -44,6 +48,10 @@ public class OrgDepartmentDomainService {
|
|||
if (existing == null) {
|
||||
throw new BizException(ErrorCode.ORG_DEPARTMENT_NOT_FOUND);
|
||||
}
|
||||
List<Long> deptIds = orgDepartmentGateway.listSelfAndDescendantIds(id);
|
||||
if (orgPersonnelGateway.existsByDeptIds(deptIds)) {
|
||||
throw new BizException(ErrorCode.ORG_DEPARTMENT_HAS_PERSONNEL);
|
||||
}
|
||||
orgDepartmentGateway.delete(id);
|
||||
}
|
||||
|
||||
|
|
|
|||
|
|
@ -3,6 +3,7 @@ package org.qinan.safetyeval.domain.service;
|
|||
import org.qinan.safetyeval.domain.entity.OrgPositionEntity;
|
||||
import org.qinan.safetyeval.domain.exception.BizException;
|
||||
import org.qinan.safetyeval.domain.exception.ErrorCode;
|
||||
import org.qinan.safetyeval.domain.gateway.OrgPersonnelGateway;
|
||||
import org.qinan.safetyeval.domain.gateway.OrgPositionGateway;
|
||||
import org.qinan.safetyeval.domain.query.OrgPositionQuery;
|
||||
import org.qinan.safetyeval.domain.query.PageResult;
|
||||
|
|
@ -21,6 +22,9 @@ public class OrgPositionDomainService {
|
|||
@Resource
|
||||
private OrgPositionGateway orgPositionGateway;
|
||||
|
||||
@Resource
|
||||
private OrgPersonnelGateway orgPersonnelGateway;
|
||||
|
||||
public OrgPositionEntity add(OrgPositionEntity entity) {
|
||||
return orgPositionGateway.save(entity);
|
||||
}
|
||||
|
|
@ -42,6 +46,9 @@ public class OrgPositionDomainService {
|
|||
if (existing == null) {
|
||||
throw new BizException(ErrorCode.ORG_POSITION_NOT_FOUND);
|
||||
}
|
||||
if (orgPersonnelGateway.existsByPostId(id)) {
|
||||
throw new BizException(ErrorCode.ORG_POSITION_HAS_PERSONNEL);
|
||||
}
|
||||
orgPositionGateway.delete(id);
|
||||
}
|
||||
|
||||
|
|
|
|||
|
|
@ -0,0 +1,16 @@
|
|||
package org.qinan.safetyeval.infrastructure.dataobject;
|
||||
|
||||
import lombok.Data;
|
||||
|
||||
/**
|
||||
* 部门人员数量统计结果
|
||||
*
|
||||
* @author safety-eval
|
||||
*/
|
||||
@Data
|
||||
public class OrgPersonnelDeptCountDO {
|
||||
|
||||
private Long deptId;
|
||||
|
||||
private Integer personCount;
|
||||
}
|
||||
|
|
@ -15,8 +15,13 @@ import org.springframework.stereotype.Component;
|
|||
import org.springframework.util.StringUtils;
|
||||
|
||||
import javax.annotation.Resource;
|
||||
import java.util.ArrayDeque;
|
||||
import java.util.ArrayList;
|
||||
import java.util.Collection;
|
||||
import java.util.Collections;
|
||||
import java.util.HashMap;
|
||||
import java.util.List;
|
||||
import java.util.Map;
|
||||
import java.util.stream.Collectors;
|
||||
|
||||
/**
|
||||
|
|
@ -97,6 +102,49 @@ public class OrgDepartmentGatewayImpl implements OrgDepartmentGateway {
|
|||
.collect(Collectors.toList());
|
||||
}
|
||||
|
||||
@Override
|
||||
public List<Long> listSelfAndDescendantIds(Long deptId) {
|
||||
if (deptId == null) {
|
||||
return Collections.emptyList();
|
||||
}
|
||||
OrgDepartmentDO root = orgDepartmentMapper.selectById(deptId);
|
||||
if (root == null) {
|
||||
return Collections.emptyList();
|
||||
}
|
||||
LambdaQueryWrapper<OrgDepartmentDO> wrapper = new LambdaQueryWrapper<>();
|
||||
wrapper.eq(OrgDepartmentDO::getDeleteEnum, "false");
|
||||
if (root.getOrgId() != null) {
|
||||
wrapper.eq(OrgDepartmentDO::getOrgId, root.getOrgId());
|
||||
}
|
||||
wrapper.select(OrgDepartmentDO::getId, OrgDepartmentDO::getParentId);
|
||||
List<OrgDepartmentDO> all = orgDepartmentMapper.selectList(wrapper);
|
||||
|
||||
Map<Long, List<Long>> childrenMap = new HashMap<>();
|
||||
for (OrgDepartmentDO item : all) {
|
||||
if (item.getId() == null) {
|
||||
continue;
|
||||
}
|
||||
Long parentId = item.getParentId();
|
||||
if (parentId == null) {
|
||||
continue;
|
||||
}
|
||||
childrenMap.computeIfAbsent(parentId, k -> new ArrayList<>()).add(item.getId());
|
||||
}
|
||||
|
||||
List<Long> result = new ArrayList<>();
|
||||
ArrayDeque<Long> queue = new ArrayDeque<>();
|
||||
queue.add(deptId);
|
||||
while (!queue.isEmpty()) {
|
||||
Long current = queue.poll();
|
||||
result.add(current);
|
||||
List<Long> children = childrenMap.get(current);
|
||||
if (children != null) {
|
||||
queue.addAll(children);
|
||||
}
|
||||
}
|
||||
return result;
|
||||
}
|
||||
|
||||
private LambdaQueryWrapper<OrgDepartmentDO> buildQueryWrapper(OrgDepartmentQuery query) {
|
||||
LambdaQueryWrapper<OrgDepartmentDO> wrapper = new LambdaQueryWrapper<>();
|
||||
wrapper.eq(OrgDepartmentDO::getDeleteEnum, "false");
|
||||
|
|
|
|||
|
|
@ -215,5 +215,29 @@ public class OrgPersonnelGatewayImpl implements OrgPersonnelGateway {
|
|||
return orgPersonnelDoConvertor.converDosToEes(orgPersonnelMapper.selectList(wrapper));
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean existsByDeptIds(Collection<Long> deptIds) {
|
||||
if (deptIds == null || deptIds.isEmpty()) {
|
||||
return false;
|
||||
}
|
||||
LambdaQueryWrapper<OrgPersonnelDO> wrapper = new LambdaQueryWrapper<>();
|
||||
wrapper.eq(OrgPersonnelDO::getDeleteEnum, "false");
|
||||
wrapper.in(OrgPersonnelDO::getDeptId, deptIds);
|
||||
wrapper.last("LIMIT 1");
|
||||
return orgPersonnelMapper.selectCount(wrapper) > 0;
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean existsByPostId(Long postId) {
|
||||
if (postId == null) {
|
||||
return false;
|
||||
}
|
||||
LambdaQueryWrapper<OrgPersonnelDO> wrapper = new LambdaQueryWrapper<>();
|
||||
wrapper.eq(OrgPersonnelDO::getDeleteEnum, "false");
|
||||
wrapper.eq(OrgPersonnelDO::getPostId, postId);
|
||||
wrapper.last("LIMIT 1");
|
||||
return orgPersonnelMapper.selectCount(wrapper) > 0;
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
|
|
|
|||
|
|
@ -9,6 +9,7 @@ import org.qinan.safetyeval.client.co.IndustryProfessionalPersonCo;
|
|||
import org.qinan.safetyeval.client.co.QualFilingPersonnelInfoCO;
|
||||
import org.qinan.safetyeval.client.dto.OrgFilingPersonnelPageQuery;
|
||||
import org.qinan.safetyeval.infrastructure.dataobject.OrgPersonnelDO;
|
||||
import org.qinan.safetyeval.infrastructure.dataobject.OrgPersonnelDeptCountDO;
|
||||
import org.qinan.safetyeval.infrastructure.persistence.domainobject.OrgPersonnelLeaderCountDO;
|
||||
|
||||
import java.util.List;
|
||||
|
|
@ -16,6 +17,14 @@ import java.util.List;
|
|||
@Mapper
|
||||
public interface OrgPersonnelMapper extends BaseMapper<OrgPersonnelDO> {
|
||||
|
||||
/**
|
||||
* 按部门批量统计未删除人员数量(直接归属,不含下级部门汇总)
|
||||
*
|
||||
* @param orgId 机构ID
|
||||
* @return 各部门人员数量
|
||||
*/
|
||||
List<OrgPersonnelDeptCountDO> countPersonGroupByDept(@Param("orgId") Long orgId);
|
||||
|
||||
/**
|
||||
* 根据人员id列表统计技术负责人和过程控制负责人数量(按业务范围 qual_scope 分组)
|
||||
*
|
||||
|
|
|
|||
|
|
@ -41,6 +41,16 @@
|
|||
`id`, `org_id`, `dept_id`, `post_id`, `user_name`, `account`, `gender_code`, `gender_name`, `birth_date`, `id_card_no`, `current_address`, `office_address`, `education_code`, `education_name`, `graduate_school`, `major`, `employment_status_code`, `employment_status_name`, `evaluator_flag`, `delete_enum`, `remarks`, `create_name`, `update_name`, `tenant_id`, `version`, `create_time`, `update_time`, `create_id`, `update_id`, `env`
|
||||
</sql>
|
||||
|
||||
<!-- 按部门批量统计未删除人员数量(直接归属) -->
|
||||
<select id="countPersonGroupByDept" resultType="org.qinan.safetyeval.infrastructure.dataobject.OrgPersonnelDeptCountDO">
|
||||
SELECT dept_id AS deptId, COUNT(*) AS personCount
|
||||
FROM org_personnel
|
||||
WHERE delete_enum = 'false'
|
||||
AND org_id = #{orgId}
|
||||
AND dept_id IS NOT NULL
|
||||
GROUP BY dept_id
|
||||
</select>
|
||||
|
||||
<!-- 根据人员id列表统计技术负责人和过程控制负责人数量(按业务范围分组) -->
|
||||
<select id="countLeaderFlags" resultType="org.qinan.safetyeval.infrastructure.persistence.domainobject.OrgPersonnelLeaderCountDO">
|
||||
SELECT
|
||||
|
|
|
|||
Loading…
Reference in New Issue