Blame view

fw-valhalla-service/src/main/java/cn/fw/valhalla/service/bus/follow/strategy/AbstractFollowStrategy.java 32.3 KB
65610b54   张志伟   :art:
1
2
  package cn.fw.valhalla.service.bus.follow.strategy;
  
59ae8b14   张志伟   feature(*): 售后crm...
3
  import cn.fw.oop.sdk.enums.BizTypeEnum;
786b1ee2   张志伟   feature(*): - 事故车...
4
  import cn.fw.shirasawa.sdk.enums.BusinessTypeEnum;
59ae8b14   张志伟   feature(*): 售后crm...
5
  import cn.fw.shirasawa.sdk.enums.DataTypeEnum;
2a51fef7   张志伟   feature(*): 清理代码监...
6
  import cn.fw.shirasawa.sdk.enums.TerminationReason;
ad395b9c   张志伟   :art:
7
  import cn.fw.valhalla.common.utils.DateUtil;
ffc9b4e2   张志伟   :sparkles:
8
  import cn.fw.valhalla.common.utils.StringUtils;
23b952c1   张志伟   :art:
9
  import cn.fw.valhalla.domain.db.OriginalData;
65610b54   张志伟   :art:
10
  import cn.fw.valhalla.domain.db.customer.Customer;
59ae8b14   张志伟   feature(*): 售后crm...
11
  import cn.fw.valhalla.domain.db.customer.CustomerBaseInfo;
55003764   张志伟   feature(*): 售后crm...
12
13
14
  import cn.fw.valhalla.domain.db.follow.ClueTask;
  import cn.fw.valhalla.domain.db.follow.FollowClue;
  import cn.fw.valhalla.domain.db.follow.FollowNoticeRecord;
8b00f03a   张志伟   :sparkles:
15
  import cn.fw.valhalla.domain.db.setting.FollowSettingDetail;
786b1ee2   张志伟   feature(*): - 事故车...
16
  import cn.fw.valhalla.domain.dto.CustomerDetailDto;
23b952c1   张志伟   :art:
17
  import cn.fw.valhalla.domain.enums.*;
08704989   张志伟   :art:
18
  import cn.fw.valhalla.domain.vo.setting.SettingVO;
786b1ee2   张志伟   feature(*): - 事故车...
19
  import cn.fw.valhalla.rpc.ehr.EhrRpcService;
59ae8b14   张志伟   feature(*): 售后crm...
20
  import cn.fw.valhalla.rpc.ehr.dto.StaffInfoDTO;
945beeb0   张志伟   :fire:
21
  import cn.fw.valhalla.rpc.erp.UserService;
f2437f9a   张志伟   :sparkles:
22
  import cn.fw.valhalla.rpc.erp.dto.PostUserDTO;
55003764   张志伟   feature(*): 售后crm...
23
  import cn.fw.valhalla.rpc.member.MemberRpcService;
23b952c1   张志伟   :art:
24
  import cn.fw.valhalla.rpc.oop.OopService;
612d25d9   张志伟   :art:
25
  import cn.fw.valhalla.rpc.oop.dto.ShopDTO;
786b1ee2   张志伟   feature(*): - 事故车...
26
  import cn.fw.valhalla.rpc.shirasawa.ShirasawaRpcService;
59ae8b14   张志伟   feature(*): 售后crm...
27
  import cn.fw.valhalla.rpc.shirasawa.dto.ClueStopDTO;
786b1ee2   张志伟   feature(*): - 事故车...
28
  import cn.fw.valhalla.rpc.shirasawa.dto.FollowInitDTO;
8587e21d   张志伟   :art:
29
30
  import cn.fw.valhalla.service.bus.cust.CustomerBizService;
  import cn.fw.valhalla.service.bus.cust.CustomerChangeBizService;
ad395b9c   张志伟   :art:
31
  import cn.fw.valhalla.service.bus.setting.SettingBizService;
b2f969bd   张志伟   :art:
32
  import cn.fw.valhalla.service.data.*;
65610b54   张志伟   :art:
33
  import com.baomidou.mybatisplus.core.toolkit.Wrappers;
9091e42f   张志伟   :art:
34
  import lombok.Getter;
65610b54   张志伟   :art:
35
  import lombok.extern.slf4j.Slf4j;
65610b54   张志伟   :art:
36
  import org.springframework.beans.factory.annotation.Autowired;
9091e42f   张志伟   :art:
37
  import org.springframework.beans.factory.annotation.Value;
c6ea42b4   张志伟   feature(*): 新增线索结...
38
  import org.springframework.data.redis.core.StringRedisTemplate;
ad395b9c   张志伟   :art:
39
  import org.springframework.transaction.annotation.Transactional;
b2f969bd   张志伟   :art:
40
  import org.springframework.util.CollectionUtils;
65610b54   张志伟   :art:
41
  
2a51fef7   张志伟   feature(*): 清理代码监...
42
  import java.time.Duration;
59ae8b14   张志伟   feature(*): 售后crm...
43
  import java.time.LocalDate;
23b952c1   张志伟   :art:
44
  import java.time.LocalDateTime;
b2f969bd   张志伟   :art:
45
  import java.util.*;
b2f969bd   张志伟   :art:
46
47
48
  import java.util.stream.Collectors;
  
  import static cn.fw.common.businessvalidator.Validator.BV;
