feat: QQ主动消息管道 + 戳一戳事件 + thinker提示词优化
- ProactiveTarget 结构体 + QQ目标正则解析(extractProactiveMessage 返回双值) - storeThought 双路推送:platform消息 → platformMessagePusher,web消息 → messagePusher - platform-bridge: SendProactive接口 + ProactiveSender + /api/v1/internal/send-proactive端点 - QQ戳一戳/notice事件 → noticeToUnified → ContentType "action" - thinker提示词注入QQ频道上下文:群名称(群号)、活跃时间、trigger-aware引导 - SetBotUID/SetPlatformMessagePusher/AddOrUpdatePlatformChannel 方法 - ai-core source 增加 BotUID/GroupName,platform-bridge source 增加 bot_uid/group_name - 支持 [CQ:at,qq=xxx] @提及标签自动拼接 Co-Authored-By: Claude <noreply@anthropic.com>
This commit is contained in:
@@ -373,6 +373,37 @@ func main() {
|
||||
}
|
||||
})
|
||||
log.Printf("[主动消息] 推送已启用 (Gateway=%s)", gatewayURL)
|
||||
|
||||
// 设置平台主动消息推送回调(调用 Platform Bridge 内部 API)
|
||||
platformBridgeURL := getEnv("PLATFORM_BRIDGE_URL", "http://localhost:8082")
|
||||
thinker.SetPlatformMessagePusher(func(target background.ProactiveTarget, message string) {
|
||||
reqBody, _ := json.Marshal(map[string]string{
|
||||
"platform": target.Platform,
|
||||
"chat_type": target.ChatType,
|
||||
"user_id": target.UserID,
|
||||
"group_id": target.GroupID,
|
||||
"at_user_id": target.AtUserID,
|
||||
"content": message,
|
||||
})
|
||||
req, _ := http.NewRequest("POST",
|
||||
platformBridgeURL+"/api/v1/internal/send-proactive",
|
||||
strings.NewReader(string(reqBody)))
|
||||
req.Header.Set("Content-Type", "application/json")
|
||||
req.Header.Set("X-Internal-Token", internalToken)
|
||||
resp, err := proactiveClient.Do(req)
|
||||
if err != nil {
|
||||
log.Printf("[主动消息] 平台推送失败: %v", err)
|
||||
return
|
||||
}
|
||||
resp.Body.Close()
|
||||
if resp.StatusCode == http.StatusOK {
|
||||
log.Printf("[主动消息] 已推送到 Platform Bridge: target=%s/%s user=%s group=%s len=%d",
|
||||
target.Platform, target.ChatType, target.UserID, target.GroupID, len(message))
|
||||
} else {
|
||||
log.Printf("[主动消息] Platform Bridge 返回 %d", resp.StatusCode)
|
||||
}
|
||||
})
|
||||
log.Printf("[主动消息] 平台推送已启用 (PlatformBridge=%s)", platformBridgeURL)
|
||||
} else {
|
||||
log.Println("[主动消息] 未配置 INTERNAL_SERVICE_TOKEN,主动消息推送已禁用")
|
||||
}
|
||||
@@ -825,6 +856,8 @@ func handleChat(
|
||||
ChannelType string `json:"channel_type"`
|
||||
SenderName string `json:"sender_name"`
|
||||
OriginalUID string `json:"original_uid"`
|
||||
BotUID string `json:"bot_uid"`
|
||||
GroupName string `json:"group_name,omitempty"`
|
||||
} `json:"source,omitempty"`
|
||||
}
|
||||
if err := json.NewDecoder(r.Body).Decode(&req); err != nil {
|
||||
@@ -840,6 +873,12 @@ func handleChat(
|
||||
if req.Mode == "platform_silent" {
|
||||
if thinker != nil {
|
||||
thinker.RecordUserMessage(req.SessionID)
|
||||
if req.Source.Platform != "" && req.Source.BotUID != "" {
|
||||
thinker.SetBotUID(req.Source.Platform, req.Source.BotUID)
|
||||
}
|
||||
if req.Source.Platform != "" && req.Source.ChannelID != "" {
|
||||
thinker.AddOrUpdatePlatformChannel(req.Source.Platform, req.Source.ChannelType, req.Source.ChannelID, req.Source.GroupName)
|
||||
}
|
||||
}
|
||||
// 图片预处理:静默观察时也分析图片内容,供后台思考使用
|
||||
message := req.Message
|
||||
@@ -870,6 +909,12 @@ func handleChat(
|
||||
// 0. 记录用户活动(重置闲置计时器)
|
||||
if thinker != nil {
|
||||
thinker.RecordUserMessage(req.SessionID)
|
||||
if req.Source.Platform != "" && req.Source.BotUID != "" {
|
||||
thinker.SetBotUID(req.Source.Platform, req.Source.BotUID)
|
||||
}
|
||||
if req.Source.Platform != "" && req.Source.ChannelID != "" {
|
||||
thinker.AddOrUpdatePlatformChannel(req.Source.Platform, req.Source.ChannelType, req.Source.ChannelID, req.Source.GroupName)
|
||||
}
|
||||
}
|
||||
|
||||
// Admin private messages: redirect to the main admin session so conversation
|
||||
@@ -911,6 +956,8 @@ func handleChat(
|
||||
Mode: req.Mode,
|
||||
Nickname: userNickname,
|
||||
ChannelType: req.Source.ChannelType,
|
||||
ChannelID: req.Source.ChannelID,
|
||||
BotUID: req.Source.BotUID,
|
||||
})
|
||||
if err != nil {
|
||||
errData, _ := json.Marshal(map[string]string{"delta": "", "error": fmt.Sprintf("处理失败: %v", err)})
|
||||
|
||||
Reference in New Issue
Block a user