|
|
@@ -39,6 +39,7 @@ import com.fs.sop.service.IQwSopLogsService;
|
|
|
import com.fs.sop.service.IQwSopTempContentService;
|
|
|
import com.fs.sop.service.IQwSopTempRulesService;
|
|
|
import com.fs.sop.service.IQwSopTempVoiceService;
|
|
|
+import com.fs.sop.service.ISopGenerationFailedLogService;
|
|
|
import com.fs.sop.vo.QwCreateLinkByAppVO;
|
|
|
import com.fs.sop.vo.SopUserLogsVo;
|
|
|
import com.fs.system.service.ISysConfigService;
|
|
|
@@ -193,6 +194,9 @@ public class SopLogsTaskServiceImpl implements SopLogsTaskService {
|
|
|
@Autowired
|
|
|
LiveWatchLogMapper liveWatchLogMapper;
|
|
|
|
|
|
+ @Autowired
|
|
|
+ private ISopGenerationFailedLogService sopGenerationFailedLogService;
|
|
|
+
|
|
|
@PostConstruct
|
|
|
public void init() {
|
|
|
loadCourseConfig();
|
|
|
@@ -695,6 +699,24 @@ public class SopLogsTaskServiceImpl implements SopLogsTaskService {
|
|
|
if (!externalContactIdList.isEmpty()) {
|
|
|
List<QwExternalContact> list = qwExternalContactService.list(new QueryWrapper<QwExternalContact>().isNotNull("fs_user_id").in("id", externalContactIdList));
|
|
|
Map<Long, QwExternalContact> map = PubFun.listToMapByGroupObject(list, QwExternalContact::getId);
|
|
|
+//
|
|
|
+// // 记录被过滤的客户(未注册小程序)
|
|
|
+// List<SopUserLogsInfo> filteredCustomers = sopUserLogsInfos.stream()
|
|
|
+// .filter(e -> !map.containsKey(e.getExternalId()))
|
|
|
+// .collect(Collectors.toList());
|
|
|
+//
|
|
|
+// if (!filteredCustomers.isEmpty()) {
|
|
|
+// try {
|
|
|
+// String dayFormattedSendTime = OUTPUT_FORMATTER.format(targetDate);
|
|
|
+// recordFailedCustomers(filteredCustomers, logVo, day, dayFormattedSendTime, content.getTime(),
|
|
|
+// SopGenerationFailedLog.FailType.NOT_REGISTERED, "未注册小程序(isRegister=1过滤)",
|
|
|
+// qwUserId, qwUserByRedis.getQwUserName(), companyUserId, companyId, logVo.getCorpId());
|
|
|
+// } catch (Exception e) {
|
|
|
+// log.error("记录未注册客户失败: sopId={}, userLogsId={}, error={}",
|
|
|
+// logVo.getSopId(), logVo.getId(), e.getMessage(), e);
|
|
|
+// }
|
|
|
+// }
|
|
|
+
|
|
|
sopUserLogsInfos = sopUserLogsInfos.stream().filter(e -> map.containsKey(e.getExternalId())).collect(Collectors.toList());
|
|
|
}
|
|
|
}
|
|
|
@@ -844,6 +866,9 @@ public class SopLogsTaskServiceImpl implements SopLogsTaskService {
|
|
|
// }
|
|
|
} else {
|
|
|
// 处理每个 externalContactId
|
|
|
+ // 记录所有被跳过的客户
|
|
|
+ List<SopUserLogsInfo> skippedCustomers = new ArrayList<>();
|
|
|
+
|
|
|
sopUserLogsInfos.forEach(contactId -> {
|
|
|
try {
|
|
|
// 空值检查
|
|
|
@@ -853,10 +878,12 @@ public class SopLogsTaskServiceImpl implements SopLogsTaskService {
|
|
|
}
|
|
|
if (contactId.getExternalId() == null) {
|
|
|
log.error("contactId.getExternalId() 为 null,contactId: {}", contactId);
|
|
|
+ skippedCustomers.add(contactId);
|
|
|
return;
|
|
|
}
|
|
|
if (contactId.getExternalContactId() == null) {
|
|
|
log.error("contactId.getExternalContactId() 为 null,contactId: {}", contactId);
|
|
|
+ skippedCustomers.add(contactId);
|
|
|
return;
|
|
|
}
|
|
|
|
|
|
@@ -871,8 +898,22 @@ public class SopLogsTaskServiceImpl implements SopLogsTaskService {
|
|
|
} catch (Exception e) {
|
|
|
e.printStackTrace();
|
|
|
log.error("处理 externalContactId {} 时发生异常", contactId, e);
|
|
|
+ if (contactId != null) {
|
|
|
+ skippedCustomers.add(contactId);
|
|
|
+ }
|
|
|
}
|
|
|
});
|
|
|
+
|
|
|
+ // 批量记录被跳过的客户
|
|
|
+ if (!skippedCustomers.isEmpty()) {
|
|
|
+ try {
|
|
|
+ recordFailedCustomersInBatch(skippedCustomers, logVo, formattedSendTime, content.getTime(),
|
|
|
+ qwUserId, qwUserName, companyUserId, companyId, logVo.getCorpId());
|
|
|
+ } catch (Exception e) {
|
|
|
+ log.error("批量记录跳过客户失败: sopId={}, userLogsId={}, error={}",
|
|
|
+ logVo.getSopId(), logVo.getId(), e.getMessage(), e);
|
|
|
+ }
|
|
|
+ }
|
|
|
}
|
|
|
// // 处理每个 externalContactId
|
|
|
// sopUserLogsInfos.forEach(contactId -> {
|
|
|
@@ -2738,4 +2779,176 @@ public class SopLogsTaskServiceImpl implements SopLogsTaskService {
|
|
|
private boolean isValidExternalContact(QwExternalContact externalContact) {
|
|
|
return externalContact.getStatus() == 0 || externalContact.getStatus() == 2 || externalContact.getStatus() == 3;
|
|
|
}
|
|
|
+
|
|
|
+ /**
|
|
|
+ * 批量记录被过滤/跳过的客户
|
|
|
+ *
|
|
|
+ * @param customers 被过滤的客户列表
|
|
|
+ * @param logVo SOP营期信息
|
|
|
+ * @param sendTime 发送时间
|
|
|
+ * @param elementTime 元素时间
|
|
|
+ * @param qwUserId 企微员工ID
|
|
|
+ * @param qwUserName 企微员工名称
|
|
|
+ * @param companyUserId 公司员工ID
|
|
|
+ * @param companyId 公司ID
|
|
|
+ * @param corpId 企微主体ID
|
|
|
+ */
|
|
|
+ private void recordFailedCustomersInBatch(List<SopUserLogsInfo> customers,
|
|
|
+ SopUserLogsVo logVo,
|
|
|
+ String sendTime,
|
|
|
+ String elementTime,
|
|
|
+ String qwUserId,
|
|
|
+ String qwUserName,
|
|
|
+ String companyUserId,
|
|
|
+ String companyId,
|
|
|
+ String corpId) {
|
|
|
+ if (customers == null || customers.isEmpty()) {
|
|
|
+ return;
|
|
|
+ }
|
|
|
+
|
|
|
+ List<SopGenerationFailedLog> failedLogs = new ArrayList<>();
|
|
|
+
|
|
|
+ for (SopUserLogsInfo customer : customers) {
|
|
|
+ try {
|
|
|
+ SopGenerationFailedLog failedLog = new SopGenerationFailedLog();
|
|
|
+
|
|
|
+ failedLog.setSopId(logVo.getSopId());
|
|
|
+ failedLog.setUserLogsId(logVo.getId());
|
|
|
+ failedLog.setExternalId(customer.getExternalId());
|
|
|
+ failedLog.setFsUserId(customer.getFsUserId());
|
|
|
+
|
|
|
+ failedLog.setQwUserId(qwUserId);
|
|
|
+ failedLog.setQwUserName(qwUserName);
|
|
|
+ failedLog.setCompanyUserId(companyUserId);
|
|
|
+ failedLog.setCompanyId(companyId);
|
|
|
+ failedLog.setCorpId(corpId);
|
|
|
+
|
|
|
+ SopGenerationFailedLog.FailType failType;
|
|
|
+ String failReason;
|
|
|
+
|
|
|
+ if (customer.getExternalId() == null) {
|
|
|
+ failType = SopGenerationFailedLog.FailType.DATA_MISSING;
|
|
|
+ failReason = "客户ID(externalId)为空";
|
|
|
+ } else if (customer.getExternalContactId() == null) {
|
|
|
+ failType = SopGenerationFailedLog.FailType.DATA_MISSING;
|
|
|
+ failReason = "企微客户ID(externalContactId)为空";
|
|
|
+ } else if (Integer.valueOf(1).equals(customer.getIsDaysNotStudy())) {
|
|
|
+ failType = SopGenerationFailedLog.FailType.E_LEVEL_FILTERED;
|
|
|
+ failReason = "E级客户过滤(非官方群发且isDaysNotStudy=1)";
|
|
|
+ } else {
|
|
|
+ failType = SopGenerationFailedLog.FailType.OTHER;
|
|
|
+ failReason = "其他原因跳过处理";
|
|
|
+ }
|
|
|
+
|
|
|
+ failedLog.setFailType(failType.getCode());
|
|
|
+ String fsUserIdStr = customer.getFsUserId() == null ? "NULL" : customer.getFsUserId().toString();
|
|
|
+ failedLog.setFailReason(failReason + " (fs_user_id=" + fsUserIdStr + ")");
|
|
|
+
|
|
|
+ // 补发状态
|
|
|
+ failedLog.setIsRetry(SopGenerationFailedLog.RetryStatus.NOT_RETRY.getCode());
|
|
|
+
|
|
|
+ // 任务信息
|
|
|
+ failedLog.setDayNum(0L); // 这里没有day信息,设为0
|
|
|
+ failedLog.setSendTime(sendTime);
|
|
|
+ failedLog.setElementTime(elementTime);
|
|
|
+
|
|
|
+ failedLogs.add(failedLog);
|
|
|
+ } catch (Exception e) {
|
|
|
+ log.error("构建失败日志对象失败: externalId={}, error={}",
|
|
|
+ customer.getExternalId(), e.getMessage(), e);
|
|
|
+ }
|
|
|
+ }
|
|
|
+
|
|
|
+ // 批量插入
|
|
|
+ if (!failedLogs.isEmpty()) {
|
|
|
+ try {
|
|
|
+ int count = sopGenerationFailedLogService.batchInsert(failedLogs);
|
|
|
+ log.info("批量记录SOP生成跳过日志成功: sopId={}, userLogsId={}, count={}",
|
|
|
+ logVo.getSopId(), logVo.getId(), count);
|
|
|
+ } catch (Exception e) {
|
|
|
+ log.error("批量插入跳过日志失败: sopId={}, userLogsId={}, error={}",
|
|
|
+ logVo.getSopId(), logVo.getId(), e.getMessage(), e);
|
|
|
+ }
|
|
|
+ }
|
|
|
+ }
|
|
|
+
|
|
|
+ /**
|
|
|
+ * 记录被过滤的客户
|
|
|
+ *
|
|
|
+ * @param filteredCustomers 被过滤的客户列表
|
|
|
+ * @param logVo SOP营期信息
|
|
|
+ * @param currentDay 当前天数
|
|
|
+ * @param sendTime 发送时间
|
|
|
+ * @param elementTime 元素时间
|
|
|
+ * @param failType 失败类型
|
|
|
+ * @param failReasonPrefix 失败原因前缀
|
|
|
+ * @param qwUserId 企微员工ID(发送人)
|
|
|
+ * @param qwUserName 企微员工名称(发送人)
|
|
|
+ * @param companyUserId 公司员工ID
|
|
|
+ * @param companyId 公司ID
|
|
|
+ * @param corpId 企微主体ID
|
|
|
+ */
|
|
|
+ private void recordFailedCustomers(List<SopUserLogsInfo> filteredCustomers,
|
|
|
+ SopUserLogsVo logVo,
|
|
|
+ long currentDay,
|
|
|
+ String sendTime,
|
|
|
+ String elementTime,
|
|
|
+ SopGenerationFailedLog.FailType failType,
|
|
|
+ String failReasonPrefix,
|
|
|
+ String qwUserId,
|
|
|
+ String qwUserName,
|
|
|
+ String companyUserId,
|
|
|
+ String companyId,
|
|
|
+ String corpId) {
|
|
|
+ if (filteredCustomers == null || filteredCustomers.isEmpty()) {
|
|
|
+ return;
|
|
|
+ }
|
|
|
+
|
|
|
+ List<SopGenerationFailedLog> failedLogs = new ArrayList<>();
|
|
|
+
|
|
|
+ for (SopUserLogsInfo customer : filteredCustomers) {
|
|
|
+ try {
|
|
|
+ SopGenerationFailedLog failedLog = new SopGenerationFailedLog();
|
|
|
+
|
|
|
+ failedLog.setSopId(logVo.getSopId());
|
|
|
+ failedLog.setUserLogsId(logVo.getId());
|
|
|
+ failedLog.setExternalId(customer.getExternalId());
|
|
|
+ failedLog.setFsUserId(customer.getFsUserId());
|
|
|
+
|
|
|
+ failedLog.setQwUserId(qwUserId);
|
|
|
+ failedLog.setQwUserName(qwUserName);
|
|
|
+ failedLog.setCompanyUserId(companyUserId);
|
|
|
+ failedLog.setCompanyId(companyId);
|
|
|
+ failedLog.setCorpId(corpId);
|
|
|
+
|
|
|
+ failedLog.setFailType(failType.getCode());
|
|
|
+ String fsUserIdStr = customer.getFsUserId() == null ? "NULL" : customer.getFsUserId().toString();
|
|
|
+ failedLog.setFailReason(failReasonPrefix + " (fs_user_id=" + fsUserIdStr + ")");
|
|
|
+
|
|
|
+
|
|
|
+ failedLog.setIsRetry(SopGenerationFailedLog.RetryStatus.NOT_RETRY.getCode());
|
|
|
+
|
|
|
+
|
|
|
+ failedLog.setDayNum(currentDay);
|
|
|
+ failedLog.setSendTime(sendTime);
|
|
|
+ failedLog.setElementTime(elementTime);
|
|
|
+
|
|
|
+ failedLogs.add(failedLog);
|
|
|
+ } catch (Exception e) {
|
|
|
+ log.error("构建失败日志对象失败: externalId={}, error={}",
|
|
|
+ customer.getExternalId(), e.getMessage(), e);
|
|
|
+ }
|
|
|
+ }
|
|
|
+
|
|
|
+ if (!failedLogs.isEmpty()) {
|
|
|
+ try {
|
|
|
+ int count = sopGenerationFailedLogService.batchInsert(failedLogs);
|
|
|
+ log.info("记录SOP生成失败日志成功: sopId={}, userLogsId={}, qwUserId={}, qwUserName={}, failType={}, count={}",
|
|
|
+ logVo.getSopId(), logVo.getId(), qwUserId, qwUserName, failType.getDescription(), count);
|
|
|
+ } catch (Exception e) {
|
|
|
+ log.error("批量插入失败日志失败: sopId={}, userLogsId={}, error={}",
|
|
|
+ logVo.getSopId(), logVo.getId(), e.getMessage(), e);
|
|
|
+ }
|
|
|
+ }
|
|
|
+ }
|
|
|
}
|