8b00f03a   张志伟   :sparkles:
49
  import static cn.fw.valhalla.service.bus.setting.strategy.SettingStrategy.COMMON_BRAND_ID;
65610b54   张志伟   :art:
50
51
52
53
  
  /**
   * @author : kurisu
   * @className : AbstractFollowStrategy
2ffbcd9b   张志伟   feature(*): bug修复
54
   * @description : 策略抽象类
65610b54   张志伟   :art:
55
56
57
58
59
60
61
62
63
   * @date: 2020-08-17 10:42
   */
  @Slf4j
  public abstract class AbstractFollowStrategy implements FollowStrategy {
      @Autowired
      protected CustomerService customerService;
      @Autowired
      protected CustomerBaseInfoService customerBaseInfoService;
      @Autowired
8587e21d   张志伟   :art:
64
65
      protected CustomerBizService customerBizService;
      @Autowired
b2f969bd   张志伟   :art:
66
67
      protected UserService userService;
      @Autowired
ad395b9c   张志伟   :art:
68
69
70
      protected FollowNoticeRecordService followNoticeRecordService;
      @Autowired
      protected SettingBizService settingBizService;
23b952c1   张志伟   :art:
71
      @Autowired
8b00f03a   张志伟   :sparkles:
72
73
      protected FollowSettingDetailService followSettingDetailService;
      @Autowired
23b952c1   张志伟   :art:
74
      protected OopService oopService;
d64369bc   张志伟   :art:
75
      @Autowired
8587e21d   张志伟   :art:
76
      protected CustomerChangeBizService customerChangeBizService;
58d889cc   张志伟   新增重复提交校验和事故车跟进逾期时间查询
77
      @Autowired
786b1ee2   张志伟   feature(*): - 事故车...
78
79
80
81
82
83
84
      protected ShirasawaRpcService shirasawaRpcService;
      @Autowired
      protected ClueTaskService clueTaskService;
      @Autowired
      protected FollowClueService followClueService;
      @Autowired
      protected EhrRpcService ehrRpcService;
55003764   张志伟   feature(*): 售后crm...
85
86
      @Autowired
      protected MemberRpcService memberRpcService;
c6ea42b4   张志伟   feature(*): 新增线索结...
87
88
      @Autowired
      protected StringRedisTemplate redisTemplate;
58d889cc   张志伟   新增重复提交校验和事故车跟进逾期时间查询
89
90
91
      @Value("${spring.cache.custom.global-prefix}:follow")
      @Getter
      private String keyPrefix;
2d4ea8eb   张志伟   :art:
92
      @Value("${follow.todo.FMCode}")
9091e42f   张志伟   :art:
93
      @Getter
2d4ea8eb   张志伟   :art:
94
      private String FMCode;
2d4ea8eb   张志伟   :art:
95
96
97
      @Value("${follow.todo.RMCode}")
      @Getter
      private String RMCode;
2d4ea8eb   张志伟   :art:
98
99
100
      @Value("${follow.todo.IRCode}")
      @Getter
      private String IRCode;
2d4ea8eb   张志伟   :art:
101
102
103
      @Value("${follow.todo.ACCode}")
      @Getter
      private String ACCode;
c6ea42b4   张志伟   feature(*): 新增线索结...
104
105
106
      @Value("${spring.cache.custom.global-prefix}:follow:clue:change")
      @Getter
      private String clueChangeKeyPrefix;
65610b54   张志伟   :art:
107
108
  
  
fe7014b6   张志伟   :art:
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
      /**
       * 单位转换
       *
       * @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;
          }
      }
  
b2f969bd   张志伟   :art:
128
      @Override
2a40e3f8   张志伟   feature(*): 续保跟进调整
129
      @Transactional(rollbackFor = Exception.class)
59ae8b14   张志伟   feature(*): 售后crm...
130
131
132
133
134
135
136
137
138
      public void settingChanged(List<SettingVO> setting, Long groupId) {
          List<FollowClue> poolList = followClueService.list(Wrappers.<FollowClue>lambdaQuery()
                  .eq(FollowClue::getClueType, getFollowType())
                  .eq(FollowClue::getGroupId, groupId)
                  .eq(FollowClue::getClueState, ClueStatusEnum.WAITING)
          );
  
          if (CollectionUtils.isEmpty(poolList)) {
              return;
c115219a   张志伟   :sparkles:
139
          }
8b00f03a   张志伟   :sparkles:
140
141
142
143
144
145
          List<String> 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<Long> otherBrandIdList = followSettingDetailService.listObjs(Wrappers.<FollowSettingDetail>lambdaQuery()
e3aafddf   张志伟   :sparkles:
146
                              .select(FollowSettingDetail::getBrandId)
8b00f03a   张志伟   :sparkles:
147
148
149
150
                              .eq(FollowSettingDetail::getSettingId, settingId)
                              .eq(FollowSettingDetail::getType, SettingTypeEnum.FIRST_TRIGGER_TIME)
                              .eq(FollowSettingDetail::getYn, Boolean.TRUE)
                              .ne(FollowSettingDetail::getBrandId, brandId),
e3aafddf   张志伟   :sparkles:
151
                      bid -> Long.parseLong((String) bid)
8b00f03a   张志伟   :sparkles:
152
153
154
155
              );
  
              if (!CollectionUtils.isEmpty(otherBrandIdList)) {
                  List<String> frameNoList = customerService.listObjs(Wrappers.<Customer>lambdaQuery()
e3aafddf   张志伟   :sparkles:
156
                                  .select(Customer::getFrameNo)
8b00f03a   张志伟   :sparkles:
157
158
159
                                  .in(Customer::getBrandId, otherBrandIdList)
                                  .in(Customer::getFrameNo, vinList)
                                  .eq(Customer::getGroupId, groupId),
e3aafddf   张志伟   :sparkles:
160
                          Object::toString
8b00f03a   张志伟   :sparkles:
161
162
163
164
165
166
167
168
                  );
                  if (!CollectionUtils.isEmpty(frameNoList)) {
                      Set<String> vinSet = new HashSet<>(frameNoList);
                      poolList = poolList.stream().filter(r -> vinSet.contains(r.getVin())).collect(Collectors.toList());
                  }
              }
          } else {
              List<String> frameNoList = customerService.listObjs(Wrappers.<Customer>lambdaQuery()
e3aafddf   张志伟   :sparkles:
169
                              .select(Customer::getFrameNo)
8b00f03a   张志伟   :sparkles:
170
171
172
                              .eq(Customer::getBrandId, brandId)
                              .in(Customer::getFrameNo, vinList)
                              .eq(Customer::getGroupId, groupId),
e3aafddf   张志伟   :sparkles:
173
                      Object::toString
8b00f03a   张志伟   :sparkles:
174
175
176
177
178
179
180
              );
              if (!CollectionUtils.isEmpty(frameNoList)) {
                  Set<String> vinSet = new HashSet<>(frameNoList);
                  poolList = poolList.stream().filter(r -> vinSet.contains(r.getVin())).collect(Collectors.toList());
              }
          }
  
59ae8b14   张志伟   feature(*): 售后crm...
181
182
183
          updateClue(poolList, setting);
          SettingVO noticeSetting = setting.stream().filter(r -> SettingTypeEnum.FIRST_NOTICE_TIME.getValue().equals(r.getType())).findFirst().orElse(new SettingVO());
          updateNoticeRecord(poolList, noticeSetting);
b2f969bd   张志伟   :art:
184
185
      }
  
65610b54   张志伟   :art:
186
  
8587e21d   张志伟   :art:
187
188
      @Override
      @Transactional(rollbackFor = Exception.class)
9dad9666   张志伟   feature(*): 售后crm...
189
      public void closeTask(ClueTask task) {
78a11476   张志伟   取消二次分配
190
          final Long clueId = task.getClueId();
9dad9666   张志伟   feature(*): 售后crm...
191
          FollowClue clue = followClueService.getById(clueId);
78a11476   张志伟   取消二次分配
192
          BV.notNull(clue, () -> "跟进线索不存在: " + clueId);
9dad9666   张志伟   feature(*): 售后crm...
193
          task.setCloseTime(task.getDeadline().minusSeconds(1L));
2a40e3f8   张志伟   feature(*): 续保跟进调整
194
          task.setState(TaskStateEnum.DEFEAT);
78a11476   张志伟   取消二次分配
195
          task.setReason(TaskDefeatTypeEnum.C);
9dad9666   张志伟   feature(*): 售后crm...
196
          boolean rpcSucess = rpcStopTask(task);
9de0e2d7   张志伟   feature(*): 公共池线索...
197
198
199
          if (!rpcSucess) {
              log.info("跟进系统终止任务失败");
          }
9dad9666   张志伟   feature(*): 售后crm...
200
          task.setRpcSuccess(rpcSucess);
9dad9666   张志伟   feature(*): 售后crm...
201
          clueTaskService.updateById(task);
55003764   张志伟   feature(*): 售后crm...
202
          if (Objects.nonNull(clue)) {
2a40e3f8   张志伟   feature(*): 续保跟进调整
203
204
205
              clue.setCloseTime(task.getCloseTime());
              clue.setClueState(ClueStatusEnum.FAILURE);
              followClueService.updateById(clue);
9c86aa21   张志伟   feature(*): 线索到期后...
206
              redisTemplate.opsForSet().add(generateStopKey(), String.valueOf(task.getId()));
2a40e3f8   张志伟   feature(*): 续保跟进调整
207
              customerBizService.taskEndAbandon(task, clue);
9dad9666   张志伟   feature(*): 售后crm...
208
209
210
          }
      }
  
931be588   张志伟   feature(*): 售后crm...
211
212
213
214
215
216
217
218
      /**
       * [角色变动]结束任务
       *
       * @param task
       */
      @Override
      @Transactional(rollbackFor = Exception.class)
      public void onRoleChangeCloseTask(ClueTask task) {
931be588   张志伟   feature(*): 售后crm...
219
220
221
222
223
224
225
          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);
9de0e2d7   张志伟   feature(*): 公共池线索...
226
227
228
              if (!rpcSucess) {
                  log.info("跟进系统终止任务失败");
              }
931be588   张志伟   feature(*): 售后crm...
229
230
231
232
233
234
235
236
237
              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();
              }
