feat: V1 VLM复核 + 企微通知 + 手动结单
- 新增3张通知路由表模型(notify_area, camera_area_binding, area_person_binding) - 新增VLM复核服务,通过qwen3-vl-flash对告警截图二次确认 - 新增企微通知服务,告警确认后推送文本卡片给责任人 - 新增通知调度服务,编排VLM复核→查表路由→企微推送流水线 - 新增企微回调接口,支持手动结单/确认处理/标记误报 - 新增通知管理API,区域/摄像头绑定/人员绑定CRUD - 告警上报主流程(edge_compat + yudao_aiot_alarm)接入异步通知 - 扩展配置项支持VLM和企微环境变量 - 添加openai==1.68.0依赖(通过DashScope兼容端点调用)
This commit is contained in:
78
app/routers/wechat_callback.py
Normal file
78
app/routers/wechat_callback.py
Normal file
@@ -0,0 +1,78 @@
|
||||
"""
|
||||
企微回调路由
|
||||
|
||||
处理安保人员在企微卡片上的操作(确认处理/已处理完成/误报忽略)。
|
||||
"""
|
||||
|
||||
from datetime import datetime
|
||||
from fastapi import APIRouter, Depends
|
||||
from pydantic import BaseModel
|
||||
from typing import Optional
|
||||
|
||||
from app.yudao_compat import YudaoResponse
|
||||
from app.services.alarm_event_service import get_alarm_event_service, AlarmEventService
|
||||
from app.utils.logger import logger
|
||||
|
||||
router = APIRouter(prefix="/api/wechat", tags=["企微回调"])
|
||||
|
||||
|
||||
class AlarmActionRequest(BaseModel):
|
||||
"""企微卡片操作请求"""
|
||||
alarm_id: str
|
||||
action: str # confirm / complete / ignore
|
||||
operator_uid: str # 企微 userid
|
||||
remark: Optional[str] = None
|
||||
|
||||
|
||||
@router.post("/callback/alarm_action")
|
||||
async def alarm_action_callback(
|
||||
req: AlarmActionRequest,
|
||||
service: AlarmEventService = Depends(get_alarm_event_service),
|
||||
):
|
||||
"""
|
||||
企微告警操作回调(无认证,由企微服务端调用)
|
||||
|
||||
action:
|
||||
- confirm: 确认处理 → handle_status=HANDLING
|
||||
- complete: 已处理完成 → handle_status=DONE, alarm_status=CLOSED
|
||||
- ignore: 误报忽略 → alarm_status=FALSE, handle_status=DONE
|
||||
"""
|
||||
action_map = {
|
||||
"confirm": {
|
||||
"alarm_status": "CONFIRMED",
|
||||
"handle_status": "HANDLING",
|
||||
"remark": "企微确认处理",
|
||||
},
|
||||
"complete": {
|
||||
"alarm_status": "CLOSED",
|
||||
"handle_status": "DONE",
|
||||
"remark": "企微手动结单",
|
||||
},
|
||||
"ignore": {
|
||||
"alarm_status": "FALSE",
|
||||
"handle_status": "DONE",
|
||||
"remark": "企微标记误报",
|
||||
},
|
||||
}
|
||||
|
||||
action_cfg = action_map.get(req.action)
|
||||
if not action_cfg:
|
||||
return YudaoResponse.error(400, f"无效操作: {req.action}")
|
||||
|
||||
result = service.handle_alarm(
|
||||
alarm_id=req.alarm_id,
|
||||
alarm_status=action_cfg["alarm_status"],
|
||||
handle_status=action_cfg["handle_status"],
|
||||
handler=req.operator_uid,
|
||||
remark=req.remark or action_cfg["remark"],
|
||||
)
|
||||
|
||||
if not result:
|
||||
return YudaoResponse.error(404, "告警不存在")
|
||||
|
||||
logger.info(
|
||||
f"企微操作: alarm={req.alarm_id}, action={req.action}, "
|
||||
f"operator={req.operator_uid}"
|
||||
)
|
||||
|
||||
return YudaoResponse.success(True)
|
||||
Reference in New Issue
Block a user