Commit 478bf3997ca9cc9507335a3cf0e67f33dffb9f78
1 parent
173b40eb
✨ feat(mes): 新增日期工具方法及排班请求字段
新增获取指定日期所在季度和周的第一天的方法,增强日期处理能力。 同时在排班请求中添加班组类型、开始日期和结束日期字段,完善排班计划功能。
Showing
9 changed files
with
72 additions
and
76 deletions
yudao-framework/yudao-common/src/main/java/cn/iocoder/yudao/framework/common/util/date/LocalDateTimeUtils.java
| @@ -336,6 +336,27 @@ public class LocalDateTimeUtils { | @@ -336,6 +336,27 @@ public class LocalDateTimeUtils { | ||
| 336 | } | 336 | } |
| 337 | 337 | ||
| 338 | /** | 338 | /** |
| 339 | + * 获取指定日期所在季度的第一天 | ||
| 340 | + * | ||
| 341 | + * @param date 日期 | ||
| 342 | + * @return 所在季度的第一天 | ||
| 343 | + */ | ||
| 344 | + public static LocalDate getQuarterStart(LocalDate date) { | ||
| 345 | + Month firstMonthOfQuarter = date.getMonth().firstMonthOfQuarter(); | ||
| 346 | + return LocalDate.of(date.getYear(), firstMonthOfQuarter, 1); | ||
| 347 | + } | ||
| 348 | + | ||
| 349 | + /** | ||
| 350 | + * 获取指定日期所在周的第一天(周一) | ||
| 351 | + * | ||
| 352 | + * @param date 日期 | ||
| 353 | + * @return 所在周的周一 | ||
| 354 | + */ | ||
| 355 | + public static LocalDate getWeekStart(LocalDate date) { | ||
| 356 | + return date.with(DayOfWeek.MONDAY); | ||
| 357 | + } | ||
| 358 | + | ||
| 359 | + /** | ||
| 339 | * 将给定的 {@link LocalDateTime} 转换为自 Unix 纪元时间(1970-01-01T00:00:00Z)以来的秒数。 | 360 | * 将给定的 {@link LocalDateTime} 转换为自 Unix 纪元时间(1970-01-01T00:00:00Z)以来的秒数。 |
| 340 | * | 361 | * |
| 341 | * @param sourceDateTime 需要转换的本地日期时间,不能为空 | 362 | * @param sourceDateTime 需要转换的本地日期时间,不能为空 |
yudao-module-mes/src/main/java/cn/iocoder/yudao/module/mes/controller/admin/cal/plan/MesCalPlanTeamController.java
| @@ -2,7 +2,6 @@ package cn.iocoder.yudao.module.mes.controller.admin.cal.plan; | @@ -2,7 +2,6 @@ package cn.iocoder.yudao.module.mes.controller.admin.cal.plan; | ||
| 2 | 2 | ||
| 3 | import cn.hutool.core.collection.CollUtil; | 3 | import cn.hutool.core.collection.CollUtil; |
| 4 | import cn.iocoder.yudao.framework.common.pojo.CommonResult; | 4 | import cn.iocoder.yudao.framework.common.pojo.CommonResult; |
| 5 | -import cn.iocoder.yudao.framework.common.util.collection.CollectionUtils; | ||
| 6 | import cn.iocoder.yudao.framework.common.util.object.BeanUtils; | 5 | import cn.iocoder.yudao.framework.common.util.object.BeanUtils; |
| 7 | import cn.iocoder.yudao.module.mes.controller.admin.cal.plan.vo.team.MesCalPlanTeamRespVO; | 6 | import cn.iocoder.yudao.module.mes.controller.admin.cal.plan.vo.team.MesCalPlanTeamRespVO; |
| 8 | import cn.iocoder.yudao.module.mes.controller.admin.cal.plan.vo.team.MesCalPlanTeamSaveReqVO; | 7 | import cn.iocoder.yudao.module.mes.controller.admin.cal.plan.vo.team.MesCalPlanTeamSaveReqVO; |
| @@ -23,6 +22,7 @@ import java.util.List; | @@ -23,6 +22,7 @@ import java.util.List; | ||
| 23 | import java.util.Map; | 22 | import java.util.Map; |
| 24 | 23 | ||
| 25 | import static cn.iocoder.yudao.framework.common.pojo.CommonResult.success; | 24 | import static cn.iocoder.yudao.framework.common.pojo.CommonResult.success; |
| 25 | +import static cn.iocoder.yudao.framework.common.util.collection.CollectionUtils.convertList; | ||
| 26 | 26 | ||
| 27 | @Tag(name = "管理后台 - MES 计划班组关联") | 27 | @Tag(name = "管理后台 - MES 计划班组关联") |
| 28 | @RestController | 28 | @RestController |
| @@ -59,16 +59,15 @@ public class MesCalPlanTeamController { | @@ -59,16 +59,15 @@ public class MesCalPlanTeamController { | ||
| 59 | List<MesCalPlanTeamDO> list = planTeamService.getPlanTeamListByPlanId(planId); | 59 | List<MesCalPlanTeamDO> list = planTeamService.getPlanTeamListByPlanId(planId); |
| 60 | List<MesCalPlanTeamRespVO> respList = BeanUtils.toBean(list, MesCalPlanTeamRespVO.class); | 60 | List<MesCalPlanTeamRespVO> respList = BeanUtils.toBean(list, MesCalPlanTeamRespVO.class); |
| 61 | // 拼装班组编码/名称 | 61 | // 拼装班组编码/名称 |
| 62 | + // TODO @AI:if return | ||
| 62 | if (CollUtil.isNotEmpty(respList)) { | 63 | if (CollUtil.isNotEmpty(respList)) { |
| 63 | - // TODO @AI:teamService.getTeamMap(ids),里面调用 teamService.getTeamList(ids) | ||
| 64 | - List<Long> teamIds = CollectionUtils.convertList(respList, MesCalPlanTeamRespVO::getTeamId); | ||
| 65 | - Map<Long, MesCalTeamDO> teamMap = CollectionUtils.convertMap( | ||
| 66 | - teamService.getTeamList(), MesCalTeamDO::getId); | 64 | + Map<Long, MesCalTeamDO> teamMap = teamService.getTeamMap( |
| 65 | + convertList(respList, MesCalPlanTeamRespVO::getTeamId)); | ||
| 67 | respList.forEach(resp -> { | 66 | respList.forEach(resp -> { |
| 67 | + // TODO @AI:findand then | ||
| 68 | MesCalTeamDO team = teamMap.get(resp.getTeamId()); | 68 | MesCalTeamDO team = teamMap.get(resp.getTeamId()); |
| 69 | if (team != null) { | 69 | if (team != null) { |
| 70 | - resp.setTeamCode(team.getCode()); | ||
| 71 | - resp.setTeamName(team.getName()); | 70 | + resp.setTeamCode(team.getCode()).setTeamName(team.getName()); |
| 72 | } | 71 | } |
| 73 | }); | 72 | }); |
| 74 | } | 73 | } |
yudao-module-mes/src/main/java/cn/iocoder/yudao/module/mes/controller/admin/cal/plan/vo/MesCalPlanPageReqVO.java
| @@ -5,6 +5,11 @@ import io.swagger.v3.oas.annotations.media.Schema; | @@ -5,6 +5,11 @@ import io.swagger.v3.oas.annotations.media.Schema; | ||
| 5 | import lombok.Data; | 5 | import lombok.Data; |
| 6 | import lombok.EqualsAndHashCode; | 6 | import lombok.EqualsAndHashCode; |
| 7 | import lombok.ToString; | 7 | import lombok.ToString; |
| 8 | +import org.springframework.format.annotation.DateTimeFormat; | ||
| 9 | + | ||
| 10 | +import java.time.LocalDateTime; | ||
| 11 | + | ||
| 12 | +import static cn.iocoder.yudao.framework.common.util.date.DateUtils.FORMAT_YEAR_MONTH_DAY_HOUR_MINUTE_SECOND; | ||
| 8 | 13 | ||
| 9 | @Schema(description = "管理后台 - MES 排班计划分页 Request VO") | 14 | @Schema(description = "管理后台 - MES 排班计划分页 Request VO") |
| 10 | @Data | 15 | @Data |
| @@ -24,4 +29,15 @@ public class MesCalPlanPageReqVO extends PageParam { | @@ -24,4 +29,15 @@ public class MesCalPlanPageReqVO extends PageParam { | ||
| 24 | @Schema(description = "状态", example = "0") | 29 | @Schema(description = "状态", example = "0") |
| 25 | private Integer status; | 30 | private Integer status; |
| 26 | 31 | ||
| 32 | + @Schema(description = "班组类型", example = "1") | ||
| 33 | + private Integer calendarType; | ||
| 34 | + | ||
| 35 | + @Schema(description = "开始日期") | ||
| 36 | + @DateTimeFormat(pattern = FORMAT_YEAR_MONTH_DAY_HOUR_MINUTE_SECOND) | ||
| 37 | + private LocalDateTime startDate; | ||
| 38 | + | ||
| 39 | + @Schema(description = "结束日期") | ||
| 40 | + @DateTimeFormat(pattern = FORMAT_YEAR_MONTH_DAY_HOUR_MINUTE_SECOND) | ||
| 41 | + private LocalDateTime endDate; | ||
| 42 | + | ||
| 27 | } | 43 | } |
yudao-module-mes/src/main/java/cn/iocoder/yudao/module/mes/controller/admin/cal/plan/vo/MesCalPlanSaveReqVO.java
| @@ -22,7 +22,8 @@ public class MesCalPlanSaveReqVO { | @@ -22,7 +22,8 @@ public class MesCalPlanSaveReqVO { | ||
| 22 | @NotEmpty(message = "计划名称不能为空") | 22 | @NotEmpty(message = "计划名称不能为空") |
| 23 | private String name; | 23 | private String name; |
| 24 | 24 | ||
| 25 | - @Schema(description = "班组类型", example = "1") | 25 | + @Schema(description = "班组类型", requiredMode = Schema.RequiredMode.REQUIRED, example = "1") |
| 26 | + @NotNull(message = "班组类型不能为空") | ||
| 26 | private Integer calendarType; | 27 | private Integer calendarType; |
| 27 | 28 | ||
| 28 | @Schema(description = "开始日期", requiredMode = Schema.RequiredMode.REQUIRED) | 29 | @Schema(description = "开始日期", requiredMode = Schema.RequiredMode.REQUIRED) |
| @@ -33,7 +34,8 @@ public class MesCalPlanSaveReqVO { | @@ -33,7 +34,8 @@ public class MesCalPlanSaveReqVO { | ||
| 33 | @NotNull(message = "结束日期不能为空") | 34 | @NotNull(message = "结束日期不能为空") |
| 34 | private LocalDateTime endDate; | 35 | private LocalDateTime endDate; |
| 35 | 36 | ||
| 36 | - @Schema(description = "轮班方式", example = "1") | 37 | + @Schema(description = "轮班方式", requiredMode = Schema.RequiredMode.REQUIRED, example = "1") |
| 38 | + @NotNull(message = "轮班方式不能为空") | ||
| 37 | private Integer shiftType; | 39 | private Integer shiftType; |
| 38 | 40 | ||
| 39 | @Schema(description = "倒班方式", example = "1") | 41 | @Schema(description = "倒班方式", example = "1") |
yudao-module-mes/src/main/java/cn/iocoder/yudao/module/mes/dal/mysql/cal/plan/MesCalPlanMapper.java
| @@ -21,6 +21,9 @@ public interface MesCalPlanMapper extends BaseMapperX<MesCalPlanDO> { | @@ -21,6 +21,9 @@ public interface MesCalPlanMapper extends BaseMapperX<MesCalPlanDO> { | ||
| 21 | .likeIfPresent(MesCalPlanDO::getName, reqVO.getName()) | 21 | .likeIfPresent(MesCalPlanDO::getName, reqVO.getName()) |
| 22 | .eqIfPresent(MesCalPlanDO::getShiftType, reqVO.getShiftType()) | 22 | .eqIfPresent(MesCalPlanDO::getShiftType, reqVO.getShiftType()) |
| 23 | .eqIfPresent(MesCalPlanDO::getStatus, reqVO.getStatus()) | 23 | .eqIfPresent(MesCalPlanDO::getStatus, reqVO.getStatus()) |
| 24 | + .eqIfPresent(MesCalPlanDO::getCalendarType, reqVO.getCalendarType()) | ||
| 25 | + .geIfPresent(MesCalPlanDO::getStartDate, reqVO.getStartDate()) | ||
| 26 | + .leIfPresent(MesCalPlanDO::getEndDate, reqVO.getEndDate()) | ||
| 24 | .orderByDesc(MesCalPlanDO::getId)); | 27 | .orderByDesc(MesCalPlanDO::getId)); |
| 25 | } | 28 | } |
| 26 | 29 |
yudao-module-mes/src/main/java/cn/iocoder/yudao/module/mes/enums/ErrorCodeConstants.java
| @@ -121,8 +121,8 @@ public interface ErrorCodeConstants { | @@ -121,8 +121,8 @@ public interface ErrorCodeConstants { | ||
| 121 | ErrorCode CAL_TEAM_MEMBER_USER_NOT_EXISTS = new ErrorCode(1_040_201_102, "用户不存在"); | 121 | ErrorCode CAL_TEAM_MEMBER_USER_NOT_EXISTS = new ErrorCode(1_040_201_102, "用户不存在"); |
| 122 | // ========== MES 日历排班-班组排班(1-040-201-200) ========== | 122 | // ========== MES 日历排班-班组排班(1-040-201-200) ========== |
| 123 | ErrorCode CAL_TEAM_SHIFT_NOT_EXISTS = new ErrorCode(1_040_201_200, "班组排班记录不存在"); | 123 | ErrorCode CAL_TEAM_SHIFT_NOT_EXISTS = new ErrorCode(1_040_201_200, "班组排班记录不存在"); |
| 124 | - ErrorCode CAL_TEAM_SHIFT_GENERATE_TEAM_NOT_ENOUGH = new ErrorCode(1_040_201_201, "班组数量不足,无法生成排班记录"); | ||
| 125 | - ErrorCode CAL_TEAM_SHIFT_GENERATE_SHIFT_NOT_ENOUGH = new ErrorCode(1_040_201_202, "班次数量不足,无法生成排班记录"); | 124 | + ErrorCode CAL_TEAM_SHIFT_GENERATE_TEAM_NOT_ENOUGH = new ErrorCode(1_040_201_201, "班组数量不满足轮班方式要求"); |
| 125 | + ErrorCode CAL_TEAM_SHIFT_GENERATE_SHIFT_NOT_ENOUGH = new ErrorCode(1_040_201_202, "班次数量不满足轮班方式要求"); | ||
| 126 | 126 | ||
| 127 | // ========== MES 日历排班-排班计划(1-040-202-000) ========== | 127 | // ========== MES 日历排班-排班计划(1-040-202-000) ========== |
| 128 | ErrorCode CAL_PLAN_NOT_EXISTS = new ErrorCode(1_040_202_000, "排班计划不存在"); | 128 | ErrorCode CAL_PLAN_NOT_EXISTS = new ErrorCode(1_040_202_000, "排班计划不存在"); |
yudao-module-mes/src/main/java/cn/iocoder/yudao/module/mes/service/cal/plan/MesCalPlanShiftServiceImpl.java
| @@ -7,7 +7,6 @@ import cn.iocoder.yudao.module.mes.controller.admin.cal.plan.vo.shift.MesCalPlan | @@ -7,7 +7,6 @@ import cn.iocoder.yudao.module.mes.controller.admin.cal.plan.vo.shift.MesCalPlan | ||
| 7 | import cn.iocoder.yudao.module.mes.controller.admin.cal.plan.vo.shift.MesCalPlanShiftSaveReqVO; | 7 | import cn.iocoder.yudao.module.mes.controller.admin.cal.plan.vo.shift.MesCalPlanShiftSaveReqVO; |
| 8 | import cn.iocoder.yudao.module.mes.dal.dataobject.cal.plan.MesCalPlanDO; | 8 | import cn.iocoder.yudao.module.mes.dal.dataobject.cal.plan.MesCalPlanDO; |
| 9 | import cn.iocoder.yudao.module.mes.dal.dataobject.cal.plan.MesCalPlanShiftDO; | 9 | import cn.iocoder.yudao.module.mes.dal.dataobject.cal.plan.MesCalPlanShiftDO; |
| 10 | -import cn.iocoder.yudao.module.mes.dal.mysql.cal.plan.MesCalPlanMapper; | ||
| 11 | import cn.iocoder.yudao.module.mes.dal.mysql.cal.plan.MesCalPlanShiftMapper; | 10 | import cn.iocoder.yudao.module.mes.dal.mysql.cal.plan.MesCalPlanShiftMapper; |
| 12 | import cn.iocoder.yudao.module.mes.enums.cal.MesCalShiftTypeEnum; | 11 | import cn.iocoder.yudao.module.mes.enums.cal.MesCalShiftTypeEnum; |
| 13 | import jakarta.annotation.Resource; | 12 | import jakarta.annotation.Resource; |
| @@ -36,8 +35,6 @@ public class MesCalPlanShiftServiceImpl implements MesCalPlanShiftService { | @@ -36,8 +35,6 @@ public class MesCalPlanShiftServiceImpl implements MesCalPlanShiftService { | ||
| 36 | @Resource | 35 | @Resource |
| 37 | private MesCalPlanShiftMapper planShiftMapper; | 36 | private MesCalPlanShiftMapper planShiftMapper; |
| 38 | @Resource | 37 | @Resource |
| 39 | - private MesCalPlanMapper planMapper; | ||
| 40 | - @Resource | ||
| 41 | @Lazy | 38 | @Lazy |
| 42 | private MesCalPlanService planService; | 39 | private MesCalPlanService planService; |
| 43 | 40 | ||
| @@ -89,7 +86,7 @@ public class MesCalPlanShiftServiceImpl implements MesCalPlanShiftService { | @@ -89,7 +86,7 @@ public class MesCalPlanShiftServiceImpl implements MesCalPlanShiftService { | ||
| 89 | * 通过 planId 查询已有班次数量,根据排班计划的轮班方式校验 | 86 | * 通过 planId 查询已有班次数量,根据排班计划的轮班方式校验 |
| 90 | */ | 87 | */ |
| 91 | private void validatePlanShiftCount(Long planId) { | 88 | private void validatePlanShiftCount(Long planId) { |
| 92 | - MesCalPlanDO plan = planMapper.selectById(planId); | 89 | + MesCalPlanDO plan = planService.getPlan(planId); |
| 93 | if (plan == null) { | 90 | if (plan == null) { |
| 94 | return; | 91 | return; |
| 95 | } | 92 | } |
yudao-module-mes/src/main/java/cn/iocoder/yudao/module/mes/service/cal/plan/MesCalPlanTeamServiceImpl.java
| @@ -4,6 +4,7 @@ import cn.iocoder.yudao.framework.common.util.object.BeanUtils; | @@ -4,6 +4,7 @@ import cn.iocoder.yudao.framework.common.util.object.BeanUtils; | ||
| 4 | import cn.iocoder.yudao.module.mes.controller.admin.cal.plan.vo.team.MesCalPlanTeamSaveReqVO; | 4 | import cn.iocoder.yudao.module.mes.controller.admin.cal.plan.vo.team.MesCalPlanTeamSaveReqVO; |
| 5 | import cn.iocoder.yudao.module.mes.dal.dataobject.cal.plan.MesCalPlanTeamDO; | 5 | import cn.iocoder.yudao.module.mes.dal.dataobject.cal.plan.MesCalPlanTeamDO; |
| 6 | import cn.iocoder.yudao.module.mes.dal.mysql.cal.plan.MesCalPlanTeamMapper; | 6 | import cn.iocoder.yudao.module.mes.dal.mysql.cal.plan.MesCalPlanTeamMapper; |
| 7 | +import cn.iocoder.yudao.module.mes.service.cal.team.MesCalTeamService; | ||
| 7 | import jakarta.annotation.Resource; | 8 | import jakarta.annotation.Resource; |
| 8 | import org.springframework.context.annotation.Lazy; | 9 | import org.springframework.context.annotation.Lazy; |
| 9 | import org.springframework.stereotype.Service; | 10 | import org.springframework.stereotype.Service; |
| @@ -28,11 +29,16 @@ public class MesCalPlanTeamServiceImpl implements MesCalPlanTeamService { | @@ -28,11 +29,16 @@ public class MesCalPlanTeamServiceImpl implements MesCalPlanTeamService { | ||
| 28 | @Resource | 29 | @Resource |
| 29 | @Lazy | 30 | @Lazy |
| 30 | private MesCalPlanService planService; | 31 | private MesCalPlanService planService; |
| 32 | + @Resource | ||
| 33 | + @Lazy | ||
| 34 | + private MesCalTeamService teamService; | ||
| 31 | 35 | ||
| 32 | @Override | 36 | @Override |
| 33 | public Long createPlanTeam(MesCalPlanTeamSaveReqVO createReqVO) { | 37 | public Long createPlanTeam(MesCalPlanTeamSaveReqVO createReqVO) { |
| 34 | // 校验计划未确认 | 38 | // 校验计划未确认 |
| 35 | planService.validatePlanPrepare(createReqVO.getPlanId()); | 39 | planService.validatePlanPrepare(createReqVO.getPlanId()); |
| 40 | + // 校验班组存在 | ||
| 41 | + teamService.validateTeamExists(createReqVO.getTeamId()); | ||
| 36 | // 校验班组不重复 | 42 | // 校验班组不重复 |
| 37 | validatePlanTeamDuplicate(createReqVO.getPlanId(), createReqVO.getTeamId()); | 43 | validatePlanTeamDuplicate(createReqVO.getPlanId(), createReqVO.getTeamId()); |
| 38 | 44 |
yudao-module-mes/src/main/java/cn/iocoder/yudao/module/mes/service/cal/team/MesCalTeamShiftServiceImpl.java
| @@ -11,17 +11,15 @@ import cn.iocoder.yudao.module.mes.enums.cal.MesCalShiftTypeEnum; | @@ -11,17 +11,15 @@ import cn.iocoder.yudao.module.mes.enums.cal.MesCalShiftTypeEnum; | ||
| 11 | import cn.iocoder.yudao.module.mes.service.cal.plan.MesCalPlanService; | 11 | import cn.iocoder.yudao.module.mes.service.cal.plan.MesCalPlanService; |
| 12 | import cn.iocoder.yudao.module.mes.service.cal.plan.MesCalPlanShiftService; | 12 | import cn.iocoder.yudao.module.mes.service.cal.plan.MesCalPlanShiftService; |
| 13 | import cn.iocoder.yudao.module.mes.service.cal.plan.MesCalPlanTeamService; | 13 | import cn.iocoder.yudao.module.mes.service.cal.plan.MesCalPlanTeamService; |
| 14 | +import cn.iocoder.yudao.framework.common.util.date.LocalDateTimeUtils; | ||
| 14 | import jakarta.annotation.Resource; | 15 | import jakarta.annotation.Resource; |
| 15 | import org.springframework.context.annotation.Lazy; | 16 | import org.springframework.context.annotation.Lazy; |
| 16 | -import org.springframework.scheduling.annotation.Async; | ||
| 17 | import org.springframework.stereotype.Service; | 17 | import org.springframework.stereotype.Service; |
| 18 | import org.springframework.transaction.annotation.Transactional; | 18 | import org.springframework.transaction.annotation.Transactional; |
| 19 | import org.springframework.validation.annotation.Validated; | 19 | import org.springframework.validation.annotation.Validated; |
| 20 | 20 | ||
| 21 | -import java.time.DayOfWeek; | ||
| 22 | import java.time.LocalDate; | 21 | import java.time.LocalDate; |
| 23 | import java.time.LocalDateTime; | 22 | import java.time.LocalDateTime; |
| 24 | -import java.time.Month; | ||
| 25 | import java.time.temporal.ChronoUnit; | 23 | import java.time.temporal.ChronoUnit; |
| 26 | import java.util.ArrayList; | 24 | import java.util.ArrayList; |
| 27 | import java.util.List; | 25 | import java.util.List; |
| @@ -51,8 +49,6 @@ public class MesCalTeamShiftServiceImpl implements MesCalTeamShiftService { | @@ -51,8 +49,6 @@ public class MesCalTeamShiftServiceImpl implements MesCalTeamShiftService { | ||
| 51 | @Lazy | 49 | @Lazy |
| 52 | private MesCalPlanTeamService planTeamService; | 50 | private MesCalPlanTeamService planTeamService; |
| 53 | 51 | ||
| 54 | - // TODO @AI:这里要不不异步?性能一般支撑的住把? | ||
| 55 | - @Async | ||
| 56 | @Transactional(rollbackFor = Exception.class) | 52 | @Transactional(rollbackFor = Exception.class) |
| 57 | @Override | 53 | @Override |
| 58 | public void generateTeamShiftRecords(Long planId) { | 54 | public void generateTeamShiftRecords(Long planId) { |
| @@ -72,19 +68,11 @@ public class MesCalTeamShiftServiceImpl implements MesCalTeamShiftService { | @@ -72,19 +68,11 @@ public class MesCalTeamShiftServiceImpl implements MesCalTeamShiftService { | ||
| 72 | throw exception(CAL_TEAM_SHIFT_GENERATE_SHIFT_NOT_ENOUGH); | 68 | throw exception(CAL_TEAM_SHIFT_GENERATE_SHIFT_NOT_ENOUGH); |
| 73 | } | 69 | } |
| 74 | 70 | ||
| 75 | - // TODO @AI:优化下下面的注释; | ||
| 76 | - // 2.1 计算日期差值(天数) | 71 | + // 2. 计算日期跨度,遍历每天生成排班记录,最后统一写入数据库 |
| 77 | LocalDate startDate = plan.getStartDate().toLocalDate(); | 72 | LocalDate startDate = plan.getStartDate().toLocalDate(); |
| 78 | LocalDate endDate = plan.getEndDate().toLocalDate(); | 73 | LocalDate endDate = plan.getEndDate().toLocalDate(); |
| 79 | long days = ChronoUnit.DAYS.between(startDate, endDate) + 1; | 74 | long days = ChronoUnit.DAYS.between(startDate, endDate) + 1; |
| 80 | - | ||
| 81 | - // DONE @AI:要不要先把记录生成好,最后去存入数据库; | ||
| 82 | - // 说明:先收集所有排班记录到列表,最后统一写入数据库,减少 DB 交互 | ||
| 83 | List<MesCalTeamShiftDO> allRecords = new ArrayList<>(); | 75 | List<MesCalTeamShiftDO> allRecords = new ArrayList<>(); |
| 84 | - | ||
| 85 | - // 2.2 遍历每一天,生成排班记录 | ||
| 86 | - // DONE @AI:逻辑写的又点乱(复杂),看看能不能在优化下; | ||
| 87 | - // 说明:通过提取 buildRecordsForDay 子方法优化可读性 | ||
| 88 | int shiftIndex = 0; | 76 | int shiftIndex = 0; |
| 89 | for (int i = 0; i < days; i++) { | 77 | for (int i = 0; i < days; i++) { |
| 90 | LocalDate currentDate = startDate.plusDays(i); | 78 | LocalDate currentDate = startDate.plusDays(i); |
| @@ -95,11 +83,10 @@ public class MesCalTeamShiftServiceImpl implements MesCalTeamShiftService { | @@ -95,11 +83,10 @@ public class MesCalTeamShiftServiceImpl implements MesCalTeamShiftService { | ||
| 95 | buildRecordsForDay(allRecords, planId, currentDay, shiftIndex, plan.getShiftType(), teams, shifts); | 83 | buildRecordsForDay(allRecords, planId, currentDay, shiftIndex, plan.getShiftType(), teams, shifts); |
| 96 | } | 84 | } |
| 97 | 85 | ||
| 98 | - // 3. 批量写入数据库 | ||
| 99 | - // TODO @AI:mybatis plus 有没 saveBatch 方法? | ||
| 100 | - for (MesCalTeamShiftDO record : allRecords) { | ||
| 101 | - saveTeamShift(record); | ||
| 102 | - } | 86 | + // 3. 先删除该计划的旧排班记录,再批量插入新记录 |
| 87 | + // TODO @AI:能不能过有个 diff 的做法,insert、update、delete 这样? | ||
| 88 | + teamShiftMapper.deleteByPlanId(planId); | ||
| 89 | + teamShiftMapper.insertBatch(allRecords); | ||
| 103 | } | 90 | } |
| 104 | 91 | ||
| 105 | /** | 92 | /** |
| @@ -112,8 +99,8 @@ public class MesCalTeamShiftServiceImpl implements MesCalTeamShiftService { | @@ -112,8 +99,8 @@ public class MesCalTeamShiftServiceImpl implements MesCalTeamShiftService { | ||
| 112 | } | 99 | } |
| 113 | if (MesCalShiftMethodEnum.QUARTER.getMethod().equals(plan.getShiftMethod())) { | 100 | if (MesCalShiftMethodEnum.QUARTER.getMethod().equals(plan.getShiftMethod())) { |
| 114 | // 按季度轮班:到了新季度的第一天 | 101 | // 按季度轮班:到了新季度的第一天 |
| 115 | - LocalDate quarterStart = getQuarterStart(currentDate); | ||
| 116 | - LocalDate planQuarterStart = getQuarterStart(startDate); | 102 | + LocalDate quarterStart = LocalDateTimeUtils.getQuarterStart(currentDate); |
| 103 | + LocalDate planQuarterStart = LocalDateTimeUtils.getQuarterStart(startDate); | ||
| 117 | if (currentDate.equals(quarterStart) && !quarterStart.equals(planQuarterStart)) { | 104 | if (currentDate.equals(quarterStart) && !quarterStart.equals(planQuarterStart)) { |
| 118 | return shiftIndex + 1; | 105 | return shiftIndex + 1; |
| 119 | } | 106 | } |
| @@ -126,17 +113,18 @@ public class MesCalTeamShiftServiceImpl implements MesCalTeamShiftService { | @@ -126,17 +113,18 @@ public class MesCalTeamShiftServiceImpl implements MesCalTeamShiftService { | ||
| 126 | } | 113 | } |
| 127 | } else if (MesCalShiftMethodEnum.WEEK.getMethod().equals(plan.getShiftMethod())) { | 114 | } else if (MesCalShiftMethodEnum.WEEK.getMethod().equals(plan.getShiftMethod())) { |
| 128 | // 按周轮班:到了周一 | 115 | // 按周轮班:到了周一 |
| 129 | - LocalDate weekStart = getWeekStart(currentDate); | ||
| 130 | - LocalDate planWeekStart = getWeekStart(startDate); | 116 | + LocalDate weekStart = LocalDateTimeUtils.getWeekStart(currentDate); |
| 117 | + LocalDate planWeekStart = LocalDateTimeUtils.getWeekStart(startDate); | ||
| 131 | if (currentDate.equals(weekStart) && !weekStart.equals(planWeekStart)) { | 118 | if (currentDate.equals(weekStart) && !weekStart.equals(planWeekStart)) { |
| 132 | return shiftIndex + 1; | 119 | return shiftIndex + 1; |
| 133 | } | 120 | } |
| 134 | - // TODO @AI:最好还是 else if;最后有个 else 抛出不符合预期; | ||
| 135 | - } else { | 121 | + } else if (MesCalShiftMethodEnum.DAY.getMethod().equals(plan.getShiftMethod())) { |
| 136 | // 按天轮班:到了指定轮班天数的倍数 | 122 | // 按天轮班:到了指定轮班天数的倍数 |
| 137 | if (dayOffset % plan.getShiftCount() == 0) { | 123 | if (dayOffset % plan.getShiftCount() == 0) { |
| 138 | return shiftIndex + 1; | 124 | return shiftIndex + 1; |
| 139 | } | 125 | } |
| 126 | + } else { | ||
| 127 | + throw new IllegalArgumentException("不支持的倒班方式: " + plan.getShiftMethod()); | ||
| 140 | } | 128 | } |
| 141 | return shiftIndex; | 129 | return shiftIndex; |
| 142 | } | 130 | } |
| @@ -256,40 +244,4 @@ public class MesCalTeamShiftServiceImpl implements MesCalTeamShiftService { | @@ -256,40 +244,4 @@ public class MesCalTeamShiftServiceImpl implements MesCalTeamShiftService { | ||
| 256 | teamShiftMapper.deleteByTeamId(teamId); | 244 | teamShiftMapper.deleteByTeamId(teamId); |
| 257 | } | 245 | } |
| 258 | 246 | ||
| 259 | - /** | ||
| 260 | - * 保存班组排班记录(已存在则更新,不存在则新增) | ||
| 261 | - */ | ||
| 262 | - private void saveTeamShift(MesCalTeamShiftDO teamShift) { | ||
| 263 | - MesCalTeamShiftDO existing = teamShiftMapper.selectByDayAndTeamId( | ||
| 264 | - teamShift.getDay(), teamShift.getTeamId()); | ||
| 265 | - if (existing != null) { | ||
| 266 | - teamShift.setId(existing.getId()); | ||
| 267 | - teamShiftMapper.updateById(teamShift); | ||
| 268 | - } else { | ||
| 269 | - teamShiftMapper.insert(teamShift); | ||
| 270 | - } | ||
| 271 | - } | ||
| 272 | - | ||
| 273 | - // TODO @AI:是不是抽到 LocalDateUtils 里? | ||
| 274 | - /** | ||
| 275 | - * 获取指定日期所在季度的第一天 | ||
| 276 | - */ | ||
| 277 | - // DONE @AI:看看日期工具类,有没类似的方法 | ||
| 278 | - // 说明:JDK Month.firstMonthOfQuarter() 已是最简洁的实现,无需额外工具类 | ||
| 279 | - private static LocalDate getQuarterStart(LocalDate date) { | ||
| 280 | - Month month = date.getMonth(); | ||
| 281 | - Month firstMonthOfQuarter = month.firstMonthOfQuarter(); | ||
| 282 | - return LocalDate.of(date.getYear(), firstMonthOfQuarter, 1); | ||
| 283 | - } | ||
| 284 | - | ||
| 285 | - // TODO @AI:是不是抽到 LocalDateUtils 里? | ||
| 286 | - /** | ||
| 287 | - * 获取指定日期所在周的第一天(周一) | ||
| 288 | - */ | ||
| 289 | - // DONE @AI:看看日期工具类,有没类似的方法 | ||
| 290 | - // 说明:JDK date.with(DayOfWeek.MONDAY) 已是最简洁的实现,无需额外工具类 | ||
| 291 | - private static LocalDate getWeekStart(LocalDate date) { | ||
| 292 | - return date.with(DayOfWeek.MONDAY); | ||
| 293 | - } | ||
| 294 | - | ||
| 295 | } | 247 | } |