8e20ca94   张志伟   fix: 修复一个角色变动导致的bug
238
              if (task.getFollowUser().equals(adviserId)) {
931be588   张志伟   feature(*): 售后crm...
239
240
                  return;
              }
2a40e3f8   张志伟   feature(*): 续保跟进调整
241
242
243
244
245
246
247
              if (Objects.isNull(adviserId)) {
                  boolean rpcSuccess = rpcStopTask(task);
                  if (!rpcSuccess) {
                      log.info("跟进系统终止任务失败");
                  }
                  task.setRpcSuccess(rpcSuccess);
                  clueTaskService.updateById(task);
931be588   张志伟   feature(*): 售后crm...
248
249
250
                  clue.setCloseTime(task.getCloseTime());
                  clue.setClueState(ClueStatusEnum.FAILURE);
                  followClueService.updateById(clue);
2a40e3f8   张志伟   feature(*): 续保跟进调整
251
  
9c86aa21   张志伟   feature(*): 线索到期后...
252
                  redisTemplate.opsForSet().add(generateStopKey(), String.valueOf(task.getId()));
931be588   张志伟   feature(*): 售后crm...
253
              } else {
2a40e3f8   张志伟   feature(*): 续保跟进调整
254
255
                  task.setRpcSuccess(true);
                  clueTaskService.updateById(task);
931be588   张志伟   feature(*): 售后crm...
256
257
                  createSecondaryTask(clue, adviserId);
              }
