实现CDN媒体下载解密(parse_aes_key支持base64(raw16B)和base64(hex32)两种编码)+extract_inbound_media(图片/语音/文件/视频)。接收循环检测媒体消息下载解密保存到/tmp。图片已保存供后续vision模型接入。
This commit is contained in:
1 parent
e284d43cc7
commit
51d8df6e6a
2 files changed
+156
-1
No files matched your search
@@ -425,6 +425,42 @@ def _wechat_extract_text(msg: dict) -> str:
|
||||
return "\n".join(parts)
|
||||
|
||||
|
||||
def _extract_and_save_inbound_media(msg: dict) -> str:
|
||||
"""检测入站媒体消息(图片/语音/文件/视频),下载解密保存,返回给 LLM 的提示文本。
|
||||
|
||||
无媒体或解密失败返回空字符串。图片已保存到本地,供后续 vision 模型接入。
|
||||
"""
|
||||
try:
|
||||
from app.api.im_ilink_media import extract_inbound_media
|
||||
import os as _os
|
||||
for it in (msg.get("item_list") or []):
|
||||
if it.get("type") in (2, 3, 4, 5):
|
||||
kind, data = extract_inbound_media(it)
|
||||
if kind and data:
|
||||
_dir = "/tmp/wechat_inbound_media"
|
||||
_os.makedirs(_dir, exist_ok=True)
|
||||
_ext = {"image": "jpg", "voice": "silk", "file": "bin", "video": "mp4"}.get(kind, "bin")
|
||||
_path = _os.path.join(_dir, "%d_%s.%s" % (int(time.time() * 1000), kind, _ext))
|
||||
with open(_path, "wb") as _f:
|
||||
_f.write(data)
|
||||
_label = {"image": "图片", "voice": "语音", "file": "文件", "video": "视频"}.get(kind, kind)
|
||||
try:
|
||||
with open("/tmp/wechat_inbound_media.log", "a", encoding="utf-8") as _f:
|
||||
_f.write(_beijing_now().isoformat() + " %s saved=%s size=%d\n"
|
||||
% (kind, _path, len(data)))
|
||||
except Exception:
|
||||
pass
|
||||
return "[用户发送了%s,已保存到 %s(%d 字节)]" % (_label, _path, len(data))
|
||||
return ""
|
||||
except Exception as _e:
|
||||
try:
|
||||
with open("/tmp/wechat_inbound_media.log", "a", encoding="utf-8") as _f:
|
||||
_f.write(_beijing_now().isoformat() + " MEDIA_EXTRACT_ERR %s\n" % (_e,))
|
||||
except Exception:
|
||||
pass
|
||||
return ""
|
||||
|
||||
|
||||
def _wechat_sender_id(m: dict) -> str:
|
||||
"""从入站消息中提取发送者 id(兼容多套字段名)。"""
|
||||
for k in ("from_user_id", "from_user_name", "from_username", "user_id",
|
||||
@@ -576,7 +612,10 @@ def _wechat_receiver_loop(account_id: int):
|
||||
continue # 仅跳过 bot 自己发出的回声,其余(含后续追问)均尝试处理
|
||||
content = _wechat_extract_text(m)
|
||||
if not content:
|
||||
continue
|
||||
# 入站媒体(图片/语音/文件/视频):下载解密保存,供 LLM 感知
|
||||
content = _extract_and_save_inbound_media(m)
|
||||
if not content:
|
||||
continue
|
||||
sender = _wechat_sender_id(m)
|
||||
ctx = _wechat_context_token(m)
|
||||
# 诊断:记录原始入站消息,定位字段名 / 第二轮不回复
|
||||
|
||||
Reference in new issue
Block a user