package cn.fw.valhalla.service.bus.follow.strategy; import cn.fw.oop.sdk.enums.BizTypeEnum; import cn.fw.shirasawa.sdk.enums.BusinessTypeEnum; import cn.fw.shirasawa.sdk.enums.DataTypeEnum; import cn.fw.shirasawa.sdk.enums.TerminationReason; import cn.fw.valhalla.common.utils.DateUtil; import cn.fw.valhalla.common.utils.StringUtils; import cn.fw.valhalla.domain.db.OriginalData; import cn.fw.valhalla.domain.db.customer.Customer; import cn.fw.valhalla.domain.db.customer.CustomerBaseInfo; import cn.fw.valhalla.domain.db.follow.ClueTask; import cn.fw.valhalla.domain.db.follow.FollowClue; import cn.fw.valhalla.domain.db.follow.FollowNoticeRecord; import cn.fw.valhalla.domain.db.setting.FollowSettingDetail; import cn.fw.valhalla.domain.dto.CustomerDetailDto; import cn.fw.valhalla.domain.enums.*; import cn.fw.valhalla.domain.vo.setting.SettingVO; import cn.fw.valhalla.rpc.ehr.EhrRpcService; import cn.fw.valhalla.rpc.ehr.dto.StaffInfoDTO; import cn.fw.valhalla.rpc.erp.UserService; import cn.fw.valhalla.rpc.erp.dto.PostUserDTO; import cn.fw.valhalla.rpc.member.MemberRpcService; import cn.fw.valhalla.rpc.oop.OopService; import cn.fw.valhalla.rpc.oop.dto.ShopDTO; import cn.fw.valhalla.rpc.shirasawa.ShirasawaRpcService; import cn.fw.valhalla.rpc.shirasawa.dto.ClueStopDTO; import cn.fw.valhalla.rpc.shirasawa.dto.FollowInitDTO; import cn.fw.valhalla.service.bus.cust.CustomerBizService; import cn.fw.valhalla.service.bus.cust.CustomerChangeBizService; import cn.fw.valhalla.service.bus.setting.SettingBizService; import cn.fw.valhalla.service.data.*; import com.baomidou.mybatisplus.core.toolkit.Wrappers; import lombok.Getter; import lombok.extern.slf4j.Slf4j; import org.springframework.beans.factory.annotation.Autowired; import org.springframework.beans.factory.annotation.Value; import org.springframework.data.redis.core.StringRedisTemplate; import org.springframework.transaction.annotation.Transactional; import org.springframework.util.CollectionUtils; import java.time.Duration; import java.time.LocalDate; import java.time.LocalDateTime; import java.util.*; import java.util.stream.Collectors; import static cn.fw.common.businessvalidator.Validator.BV; import static cn.fw.valhalla.service.bus.setting.strategy.SettingStrategy.COMMON_BRAND_ID; /** * @author : kurisu * @className : AbstractFollowStrategy * @description : 策略抽象类 * @date: 2020-08-17 10:42 */ @Slf4j public abstract class AbstractFollowStrategy implements FollowStrategy { @Autowired protected CustomerService customerService; @Autowired protected CustomerBaseInfoService customerBaseInfoService; @Autowired protected CustomerBizService customerBizService; @Autowired protected UserService userService; @Autowired protected FollowNoticeRecordService followNoticeRecordService; @Autowired protected SettingBizService settingBizService; @Autowired protected FollowSettingDetailService followSettingDetailService; @Autowired protected OopService oopService; @Autowired protected CustomerChangeBizService customerChangeBizService; @Autowired protected ShirasawaRpcService shirasawaRpcService; @Autowired protected ClueTaskService clueTaskService; @Autowired protected FollowClueService followClueService; @Autowired protected EhrRpcService ehrRpcService; @Autowired protected MemberRpcService memberRpcService; @Autowired protected StringRedisTemplate redisTemplate; @Value("${spring.cache.custom.global-prefix}:follow") @Getter private String keyPrefix; @Value("${follow.todo.FMCode}") @Getter private String FMCode; @Value("${follow.todo.RMCode}") @Getter private String RMCode; @Value("${follow.todo.IRCode}") @Getter private String IRCode; @Value("${follow.todo.ACCode}") @Getter private String ACCode; @Value("${spring.cache.custom.global-prefix}:follow:clue:change") @Getter private String clueChangeKeyPrefix; /** * 单位转换 * * @param unit * @return */ public static int getCalendarType(SettingUnitEnum unit) { switch (unit) { case HOUR: return Calendar.HOUR; case MONTH: return Calendar.MONTH; case MINUTE: return Calendar.MINUTE; default: return Calendar.DATE; } } @Override @Transactional(rollbackFor = Exception.class) public void settingChanged(List setting, Long groupId) { List poolList = followClueService.list(Wrappers.lambdaQuery() .eq(FollowClue::getClueType, getFollowType()) .eq(FollowClue::getGroupId, groupId) .eq(FollowClue::getClueState, ClueStatusEnum.WAITING) ); if (CollectionUtils.isEmpty(poolList)) { return; } List vinList = poolList.stream().map(FollowClue::getVin).collect(Collectors.toList()); final Long brandId = setting.get(0).getBrandId(); final Long settingId = setting.get(0).getSettingId(); if (COMMON_BRAND_ID.equals(brandId)) { List otherBrandIdList = followSettingDetailService.listObjs(Wrappers.lambdaQuery() .select(FollowSettingDetail::getBrandId) .eq(FollowSettingDetail::getSettingId, settingId) .eq(FollowSettingDetail::getType, SettingTypeEnum.FIRST_TRIGGER_TIME) .eq(FollowSettingDetail::getYn, Boolean.TRUE) .ne(FollowSettingDetail::getBrandId, brandId), bid -> Long.parseLong((String) bid) ); if (!CollectionUtils.isEmpty(otherBrandIdList)) { List frameNoList = customerService.listObjs(Wrappers.lambdaQuery() .select(Customer::getFrameNo) .in(Customer::getBrandId, otherBrandIdList) .in(Customer::getFrameNo, vinList) .eq(Customer::getGroupId, groupId), Object::toString ); if (!CollectionUtils.isEmpty(frameNoList)) { Set vinSet = new HashSet<>(frameNoList); poolList = poolList.stream().filter(r -> vinSet.contains(r.getVin())).collect(Collectors.toList()); } } } else { List frameNoList = customerService.listObjs(Wrappers.lambdaQuery() .select(Customer::getFrameNo) .eq(Customer::getBrandId, brandId) .in(Customer::getFrameNo, vinList) .eq(Customer::getGroupId, groupId), Object::toString ); if (!CollectionUtils.isEmpty(frameNoList)) { Set vinSet = new HashSet<>(frameNoList); poolList = poolList.stream().filter(r -> vinSet.contains(r.getVin())).collect(Collectors.toList()); } } updateClue(poolList, setting); SettingVO noticeSetting = setting.stream().filter(r -> SettingTypeEnum.FIRST_NOTICE_TIME.getValue().equals(r.getType())).findFirst().orElse(new SettingVO()); updateNoticeRecord(poolList, noticeSetting); } @Override @Transactional(rollbackFor = Exception.class) public void closeTask(ClueTask task) { final Long clueId = task.getClueId(); FollowClue clue = followClueService.getById(clueId); BV.notNull(clue, () -> "跟进线索不存在: " + clueId); task.setCloseTime(task.getDeadline().minusSeconds(1L)); task.setState(TaskStateEnum.DEFEAT); task.setReason(TaskDefeatTypeEnum.C); boolean rpcSucess = rpcStopTask(task); if (!rpcSucess) { log.info("跟进系统终止任务失败"); } task.setRpcSuccess(rpcSucess); clueTaskService.updateById(task); if (Objects.nonNull(clue)) { clue.setCloseTime(task.getCloseTime()); clue.setClueState(ClueStatusEnum.FAILURE); followClueService.updateById(clue); redisTemplate.opsForSet().add(generateStopKey(), String.valueOf(task.getId())); customerBizService.taskEndAbandon(task, clue); } } /** * [角色变动]结束任务 * * @param task */ @Override @Transactional(rollbackFor = Exception.class) public void onRoleChangeCloseTask(ClueTask task) { Long clueId = task.getClueId(); FollowClue clue = followClueService.getById(clueId); task.setState(TaskStateEnum.DEFEAT); task.setCloseTime(LocalDateTime.now()); task.setReason(TaskDefeatTypeEnum.D); if (Objects.isNull(clue)) { boolean rpcSucess = rpcStopTask(task); if (!rpcSucess) { log.info("跟进系统终止任务失败"); } task.setRpcSuccess(rpcSucess); clueTaskService.updateById(task); } else { String vin = clue.getVin(); Long adviserId = null; Customer customer = customerService.queryByFrameNo(vin, task.getGroupId()); if (Objects.nonNull(customer)) { adviserId = customer.getAdviserId(); } if (task.getFollowUser().equals(adviserId)) { return; } if (Objects.isNull(adviserId)) { boolean rpcSuccess = rpcStopTask(task); if (!rpcSuccess) { log.info("跟进系统终止任务失败"); } task.setRpcSuccess(rpcSuccess); clueTaskService.updateById(task); clue.setCloseTime(task.getCloseTime()); clue.setClueState(ClueStatusEnum.FAILURE); followClueService.updateById(clue); redisTemplate.opsForSet().add(generateStopKey(), String.valueOf(task.getId())); } else { task.setRpcSuccess(true); clueTaskService.updateById(task); createSecondaryTask(clue, adviserId); } } } @Override @Transactional(rollbackFor = Exception.class) public void forceStopClue(FollowClue clue, boolean fromTask) { clue.setClueState(ClueStatusEnum.FAILURE); clue.setCloseTime(LocalDateTime.now()); followClueService.updateById(clue); redisTemplate.opsForSet().add(generateStopKey(), String.valueOf(clue.getId())); ClueTask task = clueTaskService.queryOngoingTaskByClueId(clue.getId(), clue.getClueType()); if (Objects.isNull(task)) { return; } task.setState(TaskStateEnum.DEFEAT); task.setCloseTime(LocalDateTime.now()); task.setReason(TaskDefeatTypeEnum.A); if (fromTask) { task.setReason(TaskDefeatTypeEnum.C); } boolean rpcSucess = rpcStopTask(task); task.setRpcSuccess(rpcSucess); clueTaskService.updateById(task); } @Override @Transactional(rollbackFor = Exception.class) public void forceStopTask(ClueTask task) { Long clueId = task.getClueId(); FollowClue clue = followClueService.getById(clueId); task.setState(TaskStateEnum.DEFEAT); task.setCloseTime(LocalDateTime.now()); task.setReason(TaskDefeatTypeEnum.A); boolean rpcSucess = rpcStopTask(task); task.setRpcSuccess(rpcSucess); clueTaskService.updateById(task); if (Objects.nonNull(clue)) { clue.setClueState(ClueStatusEnum.FAILURE); clue.setCloseTime(LocalDateTime.now()); followClueService.updateById(clue); redisTemplate.opsForSet().add(generateStopKey(), String.valueOf(task.getId())); } } /** * 当跟进待办结束(包括完成和逾期) * * @param clue * @param overdue */ @Override @Transactional(rollbackFor = Exception.class) public void onFollowComplete(FollowClue clue, boolean overdue) { ClueTask task = clueTaskService.queryOngoingTaskByClueId(clue.getId(), clue.getClueType()); if (!overdue && Objects.nonNull(task)) { Integer times = Optional.ofNullable(task.getTimes()).orElse(0); task.setTimes(times + 1); clueTaskService.updateById(task); } } /** * 任务结束同步状态到跟进系统 * * @param task */ @Override @Transactional(rollbackFor = Exception.class) public void syncEndTask(ClueTask task) { if (TaskStateEnum.ONGOING.equals(task.getState())) { return; } boolean res = rpcStopTask(task); task.setRpcSuccess(res); clueTaskService.updateById(task); } /** * 更新任务 * * @param list * @param setting */ @Transactional(rollbackFor = Exception.class) public void updateClue(List list, List setting) { for (SettingVO vo : setting) { final Integer unit = vo.getUnit(); final int value = Optional.ofNullable(vo.getDetailValue()).orElse(0); SettingUnitEnum unitEnum = SettingUnitEnum.ofValue(unit); if (SettingTypeEnum.FIRST_TRIGGER_TIME.getValue().equals(vo.getType())) { if (Objects.nonNull(unitEnum) && value > 0) { for (FollowClue clue : list) { LocalDateTime originTime = clue.getOriginTime(); LocalDateTime newStartTime = calTime(originTime, unitEnum, value); if (FollowTypeEnum.IR.equals(clue.getClueType())) { newStartTime = calTime(originTime, unitEnum, value * -1); } if (LocalDate.now().isBefore(newStartTime.toLocalDate())) { clue.setStartTime(newStartTime); } } } } if (SettingTypeEnum.FAIL_TIME.getValue().equals(vo.getType())) { if (Objects.nonNull(unitEnum) && value > 0) { for (FollowClue clue : list) { LocalDateTime originTime = clue.getOriginTime(); LocalDateTime newEndTime = calTime(originTime, unitEnum, value); if (LocalDate.now().isBefore(newEndTime.toLocalDate())) { clue.setEndTime(newEndTime); } } } } } followClueService.updateBatchById(list); } /** * 更新服务号消息记录 * * @param list * @param vo */ @Transactional(rollbackFor = Exception.class) public void updateNoticeRecord(List list, SettingVO vo) { List idList = list.stream().map(FollowClue::getId).collect(Collectors.toList()); List noticeList = followNoticeRecordService.list(Wrappers.lambdaQuery() .eq(FollowNoticeRecord::getStatus, SendStatusEnum.NOT_SENT) .in(FollowNoticeRecord::getClueId, idList) ); Integer unit = vo.getUnit(); int value = Optional.ofNullable(vo.getDetailValue()).orElse(0); SettingUnitEnum unitEnum = SettingUnitEnum.ofValue(unit); if (Objects.isNull(unitEnum) || value <= 0) { return; } for (FollowClue clue : list) { for (FollowNoticeRecord noticeRecord : noticeList) { if (clue.getId().equals(noticeRecord.getClueId())) { LocalDateTime originTime = clue.getOriginTime(); LocalDateTime newSendTime = calTime(originTime, unitEnum, value); if (FollowTypeEnum.IR.equals(clue.getClueType())) { newSendTime = calTime(originTime, unitEnum, value * -1); } noticeRecord.setSendTime(DateUtil.localDateTime2Date(newSendTime)); } } } followNoticeRecordService.updateBatchById(noticeList); } /** * 线索成交 * * @param originalData */ protected void finishClue(OriginalData originalData, FollowClue followClue) { if (Objects.isNull(followClue)) { return; } ClueTask clueTask = clueTaskService.queryOngoingTaskByClueId(followClue.getId(), followClue.getClueType()); if (Objects.isNull(clueTask)) { return; } followClue.setClueState(ClueStatusEnum.COMPLETE); clueTask.setCloseTime(LocalDateTime.now()); clueTask.setFinishUser(originalData.getUserId()); clueTask.setState(TaskStateEnum.COMPLETE); StaffInfoDTO infoDTO = ehrRpcService.queryStaffInfo(originalData.getUserId()); if (Objects.nonNull(infoDTO)) { clueTask.setFinishUserName(infoDTO.getName()); } if (!originalData.getUserId().equals(clueTask.getFollowUser())) { clueTask.setState(TaskStateEnum.DEFEAT); clueTask.setReason(TaskDefeatTypeEnum.F); } clueTask.setFinishShop(originalData.getShopId()); followClue.setCloseTime(clueTask.getCloseTime()); followClueService.updateById(followClue); redisTemplate.opsForSet().add(generateStopKey(), String.valueOf(clueTask.getId())); boolean rpcSucess = rpcStopTask(clueTask); clueTask.setRpcSuccess(rpcSucess); clueTaskService.updateById(clueTask); } /** * 生成任务实体 * * @param originalData * @return */ protected FollowClue createClueInfo(final OriginalData originalData, FollowTypeEnum followType, Customer customer) { LocalDateTime originTime = DateUtil.date2LocalDate(originalData.getGenerateTime()).atStartOfDay(); final FollowClue pool = new FollowClue(); pool.setVin(customer.getFrameNo()); pool.setOriginTime(DateUtil.date2LocalDateTime(originalData.getGenerateTime())); pool.setPlateNo(customer.getPlateNo()); pool.setClueState(ClueStatusEnum.WAITING); pool.setClueType(followType); pool.setBizId(originalData.getId()); Long shopId = originalData.getShopId(); if (Objects.nonNull(customer.getShopId())) { shopId = customer.getShopId(); } ShopDTO shop = oopService.shop(shopId); if (Objects.nonNull(shop)) { if (!BizTypeEnum.AFTER_SALE.getValue().equals(shop.getBizType())) { if (Objects.nonNull(shop.getCasShopId())) { shopId = shop.getCasShopId(); } } } pool.setSuggestShopId(shopId); pool.setGroupId(originalData.getGroupId()); settingBizService.querySettingByType(followType, SettingTypeEnum.FIRST_TRIGGER_TIME, originalData.getGroupId(), customer.getBrandId()) .ifPresent(r -> { int detailValue = Optional.ofNullable(r.getDetailValue()).orElse(0); if (FollowTypeEnum.IR.equals(pool.getClueType())) { detailValue = detailValue * -1; } SettingUnitEnum unitEnum = Objects.requireNonNull(SettingUnitEnum.ofValue(r.getUnit()), "时间单位缺失"); LocalDateTime localDateTime = calTime(originTime, unitEnum, detailValue); pool.setStartTime(localDateTime); }); CustomerBaseInfo customerBaseInfo = customerBaseInfoService.queryById(customer.getBaseId()); if (Objects.nonNull(customerBaseInfo)) { pool.setSuggestMobile(customerBaseInfo.getMobile()); } settingBizService.querySettingByType(followType, SettingTypeEnum.FAIL_TIME, originalData.getGroupId(), customer.getBrandId()) .ifPresent(r -> { int detailValue = Optional.ofNullable(r.getDetailValue()).orElse(0); SettingUnitEnum unitEnum = Objects.requireNonNull(SettingUnitEnum.ofValue(r.getUnit()), "时间单位缺失"); LocalDateTime localDateTime = calTime(originTime, unitEnum, detailValue); pool.setEndTime(localDateTime); }); return pool; } protected FollowInitDTO creteFollowInitDTO(FollowClue followClue, ClueTask clueTask) { Long customerId = null; String customerName = null; Long memberId = null; Long brandId = COMMON_BRAND_ID; String phone = followClue.getSuggestMobile(); if (StringUtils.isValid(followClue.getVin())) { CustomerDetailDto customerDetailDto = customerBizService.queryByFrameNo(followClue.getVin(), followClue.getGroupId()); if (Objects.nonNull(customerDetailDto)) { customerId = customerDetailDto.getId(); customerName = customerDetailDto.getName(); memberId = customerDetailDto.getMemberId(); phone = customerDetailDto.getMobile(); brandId = customerDetailDto.getBrandId(); } } final FollowInitDTO followInitDTO = FollowInitDTO.builder() .businessType(BusinessTypeEnum.AS) .type(DataTypeEnum.ofValue(clueTask.getType().getValue())) .customerId(customerId) .customerName(customerName) .memberId(memberId) .plateNo(followClue.getPlateNo()) .frameNo(followClue.getVin()) .contacts(phone) .detailId(String.valueOf(followClue.getId())) .generateTime(DateUtil.localDateTime2Date(clueTask.getBeginTime())) .deadline(DateUtil.localDateTime2Date(clueTask.getDeadline())) .groupId(clueTask.getGroupId()) .shopId(clueTask.getFollowShop()) .userId(clueTask.getFollowUser()) .userName(clueTask.getFollowUserName()) .bizId(followClue.getVin()) .followDuration(Duration.ofHours(36L)) .build(); ShopDTO shop = oopService.shop(clueTask.getFollowShop()); if (Objects.nonNull(shop)) { followInitDTO.setShopName(shop.getShopName()); } // 除事故车以外,其他待办跟进时长统一配置 settingBizService.querySettingByType(FollowTypeEnum.OT, SettingTypeEnum.EFFECTIVE_TIME, clueTask.getGroupId(), brandId) .ifPresent(r -> { Integer unit = r.getUnit(); int detailValue = Optional.ofNullable(r.getDetailValue()).orElse(0); Duration duration = transferDuration(detailValue, unit); BV.notNull(duration, () -> "设置有误,周期计算不成功"); followInitDTO.setFollowDuration(duration); }); Map noteMap = createNoteMap(followClue); followInitDTO.setNoteMap(noteMap); return followInitDTO; } protected FollowInitDTO creteRedistributionFollowInitDTO(FollowClue followClue, ClueTask clueTask) { final LocalDateTime nextTime = clueTask.getBeginTime(); final FollowInitDTO followInitDTO = creteFollowInitDTO(followClue, clueTask); followInitDTO.setGenerateTime(DateUtil.localDateTime2Date(nextTime)); Long brandId = COMMON_BRAND_ID; Customer customer = customerService.queryByFrameNo(followClue.getVin(), followClue.getGroupId()); if (Objects.nonNull(customer)) { brandId = customer.getBrandId(); } settingBizService.querySettingByType(FollowTypeEnum.OT, SettingTypeEnum.EFFECTIVE_TIME, clueTask.getGroupId(), brandId) .ifPresent(r -> { Integer unit = r.getUnit(); int detailValue = Optional.ofNullable(r.getDetailValue()).orElse(0); Duration duration = transferDuration(detailValue, unit); BV.notNull(duration, () -> "设置有误,周期计算不成功"); followInitDTO.setFollowDuration(duration); }); Map noteMap = createNoteMap(followClue); followInitDTO.setNoteMap(noteMap); return followInitDTO; } /** * 生成消息推送 * * @param cluePool * @param customerId */ protected void createFirstNotice(final FollowClue cluePool, final Long customerId, final Long brandId) { if (!cluePool.getEndTime().isAfter(cluePool.getStartTime()) || !cluePool.getEndTime().isAfter(LocalDateTime.now())) { return; } final FollowNoticeRecord record = new FollowNoticeRecord(); record.setClueId(cluePool.getId()); record.setFollowType(cluePool.getClueType()); record.setCustomerId(customerId); record.setStatus(SendStatusEnum.NOT_SENT); settingBizService.querySettingByType(cluePool.getClueType(), SettingTypeEnum.FIRST_NOTICE_TIME, cluePool.getGroupId(), brandId) .ifPresent(r -> { int detailValue = Optional.ofNullable(r.getDetailValue()).orElse(0); if (FollowTypeEnum.IR.equals(cluePool.getClueType())) { detailValue = detailValue * -1; } SettingUnitEnum unitEnum = Objects.requireNonNull(SettingUnitEnum.ofValue(r.getUnit()), "时间单位缺失"); LocalDateTime localDateTime = calTime(cluePool.getOriginTime(), unitEnum, detailValue); record.setSendTime(DateUtil.localDateTime2Date(localDateTime)); }); record.setCreateTime(new Date()); followNoticeRecordService.save(record); } protected boolean rpcStopTask(ClueTask clueTask) { TaskDefeatTypeEnum reason = clueTask.getReason(); if (TaskDefeatTypeEnum.B.equals(reason) || TaskDefeatTypeEnum.C.equals(reason)) { return true; } ClueStopDTO clueStopDTO = new ClueStopDTO(); clueStopDTO.setType(DataTypeEnum.ofValue(clueTask.getType().getValue())); clueStopDTO.setBusinessType(BusinessTypeEnum.AS); if (TaskStateEnum.DEFEAT.equals(clueTask.getState())) { clueStopDTO.setTermination(Boolean.TRUE); if (TaskDefeatTypeEnum.A.equals(reason)) { clueStopDTO.setReason(TerminationReason.ABANDON); } if (TaskDefeatTypeEnum.F.equals(reason)) { clueStopDTO.setReason(TerminationReason.ANOTHER); } if (TaskDefeatTypeEnum.D.equals(reason)) { clueStopDTO.setReason(TerminationReason.ROLE_CHANGE); } } clueStopDTO.setDetailId(String.valueOf(clueTask.getClueId())); clueStopDTO.setShopId(clueTask.getFinishShop()); ShopDTO shop = oopService.shop(clueTask.getFinishShop()); if (Objects.nonNull(shop)) { clueStopDTO.setShopName(shop.getShortName()); } clueStopDTO.setCompleteTime(DateUtil.localDateTime2Date(clueTask.getCloseTime())); clueStopDTO.setGroupId(clueTask.getGroupId()); clueStopDTO.setUserId(clueTask.getFollowUser()); clueStopDTO.setUserName(clueTask.getFollowUserName()); return shirasawaRpcService.stopTask(clueStopDTO); } protected ClueTask createNewTask(FollowClue followClue) { final FollowTypeEnum followTypeEnum = followClue.getClueType(); final ClueTask clueTask = new ClueTask(); clueTask.setClueId(followClue.getId()); clueTask.setType(followTypeEnum); clueTask.setBeginTime(followClue.getStartTime()); clueTask.setRedistribution(Boolean.FALSE); clueTask.setDeadline(followClue.getEndTime()); clueTask.setState(TaskStateEnum.ONGOING); clueTask.setGroupId(followClue.getGroupId()); Long userId = null; Long shopId = null; if (StringUtils.isValid(followClue.getVin())) { Customer customer = customerService.queryByFrameNo(followClue.getVin(), followClue.getGroupId()); if (Objects.nonNull(customer)) { userId = customer.getAdviserId(); shopId = customer.getShopId(); ShopDTO shop = oopService.shop(shopId); if (Objects.isNull(shop)) { shopId = followClue.getSuggestShopId(); } } } if (Objects.isNull(shopId)) { shopId = followClue.getSuggestShopId(); } clueTask.setFollowShop(shopId); clueTask.setFollowUser(userId); clueTask.setVersion(2); return clueTask; } protected void fillTaskUser(ClueTask clueTask, List userByRole) { Long userId = clueTask.getFollowUser(); if (Objects.nonNull(userId)) { for (PostUserDTO dto : userByRole) { if (dto.getUserId().equals(clueTask.getFollowUser())) { clueTask.setFollowUserName(dto.getUserName()); break; } } } if (StringUtils.isEmpty(clueTask.getFollowUserName())) { userId = null; } if (Objects.isNull(userId)) { int randomIndex = new Random().nextInt(userByRole.size()); PostUserDTO userDTO = userByRole.get(randomIndex); clueTask.setFollowUser(userDTO.getUserId()); clueTask.setFollowUserName(userDTO.getUserName()); } } protected Map createNoteMap(FollowClue followClue) { Map dynamicMap = new HashMap<>(); if (Objects.nonNull(followClue)) { FollowTypeEnum clueType = followClue.getClueType(); String name = "-"; CustomerDetailDto vo = customerBizService.queryByFrameNo(followClue.getVin(), followClue.getGroupId()); if (Objects.nonNull(vo)) { name = StringUtils.isValid(vo.getName()) ? vo.getName() : "-"; } dynamicMap.put("name", name); dynamicMap.put("state", "1"); dynamicMap.put("plateNo", StringUtils.isValid(followClue.getPlateNo()) ? followClue.getPlateNo() : "-"); if (FollowTypeEnum.FM.equals(clueType)) { dynamicMap.put("buyDate", DateUtil.getStringDateShort(vo.getBuyDate(), "-")); dynamicMap.put("expirTime", DateUtil.getStringDateShort(DateUtil.localDateTime2Date(followClue.getEndTime()), "-")); } else if (FollowTypeEnum.RM.equals(clueType)) { dynamicMap.put("currentMileage", Optional.ofNullable(vo.getCurrentMileage()).map(String::valueOf).orElse("-")); dynamicMap.put("arrivalTime", DateUtil.getStringDateShort(vo.getArrivalTime(), "-")); } else if (FollowTypeEnum.IR.equals(clueType)) { dynamicMap.put("expirTime", DateUtil.getStringDateShort(DateUtil.localDateTime2Date(followClue.getOriginTime()), "-")); dynamicMap.put("insComName", "-"); } else if (FollowTypeEnum.AC.equals(clueType)) { dynamicMap.put("insComName", "-"); } } return dynamicMap; } protected void createSecondaryTask(FollowClue clue, Long userId) { ClueTask redistributionTask = new ClueTask(); redistributionTask.setClueId(clue.getId()); redistributionTask.setType(clue.getClueType()); redistributionTask.setBeginTime(LocalDate.now().plusDays(1L).atStartOfDay()); redistributionTask.setRedistribution(Boolean.TRUE); redistributionTask.setDeadline(clue.getEndTime()); redistributionTask.setState(TaskStateEnum.ONGOING); redistributionTask.setFollowUser(userId); redistributionTask.setFollowShop(clue.getSuggestShopId()); StaffInfoDTO staffInfoDTO = ehrRpcService.queryStaffInfo(userId); if (Objects.nonNull(staffInfoDTO)) { redistributionTask.setFollowUserName(staffInfoDTO.getName()); } redistributionTask.setGroupId(clue.getGroupId()); redistributionTask.setRpcSuccess(Boolean.FALSE); redistributionTask.setVersion(2); clueTaskService.save(redistributionTask); FollowInitDTO followInitDTO = creteRedistributionFollowInitDTO(clue, redistributionTask); shirasawaRpcService.changeFollowData(followInitDTO, redistributionTask.getBeginTime().toLocalDate()); followClueService.updateById(clue); } protected String generateStopKey() { return String.format("%s:%s", getClueChangeKeyPrefix(), "STOP"); } }