59ae8b14   张志伟   feature(*): 售后crm...
258
          }
59ae8b14   张志伟   feature(*): 售后crm...
259
260
      }
  
dac2e8b1   张志伟   :art:
261
262
      @Override
      @Transactional(rollbackFor = Exception.class)
2a51fef7   张志伟   feature(*): 清理代码监...
263
      public void forceStopClue(FollowClue clue, boolean fromTask) {
9dad9666   张志伟   feature(*): 售后crm...
264
265
266
          clue.setClueState(ClueStatusEnum.FAILURE);
          clue.setCloseTime(LocalDateTime.now());
          followClueService.updateById(clue);
c6ea42b4   张志伟   feature(*): 新增线索结...
267
          redisTemplate.opsForSet().add(generateStopKey(), String.valueOf(clue.getId()));
8bf465d6   张志伟   feature(*): 修改人员站岗信息
268
          ClueTask task = clueTaskService.queryOngoingTaskByClueId(clue.getId(), clue.getClueType());
9dad9666   张志伟   feature(*): 售后crm...
269
270
271
272
273
274
          if (Objects.isNull(task)) {
              return;
          }
          task.setState(TaskStateEnum.DEFEAT);
          task.setCloseTime(LocalDateTime.now());
          task.setReason(TaskDefeatTypeEnum.A);
2a51fef7   张志伟   feature(*): 清理代码监...
275
276
277
          if (fromTask) {
              task.setReason(TaskDefeatTypeEnum.C);
          }
9dad9666   张志伟   feature(*): 售后crm...
278
279
280
          boolean rpcSucess = rpcStopTask(task);
          task.setRpcSuccess(rpcSucess);
          clueTaskService.updateById(task);
91c29e23   张志伟   :fire:
281
      }
dac2e8b1   张志伟   :art:
282
  
91c29e23   张志伟   :fire:
283
284
      @Override
      @Transactional(rollbackFor = Exception.class)
55003764   张志伟   feature(*): 售后crm...
285
286
287
288
289
290
291
292
293
294
295
296
297
      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);
9c86aa21   张志伟   feature(*): 线索到期后...
298
              redisTemplate.opsForSet().add(generateStopKey(), String.valueOf(task.getId()));
55003764   张志伟   feature(*): 售后crm...
299
          }
dac2e8b1   张志伟   :art:
300
301
      }
  
55003764   张志伟   feature(*): 售后crm...
302
303
304
      /**
       * 当跟进待办结束(包括完成和逾期)
       *
2a40e3f8   张志伟   feature(*): 续保跟进调整
305
       * @param clue
55003764   张志伟   feature(*): 售后crm...
306
307
308
       * @param overdue
       */
      @Override
8587e21d   张志伟   :art:
309
      @Transactional(rollbackFor = Exception.class)
2a40e3f8   张志伟   feature(*): 续保跟进调整
310
      public void onFollowComplete(FollowClue clue, boolean overdue) {
8bf465d6   张志伟   feature(*): 修改人员站岗信息
311
          ClueTask task = clueTaskService.queryOngoingTaskByClueId(clue.getId(), clue.getClueType());
2a40e3f8   张志伟   feature(*): 续保跟进调整
312
          if (!overdue && Objects.nonNull(task)) {
d4e6d3ec   张志伟   feature(*): 跟进池接口调整
313
314
315
316
              Integer times = Optional.ofNullable(task.getTimes()).orElse(0);
              task.setTimes(times + 1);
              clueTaskService.updateById(task);
          }
8587e21d   张志伟   :art:
317
318
      }
  
