ForcePilot/backend/package/yuxi/channels/adapters/zalo_oa/webhook.py
Kris 30dd9e16f4 feat(zalo-oa): 实现完整的 Zalo OA 渠道适配器模块
新增 Zalo OA 官方账号完整集成能力,包含:
1. 基础通信能力:消息编解码、目标归一化、文本分块
2. 安全与校验:Webhook 签名验证、DM 策略管理、配对流程
3. 辅助工具:重复事件去重、请求限流、异常告警
4. 管理功能:账号多实例管理、配置验证、健康诊断
5. 扩展能力:媒体托管、视觉识别、TTS 语音合成
6. 运维支持:审计日志、状态监控、目录同步
2026-05-12 00:52:47 +08:00

75 lines
2.5 KiB
Python

from __future__ import annotations
from typing import Any
from yuxi.channels.adapters.zalo_oa.client import API_BASE_URL
from yuxi.utils.logging_config import logger
async def register_webhook(client: Any, webhook_url: str) -> bool:
if not webhook_url:
logger.warning("[ZaloOA] webhook: no webhook URL configured, skipping register")
return False
try:
response = await client._request(
"POST",
f"{API_BASE_URL}/webhook",
headers={"access_token": client.access_token},
json={"url": webhook_url},
)
result = response.json()
if result.get("error") != 0:
logger.warning(f"[ZaloOA] webhook: register failed: {result.get('message', 'unknown')}")
return False
logger.info(f"[ZaloOA] webhook: registered URL {webhook_url}")
return True
except Exception as e:
logger.warning(f"[ZaloOA] webhook: register error: {e}")
return False
async def unregister_webhook(client: Any, webhook_url: str = "") -> bool:
try:
response = await client._request(
"POST",
f"{API_BASE_URL}/webhook",
headers={"access_token": client.access_token},
json={"url": webhook_url or ""},
)
result = response.json()
if result.get("error") != 0:
logger.warning(f"[ZaloOA] webhook: unregister failed: {result.get('message', 'unknown')}")
return False
logger.info("[ZaloOA] webhook: unregistered")
return True
except Exception as e:
logger.warning(f"[ZaloOA] webhook: unregister error: {e}")
return False
async def get_webhook_info(client: Any) -> dict[str, Any]:
try:
response = await client._request(
"GET",
f"{API_BASE_URL}/webhook",
headers={"access_token": client.access_token},
)
result = response.json()
data = result.get("data", {})
return {
"registered": result.get("error") == 0,
"url": data.get("url", ""),
"status": data.get("status", ""),
"created_at": data.get("created_at", ""),
"updated_at": data.get("updated_at", ""),
"error_code": result.get("error", -1),
"error_message": result.get("message", ""),
"raw": result,
}
except Exception as e:
return {
"registered": False,
"url": "",
"error": str(e),
}