feat(微信控制): 添加等待回复机制以支持消息引用

在检测到新消息后暂停主循环扫描,等待服务端回复指令
自动保存最后收到的消息内容用于引用回复
超时未收到回复则发送"网络异常"提示
避免多消息处理混乱,提升交互准确性
This commit is contained in:
2026-03-25 16:42:56 +08:00
parent fc4ffcdc5b
commit 36ef2e12a2
2 changed files with 109 additions and 4 deletions

View File

@@ -15,6 +15,12 @@ object WeworkController {
lateinit var weworkService: WeworkService lateinit var weworkService: WeworkService
var enableLoopRunning = false var enableLoopRunning = false
var mainLoopRunning = false var mainLoopRunning = false
/** 是否正在等待回复 - 等待时会暂停主循环扫描新消息 */
var waitingForReply = false
/** 最后收到的消息内容,用于回复时引用 */
var lastReceivedMessage: String? = null
/** 最后收到消息的发送者名称 */
var lastReceivedName: String? = null
/** /**
* 交互通知 * 交互通知
@@ -61,7 +67,27 @@ object WeworkController {
@RequestMapping @RequestMapping
fun sendMessage(message: WeworkMessageBean): Boolean { fun sendMessage(message: WeworkMessageBean): Boolean {
LogUtils.d("REQUEST sendMessage(): ${message.messageId} ${message.titleList} ${message.receivedContent} ${message.at} ${message.atList?.joinToString()}") LogUtils.d("REQUEST sendMessage(): ${message.messageId} ${message.titleList} ${message.receivedContent} ${message.at} ${message.atList?.joinToString()}")
return WeworkOperationImpl.sendMessage(message, message.titleList, message.receivedContent, message.at, message.atList) // 如果有待引用消息,自动使用引用回复
val result = if (!lastReceivedMessage.isNullOrBlank() && !lastReceivedName.isNullOrBlank()) {
LogUtils.d("使用引用回复: ${lastReceivedName} -> $lastReceivedMessage")
val replyResult = WeworkOperationImpl.replyMessage(
message,
message.titleList,
lastReceivedName,
lastReceivedMessage,
null,
message.receivedContent
)
// 发送完成后清除引用信息
lastReceivedMessage = null
lastReceivedName = null
replyResult
} else {
WeworkOperationImpl.sendMessage(message, message.titleList, message.receivedContent, message.at, message.atList)
}
// 发送完成,通知等待结束
waitingForReply = false
return result
} }
/** /**
@@ -77,7 +103,7 @@ object WeworkController {
@RequestMapping @RequestMapping
fun replyMessage(message: WeworkMessageBean): Boolean { fun replyMessage(message: WeworkMessageBean): Boolean {
LogUtils.d("REQUEST replyMessage(): ${message.messageId} ${message.receivedName} ${message.originalContent} ${message.textType} ${message.receivedContent}") LogUtils.d("REQUEST replyMessage(): ${message.messageId} ${message.receivedName} ${message.originalContent} ${message.textType} ${message.receivedContent}")
return WeworkOperationImpl.replyMessage( val result = WeworkOperationImpl.replyMessage(
message, message,
message.titleList, message.titleList,
message.receivedName, message.receivedName,
@@ -85,6 +111,9 @@ object WeworkController {
message.textType, message.textType,
message.receivedContent message.receivedContent
) )
// 发送完成,通知等待结束
waitingForReply = false
return result
} }
/** /**

View File

@@ -36,11 +36,22 @@ object WeworkLoopImpl {
mainLoopRunning = true mainLoopRunning = true
try { try {
while (mainLoopRunning) { while (mainLoopRunning) {
// 如果正在等待回复,跳过新消息检测,避免多消息处理混乱
if (WeworkController.waitingForReply) {
LogUtils.d("等待回复中,暂停检测新消息...")
sleep(Constant.POP_WINDOW_INTERVAL)
continue
}
if (!isAtHome()) { if (!isAtHome()) {
LogUtils.d("当前在房间: ") LogUtils.d("当前在房间: ")
getChatMessageList() getChatMessageList()
if (mainLoopRunning) { if (mainLoopRunning) {
goHome() // 如果不是等待回复状态,则返回主页
if (!WeworkController.waitingForReply) {
goHome()
} else {
LogUtils.d("等待回复中,保持当前页面...")
}
} }
continue continue
} }
@@ -53,6 +64,14 @@ object WeworkLoopImpl {
LogUtils.d("重试获取聊天列表: ") LogUtils.d("重试获取聊天列表: ")
getChatMessageList() getChatMessageList()
} }
// 获取消息后等待服务端回复指令最多30秒
if (mainLoopRunning) {
waitForServerReply()
}
// 等待完成后返回主页
if (mainLoopRunning) {
goHome()
}
} }
if (!mainLoopRunning) break if (!mainLoopRunning) break
getFriendRequest() getFriendRequest()
@@ -72,7 +91,51 @@ object WeworkLoopImpl {
}) })
} }
} }
/**
* 等待服务端回复指令最多30秒
* 如果超时则发送"网络异常"消息
*/
private fun waitForServerReply() {
val waitTimeout = 30 * 1000L // 30秒超时
val startTime = System.currentTimeMillis()
LogUtils.d("等待服务端回复指令...")
WeworkController.waitingForReply = true
while (mainLoopRunning && System.currentTimeMillis() - startTime < waitTimeout) {
sleep(1000)
// 如果waitingForReply被设置为false说明已收到服务端回复指令
// sendMessage/replyMessage会被自动调用并处理
if (!WeworkController.waitingForReply) {
LogUtils.d("收到服务端回复指令,已自动发送消息")
return
}
// 检查是否离开当前聊天页面
if (isAtHome()) {
LogUtils.d("用户已离开聊天页面")
return
}
}
// 超时未收到回复,发送"网络异常"消息
WeworkController.waitingForReply = false
LogUtils.e("等待服务端回复超时,发送网络异常")
try {
val titleList = WeworkRoomUtil.getRoomTitle()
if (titleList.isNotEmpty()) {
val errorMessage = WeworkMessageBean().apply {
type = WeworkMessageBean.SEND_MESSAGE
this.titleList = titleList
receivedContent = "网络异常"
}
WeworkController.sendMessage(errorMessage)
}
} catch (e: Exception) {
LogUtils.e("发送网络异常消息失败: ${e.message}")
}
}
/** /**
* 检查账号是否已实名 & 新号使用模拟环境 * 检查账号是否已实名 & 新号使用模拟环境
* @return 通过检查 true 否则 false * @return 通过检查 true 否则 false
@@ -289,6 +352,15 @@ object WeworkLoopImpl {
null null
) )
WeworkController.weworkService.webSocketManager.send(messageBean) WeworkController.weworkService.webSocketManager.send(messageBean)
// 保存最后收到的消息内容,用于回复时引用
val lastMsg = messageList.lastOrNull()
if (lastMsg != null && lastMsg.sender == 0) {
val msgContent = lastMsg.itemMessageList.lastOrNull()?.text ?: ""
val senderName = lastMsg.nameList.firstOrNull() ?: ""
WeworkController.lastReceivedMessage = msgContent
WeworkController.lastReceivedName = senderName
LogUtils.d("保存最后消息用于引用: $senderName: $msgContent")
}
//推测是否回复并在房间等待指令 //推测是否回复并在房间等待指令
if (needInfer) { if (needInfer) {
val lastMessage = messageList.lastOrNull() val lastMessage = messageList.lastOrNull()
@@ -306,22 +378,26 @@ object WeworkLoopImpl {
|| tempContent.isNotBlank() || tempContent.isNotBlank()
) { ) {
LogUtils.v("推测需要回复: $tempContent") LogUtils.v("推测需要回复: $tempContent")
WeworkController.waitingForReply = true
val startTime = System.currentTimeMillis() val startTime = System.currentTimeMillis()
var currentTime = startTime var currentTime = startTime
while (mainLoopRunning && currentTime - startTime < timeout) { while (mainLoopRunning && currentTime - startTime < timeout) {
sleep(Constant.POP_WINDOW_INTERVAL / 5) sleep(Constant.POP_WINDOW_INTERVAL / 5)
currentTime = System.currentTimeMillis() currentTime = System.currentTimeMillis()
} }
WeworkController.waitingForReply = false
return getChatMessageList(needInfer = false, titleList = titleList) return getChatMessageList(needInfer = false, titleList = titleList)
} }
} }
2 -> { 2 -> {
WeworkController.waitingForReply = true
val startTime = System.currentTimeMillis() val startTime = System.currentTimeMillis()
var currentTime = startTime var currentTime = startTime
while (mainLoopRunning && currentTime - startTime < timeout) { while (mainLoopRunning && currentTime - startTime < timeout) {
sleep(Constant.POP_WINDOW_INTERVAL / 5) sleep(Constant.POP_WINDOW_INTERVAL / 5)
currentTime = System.currentTimeMillis() currentTime = System.currentTimeMillis()
} }
WeworkController.waitingForReply = false
return getChatMessageList(needInfer = false, titleList = titleList) return getChatMessageList(needInfer = false, titleList = titleList)
} }
else -> return true else -> return true