931be588   张志伟   feature(*): 售后crm...
319
320
321
322
323
324
325
326
327
328
329
330
331
332
333
334
335
336
337
338
339
340
341
342
343
344
345
346
347
348
349
350
351
352
353
354
355
356
357
358
359
360
361
362
363
364
365
366
367
368
369
370
371
372
373
374
375
376
377
378
379
380
381
382
383
384
385
386
387
388
389
390
391
392
393
394
395
396
397
398
399
400
401
402
403
404
405
406
407
408
409
410
411
412
      /**
       * 任务结束同步状态到跟进系统
       *
       * @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<FollowClue> list, List<SettingVO> 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<FollowClue> list, SettingVO vo) {
          List<Long> idList = list.stream().map(FollowClue::getId).collect(Collectors.toList());
          List<FollowNoticeRecord> noticeList = followNoticeRecordService.list(Wrappers.<FollowNoticeRecord>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);
      }
  
931be588   张志伟   feature(*): 售后crm...
413
414
415
416
417
418
419
420
421
      /**
       * 线索成交
       *
       * @param originalData
       */
      protected void finishClue(OriginalData originalData, FollowClue followClue) {
          if (Objects.isNull(followClue)) {
              return;
          }
8bf465d6   张志伟   feature(*): 修改人员站岗信息
422
          ClueTask clueTask = clueTaskService.queryOngoingTaskByClueId(followClue.getId(), followClue.getClueType());
931be588   张志伟   feature(*): 售后crm...
423
424
425
426
          if (Objects.isNull(clueTask)) {
              return;
          }
          followClue.setClueState(ClueStatusEnum.COMPLETE);
591193c3   张志伟   feature(*): bug修复
427
          clueTask.setCloseTime(LocalDateTime.now());
931be588   张志伟   feature(*): 售后crm...
428
          clueTask.setFinishUser(originalData.getUserId());
2aef79cb   张志伟   feature(*): 续保成交判定调整
429
430
          clueTask.setState(TaskStateEnum.COMPLETE);
  
931be588   张志伟   feature(*): 售后crm...
431
432
433
434
          StaffInfoDTO infoDTO = ehrRpcService.queryStaffInfo(originalData.getUserId());
          if (Objects.nonNull(infoDTO)) {
              clueTask.setFinishUserName(infoDTO.getName());
          }
2aef79cb   张志伟   feature(*): 续保成交判定调整
435
436
437
          if (!originalData.getUserId().equals(clueTask.getFollowUser())) {
              clueTask.setState(TaskStateEnum.DEFEAT);
              clueTask.setReason(TaskDefeatTypeEnum.F);
d4e6d3ec   张志伟   feature(*): 跟进池接口调整
438
          }
931be588   张志伟   feature(*): 售后crm...
439
          clueTask.setFinishShop(originalData.getShopId());
b5f807fa   张志伟   feature(*): bug修复
440
          followClue.setCloseTime(clueTask.getCloseTime());
931be588   张志伟   feature(*): 售后crm...
441
          followClueService.updateById(followClue);
9c86aa21   张志伟   feature(*): 线索到期后...
442
          redisTemplate.opsForSet().add(generateStopKey(), String.valueOf(clueTask.getId()));
931be588   张志伟   feature(*): 售后crm...
443
444
445
446
447
448
449
450
451
452
453
454
455
456
457
458
          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());
eff44caf   张志伟   fix: 优化部分时间计算
459
          pool.setOriginTime(DateUtil.date2LocalDateTime(originalData.getGenerateTime()));
931be588   张志伟   feature(*): 售后crm...
460
461
462
          pool.setPlateNo(customer.getPlateNo());
          pool.setClueState(ClueStatusEnum.WAITING);
          pool.setClueType(followType);
d4e6d3ec   张志伟   feature(*): 跟进池接口调整
463
          pool.setBizId(originalData.getId());
931be588   张志伟   feature(*): 售后crm...
464
465
466
467
468
469
470
471
472
473
474
475
476
477
          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());
8b00f03a   张志伟   :sparkles:
478
          settingBizService.querySettingByType(followType, SettingTypeEnum.FIRST_TRIGGER_TIME, originalData.getGroupId(), customer.getBrandId())
931be588   张志伟   feature(*): 售后crm...
479
480
481
482
483
484
485
486
487
488
489
490
491
492
493
                  .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());
          }
  
8b00f03a   张志伟   :sparkles:
494
          settingBizService.querySettingByType(followType, SettingTypeEnum.FAIL_TIME, originalData.getGroupId(), customer.getBrandId())
931be588   张志伟   feature(*): 售后crm...
495
496
                  .ifPresent(r -> {
                      int detailValue = Optional.ofNullable(r.getDetailValue()).orElse(0);
931be588   张志伟   feature(*): 售后crm...
497
498
499
500
501
502
503
                      SettingUnitEnum unitEnum = Objects.requireNonNull(SettingUnitEnum.ofValue(r.getUnit()), "时间单位缺失");
                      LocalDateTime localDateTime = calTime(originTime, unitEnum, detailValue);
                      pool.setEndTime(localDateTime);
                  });
          return pool;
      }
  
