Merge pull request 'dev-ui' (#1) from dev-ui into dev
Reviewed-on: #1
This commit was merged in pull request #1.
This commit is contained in:
@@ -5,6 +5,7 @@ import com.ruoyi.info.collection.domain.dto.CcdiStaffRecruitmentAddDTO;
|
||||
import com.ruoyi.info.collection.domain.dto.CcdiStaffRecruitmentEditDTO;
|
||||
import com.ruoyi.info.collection.domain.dto.CcdiStaffRecruitmentQueryDTO;
|
||||
import com.ruoyi.info.collection.domain.excel.CcdiStaffRecruitmentExcel;
|
||||
import com.ruoyi.info.collection.domain.excel.CcdiStaffRecruitmentWorkExcel;
|
||||
import com.ruoyi.info.collection.domain.vo.CcdiStaffRecruitmentVO;
|
||||
import com.ruoyi.info.collection.domain.vo.ImportResultVO;
|
||||
import com.ruoyi.info.collection.domain.vo.ImportStatusVO;
|
||||
@@ -128,6 +129,15 @@ public class CcdiStaffRecruitmentController extends BaseController {
|
||||
EasyExcelUtil.importTemplateWithDictDropdown(response, CcdiStaffRecruitmentExcel.class, "员工招聘信息");
|
||||
}
|
||||
|
||||
/**
|
||||
* 下载历史工作经历导入模板
|
||||
*/
|
||||
@Operation(summary = "下载历史工作经历导入模板")
|
||||
@PostMapping("/workImportTemplate")
|
||||
public void workImportTemplate(HttpServletResponse response) {
|
||||
EasyExcelUtil.importTemplateWithDictDropdown(response, CcdiStaffRecruitmentWorkExcel.class, "历史工作经历");
|
||||
}
|
||||
|
||||
/**
|
||||
* 异步导入招聘信息
|
||||
*/
|
||||
@@ -155,6 +165,31 @@ public class CcdiStaffRecruitmentController extends BaseController {
|
||||
return AjaxResult.success("导入任务已提交,正在后台处理", result);
|
||||
}
|
||||
|
||||
/**
|
||||
* 异步导入历史工作经历
|
||||
*/
|
||||
@Operation(summary = "异步导入历史工作经历")
|
||||
@Parameter(name = "file", description = "导入文件", required = true)
|
||||
@PreAuthorize("@ss.hasPermi('ccdi:staffRecruitment:import')")
|
||||
@Log(title = "员工招聘历史工作经历", businessType = BusinessType.IMPORT)
|
||||
@PostMapping("/importWorkData")
|
||||
public AjaxResult importWorkData(@Parameter(description = "导入文件") MultipartFile file) throws Exception {
|
||||
List<CcdiStaffRecruitmentWorkExcel> list = EasyExcelUtil.importExcel(file.getInputStream(), CcdiStaffRecruitmentWorkExcel.class);
|
||||
|
||||
if (list == null || list.isEmpty()) {
|
||||
return error("至少需要一条数据");
|
||||
}
|
||||
|
||||
String taskId = recruitmentService.importRecruitmentWork(list);
|
||||
|
||||
ImportResultVO result = new ImportResultVO();
|
||||
result.setTaskId(taskId);
|
||||
result.setStatus("PROCESSING");
|
||||
result.setMessage("历史工作经历导入任务已提交,正在后台处理");
|
||||
|
||||
return AjaxResult.success("历史工作经历导入任务已提交,正在后台处理", result);
|
||||
}
|
||||
|
||||
/**
|
||||
* 查询导入状态
|
||||
*/
|
||||
|
||||
@@ -22,7 +22,7 @@ public class CcdiStaffRecruitment implements Serializable {
|
||||
@Serial
|
||||
private static final long serialVersionUID = 1L;
|
||||
|
||||
/** 招聘项目编号 */
|
||||
/** 招聘记录编号 */
|
||||
@TableId(type = IdType.INPUT)
|
||||
private String recruitId;
|
||||
|
||||
@@ -41,6 +41,9 @@ public class CcdiStaffRecruitment implements Serializable {
|
||||
/** 应聘人员姓名 */
|
||||
private String candName;
|
||||
|
||||
/** 招聘类型:SOCIAL-社招,CAMPUS-校招 */
|
||||
private String recruitType;
|
||||
|
||||
/** 应聘人员学历 */
|
||||
private String candEdu;
|
||||
|
||||
|
||||
@@ -0,0 +1,76 @@
|
||||
package com.ruoyi.info.collection.domain;
|
||||
|
||||
import com.baomidou.mybatisplus.annotation.FieldFill;
|
||||
import com.baomidou.mybatisplus.annotation.IdType;
|
||||
import com.baomidou.mybatisplus.annotation.TableField;
|
||||
import com.baomidou.mybatisplus.annotation.TableId;
|
||||
import com.baomidou.mybatisplus.annotation.TableName;
|
||||
import lombok.Data;
|
||||
|
||||
import java.io.Serial;
|
||||
import java.io.Serializable;
|
||||
import java.util.Date;
|
||||
|
||||
/**
|
||||
* 招聘记录历史工作经历对象 ccdi_staff_recruitment_work
|
||||
*
|
||||
* @author ruoyi
|
||||
* @date 2026-04-15
|
||||
*/
|
||||
@Data
|
||||
@TableName("ccdi_staff_recruitment_work")
|
||||
public class CcdiStaffRecruitmentWork implements Serializable {
|
||||
|
||||
@Serial
|
||||
private static final long serialVersionUID = 1L;
|
||||
|
||||
/** 主键 */
|
||||
@TableId(type = IdType.AUTO)
|
||||
private Long id;
|
||||
|
||||
/** 关联招聘记录编号 */
|
||||
private String recruitId;
|
||||
|
||||
/** 排序号 */
|
||||
private Integer sortOrder;
|
||||
|
||||
/** 工作单位 */
|
||||
private String companyName;
|
||||
|
||||
/** 所属部门 */
|
||||
private String departmentName;
|
||||
|
||||
/** 岗位名称 */
|
||||
private String positionName;
|
||||
|
||||
/** 入职年月 */
|
||||
private String jobStartMonth;
|
||||
|
||||
/** 离职年月 */
|
||||
private String jobEndMonth;
|
||||
|
||||
/** 离职原因 */
|
||||
private String departureReason;
|
||||
|
||||
/** 主要工作内容 */
|
||||
private String workContent;
|
||||
|
||||
/** 备注 */
|
||||
private String remark;
|
||||
|
||||
/** 创建人 */
|
||||
@TableField(fill = FieldFill.INSERT)
|
||||
private String createdBy;
|
||||
|
||||
/** 创建时间 */
|
||||
@TableField(fill = FieldFill.INSERT)
|
||||
private Date createTime;
|
||||
|
||||
/** 更新人 */
|
||||
@TableField(fill = FieldFill.INSERT_UPDATE)
|
||||
private String updatedBy;
|
||||
|
||||
/** 更新时间 */
|
||||
@TableField(fill = FieldFill.INSERT_UPDATE)
|
||||
private Date updateTime;
|
||||
}
|
||||
@@ -2,6 +2,7 @@ package com.ruoyi.info.collection.domain.dto;
|
||||
|
||||
import com.ruoyi.info.collection.annotation.EnumValid;
|
||||
import com.ruoyi.info.collection.enums.AdmitStatus;
|
||||
import com.ruoyi.info.collection.enums.RecruitType;
|
||||
import jakarta.validation.constraints.NotBlank;
|
||||
import jakarta.validation.constraints.Pattern;
|
||||
import jakarta.validation.constraints.Size;
|
||||
@@ -22,9 +23,9 @@ public class CcdiStaffRecruitmentAddDTO implements Serializable {
|
||||
@Serial
|
||||
private static final long serialVersionUID = 1L;
|
||||
|
||||
/** 招聘项目编号 */
|
||||
@NotBlank(message = "招聘项目编号不能为空")
|
||||
@Size(max = 32, message = "招聘项目编号长度不能超过32个字符")
|
||||
/** 招聘记录编号 */
|
||||
@NotBlank(message = "招聘记录编号不能为空")
|
||||
@Size(max = 32, message = "招聘记录编号长度不能超过32个字符")
|
||||
private String recruitId;
|
||||
|
||||
/** 招聘项目名称 */
|
||||
@@ -51,6 +52,11 @@ public class CcdiStaffRecruitmentAddDTO implements Serializable {
|
||||
@Size(max = 20, message = "应聘人员姓名长度不能超过20个字符")
|
||||
private String candName;
|
||||
|
||||
/** 招聘类型 */
|
||||
@NotBlank(message = "招聘类型不能为空")
|
||||
@EnumValid(enumClass = RecruitType.class, message = "招聘类型状态值不合法")
|
||||
private String recruitType;
|
||||
|
||||
/** 应聘人员学历 */
|
||||
@NotBlank(message = "应聘人员学历不能为空")
|
||||
@Size(max = 20, message = "应聘人员学历长度不能超过20个字符")
|
||||
|
||||
@@ -2,6 +2,7 @@ package com.ruoyi.info.collection.domain.dto;
|
||||
|
||||
import com.ruoyi.info.collection.annotation.EnumValid;
|
||||
import com.ruoyi.info.collection.enums.AdmitStatus;
|
||||
import com.ruoyi.info.collection.enums.RecruitType;
|
||||
import jakarta.validation.constraints.NotBlank;
|
||||
import jakarta.validation.constraints.NotNull;
|
||||
import jakarta.validation.constraints.Pattern;
|
||||
@@ -23,8 +24,8 @@ public class CcdiStaffRecruitmentEditDTO implements Serializable {
|
||||
@Serial
|
||||
private static final long serialVersionUID = 1L;
|
||||
|
||||
/** 招聘项目编号 */
|
||||
@NotNull(message = "招聘项目编号不能为空")
|
||||
/** 招聘记录编号 */
|
||||
@NotNull(message = "招聘记录编号不能为空")
|
||||
private String recruitId;
|
||||
|
||||
/** 招聘项目名称 */
|
||||
@@ -46,6 +47,10 @@ public class CcdiStaffRecruitmentEditDTO implements Serializable {
|
||||
@Size(max = 20, message = "应聘人员姓名长度不能超过20个字符")
|
||||
private String candName;
|
||||
|
||||
/** 招聘类型 */
|
||||
@EnumValid(enumClass = RecruitType.class, message = "招聘类型状态值不合法")
|
||||
private String recruitType;
|
||||
|
||||
/** 应聘人员学历 */
|
||||
@Size(max = 20, message = "应聘人员学历长度不能超过20个字符")
|
||||
private String candEdu;
|
||||
|
||||
@@ -26,6 +26,9 @@ public class CcdiStaffRecruitmentQueryDTO implements Serializable {
|
||||
/** 候选人姓名(模糊查询) */
|
||||
private String candName;
|
||||
|
||||
/** 招聘类型(精确查询) */
|
||||
private String recruitType;
|
||||
|
||||
/** 证件号码(精确查询) */
|
||||
private String candId;
|
||||
|
||||
|
||||
@@ -0,0 +1,95 @@
|
||||
package com.ruoyi.info.collection.domain.excel;
|
||||
|
||||
import com.alibaba.excel.annotation.ExcelProperty;
|
||||
import com.alibaba.excel.annotation.write.style.ColumnWidth;
|
||||
import com.ruoyi.common.annotation.Required;
|
||||
import lombok.Data;
|
||||
|
||||
import java.io.Serial;
|
||||
import java.io.Serializable;
|
||||
|
||||
/**
|
||||
* 招聘记录历史工作经历Excel导入对象
|
||||
*
|
||||
* @author ruoyi
|
||||
* @date 2026-04-20
|
||||
*/
|
||||
@Data
|
||||
public class CcdiStaffRecruitmentWorkExcel implements Serializable {
|
||||
|
||||
@Serial
|
||||
private static final long serialVersionUID = 1L;
|
||||
|
||||
/** 招聘记录编号 */
|
||||
@ExcelProperty(value = "招聘记录编号", index = 0)
|
||||
@ColumnWidth(20)
|
||||
@Required
|
||||
private String recruitId;
|
||||
|
||||
/** 候选人姓名 */
|
||||
@ExcelProperty(value = "候选人姓名", index = 1)
|
||||
@ColumnWidth(15)
|
||||
@Required
|
||||
private String candName;
|
||||
|
||||
/** 招聘项目名称 */
|
||||
@ExcelProperty(value = "招聘项目名称", index = 2)
|
||||
@ColumnWidth(25)
|
||||
@Required
|
||||
private String recruitName;
|
||||
|
||||
/** 职位名称 */
|
||||
@ExcelProperty(value = "职位名称", index = 3)
|
||||
@ColumnWidth(20)
|
||||
@Required
|
||||
private String posName;
|
||||
|
||||
/** 排序号 */
|
||||
@ExcelProperty(value = "排序号", index = 4)
|
||||
@ColumnWidth(10)
|
||||
@Required
|
||||
private Integer sortOrder;
|
||||
|
||||
/** 工作单位 */
|
||||
@ExcelProperty(value = "工作单位", index = 5)
|
||||
@ColumnWidth(25)
|
||||
@Required
|
||||
private String companyName;
|
||||
|
||||
/** 所属部门 */
|
||||
@ExcelProperty(value = "所属部门", index = 6)
|
||||
@ColumnWidth(18)
|
||||
private String departmentName;
|
||||
|
||||
/** 岗位 */
|
||||
@ExcelProperty(value = "岗位", index = 7)
|
||||
@ColumnWidth(20)
|
||||
@Required
|
||||
private String positionName;
|
||||
|
||||
/** 入职年月 */
|
||||
@ExcelProperty(value = "入职年月", index = 8)
|
||||
@ColumnWidth(12)
|
||||
@Required
|
||||
private String jobStartMonth;
|
||||
|
||||
/** 离职年月 */
|
||||
@ExcelProperty(value = "离职年月", index = 9)
|
||||
@ColumnWidth(12)
|
||||
private String jobEndMonth;
|
||||
|
||||
/** 离职原因 */
|
||||
@ExcelProperty(value = "离职原因", index = 10)
|
||||
@ColumnWidth(30)
|
||||
private String departureReason;
|
||||
|
||||
/** 工作内容 */
|
||||
@ExcelProperty(value = "工作内容", index = 11)
|
||||
@ColumnWidth(35)
|
||||
private String workContent;
|
||||
|
||||
/** 备注 */
|
||||
@ExcelProperty(value = "备注", index = 12)
|
||||
@ColumnWidth(25)
|
||||
private String remark;
|
||||
}
|
||||
@@ -5,6 +5,7 @@ import lombok.Data;
|
||||
import java.io.Serial;
|
||||
import java.io.Serializable;
|
||||
import java.util.Date;
|
||||
import java.util.List;
|
||||
|
||||
/**
|
||||
* 员工招聘信息VO
|
||||
@@ -18,7 +19,7 @@ public class CcdiStaffRecruitmentVO implements Serializable {
|
||||
@Serial
|
||||
private static final long serialVersionUID = 1L;
|
||||
|
||||
/** 招聘项目编号 */
|
||||
/** 招聘记录编号 */
|
||||
private String recruitId;
|
||||
|
||||
/** 招聘项目名称 */
|
||||
@@ -36,6 +37,9 @@ public class CcdiStaffRecruitmentVO implements Serializable {
|
||||
/** 应聘人员姓名 */
|
||||
private String candName;
|
||||
|
||||
/** 招聘类型 */
|
||||
private String recruitType;
|
||||
|
||||
/** 应聘人员学历 */
|
||||
private String candEdu;
|
||||
|
||||
@@ -57,6 +61,12 @@ public class CcdiStaffRecruitmentVO implements Serializable {
|
||||
/** 录用情况描述 */
|
||||
private String admitStatusDesc;
|
||||
|
||||
/** 历史工作经历条数 */
|
||||
private Long workExperienceCount;
|
||||
|
||||
/** 历史工作经历列表 */
|
||||
private List<CcdiStaffRecruitmentWorkVO> workExperienceList;
|
||||
|
||||
/** 面试官1姓名 */
|
||||
private String interviewerName1;
|
||||
|
||||
|
||||
@@ -0,0 +1,46 @@
|
||||
package com.ruoyi.info.collection.domain.vo;
|
||||
|
||||
import lombok.Data;
|
||||
|
||||
import java.io.Serial;
|
||||
import java.io.Serializable;
|
||||
|
||||
/**
|
||||
* 招聘记录历史工作经历VO
|
||||
*
|
||||
* @author ruoyi
|
||||
* @date 2026-04-15
|
||||
*/
|
||||
@Data
|
||||
public class CcdiStaffRecruitmentWorkVO implements Serializable {
|
||||
|
||||
@Serial
|
||||
private static final long serialVersionUID = 1L;
|
||||
|
||||
/** 排序号 */
|
||||
private Integer sortOrder;
|
||||
|
||||
/** 工作单位 */
|
||||
private String companyName;
|
||||
|
||||
/** 所属部门 */
|
||||
private String departmentName;
|
||||
|
||||
/** 岗位名称 */
|
||||
private String positionName;
|
||||
|
||||
/** 入职年月 */
|
||||
private String jobStartMonth;
|
||||
|
||||
/** 离职年月 */
|
||||
private String jobEndMonth;
|
||||
|
||||
/** 离职原因 */
|
||||
private String departureReason;
|
||||
|
||||
/** 主要工作内容 */
|
||||
private String workContent;
|
||||
|
||||
/** 备注 */
|
||||
private String remark;
|
||||
}
|
||||
@@ -19,6 +19,9 @@ public class RecruitmentImportFailureVO {
|
||||
@Schema(description = "招聘项目名称")
|
||||
private String recruitName;
|
||||
|
||||
@Schema(description = "职位名称")
|
||||
private String posName;
|
||||
|
||||
@Schema(description = "应聘人员姓名")
|
||||
private String candName;
|
||||
|
||||
@@ -28,6 +31,12 @@ public class RecruitmentImportFailureVO {
|
||||
@Schema(description = "录用情况")
|
||||
private String admitStatus;
|
||||
|
||||
@Schema(description = "工作单位")
|
||||
private String companyName;
|
||||
|
||||
@Schema(description = "岗位")
|
||||
private String positionName;
|
||||
|
||||
@Schema(description = "错误信息")
|
||||
private String errorMessage;
|
||||
}
|
||||
|
||||
@@ -0,0 +1,49 @@
|
||||
package com.ruoyi.info.collection.enums;
|
||||
|
||||
import com.ruoyi.common.utils.StringUtils;
|
||||
|
||||
/**
|
||||
* 招聘类型枚举
|
||||
*
|
||||
* @author ruoyi
|
||||
*/
|
||||
public enum RecruitType {
|
||||
|
||||
/** 社招 */
|
||||
SOCIAL("SOCIAL", "社招"),
|
||||
|
||||
/** 校招 */
|
||||
CAMPUS("CAMPUS", "校招");
|
||||
|
||||
private final String code;
|
||||
private final String desc;
|
||||
|
||||
RecruitType(String code, String desc) {
|
||||
this.code = code;
|
||||
this.desc = desc;
|
||||
}
|
||||
|
||||
public String getCode() {
|
||||
return code;
|
||||
}
|
||||
|
||||
public String getDesc() {
|
||||
return desc;
|
||||
}
|
||||
|
||||
public static String getDescByCode(String code) {
|
||||
for (RecruitType type : values()) {
|
||||
if (type.code.equals(code)) {
|
||||
return type.desc;
|
||||
}
|
||||
}
|
||||
return null;
|
||||
}
|
||||
|
||||
public static String inferCode(String recruitName) {
|
||||
if (StringUtils.isNotEmpty(recruitName) && recruitName.contains("校园")) {
|
||||
return CAMPUS.code;
|
||||
}
|
||||
return SOCIAL.code;
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,13 @@
|
||||
package com.ruoyi.info.collection.mapper;
|
||||
|
||||
import com.baomidou.mybatisplus.core.mapper.BaseMapper;
|
||||
import com.ruoyi.info.collection.domain.CcdiStaffRecruitmentWork;
|
||||
|
||||
/**
|
||||
* 招聘记录历史工作经历 数据层
|
||||
*
|
||||
* @author ruoyi
|
||||
* @date 2026-04-15
|
||||
*/
|
||||
public interface CcdiStaffRecruitmentWorkMapper extends BaseMapper<CcdiStaffRecruitmentWork> {
|
||||
}
|
||||
@@ -1,6 +1,7 @@
|
||||
package com.ruoyi.info.collection.service;
|
||||
|
||||
import com.ruoyi.info.collection.domain.excel.CcdiStaffRecruitmentExcel;
|
||||
import com.ruoyi.info.collection.domain.excel.CcdiStaffRecruitmentWorkExcel;
|
||||
import com.ruoyi.info.collection.domain.vo.ImportStatusVO;
|
||||
import com.ruoyi.info.collection.domain.vo.RecruitmentImportFailureVO;
|
||||
|
||||
@@ -25,6 +26,17 @@ public interface ICcdiStaffRecruitmentImportService {
|
||||
String taskId,
|
||||
String userName);
|
||||
|
||||
/**
|
||||
* 异步导入招聘记录历史工作经历数据
|
||||
*
|
||||
* @param excelList Excel数据列表
|
||||
* @param taskId 任务ID
|
||||
* @param userName 用户名
|
||||
*/
|
||||
void importRecruitmentWorkAsync(List<CcdiStaffRecruitmentWorkExcel> excelList,
|
||||
String taskId,
|
||||
String userName);
|
||||
|
||||
/**
|
||||
* 查询导入状态
|
||||
*
|
||||
|
||||
@@ -5,6 +5,7 @@ import com.ruoyi.info.collection.domain.dto.CcdiStaffRecruitmentAddDTO;
|
||||
import com.ruoyi.info.collection.domain.dto.CcdiStaffRecruitmentEditDTO;
|
||||
import com.ruoyi.info.collection.domain.dto.CcdiStaffRecruitmentQueryDTO;
|
||||
import com.ruoyi.info.collection.domain.excel.CcdiStaffRecruitmentExcel;
|
||||
import com.ruoyi.info.collection.domain.excel.CcdiStaffRecruitmentWorkExcel;
|
||||
import com.ruoyi.info.collection.domain.vo.CcdiStaffRecruitmentVO;
|
||||
|
||||
import java.util.List;
|
||||
@@ -81,4 +82,12 @@ public interface ICcdiStaffRecruitmentService {
|
||||
* @return 结果
|
||||
*/
|
||||
String importRecruitment(List<CcdiStaffRecruitmentExcel> excelList);
|
||||
|
||||
/**
|
||||
* 导入招聘记录历史工作经历数据(异步)
|
||||
*
|
||||
* @param excelList Excel实体列表
|
||||
* @return 任务ID
|
||||
*/
|
||||
String importRecruitmentWork(List<CcdiStaffRecruitmentWorkExcel> excelList);
|
||||
}
|
||||
|
||||
@@ -3,13 +3,17 @@ package com.ruoyi.info.collection.service.impl;
|
||||
import com.alibaba.fastjson2.JSON;
|
||||
import com.baomidou.mybatisplus.core.conditions.query.LambdaQueryWrapper;
|
||||
import com.ruoyi.info.collection.domain.CcdiStaffRecruitment;
|
||||
import com.ruoyi.info.collection.domain.CcdiStaffRecruitmentWork;
|
||||
import com.ruoyi.info.collection.domain.dto.CcdiStaffRecruitmentAddDTO;
|
||||
import com.ruoyi.info.collection.domain.excel.CcdiStaffRecruitmentExcel;
|
||||
import com.ruoyi.info.collection.domain.excel.CcdiStaffRecruitmentWorkExcel;
|
||||
import com.ruoyi.info.collection.domain.vo.ImportResult;
|
||||
import com.ruoyi.info.collection.domain.vo.ImportStatusVO;
|
||||
import com.ruoyi.info.collection.domain.vo.RecruitmentImportFailureVO;
|
||||
import com.ruoyi.info.collection.enums.AdmitStatus;
|
||||
import com.ruoyi.info.collection.enums.RecruitType;
|
||||
import com.ruoyi.info.collection.mapper.CcdiStaffRecruitmentMapper;
|
||||
import com.ruoyi.info.collection.mapper.CcdiStaffRecruitmentWorkMapper;
|
||||
import com.ruoyi.info.collection.service.ICcdiStaffRecruitmentImportService;
|
||||
import com.ruoyi.info.collection.utils.ImportLogUtils;
|
||||
import com.ruoyi.common.utils.IdCardUtil;
|
||||
@@ -43,6 +47,9 @@ public class CcdiStaffRecruitmentImportServiceImpl implements ICcdiStaffRecruitm
|
||||
@Resource
|
||||
private CcdiStaffRecruitmentMapper recruitmentMapper;
|
||||
|
||||
@Resource
|
||||
private CcdiStaffRecruitmentWorkMapper recruitmentWorkMapper;
|
||||
|
||||
@Resource
|
||||
private RedisTemplate<String, Object> redisTemplate;
|
||||
|
||||
@@ -60,10 +67,10 @@ public class CcdiStaffRecruitmentImportServiceImpl implements ICcdiStaffRecruitm
|
||||
List<CcdiStaffRecruitment> newRecords = new ArrayList<>();
|
||||
List<RecruitmentImportFailureVO> failures = new ArrayList<>();
|
||||
|
||||
// 批量查询已存在的招聘项目编号
|
||||
ImportLogUtils.logBatchQueryStart(log, taskId, "已存在的招聘项目编号", excelList.size());
|
||||
// 批量查询已存在的招聘记录编号
|
||||
ImportLogUtils.logBatchQueryStart(log, taskId, "已存在的招聘记录编号", excelList.size());
|
||||
Set<String> existingRecruitIds = getExistingRecruitIds(excelList);
|
||||
ImportLogUtils.logBatchQueryComplete(log, taskId, "招聘项目编号", existingRecruitIds.size());
|
||||
ImportLogUtils.logBatchQueryComplete(log, taskId, "招聘记录编号", existingRecruitIds.size());
|
||||
|
||||
// 用于检测Excel内部的重复ID
|
||||
Set<String> excelProcessedIds = new HashSet<>();
|
||||
@@ -76,19 +83,21 @@ public class CcdiStaffRecruitmentImportServiceImpl implements ICcdiStaffRecruitm
|
||||
// 转换为AddDTO进行验证
|
||||
CcdiStaffRecruitmentAddDTO addDTO = new CcdiStaffRecruitmentAddDTO();
|
||||
BeanUtils.copyProperties(excel, addDTO);
|
||||
addDTO.setRecruitType(RecruitType.inferCode(addDTO.getRecruitName()));
|
||||
|
||||
// 验证数据
|
||||
validateRecruitmentData(addDTO, existingRecruitIds);
|
||||
|
||||
CcdiStaffRecruitment recruitment = new CcdiStaffRecruitment();
|
||||
BeanUtils.copyProperties(excel, recruitment);
|
||||
recruitment.setRecruitType(addDTO.getRecruitType());
|
||||
|
||||
if (existingRecruitIds.contains(excel.getRecruitId())) {
|
||||
// 招聘项目编号在数据库中已存在,直接报错
|
||||
throw new RuntimeException(String.format("招聘项目编号[%s]已存在,请勿重复导入", excel.getRecruitId()));
|
||||
// 招聘记录编号在数据库中已存在,直接报错
|
||||
throw new RuntimeException(String.format("招聘记录编号[%s]已存在,请勿重复导入", excel.getRecruitId()));
|
||||
} else if (excelProcessedIds.contains(excel.getRecruitId())) {
|
||||
// 招聘项目编号在Excel文件内部重复
|
||||
throw new RuntimeException(String.format("招聘项目编号[%s]在导入文件中重复,已跳过此条记录", excel.getRecruitId()));
|
||||
// 招聘记录编号在Excel文件内部重复
|
||||
throw new RuntimeException(String.format("招聘记录编号[%s]在导入文件中重复,已跳过此条记录", excel.getRecruitId()));
|
||||
} else {
|
||||
recruitment.setCreatedBy(userName);
|
||||
recruitment.setUpdatedBy(userName);
|
||||
@@ -107,7 +116,7 @@ public class CcdiStaffRecruitmentImportServiceImpl implements ICcdiStaffRecruitm
|
||||
failures.add(failure);
|
||||
|
||||
// 记录验证失败日志
|
||||
String keyData = String.format("招聘项目编号=%s, 项目名称=%s, 应聘人员=%s",
|
||||
String keyData = String.format("招聘记录编号=%s, 项目名称=%s, 应聘人员=%s",
|
||||
excel.getRecruitId(), excel.getRecruitName(), excel.getCandName());
|
||||
ImportLogUtils.logValidationError(log, taskId, i + 1, e.getMessage(), keyData);
|
||||
}
|
||||
@@ -142,7 +151,85 @@ public class CcdiStaffRecruitmentImportServiceImpl implements ICcdiStaffRecruitm
|
||||
|
||||
// 记录导入完成
|
||||
long duration = System.currentTimeMillis() - startTime;
|
||||
ImportLogUtils.logImportComplete(log, taskId, "招聘信息",
|
||||
ImportLogUtils.logImportComplete(log, taskId, "招聘信息",
|
||||
excelList.size(), result.getSuccessCount(), result.getFailureCount(), duration);
|
||||
}
|
||||
|
||||
@Override
|
||||
@Async
|
||||
@Transactional
|
||||
public void importRecruitmentWorkAsync(List<CcdiStaffRecruitmentWorkExcel> excelList,
|
||||
String taskId,
|
||||
String userName) {
|
||||
long startTime = System.currentTimeMillis();
|
||||
ImportLogUtils.logImportStart(log, taskId, "招聘历史工作经历", excelList.size(), userName);
|
||||
|
||||
List<RecruitmentImportFailureVO> failures = new ArrayList<>();
|
||||
List<CcdiStaffRecruitmentWork> validRecords = new ArrayList<>();
|
||||
Set<String> failedRecruitIds = new HashSet<>();
|
||||
Set<String> processedRecruitSortKeys = new HashSet<>();
|
||||
|
||||
Map<String, CcdiStaffRecruitment> recruitmentMap = getRecruitmentMap(excelList);
|
||||
|
||||
for (int i = 0; i < excelList.size(); i++) {
|
||||
CcdiStaffRecruitmentWorkExcel excel = excelList.get(i);
|
||||
try {
|
||||
CcdiStaffRecruitment recruitment = recruitmentMap.get(trim(excel.getRecruitId()));
|
||||
validateRecruitmentWorkData(excel, recruitment, processedRecruitSortKeys);
|
||||
|
||||
CcdiStaffRecruitmentWork work = new CcdiStaffRecruitmentWork();
|
||||
BeanUtils.copyProperties(excel, work);
|
||||
work.setRecruitId(trim(excel.getRecruitId()));
|
||||
work.setCreatedBy(userName);
|
||||
work.setUpdatedBy(userName);
|
||||
validRecords.add(work);
|
||||
|
||||
ImportLogUtils.logProgress(log, taskId, i + 1, excelList.size(),
|
||||
validRecords.size(), failures.size());
|
||||
} catch (Exception e) {
|
||||
failedRecruitIds.add(trim(excel.getRecruitId()));
|
||||
failures.add(buildWorkFailure(excel, e.getMessage()));
|
||||
String keyData = String.format("招聘记录编号=%s, 候选人=%s, 工作单位=%s",
|
||||
excel.getRecruitId(), excel.getCandName(), excel.getCompanyName());
|
||||
ImportLogUtils.logValidationError(log, taskId, i + 1, e.getMessage(), keyData);
|
||||
}
|
||||
}
|
||||
|
||||
List<CcdiStaffRecruitmentWork> importRecords = validRecords.stream()
|
||||
.filter(work -> !failedRecruitIds.contains(work.getRecruitId()))
|
||||
.toList();
|
||||
appendSkippedFailures(validRecords, failedRecruitIds, failures);
|
||||
|
||||
if (!importRecords.isEmpty()) {
|
||||
Set<String> importRecruitIds = importRecords.stream()
|
||||
.map(CcdiStaffRecruitmentWork::getRecruitId)
|
||||
.collect(Collectors.toSet());
|
||||
LambdaQueryWrapper<CcdiStaffRecruitmentWork> deleteWrapper = new LambdaQueryWrapper<>();
|
||||
deleteWrapper.in(CcdiStaffRecruitmentWork::getRecruitId, importRecruitIds);
|
||||
recruitmentWorkMapper.delete(deleteWrapper);
|
||||
|
||||
importRecords.forEach(recruitmentWorkMapper::insert);
|
||||
}
|
||||
|
||||
if (!failures.isEmpty()) {
|
||||
try {
|
||||
String failuresKey = "import:recruitment:" + taskId + ":failures";
|
||||
redisTemplate.opsForValue().set(failuresKey, failures, 7, TimeUnit.DAYS);
|
||||
ImportLogUtils.logRedisOperation(log, taskId, "保存失败记录", failures.size());
|
||||
} catch (Exception e) {
|
||||
ImportLogUtils.logRedisError(log, taskId, "保存失败记录", e);
|
||||
}
|
||||
}
|
||||
|
||||
ImportResult result = new ImportResult();
|
||||
result.setTotalCount(excelList.size());
|
||||
result.setSuccessCount(importRecords.size());
|
||||
result.setFailureCount(failures.size());
|
||||
String finalStatus = result.getFailureCount() == 0 ? "SUCCESS" : "PARTIAL_SUCCESS";
|
||||
updateImportStatus(taskId, finalStatus, result);
|
||||
|
||||
long duration = System.currentTimeMillis() - startTime;
|
||||
ImportLogUtils.logImportComplete(log, taskId, "招聘历史工作经历",
|
||||
excelList.size(), result.getSuccessCount(), result.getFailureCount(), duration);
|
||||
}
|
||||
|
||||
@@ -184,7 +271,7 @@ public class CcdiStaffRecruitmentImportServiceImpl implements ICcdiStaffRecruitm
|
||||
}
|
||||
|
||||
/**
|
||||
* 批量查询已存在的招聘项目编号
|
||||
* 批量查询已存在的招聘记录编号
|
||||
*/
|
||||
private Set<String> getExistingRecruitIds(List<CcdiStaffRecruitmentExcel> excelList) {
|
||||
List<String> recruitIds = excelList.stream()
|
||||
@@ -212,7 +299,7 @@ public class CcdiStaffRecruitmentImportServiceImpl implements ICcdiStaffRecruitm
|
||||
Set<String> existingRecruitIds) {
|
||||
// 验证必填字段
|
||||
if (StringUtils.isEmpty(addDTO.getRecruitId())) {
|
||||
throw new RuntimeException("招聘项目编号不能为空");
|
||||
throw new RuntimeException("招聘记录编号不能为空");
|
||||
}
|
||||
if (StringUtils.isEmpty(addDTO.getRecruitName())) {
|
||||
throw new RuntimeException("招聘项目名称不能为空");
|
||||
@@ -247,6 +334,9 @@ public class CcdiStaffRecruitmentImportServiceImpl implements ICcdiStaffRecruitm
|
||||
if (StringUtils.isEmpty(addDTO.getAdmitStatus())) {
|
||||
throw new RuntimeException("录用情况不能为空");
|
||||
}
|
||||
if (StringUtils.isEmpty(addDTO.getRecruitType())) {
|
||||
throw new RuntimeException("招聘类型不能为空");
|
||||
}
|
||||
|
||||
// 验证证件号码格式
|
||||
String idCardError = IdCardUtil.getErrorMessage(addDTO.getCandId());
|
||||
@@ -263,6 +353,115 @@ public class CcdiStaffRecruitmentImportServiceImpl implements ICcdiStaffRecruitm
|
||||
if (AdmitStatus.getDescByCode(addDTO.getAdmitStatus()) == null) {
|
||||
throw new RuntimeException("录用情况只能填写'录用'、'未录用'或'放弃'");
|
||||
}
|
||||
|
||||
if (RecruitType.getDescByCode(addDTO.getRecruitType()) == null) {
|
||||
throw new RuntimeException("招聘类型只能填写'SOCIAL'或'CAMPUS'");
|
||||
}
|
||||
}
|
||||
|
||||
private Map<String, CcdiStaffRecruitment> getRecruitmentMap(List<CcdiStaffRecruitmentWorkExcel> excelList) {
|
||||
List<String> recruitIds = excelList.stream()
|
||||
.map(CcdiStaffRecruitmentWorkExcel::getRecruitId)
|
||||
.map(this::trim)
|
||||
.filter(StringUtils::isNotEmpty)
|
||||
.distinct()
|
||||
.toList();
|
||||
if (recruitIds.isEmpty()) {
|
||||
return Collections.emptyMap();
|
||||
}
|
||||
List<CcdiStaffRecruitment> recruitments = recruitmentMapper.selectBatchIds(recruitIds);
|
||||
return recruitments.stream()
|
||||
.collect(Collectors.toMap(CcdiStaffRecruitment::getRecruitId, item -> item));
|
||||
}
|
||||
|
||||
private void validateRecruitmentWorkData(CcdiStaffRecruitmentWorkExcel excel,
|
||||
CcdiStaffRecruitment recruitment,
|
||||
Set<String> processedRecruitSortKeys) {
|
||||
if (StringUtils.isEmpty(trim(excel.getRecruitId()))) {
|
||||
throw new RuntimeException("招聘记录编号不能为空");
|
||||
}
|
||||
if (StringUtils.isEmpty(trim(excel.getCandName()))) {
|
||||
throw new RuntimeException("候选人姓名不能为空");
|
||||
}
|
||||
if (StringUtils.isEmpty(trim(excel.getRecruitName()))) {
|
||||
throw new RuntimeException("招聘项目名称不能为空");
|
||||
}
|
||||
if (StringUtils.isEmpty(trim(excel.getPosName()))) {
|
||||
throw new RuntimeException("职位名称不能为空");
|
||||
}
|
||||
if (excel.getSortOrder() == null || excel.getSortOrder() <= 0) {
|
||||
throw new RuntimeException("排序号不能为空且必须大于0");
|
||||
}
|
||||
if (StringUtils.isEmpty(trim(excel.getCompanyName()))) {
|
||||
throw new RuntimeException("工作单位不能为空");
|
||||
}
|
||||
if (StringUtils.isEmpty(trim(excel.getPositionName()))) {
|
||||
throw new RuntimeException("岗位不能为空");
|
||||
}
|
||||
if (StringUtils.isEmpty(trim(excel.getJobStartMonth()))) {
|
||||
throw new RuntimeException("入职年月不能为空");
|
||||
}
|
||||
validateMonth(excel.getJobStartMonth(), "入职年月");
|
||||
if (StringUtils.isNotEmpty(trim(excel.getJobEndMonth()))) {
|
||||
validateMonth(excel.getJobEndMonth(), "离职年月");
|
||||
}
|
||||
if (recruitment == null) {
|
||||
throw new RuntimeException("招聘记录编号不存在,请先维护招聘主信息");
|
||||
}
|
||||
if (!"SOCIAL".equals(recruitment.getRecruitType())) {
|
||||
throw new RuntimeException("该招聘记录不是社招,不允许导入历史工作经历");
|
||||
}
|
||||
if (!sameText(excel.getCandName(), recruitment.getCandName())) {
|
||||
throw new RuntimeException("招聘记录编号与候选人姓名不匹配");
|
||||
}
|
||||
if (!sameText(excel.getRecruitName(), recruitment.getRecruitName())) {
|
||||
throw new RuntimeException("招聘记录编号与招聘项目名称不匹配");
|
||||
}
|
||||
if (!sameText(excel.getPosName(), recruitment.getPosName())) {
|
||||
throw new RuntimeException("招聘记录编号与职位名称不匹配");
|
||||
}
|
||||
String duplicateKey = trim(excel.getRecruitId()) + "#" + excel.getSortOrder();
|
||||
if (!processedRecruitSortKeys.add(duplicateKey)) {
|
||||
throw new RuntimeException("同一招聘记录编号下排序号重复");
|
||||
}
|
||||
}
|
||||
|
||||
private void validateMonth(String value, String fieldName) {
|
||||
String month = trim(value);
|
||||
if (!month.matches("^((19|20)\\d{2})-(0[1-9]|1[0-2])$")) {
|
||||
throw new RuntimeException(fieldName + "格式不正确,应为YYYY-MM");
|
||||
}
|
||||
}
|
||||
|
||||
private boolean sameText(String first, String second) {
|
||||
return Objects.equals(trim(first), trim(second));
|
||||
}
|
||||
|
||||
private String trim(String value) {
|
||||
return value == null ? null : value.trim();
|
||||
}
|
||||
|
||||
private RecruitmentImportFailureVO buildWorkFailure(CcdiStaffRecruitmentWorkExcel excel, String errorMessage) {
|
||||
RecruitmentImportFailureVO failure = new RecruitmentImportFailureVO();
|
||||
BeanUtils.copyProperties(excel, failure);
|
||||
failure.setErrorMessage(errorMessage);
|
||||
return failure;
|
||||
}
|
||||
|
||||
private void appendSkippedFailures(List<CcdiStaffRecruitmentWork> validRecords,
|
||||
Set<String> failedRecruitIds,
|
||||
List<RecruitmentImportFailureVO> failures) {
|
||||
Set<String> appendedRecruitIds = new HashSet<>();
|
||||
for (CcdiStaffRecruitmentWork work : validRecords) {
|
||||
if (failedRecruitIds.contains(work.getRecruitId()) && appendedRecruitIds.add(work.getRecruitId())) {
|
||||
RecruitmentImportFailureVO failure = new RecruitmentImportFailureVO();
|
||||
failure.setRecruitId(work.getRecruitId());
|
||||
failure.setCompanyName(work.getCompanyName());
|
||||
failure.setPositionName(work.getPositionName());
|
||||
failure.setErrorMessage("同一招聘记录编号存在失败行,已跳过该编号下全部工作经历,避免覆盖旧数据");
|
||||
failures.add(failure);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
|
||||
@@ -1,13 +1,18 @@
|
||||
package com.ruoyi.info.collection.service.impl;
|
||||
|
||||
import com.baomidou.mybatisplus.core.conditions.query.LambdaQueryWrapper;
|
||||
import com.baomidou.mybatisplus.extension.plugins.pagination.Page;
|
||||
import com.ruoyi.info.collection.domain.CcdiStaffRecruitment;
|
||||
import com.ruoyi.info.collection.domain.CcdiStaffRecruitmentWork;
|
||||
import com.ruoyi.info.collection.domain.dto.CcdiStaffRecruitmentAddDTO;
|
||||
import com.ruoyi.info.collection.domain.dto.CcdiStaffRecruitmentEditDTO;
|
||||
import com.ruoyi.info.collection.domain.dto.CcdiStaffRecruitmentQueryDTO;
|
||||
import com.ruoyi.info.collection.domain.excel.CcdiStaffRecruitmentExcel;
|
||||
import com.ruoyi.info.collection.domain.excel.CcdiStaffRecruitmentWorkExcel;
|
||||
import com.ruoyi.info.collection.domain.vo.CcdiStaffRecruitmentVO;
|
||||
import com.ruoyi.info.collection.domain.vo.CcdiStaffRecruitmentWorkVO;
|
||||
import com.ruoyi.info.collection.enums.AdmitStatus;
|
||||
import com.ruoyi.info.collection.mapper.CcdiStaffRecruitmentWorkMapper;
|
||||
import com.ruoyi.info.collection.mapper.CcdiStaffRecruitmentMapper;
|
||||
import com.ruoyi.info.collection.service.ICcdiStaffRecruitmentImportService;
|
||||
import com.ruoyi.info.collection.service.ICcdiStaffRecruitmentService;
|
||||
@@ -19,6 +24,7 @@ import org.springframework.data.redis.core.RedisTemplate;
|
||||
import org.springframework.stereotype.Service;
|
||||
import org.springframework.transaction.annotation.Transactional;
|
||||
|
||||
import java.util.ArrayList;
|
||||
import java.util.HashMap;
|
||||
import java.util.List;
|
||||
import java.util.Map;
|
||||
@@ -37,6 +43,9 @@ public class CcdiStaffRecruitmentServiceImpl implements ICcdiStaffRecruitmentSer
|
||||
@Resource
|
||||
private CcdiStaffRecruitmentMapper recruitmentMapper;
|
||||
|
||||
@Resource
|
||||
private CcdiStaffRecruitmentWorkMapper recruitmentWorkMapper;
|
||||
|
||||
@Resource
|
||||
private ICcdiStaffRecruitmentImportService recruitmentImportService;
|
||||
|
||||
@@ -96,7 +105,7 @@ public class CcdiStaffRecruitmentServiceImpl implements ICcdiStaffRecruitmentSer
|
||||
/**
|
||||
* 查询招聘信息详情
|
||||
*
|
||||
* @param recruitId 招聘项目编号
|
||||
* @param recruitId 招聘记录编号
|
||||
* @return 招聘信息VO
|
||||
*/
|
||||
@Override
|
||||
@@ -104,6 +113,7 @@ public class CcdiStaffRecruitmentServiceImpl implements ICcdiStaffRecruitmentSer
|
||||
CcdiStaffRecruitmentVO vo = recruitmentMapper.selectRecruitmentById(recruitId);
|
||||
if (vo != null) {
|
||||
vo.setAdmitStatusDesc(AdmitStatus.getDescByCode(vo.getAdmitStatus()));
|
||||
vo.setWorkExperienceList(selectWorkExperienceList(recruitId));
|
||||
}
|
||||
return vo;
|
||||
}
|
||||
@@ -117,9 +127,9 @@ public class CcdiStaffRecruitmentServiceImpl implements ICcdiStaffRecruitmentSer
|
||||
@Override
|
||||
@Transactional
|
||||
public int insertRecruitment(CcdiStaffRecruitmentAddDTO addDTO) {
|
||||
// 检查招聘项目编号唯一性
|
||||
// 检查招聘记录编号唯一性
|
||||
if (recruitmentMapper.selectById(addDTO.getRecruitId()) != null) {
|
||||
throw new RuntimeException("该招聘项目编号已存在");
|
||||
throw new RuntimeException("该招聘记录编号已存在");
|
||||
}
|
||||
|
||||
CcdiStaffRecruitment recruitment = new CcdiStaffRecruitment();
|
||||
@@ -148,12 +158,15 @@ public class CcdiStaffRecruitmentServiceImpl implements ICcdiStaffRecruitmentSer
|
||||
/**
|
||||
* 批量删除招聘信息
|
||||
*
|
||||
* @param recruitIds 需要删除的招聘项目编号
|
||||
* @param recruitIds 需要删除的招聘记录编号
|
||||
* @return 结果
|
||||
*/
|
||||
@Override
|
||||
@Transactional
|
||||
public int deleteRecruitmentByIds(String[] recruitIds) {
|
||||
LambdaQueryWrapper<CcdiStaffRecruitmentWork> workWrapper = new LambdaQueryWrapper<>();
|
||||
workWrapper.in(CcdiStaffRecruitmentWork::getRecruitId, List.of(recruitIds));
|
||||
recruitmentWorkMapper.delete(workWrapper);
|
||||
return recruitmentMapper.deleteBatchIds(List.of(recruitIds));
|
||||
}
|
||||
|
||||
@@ -197,4 +210,56 @@ public class CcdiStaffRecruitmentServiceImpl implements ICcdiStaffRecruitmentSer
|
||||
|
||||
return taskId;
|
||||
}
|
||||
|
||||
/**
|
||||
* 导入招聘记录历史工作经历数据(异步)
|
||||
*
|
||||
* @param excelList Excel实体列表
|
||||
* @return 任务ID
|
||||
*/
|
||||
@Override
|
||||
@Transactional
|
||||
public String importRecruitmentWork(List<CcdiStaffRecruitmentWorkExcel> excelList) {
|
||||
if (StringUtils.isNull(excelList) || excelList.isEmpty()) {
|
||||
throw new RuntimeException("至少需要一条数据");
|
||||
}
|
||||
|
||||
String taskId = UUID.randomUUID().toString();
|
||||
long startTime = System.currentTimeMillis();
|
||||
String userName = SecurityUtils.getUsername();
|
||||
|
||||
String statusKey = "import:recruitment:" + taskId;
|
||||
Map<String, Object> statusData = new HashMap<>();
|
||||
statusData.put("taskId", taskId);
|
||||
statusData.put("status", "PROCESSING");
|
||||
statusData.put("totalCount", excelList.size());
|
||||
statusData.put("successCount", 0);
|
||||
statusData.put("failureCount", 0);
|
||||
statusData.put("progress", 0);
|
||||
statusData.put("startTime", startTime);
|
||||
statusData.put("message", "正在处理历史工作经历...");
|
||||
|
||||
redisTemplate.opsForHash().putAll(statusKey, statusData);
|
||||
redisTemplate.expire(statusKey, 7, TimeUnit.DAYS);
|
||||
|
||||
recruitmentImportService.importRecruitmentWorkAsync(excelList, taskId, userName);
|
||||
|
||||
return taskId;
|
||||
}
|
||||
|
||||
private List<CcdiStaffRecruitmentWorkVO> selectWorkExperienceList(String recruitId) {
|
||||
LambdaQueryWrapper<CcdiStaffRecruitmentWork> wrapper = new LambdaQueryWrapper<>();
|
||||
wrapper.eq(CcdiStaffRecruitmentWork::getRecruitId, recruitId)
|
||||
.orderByAsc(CcdiStaffRecruitmentWork::getSortOrder)
|
||||
.orderByDesc(CcdiStaffRecruitmentWork::getId);
|
||||
List<CcdiStaffRecruitmentWork> workList = recruitmentWorkMapper.selectList(wrapper);
|
||||
if (workList == null || workList.isEmpty()) {
|
||||
return new ArrayList<>();
|
||||
}
|
||||
return workList.stream().map(work -> {
|
||||
CcdiStaffRecruitmentWorkVO vo = new CcdiStaffRecruitmentWorkVO();
|
||||
BeanUtils.copyProperties(work, vo);
|
||||
return vo;
|
||||
}).toList();
|
||||
}
|
||||
}
|
||||
|
||||
@@ -12,12 +12,14 @@
|
||||
<result property="posCategory" column="pos_category"/>
|
||||
<result property="posDesc" column="pos_desc"/>
|
||||
<result property="candName" column="cand_name"/>
|
||||
<result property="recruitType" column="recruit_type"/>
|
||||
<result property="candEdu" column="cand_edu"/>
|
||||
<result property="candId" column="cand_id"/>
|
||||
<result property="candSchool" column="cand_school"/>
|
||||
<result property="candMajor" column="cand_major"/>
|
||||
<result property="candGrad" column="cand_grad"/>
|
||||
<result property="admitStatus" column="admit_status"/>
|
||||
<result property="workExperienceCount" column="work_experience_count"/>
|
||||
<result property="interviewerName1" column="interviewer_name1"/>
|
||||
<result property="interviewerId1" column="interviewer_id1"/>
|
||||
<result property="interviewerName2" column="interviewer_name2"/>
|
||||
@@ -31,44 +33,53 @@
|
||||
<!-- 分页查询招聘信息列表 -->
|
||||
<select id="selectRecruitmentPage" resultMap="CcdiStaffRecruitmentVOResult">
|
||||
SELECT
|
||||
recruit_id, recruit_name, pos_name, pos_category, pos_desc,
|
||||
cand_name, cand_edu, cand_id, cand_school, cand_major, cand_grad,
|
||||
admit_status, interviewer_name1, interviewer_id1, interviewer_name2, interviewer_id2,
|
||||
created_by, create_time, updated_by, update_time
|
||||
FROM ccdi_staff_recruitment
|
||||
r.recruit_id, r.recruit_name, r.pos_name, r.pos_category, r.pos_desc,
|
||||
r.cand_name, r.recruit_type, r.cand_edu, r.cand_id, r.cand_school, r.cand_major, r.cand_grad,
|
||||
r.admit_status, COALESCE(w.work_experience_count, 0) AS work_experience_count,
|
||||
r.interviewer_name1, r.interviewer_id1, r.interviewer_name2, r.interviewer_id2,
|
||||
r.created_by, r.create_time, r.updated_by, r.update_time
|
||||
FROM ccdi_staff_recruitment r
|
||||
LEFT JOIN (
|
||||
SELECT recruit_id, COUNT(1) AS work_experience_count
|
||||
FROM ccdi_staff_recruitment_work
|
||||
GROUP BY recruit_id
|
||||
) w ON w.recruit_id = r.recruit_id
|
||||
<where>
|
||||
<if test="query.recruitName != null and query.recruitName != ''">
|
||||
AND recruit_name LIKE CONCAT('%', #{query.recruitName}, '%')
|
||||
AND r.recruit_name LIKE CONCAT('%', #{query.recruitName}, '%')
|
||||
</if>
|
||||
<if test="query.posName != null and query.posName != ''">
|
||||
AND pos_name LIKE CONCAT('%', #{query.posName}, '%')
|
||||
AND r.pos_name LIKE CONCAT('%', #{query.posName}, '%')
|
||||
</if>
|
||||
<if test="query.candName != null and query.candName != ''">
|
||||
AND cand_name LIKE CONCAT('%', #{query.candName}, '%')
|
||||
AND r.cand_name LIKE CONCAT('%', #{query.candName}, '%')
|
||||
</if>
|
||||
<if test="query.recruitType != null and query.recruitType != ''">
|
||||
AND r.recruit_type = #{query.recruitType}
|
||||
</if>
|
||||
<if test="query.candId != null and query.candId != ''">
|
||||
AND cand_id = #{query.candId}
|
||||
AND r.cand_id = #{query.candId}
|
||||
</if>
|
||||
<if test="query.admitStatus != null and query.admitStatus != ''">
|
||||
AND admit_status = #{query.admitStatus}
|
||||
AND r.admit_status = #{query.admitStatus}
|
||||
</if>
|
||||
<if test="query.interviewerName != null and query.interviewerName != ''">
|
||||
AND (interviewer_name1 LIKE CONCAT('%', #{query.interviewerName}, '%')
|
||||
OR interviewer_name2 LIKE CONCAT('%', #{query.interviewerName}, '%'))
|
||||
AND (r.interviewer_name1 LIKE CONCAT('%', #{query.interviewerName}, '%')
|
||||
OR r.interviewer_name2 LIKE CONCAT('%', #{query.interviewerName}, '%'))
|
||||
</if>
|
||||
<if test="query.interviewerId != null and query.interviewerId != ''">
|
||||
AND (interviewer_id1 = #{query.interviewerId}
|
||||
OR interviewer_id2 = #{query.interviewerId})
|
||||
AND (r.interviewer_id1 = #{query.interviewerId}
|
||||
OR r.interviewer_id2 = #{query.interviewerId})
|
||||
</if>
|
||||
</where>
|
||||
ORDER BY create_time DESC
|
||||
ORDER BY r.create_time DESC
|
||||
</select>
|
||||
|
||||
<!-- 查询招聘信息详情 -->
|
||||
<select id="selectRecruitmentById" resultMap="CcdiStaffRecruitmentVOResult">
|
||||
SELECT
|
||||
recruit_id, recruit_name, pos_name, pos_category, pos_desc,
|
||||
cand_name, cand_edu, cand_id, cand_school, cand_major, cand_grad,
|
||||
cand_name, recruit_type, cand_edu, cand_id, cand_school, cand_major, cand_grad,
|
||||
admit_status, interviewer_name1, interviewer_id1, interviewer_name2, interviewer_id2,
|
||||
created_by, create_time, updated_by, update_time
|
||||
FROM ccdi_staff_recruitment
|
||||
@@ -79,13 +90,13 @@
|
||||
<insert id="insertBatch">
|
||||
INSERT INTO ccdi_staff_recruitment
|
||||
(recruit_id, recruit_name, pos_name, pos_category, pos_desc,
|
||||
cand_name, cand_edu, cand_id, cand_school, cand_major, cand_grad,
|
||||
cand_name, recruit_type, cand_edu, cand_id, cand_school, cand_major, cand_grad,
|
||||
admit_status, interviewer_name1, interviewer_id1, interviewer_name2, interviewer_id2,
|
||||
created_by, create_time, updated_by, update_time)
|
||||
VALUES
|
||||
<foreach collection="list" item="item" separator=",">
|
||||
(#{item.recruitId}, #{item.recruitName}, #{item.posName}, #{item.posCategory}, #{item.posDesc},
|
||||
#{item.candName}, #{item.candEdu}, #{item.candId}, #{item.candSchool}, #{item.candMajor}, #{item.candGrad},
|
||||
#{item.candName}, #{item.recruitType}, #{item.candEdu}, #{item.candId}, #{item.candSchool}, #{item.candMajor}, #{item.candGrad},
|
||||
#{item.admitStatus}, #{item.interviewerName1}, #{item.interviewerId1}, #{item.interviewerName2}, #{item.interviewerId2},
|
||||
#{item.createdBy}, NOW(), #{item.updatedBy}, NOW())
|
||||
</foreach>
|
||||
@@ -100,6 +111,7 @@
|
||||
pos_category = #{item.posCategory},
|
||||
pos_desc = #{item.posDesc},
|
||||
cand_name = #{item.candName},
|
||||
recruit_type = #{item.recruitType},
|
||||
cand_edu = #{item.candEdu},
|
||||
cand_id = #{item.candId},
|
||||
cand_school = #{item.candSchool},
|
||||
|
||||
Reference in New Issue
Block a user