Root cause: ensure_structured_column() executed a synchronous blocking engine.connect().execute(SELECT information_schema.columns ...) inside the async request path (_build_chat_history / _maybe_compress_history), freezing the uvicorn event loop and hanging all endpoints (~200s, recovered only by docker restart). Fix: - chat_context.py: remove per-request ensure_structured_column() calls; run once idempotently at app startup (main.py lifespan). Use CURRENT_DATABASE() for PostgreSQL compatibility. - main.py: add startup-only ensure_structured_column() hook (try/except). - llm_client.py: trust_env=False + bounded httpx.Timeout/wait_for so broken endpoints fail fast instead of hanging the event loop. - chat_service.py: run media generation in a background daemon thread with its own event loop (_launch_media_task_bg) so SSE end does not cancel image/video tasks (#811); remove TEMP faulthandler diagnostic. Safe-align: persist accumulated live container changes (admin/*, knowledge, market, models, config, observability, mcp_client, platform_knowledge, im_bot_platform, chat_media, capability_registry, requirements) and add workflow_templates. Verified: live failover test (model-006 -> conn-refused) returns in ~1.9s with concurrent login 0.83s/200; event-loop responsiveness restored (sub-second).
159 lines
8.2 KiB
Python
159 lines
8.2 KiB
Python
"""
|
||
七虎AI平台 — 全功能知识库与能力导航
|
||
注入到每轮AI对话中,确保AI回复优先使用平台已有知识和能力。
|
||
"""
|
||
import logging
|
||
|
||
logger = logging.getLogger("aiflow")
|
||
|
||
PLATFORM_KNOWLEDGE = """# 七虎AI平台能力全览
|
||
|
||
你是七虎AI(qihuyun.com)平台的AI助手,你必须充分了解并使用以下平台能力来回答用户问题,**优先引用平台内部知识而非互联网搜索**。
|
||
|
||
## 1. AI聊天(核心功能)
|
||
- **多模型支持**: DeepSeek-V4-Flash(默认)、DeepSeek-V3、通义千问、OpenAI等,可按能力自动匹配(Auto模式)
|
||
- **Auto智能匹配**: 根据用户意图自动选择最佳模型——文本对话用DeepSeek-V4-Flash、图像生成用agnes-image-2.1-flash、视频生成用agnes-video-v2.0、语音识别用MiMo-ASR
|
||
- **强大提示**: 图片理解(OCR用DeepSeek-OCR)、思维链推理、函数调用(Function Calling)
|
||
- **Markdown格式化**: 回复使用Markdown格式(标题/加粗/列表/代码块/表格),确保清晰、有层次、有逻辑
|
||
- **多模态生成**: AI绘图(文生图)、AI视频(文生视频)
|
||
- **对话管理**: 新建会话、历史管理、消息分页
|
||
|
||
## 2. 知识库系统
|
||
- **文档管理**: 上传txt/md/csv/pdf/docx/xlsx/pptx等文件,自动分块索引
|
||
- **智能检索**: BM25+语义检索,RAG增强回复
|
||
- **Dify集成**: 接入Dify外部知识库,深度RAG检索,AI聊天产出+用户文档自动入库量化
|
||
- **知识图谱**: 文档关系可视化、节点关联
|
||
|
||
## 3. 技能市场
|
||
- **Skills工具**: 从skills.sh、ClawHub、GitHub、ModelScope、SkillsMP等平台导入技能,支持SKILL.md格式验证
|
||
- **智能Agent**: 角色定制、行为指引、自动执行任务
|
||
- **MCP协议应用**: 从ModelScope MCP、MCP.so、MCPMarket导入MCP服务,支持Streamable HTTP/SSE传输协议,AI代码验证
|
||
- **导入Hub**: 一键从公共平台导入Skills/MCP应用,AI自动验证代码完整性
|
||
- **自定义创建**: 手动创建Skills/MCP/Agent应用,配置价格和发布
|
||
|
||
## 4. 进化看板
|
||
- **自进化体系**: AI对话轨迹自动分析、技能权重排序、原子化学习
|
||
- **进化仪表盘**: 技能贡献度、轨迹图谱、进化历史可视化
|
||
- **Pipeline调度**: 定期扫描对话、提取高价值轨迹、更新技能链接
|
||
|
||
## 5. IM Bot(微信集成)
|
||
- **个人微信Bot**: 通过iLink官方接口接入,扫码绑定,微信内直接AI对话
|
||
- **企业微信/飞书/QQ/悟空IM**: Webhook框架已绪,支持自定义机器人
|
||
- **统一会话管理**: 微信消息并入平台AI聊天,统一历史管理
|
||
|
||
## 6. 资源中心
|
||
- **Token驾驶舱**: 用量统计(按日/模型)、剩余额度、消耗趋势图表
|
||
- **会员订阅**: 免费版/专业版/企业版,享受不同Token配额和功能权限
|
||
- **资产文件**: 上传管理图片/视频/文档等文件,关联知识库和AI聊天
|
||
|
||
## 7. 商业服务
|
||
- **计费系统**: Token计费、订单管理、支付渠道(支持多种支付)
|
||
- **广告管理**: 首页广告位、轮播图、付费推广
|
||
- **推广系统**: 邀请码、分销返佣、等级激励机制
|
||
- **成就系统**: 用户行为奖励、里程碑徽章、积分兑换
|
||
|
||
## 8. 管理后台(Admin)
|
||
- **数据驾驶舱**: 平台概览(用户数/模型数/对话数/Token消耗)、30天趋势图、操作日志/审计日志(分页+CSV导出)
|
||
- **大模型库**: 模型供应商管理(DeepSeek/OpenAI/SiliconFlow等)、模型配置(能力标签/超时/定价)、能力默认模型设置(11项能力)
|
||
- **用户管理**: 用户列表、会员等级、角色权限(RBAC)
|
||
- **系统设置**: 网站基础配置、能力默认值、MCP全局代理
|
||
- **短信配置**: SMSBao短信服务,测试发送/余额查询
|
||
- **隐私与安全**: GDPR设置、MCP隐私策略、数据加密
|
||
|
||
## 9. 开发者工具
|
||
- **API密钥管理**: 创建/撤销API密钥,调用平台API
|
||
- **MCP Client管理**: MCP服务器配置(stdio/sse/http)、环境变量、连接测试
|
||
- **自动化**: 定时任务调度
|
||
- **代码沙箱**: 安全代码执行环境
|
||
|
||
## 10. 基础设施
|
||
- **数据存储**: MySQL主库+Redis缓存+PG向量库+Elasticsearch(可选)
|
||
- **智能路由代理**: 国内/香港双通道智能分流,容器透明代理
|
||
- **部署**: Docker容器化,Nginx反向代理,FastAPI+React前后端分离
|
||
- **安全**: JWT鉴权、HTTPS加密、操作审计日志
|
||
|
||
## AI回复规范
|
||
1. **回复格式**: 使用Markdown(标题 \"##\"/\"###\"、加粗 \"**\"、列表 \"-\"/\"1.\"、代码块等)
|
||
2. **层次分明**: 使用标题分隔段落,确保信息有层次
|
||
3. **平台优先**: 回答问题时优先引用本平台功能,而非泛泛建议
|
||
4. **准确具体**: 基于平台文档给出具体操作路径、配置方法、API示例
|
||
5. **结构清晰**: 复杂问题先概括再分点,使用编号列表或表格
|
||
"""
|
||
|
||
|
||
def get_platform_knowledge(db=None, user_id=None) -> str:
|
||
"""获取平台全功能知识库文本,注入到AI对话系统提示中。
|
||
|
||
若传入 db,则动态追加当前平台已上线的官方技能目录
|
||
(source=official 且 status=published),确保管理员/前台导入或下架技能后,
|
||
AI 能及时感知并使用「平台自身已有内容」,而非停留在陈旧硬编码清单(见 #712)。
|
||
任何异常均安全回退到静态 PLATFORM_KNOWLEDGE。
|
||
"""
|
||
if db is None:
|
||
return PLATFORM_KNOWLEDGE
|
||
try:
|
||
from .models import MarketApp
|
||
|
||
apps = (
|
||
db.query(MarketApp)
|
||
.filter(MarketApp.source == "official", MarketApp.status == "published")
|
||
.order_by(MarketApp.capability, MarketApp.type, MarketApp.name)
|
||
.all()
|
||
)
|
||
if not apps:
|
||
return PLATFORM_KNOWLEDGE
|
||
|
||
# 按类型分组统计
|
||
type_count = {}
|
||
for a in apps:
|
||
t = getattr(a, "type", None) or "skill"
|
||
type_count[t] = type_count.get(t, 0) + 1
|
||
type_brief = ", ".join([f"{({'skill':'技能','agent':'Agent','mcp':'MCP应用','mcp_tool':'MCP工具'}.get(k,k))} {v}" for k, v in sorted(type_count.items())])
|
||
|
||
# 按能力(capability)分组
|
||
from collections import OrderedDict
|
||
by_cap = OrderedDict()
|
||
for a in apps:
|
||
cap = getattr(a, "capability", None) or getattr(a, "category", None) or "通用"
|
||
by_cap.setdefault(cap, []).append(a)
|
||
|
||
# 强制完整性说明(关键变更)
|
||
lines = [
|
||
"# 📦 平台已上线能力清单(实时同步自数据库,可放心信任此清单)",
|
||
"",
|
||
f"**总数:{len(apps)} 个已上线能力**({type_brief})",
|
||
"",
|
||
"## ⚠️ 强制完整性指令",
|
||
"当用户询问以下任何一类问题时,**必须输出下方全部内容**:",
|
||
'- "平台有哪些技能/应用/MCP"',
|
||
'- "全部技能" / "列一下技能" / "技能清单"',
|
||
'- "有什么 Skills" / "支持哪些 Skills"',
|
||
'- "列举所有" / "每个都列出来"',
|
||
"",
|
||
"**绝对不允许**精简、抽样、挑代表性的几个、或改写为综述类叙述。**逐条输出下方每一项**,可以按类别分组展示,但不可省略任何一条。",
|
||
"",
|
||
]
|
||
|
||
# 按能力分组渲染
|
||
type_emoji = {"skill": "🛠", "agent": "🤖", "mcp": "🔌", "mcp_tool": "🔧"}
|
||
for cap in by_cap.keys():
|
||
cap_apps = by_cap[cap]
|
||
lines.append(f"## 【{cap}】- {len(cap_apps)} 个")
|
||
for a in cap_apps:
|
||
name = getattr(a, "name", None) or "未命名"
|
||
desc = (getattr(a, "description", "") or "").strip().replace("\n", " ")
|
||
# 描述长度提升到 100 字,给出更可识别的简介
|
||
if len(desc) > 100:
|
||
desc = desc[:100] + "…"
|
||
emoji = type_emoji.get(getattr(a, "type", "skill"), "📦")
|
||
lines.append(f"- {emoji} **{name}**: {desc}")
|
||
lines.append("")
|
||
|
||
dynamic_section = "\n".join(lines)
|
||
|
||
# 关键:动态能力清单放在最前面,让 AI 优先处理
|
||
return dynamic_section + "\n\n---\n\n# 平台静态文档\n\n" + PLATFORM_KNOWLEDGE
|
||
except Exception as e:
|
||
logger.warning(f"[platform_knowledge] 动态构建失败,回退静态知识库: {e}")
|
||
return PLATFORM_KNOWLEDGE
|