786b1ee2   张志伟   feature(*): - 事故车...
504
505
      protected FollowInitDTO creteFollowInitDTO(FollowClue followClue, ClueTask clueTask) {
          Long customerId = null;
38443fbb   张志伟   feature(*): 修改人员站岗信息
506
          String customerName = null;
786b1ee2   张志伟   feature(*): - 事故车...
507
          Long memberId = null;
8b00f03a   张志伟   :sparkles:
508
          Long brandId = COMMON_BRAND_ID;
9dad9666   张志伟   feature(*): 售后crm...
509
          String phone = followClue.getSuggestMobile();
786b1ee2   张志伟   feature(*): - 事故车...
510
511
512
513
          if (StringUtils.isValid(followClue.getVin())) {
              CustomerDetailDto customerDetailDto = customerBizService.queryByFrameNo(followClue.getVin(), followClue.getGroupId());
              if (Objects.nonNull(customerDetailDto)) {
                  customerId = customerDetailDto.getId();
38443fbb   张志伟   feature(*): 修改人员站岗信息
514
                  customerName = customerDetailDto.getName();
786b1ee2   张志伟   feature(*): - 事故车...
515
                  memberId = customerDetailDto.getMemberId();
cc0f2cd4   张志伟   feature(*): 推送下次跟...
516
                  phone = customerDetailDto.getMobile();
8b00f03a   张志伟   :sparkles:
517
                  brandId = customerDetailDto.getBrandId();
786b1ee2   张志伟   feature(*): - 事故车...
518
519
              }
          }
59ae8b14   张志伟   feature(*): 售后crm...
520
          final FollowInitDTO followInitDTO = FollowInitDTO.builder()
786b1ee2   张志伟   feature(*): - 事故车...
521
                  .businessType(BusinessTypeEnum.AS)
ee77c91b   张志伟   feature(*): 终止任务b...
522
                  .type(DataTypeEnum.ofValue(clueTask.getType().getValue()))
786b1ee2   张志伟   feature(*): - 事故车...
523
                  .customerId(customerId)
38443fbb   张志伟   feature(*): 修改人员站岗信息
524
                  .customerName(customerName)
786b1ee2   张志伟   feature(*): - 事故车...
525
526
527
                  .memberId(memberId)
                  .plateNo(followClue.getPlateNo())
                  .frameNo(followClue.getVin())
9dad9666   张志伟   feature(*): 售后crm...
528
                  .contacts(phone)
2a40e3f8   张志伟   feature(*): 续保跟进调整
529
                  .detailId(String.valueOf(followClue.getId()))
786b1ee2   张志伟   feature(*): - 事故车...
530
531
532
533
534
535
536
                  .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())
2a51fef7   张志伟   feature(*): 清理代码监...
537
                  .followDuration(Duration.ofHours(36L))
786b1ee2   张志伟   feature(*): - 事故车...
538
                  .build();
59ae8b14   张志伟   feature(*): 售后crm...
539
540
541
542
543
  
          ShopDTO shop = oopService.shop(clueTask.getFollowShop());
          if (Objects.nonNull(shop)) {
              followInitDTO.setShopName(shop.getShopName());
          }
364db3cc   张志伟   :sparkles:
544
545
          // 除事故车以外,其他待办跟进时长统一配置
          settingBizService.querySettingByType(FollowTypeEnum.OT, SettingTypeEnum.EFFECTIVE_TIME, clueTask.getGroupId(), brandId)
59ae8b14   张志伟   feature(*): 售后crm...
546
                  .ifPresent(r -> {
2a51fef7   张志伟   feature(*): 清理代码监...
547
548
549
550
551
                      Integer unit = r.getUnit();
                      int detailValue = Optional.ofNullable(r.getDetailValue()).orElse(0);
                      Duration duration = transferDuration(detailValue, unit);
                      BV.notNull(duration, () -> "设置有误,周期计算不成功");
                      followInitDTO.setFollowDuration(duration);
59ae8b14   张志伟   feature(*): 售后crm...
552
553
554
555
556
                  });
          Map<String, String> noteMap = createNoteMap(followClue);
          followInitDTO.setNoteMap(noteMap);
  
          return followInitDTO;
786b1ee2   张志伟   feature(*): - 事故车...
557
558
      }
  
9dad9666   张志伟   feature(*): 售后crm...
559
      protected FollowInitDTO creteRedistributionFollowInitDTO(FollowClue followClue, ClueTask clueTask) {
2a40e3f8   张志伟   feature(*): 续保跟进调整
560
          final LocalDateTime nextTime = clueTask.getBeginTime();
9dad9666   张志伟   feature(*): 售后crm...
561
          final FollowInitDTO followInitDTO = creteFollowInitDTO(followClue, clueTask);
c157575e   张志伟   fix: 优化部分时间计算
562
          followInitDTO.setGenerateTime(DateUtil.localDateTime2Date(nextTime));
8b00f03a   张志伟   :sparkles:
563
564
565
566
567
          Long brandId = COMMON_BRAND_ID;
          Customer customer = customerService.queryByFrameNo(followClue.getVin(), followClue.getGroupId());
          if (Objects.nonNull(customer)) {
              brandId = customer.getBrandId();
          }
5b538595   张志伟   feature(*): 新增查询线...
568
          settingBizService.querySettingByType(FollowTypeEnum.OT, SettingTypeEnum.EFFECTIVE_TIME, clueTask.getGroupId(), brandId)
9dad9666   张志伟   feature(*): 售后crm...
569
                  .ifPresent(r -> {
2a51fef7   张志伟   feature(*): 清理代码监...
570
571
572
573
574
                      Integer unit = r.getUnit();
                      int detailValue = Optional.ofNullable(r.getDetailValue()).orElse(0);
                      Duration duration = transferDuration(detailValue, unit);
                      BV.notNull(duration, () -> "设置有误,周期计算不成功");
                      followInitDTO.setFollowDuration(duration);
9dad9666   张志伟   feature(*): 售后crm...
575
576
577
578
579
580
                  });
          Map<String, String> noteMap = createNoteMap(followClue);
          followInitDTO.setNoteMap(noteMap);
          return followInitDTO;
      }
  
