Commit 7a7a4e0ed87fa29fdca1ddbc3631297722c43043
Merge remote-tracking branch 'origin/test'
Showing
16 changed files
with
290 additions
and
158 deletions
fw-valhalla-dao/src/main/java/cn/fw/valhalla/dao/mapper/CustomerImportMapper.java deleted
1 | -package cn.fw.valhalla.dao.mapper; | |
2 | - | |
3 | -import cn.fw.valhalla.domain.db.customer.CustomerImport; | |
4 | -import com.baomidou.mybatisplus.core.mapper.BaseMapper; | |
5 | -import org.springframework.stereotype.Repository; | |
6 | - | |
7 | -/** | |
8 | - * @author : kurisu | |
9 | - * @className : CustomerImportMapper | |
10 | - * @description : 档案导入处理 | |
11 | - * @date: 2020-11-18 15:03 | |
12 | - */ | |
13 | -@Repository | |
14 | -public interface CustomerImportMapper extends BaseMapper<CustomerImport> { | |
15 | -} |
fw-valhalla-dao/src/main/resources/mapper/CustomerImportMapper.xml deleted
fw-valhalla-domain/pom.xml
... | ... | @@ -19,6 +19,11 @@ |
19 | 19 | <artifactId>fw-valhalla-common</artifactId> |
20 | 20 | <optional>true</optional> |
21 | 21 | </dependency> |
22 | + <dependency> | |
23 | + <groupId>cn.fw</groupId> | |
24 | + <artifactId>fw-common-web</artifactId> | |
25 | + <optional>true</optional> | |
26 | + </dependency> | |
22 | 27 | <!-- util --> |
23 | 28 | <dependency> |
24 | 29 | <groupId>org.hibernate.validator</groupId> | ... | ... |
fw-valhalla-domain/src/main/java/cn/fw/valhalla/domain/db/customer/CustomerImport.java deleted
1 | -package cn.fw.valhalla.domain.db.customer; | |
2 | - | |
3 | -import cn.fw.common.data.entity.BaseEntity; | |
4 | -import lombok.Data; | |
5 | -import lombok.EqualsAndHashCode; | |
6 | -import lombok.ToString; | |
7 | - | |
8 | -import java.util.Date; | |
9 | - | |
10 | -/** | |
11 | - * @author : kurisu | |
12 | - * @className : CustomerImport | |
13 | - * @description : 档案导入数据 | |
14 | - * @date: 2020-11-18 14:59 | |
15 | - */ | |
16 | -@Data | |
17 | -@ToString(callSuper = true) | |
18 | -@EqualsAndHashCode(callSuper = true) | |
19 | -public class CustomerImport extends BaseEntity<CustomerImport, Long> { | |
20 | - private String plateNo; | |
21 | - private String adviserName; | |
22 | - private Long adviserId; | |
23 | - private String brandName; | |
24 | - private String seriesName; | |
25 | - private String specName; | |
26 | - private String specCode; | |
27 | - private String name; | |
28 | - private Long shopId; | |
29 | - private String engineNo; | |
30 | - private String mobile; | |
31 | - private Integer currentMileage; | |
32 | - private Date arrivalTime; | |
33 | - private String frameNo; | |
34 | - private Integer mark; | |
35 | - private Boolean needAssigning; | |
36 | - private Long oldId; | |
37 | -} |
fw-valhalla-domain/src/main/java/cn/fw/valhalla/domain/db/ipt/CustomerInitClue.kt
... | ... | @@ -15,22 +15,22 @@ import java.time.LocalDateTime |
15 | 15 | */ |
16 | 16 | @NoArg |
17 | 17 | data class CustomerInitClue( |
18 | - var plateNo: String?, | |
18 | + val plateNo: String?, | |
19 | 19 | val vin: String, |
20 | - var brandName: String?, | |
21 | - var seriesName: String?, | |
22 | - var specName: String?, | |
23 | - var engineNo: String?, | |
24 | - var buyDate: LocalDate?, | |
25 | - var customerName: String?, | |
20 | + val brandName: String?, | |
21 | + val seriesName: String?, | |
22 | + val specName: String?, | |
23 | + val engineNo: String?, | |
24 | + val buyDate: LocalDate?, | |
25 | + val customerName: String?, | |
26 | 26 | val customerMobile: String, |
27 | - var arrivalTime: LocalDateTime?, | |
28 | - var arrivalMileage: Int?, | |
29 | - var senderName: String?, | |
27 | + val arrivalTime: LocalDateTime?, | |
28 | + val arrivalMileage: Int?, | |
29 | + val senderName: String?, | |
30 | 30 | val senderMobile: String, |
31 | 31 | val adviserId: Long, |
32 | - var adviserName: String?, | |
32 | + val adviserName: String?, | |
33 | 33 | val shopId: Long, |
34 | 34 | val groupId: Long, |
35 | - var yn: Boolean, | |
35 | + val yn: Boolean, | |
36 | 36 | ) : BaseAuditableTimeEntity<CustomerInitClue, Long>() |
37 | 37 | \ No newline at end of file | ... | ... |
fw-valhalla-domain/src/main/java/cn/fw/valhalla/domain/db/ipt/CustomerInitClueCallLog.kt
fw-valhalla-domain/src/main/java/cn/fw/valhalla/domain/dto/CallReportDTO.java deleted
1 | -package cn.fw.valhalla.domain.dto; | |
2 | - | |
3 | -import cn.fw.valhalla.domain.enums.CallTypeEnum; | |
4 | -import lombok.Data; | |
5 | - | |
6 | -import java.time.LocalDateTime; | |
7 | -import java.util.Date; | |
8 | - | |
9 | -/** | |
10 | - * @author : kurisu | |
11 | - * @className : CallReportDTO | |
12 | - * @description : 通话记录 | |
13 | - * @date: 2021-01-19 15:57 | |
14 | - */ | |
15 | -@Data | |
16 | -public class CallReportDTO { | |
17 | - /** | |
18 | - * 通话id | |
19 | - */ | |
20 | - private String callId; | |
21 | - /** | |
22 | - * 工作人员id | |
23 | - */ | |
24 | - private Long staffId; | |
25 | - /** | |
26 | - * 工作人员名称 | |
27 | - */ | |
28 | - private String staffName; | |
29 | - /** | |
30 | - * 用户号码 | |
31 | - */ | |
32 | - private String staffMobile; | |
33 | - /** | |
34 | - * 目标号码 | |
35 | - */ | |
36 | - private String peerNo; | |
37 | - /** | |
38 | - * 呼叫时间 | |
39 | - */ | |
40 | - private Date callTime; | |
41 | - /** | |
42 | - * 通话时间 (秒) | |
43 | - */ | |
44 | - private Long talkTime; | |
45 | - /** | |
46 | - * 呼叫类型 | |
47 | - */ | |
48 | - private CallTypeEnum dialType; | |
49 | - /** | |
50 | - * 集团id | |
51 | - */ | |
52 | - private Long groupId; | |
53 | -} |
fw-valhalla-domain/src/main/java/cn/fw/valhalla/domain/dto/CallReportDTO.kt
0 → 100644
1 | +package cn.fw.valhalla.domain.dto | |
2 | + | |
3 | +import cn.fw.common.annotation.NoArg | |
4 | +import com.fasterxml.jackson.databind.annotation.JsonDeserialize | |
5 | +import com.fasterxml.jackson.databind.annotation.JsonSerialize | |
6 | +import java.time.LocalDateTime | |
7 | + | |
8 | +/** | |
9 | + * 通话记录mq的DTO | |
10 | + * | |
11 | + * @author : kurisu | |
12 | + * @version : 2.0 | |
13 | + * @desc : 通话记录mq的DTO | |
14 | + * @date : 2024-03-29 15:15 | |
15 | + */ | |
16 | +@NoArg | |
17 | +data class CallReportDTO( | |
18 | + /** | |
19 | + * 拨号id (查询录音用) | |
20 | + */ | |
21 | + val callId: String, | |
22 | + /** | |
23 | + * 员工id | |
24 | + */ | |
25 | + val staffId: Long, | |
26 | + /** | |
27 | + * 用户号码 | |
28 | + */ | |
29 | + val staffMobile: String, | |
30 | + /** | |
31 | + * 目标号码 | |
32 | + */ | |
33 | + val peerNo: String, | |
34 | + /** | |
35 | + * 呼叫时间 | |
36 | + */ | |
37 | + @JsonDeserialize(using = cn.fw.common.web.serializer.LocalDateTimeSerializerProcessor.LocalDateTimeDeserializer::class) | |
38 | + @JsonSerialize(using = cn.fw.common.web.serializer.LocalDateTimeSerializerProcessor.LocalDateTimeSerializer::class) | |
39 | + val callTime: LocalDateTime, | |
40 | + /** | |
41 | + * 呼叫类型 | |
42 | + */ | |
43 | + val callType: Int, | |
44 | + /** | |
45 | + * 通话时间 (秒) | |
46 | + */ | |
47 | + val talkTime: Int | |
48 | +) | |
0 | 49 | \ No newline at end of file | ... | ... |
fw-valhalla-rpc/src/main/java/cn/fw/valhalla/rpc/ehr/EhrRpcService.java
fw-valhalla-rpc/src/main/java/cn/fw/valhalla/rpc/pstn/PstnRpcService.kt
fw-valhalla-server/pom.xml
... | ... | @@ -172,7 +172,7 @@ |
172 | 172 | <profile> |
173 | 173 | <id>local-dev</id> |
174 | 174 | <properties> |
175 | - <activatedProfiles>dev,local</activatedProfiles> | |
175 | + <activatedProfiles>test,local</activatedProfiles> | |
176 | 176 | </properties> |
177 | 177 | <activation> |
178 | 178 | <activeByDefault>true</activeByDefault> | ... | ... |
fw-valhalla-server/src/main/java/cn/fw/valhalla/controller/task/CallHistoryTask.kt
0 → 100644
1 | +package cn.fw.valhalla.controller.task | |
2 | + | |
3 | +import cn.fw.valhalla.domain.db.ipt.CustomerInitClueCallLog | |
4 | +import cn.fw.valhalla.domain.dto.CallReportDTO | |
5 | +import cn.fw.valhalla.rpc.ehr.EhrRpcService | |
6 | +import cn.fw.valhalla.service.bus.ipt.CustomerInitClueBizService | |
7 | +import cn.fw.valhalla.service.data.CustomerInitClueCallLogService | |
8 | +import com.baomidou.mybatisplus.extension.kotlin.KtQueryWrapper | |
9 | +import com.fasterxml.jackson.module.kotlin.jacksonObjectMapper | |
10 | +import com.fasterxml.jackson.module.kotlin.readValue | |
11 | +import kotlinx.coroutines.CoroutineScope | |
12 | +import kotlinx.coroutines.Dispatchers | |
13 | +import kotlinx.coroutines.launch | |
14 | +import org.slf4j.LoggerFactory | |
15 | +import org.springframework.beans.factory.annotation.Value | |
16 | +import org.springframework.boot.autoconfigure.condition.ConditionalOnProperty | |
17 | +import org.springframework.data.redis.core.StringRedisTemplate | |
18 | +import org.springframework.scheduling.annotation.Scheduled | |
19 | +import org.springframework.stereotype.Component | |
20 | +import java.time.LocalDateTime | |
21 | + | |
22 | +/** | |
23 | + * 车辆进站处理task | |
24 | + * | |
25 | + * @author : kurisu | |
26 | + * @version : 1.0 | |
27 | + * @desc : 车辆进站处理task | |
28 | + * @date : 2024-03-01 09:51 | |
29 | + */ | |
30 | +@Component | |
31 | +@ConditionalOnProperty(prefix = "task", name = ["switch"], havingValue = "on") | |
32 | +class CallHistoryTask( | |
33 | + private val stringRedisTemplate: StringRedisTemplate, | |
34 | + private val ehrRpcService: EhrRpcService, | |
35 | + private val customerInitClueBizService: CustomerInitClueBizService, | |
36 | + private val customerInitClueCallLogService: CustomerInitClueCallLogService, | |
37 | + @Value("\${spring.cache.custom.global-prefix}:mq:call:log") | |
38 | + private val callReportKey: String | |
39 | +) { | |
40 | + private val logger = LoggerFactory.getLogger(javaClass) | |
41 | + | |
42 | + | |
43 | + /** | |
44 | + * 持久化通话记录 | |
45 | + */ | |
46 | + @Scheduled(initialDelay = 1000 * 10, fixedRate = 1000 * 15) | |
47 | + fun dealCallHistory() { | |
48 | + val listOps = stringRedisTemplate.boundListOps(callReportKey) | |
49 | + val dataList = mutableListOf<String>() | |
50 | + for (i in 0..100) { | |
51 | + val dataStr = listOps.leftPop() | |
52 | + dataStr?.let { | |
53 | + dataList.add(dataStr) | |
54 | + } | |
55 | + } | |
56 | + val mapper = jacksonObjectMapper() | |
57 | + CoroutineScope(Dispatchers.IO).launch { | |
58 | + dataList.forEach { | |
59 | + launch { | |
60 | + try { | |
61 | + val callReportDTO = mapper.readValue<CallReportDTO>(it) | |
62 | + val invalid = callReportDTO.callTime.isBefore( | |
63 | + LocalDateTime.now().minusMinutes(10) | |
64 | + ) && callReportDTO.staffId <= 0 | |
65 | + if (!invalid) { | |
66 | + var res = false | |
67 | + if (callReportDTO.staffId <= 0) { | |
68 | + val staffId = ehrRpcService.queryStaffInfoByMobile(callReportDTO.staffMobile)?.id ?: -1 | |
69 | + if (staffId > 0) { | |
70 | + res = customerInitClueBizService.saveCallLog(callReportDTO.copy(staffId = staffId)) | |
71 | + } | |
72 | + } else { | |
73 | + res = customerInitClueBizService.saveCallLog(callReportDTO) | |
74 | + } | |
75 | + if (!res) { | |
76 | + listOps.rightPush(it) | |
77 | + } | |
78 | + } | |
79 | + } catch (e: Exception) { | |
80 | + logger.error("持久化通话记录失败, id: $it", e) | |
81 | + listOps.rightPush(it) | |
82 | + } | |
83 | + } | |
84 | + } | |
85 | + } | |
86 | + } | |
87 | + | |
88 | + /** | |
89 | + * 拉取化通话录音 | |
90 | + */ | |
91 | + @Scheduled(initialDelay = 1000 * 10, fixedRate = 1000 * 30) | |
92 | + fun dealCallRecordings() { | |
93 | + val list = customerInitClueCallLogService.list( | |
94 | + KtQueryWrapper(CustomerInitClueCallLog::class.java) | |
95 | + .gt(CustomerInitClueCallLog::talkTime, 0) | |
96 | + .isNull(CustomerInitClueCallLog::recording) | |
97 | + .last(" limit 100") | |
98 | + ) | |
99 | + CoroutineScope(Dispatchers.IO).launch { | |
100 | + list?.forEach { | |
101 | + launch { | |
102 | + try { | |
103 | + customerInitClueBizService.fillRecordingsPath(it) | |
104 | + } catch (e: Exception) { | |
105 | + logger.error("拉取通话录音失败, id: ${it.id}", e) | |
106 | + } | |
107 | + } | |
108 | + } | |
109 | + } | |
110 | + } | |
111 | +} | |
0 | 112 | \ No newline at end of file | ... | ... |
fw-valhalla-service/src/main/java/cn/fw/valhalla/component/consumer/CallReportConsumer.kt
0 → 100644
1 | +package cn.fw.valhalla.component.consumer | |
2 | + | |
3 | +import cn.fw.common.util.logError | |
4 | +import cn.fw.common.util.logInfo | |
5 | +import cn.fw.pstn.sdk.mq.CallReport | |
6 | +import cn.fw.valhalla.common.utils.DateUtil | |
7 | +import cn.fw.valhalla.domain.dto.CallReportDTO | |
8 | +import cn.fw.valhalla.rpc.ehr.EhrRpcService | |
9 | +import cn.fw.valhalla.rpc.ehr.dto.StaffInfoDTO | |
10 | +import com.fasterxml.jackson.module.kotlin.jacksonObjectMapper | |
11 | +import org.apache.rocketmq.spring.annotation.RocketMQMessageListener | |
12 | +import org.apache.rocketmq.spring.core.RocketMQListener | |
13 | +import org.springframework.beans.factory.annotation.Value | |
14 | +import org.springframework.data.redis.core.StringRedisTemplate | |
15 | +import org.springframework.stereotype.Component | |
16 | + | |
17 | +/** | |
18 | + * 通话记录监听 | |
19 | + * | |
20 | + * @author : kurisu | |
21 | + * @version : 2.0 | |
22 | + * @desc : 通话记录监听 | |
23 | + * @date : 2024-03-29 15:09 | |
24 | + */ | |
25 | +@Component | |
26 | +@RocketMQMessageListener(topic = "call_report", consumerGroup = "\${spring.application.name}" + "-call_report") | |
27 | +class CallReportConsumer( | |
28 | + private val stringRedisTemplate: StringRedisTemplate, | |
29 | + private val ehrRpcService: EhrRpcService, | |
30 | + @Value("\${spring.cache.custom.global-prefix}:mq:call:log") | |
31 | + private val callReportKey: String | |
32 | +) : RocketMQListener<CallReport> { | |
33 | + | |
34 | + | |
35 | + override fun onMessage(message: CallReport?) { | |
36 | + logInfo("监听通话记录mq: CallReport=[{}]", message) | |
37 | + try { | |
38 | + message?.takeIf { it.talkTime > 0 }?.let { | |
39 | + val info: StaffInfoDTO? = ehrRpcService.queryStaffInfoByMobile(message.staffMobile) | |
40 | + val mapper = jacksonObjectMapper() | |
41 | + val callReportDTO = CallReportDTO( | |
42 | + callId = message.callId, | |
43 | + staffId = info?.id ?: -1, | |
44 | + staffMobile = message.staffMobile, | |
45 | + peerNo = message.peerNo, | |
46 | + callTime = DateUtil.date2LocalDateTime(message.callTime), | |
47 | + callType = message.callType.value, | |
48 | + talkTime = message.talkTime.toInt(), | |
49 | + ) | |
50 | + val jsonString = mapper.writeValueAsString(callReportDTO) | |
51 | + stringRedisTemplate.opsForList().rightPush(callReportKey, jsonString) | |
52 | + } | |
53 | + } catch (ex: Exception) { | |
54 | + logError("消费通话记录mq失败", ex) | |
55 | + throw ex | |
56 | + } | |
57 | + } | |
58 | +} | |
0 | 59 | \ No newline at end of file | ... | ... |
fw-valhalla-service/src/main/java/cn/fw/valhalla/service/bus/ipt/CustomerInitClueBizService.kt
... | ... | @@ -4,16 +4,19 @@ import cn.fw.common.data.mybatis.pagination.PageData |
4 | 4 | import cn.fw.common.page.AppPage |
5 | 5 | import cn.fw.valhalla.domain.db.ipt.CustomerInitClue |
6 | 6 | import cn.fw.valhalla.domain.db.ipt.CustomerInitClueCallLog |
7 | +import cn.fw.valhalla.domain.dto.CallReportDTO | |
7 | 8 | import cn.fw.valhalla.domain.query.InitClueQueryVO |
8 | 9 | import cn.fw.valhalla.domain.vo.AppPageVO |
9 | 10 | import cn.fw.valhalla.domain.vo.ipt.CustomerInitClueVO |
10 | 11 | import cn.fw.valhalla.domain.vo.ipt.InitClueCallLogVO |
11 | 12 | import cn.fw.valhalla.rpc.member.MemberRpcService |
12 | 13 | import cn.fw.valhalla.rpc.oop.OopService |
14 | +import cn.fw.valhalla.rpc.pstn.PstnRpcService | |
13 | 15 | import cn.fw.valhalla.service.data.CustomerInitClueCallLogService |
14 | 16 | import cn.fw.valhalla.service.data.CustomerInitClueService |
15 | 17 | import com.baomidou.mybatisplus.extension.kotlin.KtQueryWrapper |
16 | 18 | import org.springframework.stereotype.Service |
19 | +import org.springframework.transaction.annotation.Transactional | |
17 | 20 | import java.util.* |
18 | 21 | import java.util.function.Function |
19 | 22 | |
... | ... | @@ -30,7 +33,8 @@ class CustomerInitClueBizService( |
30 | 33 | private val customerInitClueService: CustomerInitClueService, |
31 | 34 | private val customerInitClueCallLogService: CustomerInitClueCallLogService, |
32 | 35 | private val oopService: OopService, |
33 | - private val memberRpcService: MemberRpcService | |
36 | + private val memberRpcService: MemberRpcService, | |
37 | + private val pstnRpcService: PstnRpcService | |
34 | 38 | ) { |
35 | 39 | /** |
36 | 40 | * 查询池子数据 |
... | ... | @@ -81,6 +85,53 @@ class CustomerInitClueBizService( |
81 | 85 | ) |
82 | 86 | } ?: listOf() |
83 | 87 | } |
88 | + | |
89 | + /** | |
90 | + * 持久化通话记录 | |
91 | + */ | |
92 | + @Transactional(rollbackFor = [Exception::class]) | |
93 | + fun saveCallLog(dto: CallReportDTO): Boolean { | |
94 | + if (customerInitClueCallLogService.count( | |
95 | + KtQueryWrapper(CustomerInitClueCallLog::class.java).eq( | |
96 | + CustomerInitClueCallLog::callId, | |
97 | + dto.callId | |
98 | + ) | |
99 | + ) > 0 | |
100 | + ) { | |
101 | + return true | |
102 | + } | |
103 | + val list = customerInitClueService.list(KtQueryWrapper(CustomerInitClue::class.java) | |
104 | + .eq(CustomerInitClue::yn, true) | |
105 | + .eq(CustomerInitClue::adviserId, dto.staffId) | |
106 | + .and { | |
107 | + it.eq(CustomerInitClue::customerMobile, dto.peerNo) | |
108 | + .or() | |
109 | + .eq(CustomerInitClue::senderMobile, dto.peerNo) | |
110 | + } | |
111 | + ) | |
112 | + return list?.mapNotNull { | |
113 | + CustomerInitClueCallLog( | |
114 | + clueId = it.id, | |
115 | + callId = dto.callId, | |
116 | + talkTime = dto.talkTime, | |
117 | + recording = null, | |
118 | + uploadTime = dto.callTime | |
119 | + ) | |
120 | + }?.let { | |
121 | + customerInitClueCallLogService.saveBatch(it) | |
122 | + } ?: false | |
123 | + } | |
124 | + | |
125 | + /** | |
126 | + * 拉取录音地址 | |
127 | + */ | |
128 | + @Transactional(rollbackFor = [Exception::class]) | |
129 | + fun fillRecordingsPath(callLog: CustomerInitClueCallLog) { | |
130 | + val path = pstnRpcService.queryRecording(callLog.callId) | |
131 | + path?.let { | |
132 | + customerInitClueCallLogService.updateById(callLog.copy(recording = it)) | |
133 | + } | |
134 | + } | |
84 | 135 | } |
85 | 136 | |
86 | 137 | ... | ... |
fw-valhalla-service/src/main/java/cn/fw/valhalla/service/data/CustomerImportService.java deleted
1 | -package cn.fw.valhalla.service.data; | |
2 | - | |
3 | -import cn.fw.valhalla.domain.db.customer.CustomerImport; | |
4 | -import com.baomidou.mybatisplus.extension.service.IService; | |
5 | - | |
6 | -/** | |
7 | - * @author : kurisu | |
8 | - * @className : CustomerImportService | |
9 | - * @description : 档案导入处理 | |
10 | - * @date: 2020-11-18 15:05 | |
11 | - */ | |
12 | -public interface CustomerImportService extends IService<CustomerImport> { | |
13 | -} |
fw-valhalla-service/src/main/java/cn/fw/valhalla/service/data/impl/CustomerImportServiceImpl.java deleted
1 | -package cn.fw.valhalla.service.data.impl; | |
2 | - | |
3 | -import cn.fw.valhalla.dao.mapper.CustomerImportMapper; | |
4 | -import cn.fw.valhalla.domain.db.customer.CustomerImport; | |
5 | -import cn.fw.valhalla.service.data.CustomerImportService; | |
6 | -import com.baomidou.mybatisplus.extension.service.impl.ServiceImpl; | |
7 | -import lombok.extern.slf4j.Slf4j; | |
8 | -import org.springframework.stereotype.Service; | |
9 | - | |
10 | -/** | |
11 | - * @author : kurisu | |
12 | - * @className : CustomerImportServiceImpl | |
13 | - * @description : 档案导入处理 | |
14 | - * @date: 2020-11-18 15:05 | |
15 | - */ | |
16 | -@Service | |
17 | -@Slf4j | |
18 | -public class CustomerImportServiceImpl extends ServiceImpl<CustomerImportMapper, CustomerImport> implements CustomerImportService { | |
19 | -} |