|
|
@@ -0,0 +1,588 @@
|
|
|
+package org.dromara.business.service.impl;
|
|
|
+
|
|
|
+import org.dromara.business.domain.*;
|
|
|
+import org.dromara.business.domain.bo.ScheduleConfigBo;
|
|
|
+import org.dromara.business.domain.bo.ScheduleConfigRequestBo;
|
|
|
+import org.dromara.business.domain.dto.ItemsPrizeDto;
|
|
|
+import org.dromara.business.domain.enums.Weekday;
|
|
|
+import org.dromara.business.domain.vo.*;
|
|
|
+import org.dromara.business.mapper.*;
|
|
|
+import org.dromara.business.service.IScheduleConfigService;
|
|
|
+import org.dromara.common.core.domain.R;
|
|
|
+import org.dromara.common.core.utils.MapstructUtils;
|
|
|
+
|
|
|
+import org.dromara.common.mybatis.core.page.TableDataInfo;
|
|
|
+import org.dromara.common.mybatis.core.page.PageQuery;
|
|
|
+import com.baomidou.mybatisplus.extension.plugins.pagination.Page;
|
|
|
+import com.baomidou.mybatisplus.core.conditions.query.LambdaQueryWrapper;
|
|
|
+import com.baomidou.mybatisplus.core.toolkit.Wrappers;
|
|
|
+import lombok.RequiredArgsConstructor;
|
|
|
+import lombok.extern.slf4j.Slf4j;
|
|
|
+import org.springframework.stereotype.Service;
|
|
|
+import java.time.LocalDate;
|
|
|
+import java.time.LocalTime;
|
|
|
+import java.util.*;
|
|
|
+import java.util.stream.Collectors;
|
|
|
+
|
|
|
+/**
|
|
|
+ * 排期配置:用于保存具体的排期实例配置Service业务层处理
|
|
|
+ *
|
|
|
+ * @author Lion Li
|
|
|
+ * @date 2025-07-28
|
|
|
+ */
|
|
|
+@Slf4j
|
|
|
+@RequiredArgsConstructor
|
|
|
+@Service
|
|
|
+public class ScheduleConfigServiceImpl implements IScheduleConfigService {
|
|
|
+
|
|
|
+ private final ScheduleConfigMapper baseMapper;
|
|
|
+
|
|
|
+ private final CreationSchemeMapper schemeRepo;
|
|
|
+
|
|
|
+ private final ScheduleRepeatMapper scheduleRepeatMapper;
|
|
|
+
|
|
|
+ private final ScheduleTimeMapper scheduleTimeMapper;
|
|
|
+
|
|
|
+ private final TournamentEntryConditionsTemplateMapper tournamentEntryConditionsMapper;
|
|
|
+
|
|
|
+
|
|
|
+ private final TournamentBlindStructuresTemplateMapper tournamentBlindStructuresMapper;
|
|
|
+
|
|
|
+
|
|
|
+ private final PrizeDistributionsTemplateMapper prizeDistributionsMapper;
|
|
|
+
|
|
|
+
|
|
|
+ private final PrizeDistributionItemsTemplateMapper prizeDistributionItemsMapper;
|
|
|
+
|
|
|
+ private final ScheduleExecutionMapper scheduleExecutionMapper;
|
|
|
+
|
|
|
+ private final ScheduleTournamentsReletionMapper scheduleTournamentsReletionMapper;
|
|
|
+
|
|
|
+ /**
|
|
|
+ * 查询排期配置:用于保存具体的排期实例配置
|
|
|
+ *
|
|
|
+ * @param id 主键
|
|
|
+ * @return 排期配置:用于保存具体的排期实例配置
|
|
|
+ */
|
|
|
+ @Override
|
|
|
+ public ScheduleConfigVo queryById(Long id){
|
|
|
+ return baseMapper.selectScheduleConfigById(id);
|
|
|
+ }
|
|
|
+
|
|
|
+ /**
|
|
|
+ * 分页查询排期配置:用于保存具体的排期实例配置列表
|
|
|
+ *
|
|
|
+ * @param bo 查询条件
|
|
|
+ * @param pageQuery 分页参数
|
|
|
+ * @return 排期配置:用于保存具体的排期实例配置分页列表
|
|
|
+ */
|
|
|
+ @Override
|
|
|
+ public TableDataInfo<ScheduleConfigVo> queryPageList(ScheduleConfigBo bo, PageQuery pageQuery) {
|
|
|
+ LambdaQueryWrapper<ScheduleConfig> lqw = buildQueryWrapper(bo);
|
|
|
+ Page<ScheduleConfigVo> result = baseMapper.selectAllScheduleConfigs(pageQuery.build(), lqw);
|
|
|
+ return TableDataInfo.build(result);
|
|
|
+ }
|
|
|
+
|
|
|
+ /**
|
|
|
+ * 查询符合条件的排期配置:用于保存具体的排期实例配置列表
|
|
|
+ *
|
|
|
+ * @param bo 查询条件
|
|
|
+ * @return 排期配置:用于保存具体的排期实例配置列表
|
|
|
+ */
|
|
|
+ @Override
|
|
|
+ public List<ScheduleConfigVo> queryList(ScheduleConfigBo bo) {
|
|
|
+ LambdaQueryWrapper<ScheduleConfig> lqw = buildQueryWrapper(bo);
|
|
|
+ return baseMapper.selectAllScheduleConfigsList(lqw);
|
|
|
+ }
|
|
|
+
|
|
|
+ private LambdaQueryWrapper<ScheduleConfig> buildQueryWrapper(ScheduleConfigBo bo) {
|
|
|
+ Map<String, Object> params = bo.getParams();
|
|
|
+ LambdaQueryWrapper<ScheduleConfig> lqw = Wrappers.lambdaQuery();
|
|
|
+ lqw.orderByAsc(ScheduleConfig::getId);
|
|
|
+ lqw.eq(bo.getTemplateId() != null, ScheduleConfig::getTemplateId, bo.getTemplateId());
|
|
|
+ lqw.eq(bo.getCreationSchemeId() != null, ScheduleConfig::getCreationSchemeId, bo.getCreationSchemeId());
|
|
|
+ lqw.eq(bo.getStartDate() != null, ScheduleConfig::getStartDate, bo.getStartDate());
|
|
|
+ lqw.eq(bo.getEndDate() != null, ScheduleConfig::getEndDate, bo.getEndDate());
|
|
|
+ lqw.eq(bo.getEnabled() != null, ScheduleConfig::getEnabled, bo.getEnabled());
|
|
|
+ lqw.eq(bo.getCreatedAt() != null, ScheduleConfig::getCreatedAt, bo.getCreatedAt());
|
|
|
+ lqw.eq(bo.getUpdatedAt() != null, ScheduleConfig::getUpdatedAt, bo.getUpdatedAt());
|
|
|
+ return lqw;
|
|
|
+ }
|
|
|
+
|
|
|
+ /**
|
|
|
+ * 新增排期配置:用于保存具体的排期实例配置
|
|
|
+ *
|
|
|
+ * @param bo 排期配置:用于保存具体的排期实例配置
|
|
|
+ * @return 是否新增成功
|
|
|
+ */
|
|
|
+ @Override
|
|
|
+ public Boolean insertByBo(ScheduleConfigBo bo) {
|
|
|
+ ScheduleConfig add = MapstructUtils.convert(bo, ScheduleConfig.class);
|
|
|
+ validEntityBeforeSave(add);
|
|
|
+ boolean flag = baseMapper.insertScheduleConfig(add) > 0;
|
|
|
+ if (flag) {
|
|
|
+ bo.setId(add.getId());
|
|
|
+ }
|
|
|
+ return flag;
|
|
|
+ }
|
|
|
+
|
|
|
+ /**
|
|
|
+ * 修改排期配置:用于保存具体的排期实例配置
|
|
|
+ *
|
|
|
+ * @param bo 排期配置:用于保存具体的排期实例配置
|
|
|
+ * @return 是否修改成功
|
|
|
+ */
|
|
|
+ @Override
|
|
|
+ public Boolean updateByBo(ScheduleConfigBo bo) {
|
|
|
+ ScheduleConfig update = MapstructUtils.convert(bo, ScheduleConfig.class);
|
|
|
+ validEntityBeforeSave(update);
|
|
|
+ return baseMapper.updateScheduleConfig(update) > 0;
|
|
|
+ }
|
|
|
+
|
|
|
+ /**
|
|
|
+ * 保存前的数据校验
|
|
|
+ */
|
|
|
+ private void validEntityBeforeSave(ScheduleConfig entity){
|
|
|
+ //TODO 做一些数据校验,如唯一约束
|
|
|
+ }
|
|
|
+
|
|
|
+ /**
|
|
|
+ * 校验并批量删除排期配置:用于保存具体的排期实例配置信息
|
|
|
+ *
|
|
|
+ * @param ids 待删除的主键集合
|
|
|
+ * @param isValid 是否进行有效性校验
|
|
|
+ * @return 是否删除成功
|
|
|
+ */
|
|
|
+ @Override
|
|
|
+ public Boolean deleteWithValidByIds(Collection<Long> ids, Boolean isValid) {
|
|
|
+ if(isValid){
|
|
|
+ //TODO 做一些业务上的校验,判断是否需要校验
|
|
|
+ }
|
|
|
+ return baseMapper.deleteScheduleConfig(ids) > 0;
|
|
|
+ }
|
|
|
+
|
|
|
+ public R<String> saveScheduleConfig(ScheduleConfigRequestBo dto) {
|
|
|
+ //todo 选择未来三天 同时周机对不上
|
|
|
+
|
|
|
+ if(dto.getExecTimes().size()<=0){
|
|
|
+ return R.fail("时间设置为空");
|
|
|
+ }
|
|
|
+ if(dto.getRepeatTypes().size()<=0){
|
|
|
+ return R.fail("重复设置为空");
|
|
|
+ }
|
|
|
+
|
|
|
+ // 1. 查询创建方案
|
|
|
+ CreationSchemeVo scheme = schemeRepo.selectAllCreationSchemesInfo(dto.getCreationSchemeCode());
|
|
|
+ if (scheme == null) throw new IllegalArgumentException("Invalid scheme code: " + dto.getCreationSchemeCode());
|
|
|
+
|
|
|
+ // 2. 计算开始和结束日期
|
|
|
+ LocalDate startDate = calculateStartDate(dto.getCreationSchemeCode());
|
|
|
+ LocalDate endDate = calculateEndDate(dto.getCreationSchemeCode(), startDate);
|
|
|
+
|
|
|
+ // 3. 保存主配置
|
|
|
+ ScheduleConfig config = new ScheduleConfig();
|
|
|
+ config.setTemplateId(dto.getTemplateId());
|
|
|
+ config.setCreationSchemeId(scheme.getId());
|
|
|
+ config.setStartDate(startDate);
|
|
|
+ config.setEndDate(endDate);
|
|
|
+ config.setEnabled(true);
|
|
|
+ baseMapper.insertScheduleConfig(config);
|
|
|
+
|
|
|
+ Long configId = config.getId();
|
|
|
+
|
|
|
+ // 5. 保存重复规则(如 DAILY, WEEKLY_MONDAY 等)
|
|
|
+ for (String repeatType : dto.getRepeatTypes()) {
|
|
|
+ ScheduleRepeat repeat = new ScheduleRepeat();
|
|
|
+ repeat.setConfigId(config.getId());
|
|
|
+ repeat.setRepeatType(repeatType);
|
|
|
+ scheduleRepeatMapper.insertScheduleRepeat(repeat);
|
|
|
+ }
|
|
|
+
|
|
|
+ // 6. 保存执行时间(如 09:00, 14:30)
|
|
|
+ for (LocalTime time : dto.getExecTimes()) {
|
|
|
+ ScheduleTime st = new ScheduleTime();
|
|
|
+ st.setConfigId(config.getId());
|
|
|
+ st.setExecTime(time);
|
|
|
+ scheduleTimeMapper.insertScheduleTime(st);
|
|
|
+ }
|
|
|
+
|
|
|
+
|
|
|
+ // 6. ✅ 预生成执行计划
|
|
|
+ generateExecutionPlan(configId, dto.getCreationSchemeCode(), startDate, endDate, dto.getRepeatTypes(), dto.getExecTimes());
|
|
|
+
|
|
|
+ return R.ok();
|
|
|
+ }
|
|
|
+
|
|
|
+ private LocalDate calculateStartDate(String schemeCode) {
|
|
|
+ return LocalDate.now();
|
|
|
+ }
|
|
|
+
|
|
|
+ private LocalDate calculateEndDate(String schemeCode, LocalDate startDate) {
|
|
|
+ switch (schemeCode.toUpperCase()) {
|
|
|
+ case "DAILY":
|
|
|
+ case "WEEKLY":
|
|
|
+ return LocalDate.of(2027, 12, 31);
|
|
|
+ case "NEXT_THREE_DAYS":
|
|
|
+ return startDate.plusDays(2);
|
|
|
+ default:
|
|
|
+ throw new IllegalArgumentException("Unknown scheme: " + schemeCode);
|
|
|
+ }
|
|
|
+ }
|
|
|
+
|
|
|
+ private void generateExecutionPlan(
|
|
|
+ Long configId,
|
|
|
+ String schemeCode,
|
|
|
+ LocalDate startDate,
|
|
|
+ LocalDate endDate,
|
|
|
+ List<String> repeatTypes,
|
|
|
+ List<LocalTime> execTimes) {
|
|
|
+
|
|
|
+ switch (schemeCode.toUpperCase()) {
|
|
|
+ case "DAILY":
|
|
|
+ // 初始化为特定日期
|
|
|
+ endDate = LocalDate.of(2025, 8, 30);
|
|
|
+ generateDailyPlan(configId, startDate, endDate, repeatTypes, execTimes);
|
|
|
+ break;
|
|
|
+ case "WEEKLY":
|
|
|
+ generateWeeklyPlan(configId, startDate, endDate, repeatTypes, execTimes);
|
|
|
+ break;
|
|
|
+ case "NEXT_THREE_DAYS":
|
|
|
+ generateNextThreeDaysPlan(configId, startDate, endDate, repeatTypes, execTimes);
|
|
|
+ break;
|
|
|
+ }
|
|
|
+ }
|
|
|
+
|
|
|
+ // 辅助方法:判断某天是否应该执行
|
|
|
+ private boolean shouldExecuteOnDate(List<String> repeatTypes, LocalDate date) {
|
|
|
+ if (repeatTypes == null || repeatTypes.isEmpty()) return false;
|
|
|
+ String dayType = "WEEKLY_" + date.getDayOfWeek().name();
|
|
|
+ return repeatTypes.contains(dayType) || repeatTypes.contains("DAILY");
|
|
|
+ }
|
|
|
+
|
|
|
+ private void generateDailyPlan(Long configId, LocalDate start, LocalDate end, List<String> repeatTypes, List<LocalTime> execTimes) {
|
|
|
+ LocalDate d = start;
|
|
|
+ while (!d.isAfter(end)) {
|
|
|
+ if (shouldExecuteOnDate(repeatTypes, d)) {
|
|
|
+ for (LocalTime t : execTimes) {
|
|
|
+ ScheduleExecution e = new ScheduleExecution();
|
|
|
+ e.setConfigId(configId);
|
|
|
+ e.setExecutionDate(d);
|
|
|
+ e.setExecutionTime(t);
|
|
|
+ scheduleExecutionMapper.insertScheduleExecution(e);
|
|
|
+ }
|
|
|
+ }
|
|
|
+ d = d.plusDays(1);
|
|
|
+ }
|
|
|
+ }
|
|
|
+
|
|
|
+ private void generateWeeklyPlan(Long configId, LocalDate start, LocalDate end, List<String> repeatTypes, List<LocalTime> execTimes) {
|
|
|
+ LocalDate d = start;
|
|
|
+ while (!d.isAfter(end)) {
|
|
|
+ if (shouldExecuteOnDate(repeatTypes, d)) {
|
|
|
+ for (LocalTime t : execTimes) {
|
|
|
+ ScheduleExecution e = new ScheduleExecution();
|
|
|
+ e.setConfigId(configId);
|
|
|
+ e.setExecutionDate(d);
|
|
|
+ e.setExecutionTime(t);
|
|
|
+ scheduleExecutionMapper.insertScheduleExecution(e);
|
|
|
+ }
|
|
|
+ }
|
|
|
+ d = d.plusDays(1);
|
|
|
+ }
|
|
|
+ }
|
|
|
+
|
|
|
+ private void generateNextThreeDaysPlan(Long configId, LocalDate start, LocalDate end, List<String> repeatTypes, List<LocalTime> execTimes) {
|
|
|
+ LocalDate d = start;
|
|
|
+ int count = 0;
|
|
|
+ while (!d.isAfter(end)) {
|
|
|
+ if (shouldExecuteOnDate(repeatTypes, d)) {
|
|
|
+ for (LocalTime t : execTimes) {
|
|
|
+ ScheduleExecution e = new ScheduleExecution();
|
|
|
+ e.setConfigId(configId);
|
|
|
+ e.setExecutionDate(d);
|
|
|
+ e.setExecutionTime(t);
|
|
|
+ scheduleExecutionMapper.insertScheduleExecution(e);
|
|
|
+ }
|
|
|
+ count++; // ✅ 仅在生成计划时递增 count
|
|
|
+ }
|
|
|
+ d = d.plusDays(1);
|
|
|
+ if (count >= 3) {
|
|
|
+ break; // ✅ 已生成 3 个计划,提前退出循环
|
|
|
+ }
|
|
|
+ }
|
|
|
+ }
|
|
|
+
|
|
|
+
|
|
|
+ @Override
|
|
|
+ public TableDataInfo<TournamentsVo> queryPageListSai(ScheduleConfigBo bo, PageQuery pageQuery) {
|
|
|
+ LambdaQueryWrapper<ScheduleConfig> lqw = buildQueryWrapper(bo);
|
|
|
+ Page<TournamentsVo> result = baseMapper.selectAllScheduleConfigsInfoList(pageQuery.build(), lqw);
|
|
|
+ List<TournamentsVo> records = result.getRecords();
|
|
|
+ for (TournamentsVo record : records) {
|
|
|
+ Long tournamentId = record.getTemplateId();
|
|
|
+ if(record.getEnabled()){
|
|
|
+ record.setStatusText("使用中");
|
|
|
+ }else{
|
|
|
+ record.setStatusText("未使用");
|
|
|
+ }
|
|
|
+ //赛事报名条件
|
|
|
+ TournamentEntryConditionsVo tournamentEntryConditionsVo = tournamentEntryConditionsMapper.selectByTournamentInfoTemplate(tournamentId);
|
|
|
+ if(tournamentEntryConditionsVo!=null){
|
|
|
+ record.setItemsId(tournamentEntryConditionsVo.getItemId());
|
|
|
+ record.setItemsNum(tournamentEntryConditionsVo.getRequiredQuantity());
|
|
|
+ record.setItemsName(tournamentEntryConditionsVo.getItemsName());
|
|
|
+ }
|
|
|
+
|
|
|
+ //绑定的盲注信息
|
|
|
+ TournamentBlindStructuresVo tournamentBlindStructuresVo = tournamentBlindStructuresMapper.selectTournamentBlindStructureByTournamentIdTemplate(tournamentId);
|
|
|
+ if(tournamentBlindStructuresVo!=null){
|
|
|
+ record.setBlindStructureId(tournamentBlindStructuresVo.getBlindStructureId());
|
|
|
+ record.setBlindStructuresName(tournamentBlindStructuresVo.getBlindStructuresName());
|
|
|
+ }
|
|
|
+
|
|
|
+ //排名
|
|
|
+ List<PrizeDistributionsVo> prizeDistributionsVos = prizeDistributionsMapper.selectByTournamentIdTemplate(tournamentId);
|
|
|
+ if(prizeDistributionsVos!=null){
|
|
|
+ List<ItemsPrizeDto> itemsPrizeList=new ArrayList<>();
|
|
|
+
|
|
|
+ // 提取并按排名正序排序后,取出 id 列表
|
|
|
+ List<Long> ids = prizeDistributionsVos.stream()
|
|
|
+ .sorted(Comparator.comparing(PrizeDistributionsVo::getPaiming))
|
|
|
+ .map(PrizeDistributionsVo::getId)
|
|
|
+ .collect(Collectors.toList());
|
|
|
+ int i=0;
|
|
|
+ for (Long id2 : ids) {
|
|
|
+ i++;
|
|
|
+ //奖品
|
|
|
+ PrizeDistributionItemsVo prizeDistributionItemsVos = prizeDistributionItemsMapper.selectByPrizeDistributionIdTemplate(id2);
|
|
|
+ ItemsPrizeDto itemsPrizeBo = new ItemsPrizeDto();
|
|
|
+ itemsPrizeBo.setRanking(Long.valueOf(i));
|
|
|
+ itemsPrizeBo.setItemId(prizeDistributionItemsVos.getItemId());
|
|
|
+ itemsPrizeBo.setQuantity(prizeDistributionItemsVos.getQuantity());
|
|
|
+ itemsPrizeBo.setItemsName(prizeDistributionItemsVos.getItemsName());
|
|
|
+ itemsPrizeList.add(itemsPrizeBo);
|
|
|
+ }
|
|
|
+ record.setItemsPrizeList(itemsPrizeList);
|
|
|
+
|
|
|
+ List<ScheduleTimeVo> scheduleTimeVos = scheduleTimeMapper.selectScheduleTimeInfoById(record.getConfigId());
|
|
|
+ //对应的频率
|
|
|
+ record.setWeekDaySize(scheduleTimeVos.size());
|
|
|
+ //对应的周期
|
|
|
+ List<String> weekDays=new ArrayList<>();
|
|
|
+ List<ScheduleRepeatVo> scheduleRepeatVo = scheduleRepeatMapper.selectScheduleRepeatByConfigId(record.getConfigId());
|
|
|
+ for (ScheduleRepeatVo repeatVo : scheduleRepeatVo) {
|
|
|
+ Weekday codeWeek = Weekday.getByCode(repeatVo.getRepeatType());
|
|
|
+ weekDays.add(codeWeek.getDescription());
|
|
|
+ }
|
|
|
+ record.setWeekDayList(weekDays);
|
|
|
+ }
|
|
|
+ }
|
|
|
+
|
|
|
+ return TableDataInfo.build(result);
|
|
|
+ }
|
|
|
+
|
|
|
+ @Override
|
|
|
+ public TournamentsVo selectScheduleConfigInfoById(Long id) {
|
|
|
+ TournamentsVo tournamentsVo = baseMapper.selectScheduleConfigInfoById(id);
|
|
|
+ if(tournamentsVo!=null){
|
|
|
+ Long tournamentId = tournamentsVo.getTemplateId();
|
|
|
+ if(tournamentsVo.getEnabled()){
|
|
|
+ tournamentsVo.setStatusText("使用中");
|
|
|
+ }else{
|
|
|
+ tournamentsVo.setStatusText("未使用");
|
|
|
+ }
|
|
|
+ //赛事报名条件
|
|
|
+ TournamentEntryConditionsVo tournamentEntryConditionsVo = tournamentEntryConditionsMapper.selectByTournamentInfoTemplate(tournamentId);
|
|
|
+ if(tournamentEntryConditionsVo!=null){
|
|
|
+ tournamentsVo.setItemsId(tournamentEntryConditionsVo.getItemId());
|
|
|
+ tournamentsVo.setItemsNum(tournamentEntryConditionsVo.getRequiredQuantity());
|
|
|
+ tournamentsVo.setItemsName(tournamentEntryConditionsVo.getItemsName());
|
|
|
+ }
|
|
|
+
|
|
|
+ //绑定的盲注信息
|
|
|
+ TournamentBlindStructuresVo tournamentBlindStructuresVo = tournamentBlindStructuresMapper.selectTournamentBlindStructureByTournamentIdTemplate(tournamentId);
|
|
|
+ if(tournamentBlindStructuresVo!=null){
|
|
|
+ tournamentsVo.setBlindStructureId(tournamentBlindStructuresVo.getBlindStructureId());
|
|
|
+ tournamentsVo.setBlindStructuresName(tournamentBlindStructuresVo.getBlindStructuresName());
|
|
|
+ }
|
|
|
+
|
|
|
+ //排名
|
|
|
+ List<PrizeDistributionsVo> prizeDistributionsVos = prizeDistributionsMapper.selectByTournamentIdTemplate(tournamentId);
|
|
|
+ if(prizeDistributionsVos!=null){
|
|
|
+ List<ItemsPrizeDto> itemsPrizeList=new ArrayList<>();
|
|
|
+
|
|
|
+ // 提取并按排名正序排序后,取出 id 列表
|
|
|
+ List<Long> ids = prizeDistributionsVos.stream()
|
|
|
+ .sorted(Comparator.comparing(PrizeDistributionsVo::getPaiming))
|
|
|
+ .map(PrizeDistributionsVo::getId)
|
|
|
+ .collect(Collectors.toList());
|
|
|
+ int i=0;
|
|
|
+ for (Long id2 : ids) {
|
|
|
+ i++;
|
|
|
+ //奖品
|
|
|
+ PrizeDistributionItemsVo prizeDistributionItemsVos = prizeDistributionItemsMapper.selectByPrizeDistributionIdTemplate(id2);
|
|
|
+ ItemsPrizeDto itemsPrizeBo = new ItemsPrizeDto();
|
|
|
+ itemsPrizeBo.setRanking(Long.valueOf(i));
|
|
|
+ itemsPrizeBo.setItemId(prizeDistributionItemsVos.getItemId());
|
|
|
+ itemsPrizeBo.setQuantity(prizeDistributionItemsVos.getQuantity());
|
|
|
+ itemsPrizeBo.setItemsName(prizeDistributionItemsVos.getItemsName());
|
|
|
+ itemsPrizeList.add(itemsPrizeBo);
|
|
|
+ }
|
|
|
+ tournamentsVo.setItemsPrizeList(itemsPrizeList);
|
|
|
+ }
|
|
|
+
|
|
|
+ List<ScheduleRepeatVo> scheduleRepeatVo = scheduleRepeatMapper.selectScheduleRepeatByConfigId(tournamentsVo.getConfigId());
|
|
|
+ if(scheduleRepeatVo!=null && scheduleRepeatVo.size()>0){
|
|
|
+ List<String> repeatTypes = new ArrayList<>();
|
|
|
+ for (ScheduleRepeatVo repeatVo : scheduleRepeatVo) {
|
|
|
+ repeatTypes.add(repeatVo.getRepeatType());
|
|
|
+ }
|
|
|
+ tournamentsVo.setRepeatTypes(repeatTypes);
|
|
|
+ }
|
|
|
+
|
|
|
+ List<ScheduleTimeVo> scheduleTimeVos = scheduleTimeMapper.selectScheduleTimeInfoById(tournamentsVo.getConfigId());
|
|
|
+ if(scheduleTimeVos!=null && scheduleTimeVos.size()>0){
|
|
|
+ List<LocalTime> timeIds = new ArrayList<>();
|
|
|
+ for (ScheduleTimeVo repeatVo : scheduleTimeVos) {
|
|
|
+ timeIds.add(repeatVo.getExecTime());
|
|
|
+ }
|
|
|
+ tournamentsVo.setExecTimes(timeIds);
|
|
|
+ }
|
|
|
+ CreationSchemeVo schemeVo = schemeRepo.selectCreationSchemeById(tournamentsVo.getCreationSchemeId());
|
|
|
+ if(schemeVo!=null){
|
|
|
+ tournamentsVo.setCreationSchemeCode(schemeVo.getCode());
|
|
|
+ }
|
|
|
+
|
|
|
+ }
|
|
|
+ return tournamentsVo;
|
|
|
+ }
|
|
|
+
|
|
|
+
|
|
|
+ public R<String> updateScheduleConfig(Long configId, ScheduleConfigRequestBo dto) {
|
|
|
+
|
|
|
+ if(dto.getExecTimes().size()<=0){
|
|
|
+ return R.fail("时间设置为空");
|
|
|
+ }
|
|
|
+ if(dto.getRepeatTypes().size()<=0){
|
|
|
+ return R.fail("重复设置为空");
|
|
|
+ }
|
|
|
+
|
|
|
+ int selectByScheduleRelationExit = scheduleTournamentsReletionMapper.selectByScheduleRelationExit(dto.getTemplateId());
|
|
|
+ if(selectByScheduleRelationExit>0){
|
|
|
+ //已经生成过赛事数据
|
|
|
+ return R.fail("该配置已经分配过赛事!");
|
|
|
+ }
|
|
|
+
|
|
|
+ // 1. 检查配置是否存在
|
|
|
+ ScheduleConfigVo existingConfig = baseMapper.selectScheduleConfigById(configId);
|
|
|
+ if (existingConfig == null) {
|
|
|
+ throw new IllegalArgumentException("Schedule config not found for id: " + configId);
|
|
|
+ }
|
|
|
+ CreationSchemeVo scheme = schemeRepo.selectAllCreationSchemesInfo(dto.getCreationSchemeCode());
|
|
|
+
|
|
|
+ // 2. 更新主配置的可变字段 (这里只更新 enabled)
|
|
|
+ ScheduleConfig updateConfig = new ScheduleConfig();
|
|
|
+ updateConfig.setId(configId);
|
|
|
+ updateConfig.setEnabled(dto.getEnabled()); // 假设 DTO 有 enabled 字段
|
|
|
+ updateConfig.setCreationSchemeId(scheme.getId());
|
|
|
+ // 注意:不更新 startDate, endDate, creationSchemeId, templateId
|
|
|
+
|
|
|
+ baseMapper.updateScheduleConfig(updateConfig); // 使用之前定义的 updateSelective
|
|
|
+
|
|
|
+ // 3. 🔴 删除旧的关联规则和时间
|
|
|
+ // 3.1 删除旧的执行时间 (ScheduleTime)
|
|
|
+ scheduleTimeMapper.deleteTimeByConfigId(configId);
|
|
|
+
|
|
|
+ // 3.2 删除旧的重复规则 (ScheduleRepeat)
|
|
|
+ scheduleRepeatMapper.deleteRepeatByConfigId(configId);
|
|
|
+
|
|
|
+ // 3.3 删除已生成的执行计划 (schedule_execution)
|
|
|
+ scheduleExecutionMapper.deleteScheduleExecutionByConfigId(configId); // 假设你有这个方法
|
|
|
+
|
|
|
+ // 4. ✅ 插入新的关联规则和时间
|
|
|
+ // 4.1 插入新的重复规则
|
|
|
+ for (String repeatType : dto.getRepeatTypes()) {
|
|
|
+ ScheduleRepeat repeat = new ScheduleRepeat();
|
|
|
+ repeat.setConfigId(configId);
|
|
|
+ repeat.setRepeatType(repeatType);
|
|
|
+ scheduleRepeatMapper.insertScheduleRepeat(repeat);
|
|
|
+ }
|
|
|
+ // 4.2 插入新的执行时间
|
|
|
+ for (LocalTime time : dto.getExecTimes()) {
|
|
|
+ ScheduleTime st = new ScheduleTime();
|
|
|
+ st.setConfigId(configId);
|
|
|
+ st.setExecTime(time);
|
|
|
+ scheduleTimeMapper.insertScheduleTime(st);
|
|
|
+ }
|
|
|
+
|
|
|
+
|
|
|
+ LocalDate startDate = calculateStartDate(dto.getCreationSchemeCode());
|
|
|
+ LocalDate endDate = calculateEndDate(dto.getCreationSchemeCode(), startDate);
|
|
|
+
|
|
|
+
|
|
|
+ // 5. ✅ 重新生成执行计划
|
|
|
+ // 需要 startDate, endDate, repeatTypes, execTimes
|
|
|
+ generateExecutionPlan(
|
|
|
+ configId,
|
|
|
+ scheme.getCode(), // 从现有配置获取 scheme code
|
|
|
+ startDate,
|
|
|
+ endDate,
|
|
|
+ dto.getRepeatTypes(), // 使用新的重复类型
|
|
|
+ dto.getExecTimes() // 使用新的执行时间
|
|
|
+ );
|
|
|
+ return R.ok();
|
|
|
+ }
|
|
|
+
|
|
|
+ @Override
|
|
|
+ public R<String> deleteScheduleConfig(Long configId) {
|
|
|
+
|
|
|
+ // 1. 检查配置是否存在
|
|
|
+ ScheduleConfigVo existingConfig = baseMapper.selectScheduleConfigById(configId);
|
|
|
+
|
|
|
+ int selectByScheduleRelationExit = scheduleTournamentsReletionMapper.selectByScheduleRelationExit(existingConfig.getTemplateId());
|
|
|
+ if(selectByScheduleRelationExit>0){
|
|
|
+ //已经生成过赛事数据
|
|
|
+ return R.fail("该配置已经分配过赛事!禁止删除!");
|
|
|
+ }
|
|
|
+
|
|
|
+ if (existingConfig == null) {
|
|
|
+ throw new IllegalArgumentException("Schedule config not found for id: " + configId);
|
|
|
+ }
|
|
|
+ try {
|
|
|
+ // 2. 🔴 按依赖顺序删除关联数据
|
|
|
+ // 2.1 删除已生成的执行计划
|
|
|
+ int deletedExecutions = scheduleExecutionMapper.deleteScheduleExecutionByConfigId(configId); // 假设返回删除行数
|
|
|
+ log.info("Deleted {} execution plans for configId: {}", deletedExecutions, configId);
|
|
|
+
|
|
|
+ // 2.2 删除执行时间
|
|
|
+ int deletedTimes = scheduleTimeMapper.deleteTimeByConfigId(configId);
|
|
|
+ log.info("Deleted {} schedule times for configId: {}", deletedTimes, configId);
|
|
|
+
|
|
|
+ // 2.3 删除重复规则
|
|
|
+ int deletedRepeats = scheduleRepeatMapper.deleteRepeatByConfigId(configId);
|
|
|
+ log.info("Deleted {} repeat rules for configId: {}", deletedRepeats, configId);
|
|
|
+
|
|
|
+ // 3. ✅ 删除主配置
|
|
|
+ Collection<Long> ids=new ArrayList<>();
|
|
|
+ ids.add(configId);
|
|
|
+ baseMapper.deleteScheduleConfig(ids);
|
|
|
+ log.info("Deleted schedule config with id: {}", configId);
|
|
|
+
|
|
|
+ } catch (Exception e) {
|
|
|
+ log.error("Error deleting schedule config and its associations, configId: {}", configId, e);
|
|
|
+ throw e; // 事务会回滚
|
|
|
+ }
|
|
|
+
|
|
|
+ return R.ok();
|
|
|
+ }
|
|
|
+
|
|
|
+ @Override
|
|
|
+ public Boolean stopScheduleConfig(Long configId) {
|
|
|
+ ScheduleConfig scheduleConfig = new ScheduleConfig();
|
|
|
+ scheduleConfig.setId(configId);
|
|
|
+ scheduleConfig.setEnabled(false);
|
|
|
+ int scheduleConfig1 = baseMapper.updateScheduleConfig(scheduleConfig);
|
|
|
+ return scheduleConfig1>0?true:false;
|
|
|
+ }
|
|
|
+
|
|
|
+}
|