23b952c1   张志伟   :art:
581
582
583
      /**
       * 生成消息推送
       *
8587e21d   张志伟   :art:
584
       * @param cluePool
59ae8b14   张志伟   feature(*): 售后crm...
585
       * @param customerId
23b952c1   张志伟   :art:
586
       */
8b00f03a   张志伟   :sparkles:
587
      protected void createFirstNotice(final FollowClue cluePool, final Long customerId, final Long brandId) {
59ae8b14   张志伟   feature(*): 售后crm...
588
          if (!cluePool.getEndTime().isAfter(cluePool.getStartTime()) || !cluePool.getEndTime().isAfter(LocalDateTime.now())) {
9b497427   张志伟   :art:
589
              return;
6dc5de50   张志伟   :art:
590
          }
23b952c1   张志伟   :art:
591
          final FollowNoticeRecord record = new FollowNoticeRecord();
8587e21d   张志伟   :art:
592
593
          record.setClueId(cluePool.getId());
          record.setFollowType(cluePool.getClueType());
59ae8b14   张志伟   feature(*): 售后crm...
594
          record.setCustomerId(customerId);
23b952c1   张志伟   :art:
595
          record.setStatus(SendStatusEnum.NOT_SENT);
8b00f03a   张志伟   :sparkles:
596
          settingBizService.querySettingByType(cluePool.getClueType(), SettingTypeEnum.FIRST_NOTICE_TIME, cluePool.getGroupId(), brandId)
59ae8b14   张志伟   feature(*): 售后crm...
597
598
599
600
601
602
603
604
605
                  .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));
                  });
23b952c1   张志伟   :art:
606
          record.setCreateTime(new Date());
9b497427   张志伟   :art:
607
          followNoticeRecordService.save(record);
612d25d9   张志伟   :art:
608
609
      }
  
931be588   张志伟   feature(*): 售后crm...
610
      protected boolean rpcStopTask(ClueTask clueTask) {
2a51fef7   张志伟   feature(*): 清理代码监...
611
612
613
614
          TaskDefeatTypeEnum reason = clueTask.getReason();
          if (TaskDefeatTypeEnum.B.equals(reason) || TaskDefeatTypeEnum.C.equals(reason)) {
              return true;
          }
931be588   张志伟   feature(*): 售后crm...
615
616
617
618
619
          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);
2a51fef7   张志伟   feature(*): 清理代码监...
620
621
622
623
624
625
626
627
628
              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);
              }
931be588   张志伟   feature(*): 售后crm...
629
          }
2a40e3f8   张志伟   feature(*): 续保跟进调整
630
          clueStopDTO.setDetailId(String.valueOf(clueTask.getClueId()));
931be588   张志伟   feature(*): 售后crm...
631
632
633
634
635
636
637
          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());
142fc828   张志伟   feature(*): 终止任务b...
638
639
          clueStopDTO.setUserId(clueTask.getFollowUser());
          clueStopDTO.setUserName(clueTask.getFollowUserName());
931be588   张志伟   feature(*): 售后crm...
640
641
642
643
          return shirasawaRpcService.stopTask(clueStopDTO);
      }
  
  
786b1ee2   张志伟   feature(*): - 事故车...
644
      protected ClueTask createNewTask(FollowClue followClue) {
59ae8b14   张志伟   feature(*): 售后crm...
645
646
647
648
          final FollowTypeEnum followTypeEnum = followClue.getClueType();
          final ClueTask clueTask = new ClueTask();
          clueTask.setClueId(followClue.getId());
          clueTask.setType(followTypeEnum);
1725a44b   张志伟   feature(*): 开始线索时...
649
          clueTask.setBeginTime(followClue.getStartTime());
59ae8b14   张志伟   feature(*): 售后crm...
650
651
          clueTask.setRedistribution(Boolean.FALSE);
          clueTask.setDeadline(followClue.getEndTime());
59ae8b14   张志伟   feature(*): 售后crm...
652
653
654
655
656
657
658
659
660
          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();
ceeb4fbb   张志伟   feature(*): bug修复
661
662
663
664
                  ShopDTO shop = oopService.shop(shopId);
                  if (Objects.isNull(shop)) {
                      shopId = followClue.getSuggestShopId();
                  }
59ae8b14   张志伟   feature(*): 售后crm...
665
666
667
668
669
670
671
              }
          }
          if (Objects.isNull(shopId)) {
              shopId = followClue.getSuggestShopId();
          }
          clueTask.setFollowShop(shopId);
          clueTask.setFollowUser(userId);
89bd2e6c   张志伟   feature(*): 新增区域站...
672
          clueTask.setVersion(2);
786b1ee2   张志伟   feature(*): - 事故车...
673
674
675
          return clueTask;
      }
  
