1b2b935832
- Platform-based architecture (Windows/Linux/Mac) - Agent instance registry (agents.yaml) - Management dashboard with cross-platform monitoring - xmpp_bot with HTTP bridge + health endpoints - wechat_agent with WeChat-Hermes bridging - Platform services: ProcessGuardian, HealthProbe, APIRouter, ChannelBridge - Deployment: systemd (Linux) + PowerShell (Windows) - Monitoring: SSH+ejabberdctl for cross-platform presence
73 lines
2.9 KiB
Python
73 lines
2.9 KiB
Python
#!/usr/bin/env python3
|
|
"""XMPP Bot mohe@yoin.fun - 通过 ejabberd REST API 实现"""
|
|
import asyncio, logging, ssl, json, urllib.request, os, time
|
|
import subprocess, threading
|
|
|
|
logging.basicConfig(level=logging.INFO, format='%(asctime)s %(message)s')
|
|
GATEWAY = "http://localhost:8642/v1/chat/completions"
|
|
API_KEY = "hermes123"
|
|
EJB_ADMIN = "admin@localhost"
|
|
EJB_PASS = "hermes123"
|
|
_opener = urllib.request.build_opener(urllib.request.ProxyHandler({}))
|
|
|
|
LAST_SEQ = 0
|
|
|
|
def call_api(content, sender, seq):
|
|
"""同步调 Hermes API 并回复"""
|
|
try:
|
|
payload = json.dumps({
|
|
"model": "hermes-agent",
|
|
"messages": [{"role": "user", "content": content}]
|
|
}).encode()
|
|
req = urllib.request.Request(GATEWAY, data=payload, method="POST")
|
|
req.add_header("Content-Type", "application/json")
|
|
req.add_header("Authorization", f"Bearer {API_KEY}")
|
|
req.add_header("X-Hermes-Session-Id", "xmpp-mohe")
|
|
|
|
result = _opener.open(req, timeout=600)
|
|
data = json.loads(result.read())
|
|
reply = data.get("choices", [{}])[0].get("message", {}).get("content", "")
|
|
finish = data.get("choices", [{}])[0].get("finish_reason", "")
|
|
|
|
global LAST_SEQ
|
|
if seq < LAST_SEQ:
|
|
logging.info(f"⏭️ 跳过过期 seq={seq}")
|
|
return
|
|
|
|
if reply.strip() and finish != "silent":
|
|
# 通过 ejabberdctl 发送回复
|
|
subprocess.run([
|
|
"docker", "exec", "ejabberd", "ejabberdctl", "send_stanza",
|
|
"mohe@yoin.fun", sender,
|
|
f"<message from='mohe@yoin.fun' to='{sender}' type='chat' xml:lang='en'><body>{reply}</body></message>"
|
|
], capture_output=True, timeout=30)
|
|
logging.info(f"✅ 回复: {reply[:80]}")
|
|
except Exception as e:
|
|
logging.error(f"❌ 错误: {e}")
|
|
|
|
def poll_messages():
|
|
"""轮询 ejabberd 离线消息"""
|
|
global LAST_SEQ
|
|
while True:
|
|
try:
|
|
# 用 ejabberdctl 获取 mohe 的离线消息
|
|
result = subprocess.run([
|
|
"docker", "exec", "ejabberd", "ejabberdctl", "get_offline_count", "mohe", "yoin.fun"
|
|
], capture_output=True, text=True, timeout=10)
|
|
count = int(result.stdout.strip())
|
|
|
|
if count > 0:
|
|
# 获取消息内容并处理
|
|
result2 = subprocess.run([
|
|
"docker", "exec", "ejabberd", "ejabberdctl", "get_offline_messages", "mohe", "yoin.fun"
|
|
], capture_output=True, text=True, timeout=10)
|
|
# 解析消息并处理(简化处理)
|
|
except:
|
|
pass
|
|
time.sleep(5)
|
|
|
|
if __name__ == '__main__':
|
|
# 实际上需要通过 XMPP 连接或 BOSH/WS
|
|
# 这个方案太复杂,直接换个思路:让 ejabberd → webhook → 处理 → reponse
|
|
print("需要更简单的方法")
|