59ae8b14   张志伟   feature(*): 售后crm...
676
677
678
679
680
681
682
683
684
685
      protected void fillTaskUser(ClueTask clueTask, List<PostUserDTO> userByRole) {
          Long userId = clueTask.getFollowUser();
          if (Objects.nonNull(userId)) {
              for (PostUserDTO dto : userByRole) {
                  if (dto.getUserId().equals(clueTask.getFollowUser())) {
                      clueTask.setFollowUserName(dto.getUserName());
                      break;
                  }
              }
          }
2ffbcd9b   张志伟   feature(*): bug修复
686
687
688
          if (StringUtils.isEmpty(clueTask.getFollowUserName())) {
              userId = null;
          }
59ae8b14   张志伟   feature(*): 售后crm...
689
690
691
692
693
694
695
696
697
  
          if (Objects.isNull(userId)) {
              int randomIndex = new Random().nextInt(userByRole.size());
              PostUserDTO userDTO = userByRole.get(randomIndex);
              clueTask.setFollowUser(userDTO.getUserId());
              clueTask.setFollowUserName(userDTO.getUserName());
          }
      }
  
786b1ee2   张志伟   feature(*): - 事故车...
698
699
700
701
      protected Map<String, String> createNoteMap(FollowClue followClue) {
          Map<String, String> dynamicMap = new HashMap<>();
          if (Objects.nonNull(followClue)) {
              FollowTypeEnum clueType = followClue.getClueType();
12c9fad1   张志伟   bug fix
702
              String name = "-";
786b1ee2   张志伟   feature(*): - 事故车...
703
704
              CustomerDetailDto vo = customerBizService.queryByFrameNo(followClue.getVin(), followClue.getGroupId());
              if (Objects.nonNull(vo)) {
12c9fad1   张志伟   bug fix
705
                  name = StringUtils.isValid(vo.getName()) ? vo.getName() : "-";
786b1ee2   张志伟   feature(*): - 事故车...
706
              }
12c9fad1   张志伟   bug fix
707
              dynamicMap.put("name", name);
786b1ee2   张志伟   feature(*): - 事故车...
708
709
710
              dynamicMap.put("state", "1");
              dynamicMap.put("plateNo", StringUtils.isValid(followClue.getPlateNo()) ? followClue.getPlateNo() : "-");
              if (FollowTypeEnum.FM.equals(clueType)) {
e3c68722   张志伟   feature(*): 终止任务b...
711
712
                  dynamicMap.put("buyDate", DateUtil.getStringDateShort(vo.getBuyDate(), "-"));
                  dynamicMap.put("expirTime", DateUtil.getStringDateShort(DateUtil.localDateTime2Date(followClue.getEndTime()), "-"));
786b1ee2   张志伟   feature(*): - 事故车...
713
714
              } else if (FollowTypeEnum.RM.equals(clueType)) {
                  dynamicMap.put("currentMileage", Optional.ofNullable(vo.getCurrentMileage()).map(String::valueOf).orElse("-"));
e3c68722   张志伟   feature(*): 终止任务b...
715
                  dynamicMap.put("arrivalTime", DateUtil.getStringDateShort(vo.getArrivalTime(), "-"));
786b1ee2   张志伟   feature(*): - 事故车...
716
              } else if (FollowTypeEnum.IR.equals(clueType)) {
dac4d790   张志伟   feature(*): 推送下次跟...
717
                  dynamicMap.put("expirTime", DateUtil.getStringDateShort(DateUtil.localDateTime2Date(followClue.getOriginTime()), "-"));
786b1ee2   张志伟   feature(*): - 事故车...
718
719
720
721
722
723
724
725
                  dynamicMap.put("insComName", "-");
              } else if (FollowTypeEnum.AC.equals(clueType)) {
                  dynamicMap.put("insComName", "-");
              }
          }
          return dynamicMap;
      }
  
931be588   张志伟   feature(*): 售后crm...
726
727
728
729
730
731
732
733
734
      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);
aa94ba59   张志伟   fix: 修复一个角色变动导致的bug
735
          redistributionTask.setFollowShop(clue.getSuggestShopId());
931be588   张志伟   feature(*): 售后crm...
736
737
738
739
740
          StaffInfoDTO staffInfoDTO = ehrRpcService.queryStaffInfo(userId);
          if (Objects.nonNull(staffInfoDTO)) {
              redistributionTask.setFollowUserName(staffInfoDTO.getName());
          }
          redistributionTask.setGroupId(clue.getGroupId());
361bbddb   张志伟   feature(*): 修复bug
741
          redistributionTask.setVersion(2);
e9b3cf04   张志伟   bug修复
742
          clueTaskService.save(redistributionTask);
931be588   张志伟   feature(*): 售后crm...
743
          FollowInitDTO followInitDTO = creteRedistributionFollowInitDTO(clue, redistributionTask);
b245c23a   张志伟   feature(*): 续保跟进调整
744
          shirasawaRpcService.changeFollowData(followInitDTO, redistributionTask.getBeginTime().toLocalDate());
931be588   张志伟   feature(*): 售后crm...
745
          followClueService.updateById(clue);
931be588   张志伟   feature(*): 售后crm...
746
      }
c6ea42b4   张志伟   feature(*): 新增线索结...
747
  
c6ea42b4   张志伟   feature(*): 新增线索结...
748
749
750
      protected String generateStopKey() {
          return String.format("%s:%s", getClueChangeKeyPrefix(), "STOP");
      }
65610b54   张志伟   :art:
751
  }