feat(ai): 阶段 2 Ask|Agent 共用 aitools Runtime 真查库

- 侧栏 Ask|Agent 分段;Ask 仍走 /api/ai/chat,Agent 走 /api/ai/agent
- RunAgent 多轮 tool call → 进程内 aitools(与 MCP 同源只读/白名单/审计)
- 回复下步骤时间线;openai-chat tools(DeepSeek);agent-accept 冒烟
This commit is contained in:
logan committed 2026-10-15 11:51:39 +08:00
1 parent b8134c4503
commit cd319ce7bd
14 files changed
+1270 -182

No files matched your search

+4 -59
View File
@@ -33,17 +33,10 @@ func main() {
server.WithToolCapabilities(true),
)
register := func(name, desc string, props map[string]any, required []string) {
schema := map[string]any{
"type": "object",
"properties": props,
}
if len(required) > 0 {
schema["required"] = required
}
raw, _ := json.Marshal(schema)
t := mcp.NewToolWithRawSchema(name, desc, raw)
toolName := name
for _, spec := range aitools.ToolSpecs() {
raw, _ := json.Marshal(spec.InputSchema())
t := mcp.NewToolWithRawSchema(spec.Name, spec.Description, raw)
toolName := spec.Name
s.AddTool(t, func(ctx context.Context, req mcp.CallToolRequest) (*mcp.CallToolResult, error) {
args := req.GetArguments()
out, err := rt.Call(ctx, toolName, args)
@@ -54,54 +47,6 @@ func main() {
})
}
connID := map[string]any{"type": "string", "description": "Saved connection id from opsxdb_list_connections"}
database := map[string]any{"type": "string", "description": "Database / schema / Redis DB index"}
register(aitools.ToolListConnections,
"List whitelisted OpsxDB connections (id/name/driver/host/port/database; never passwords).",
map[string]any{}, nil)
register(aitools.ToolListDatabases,
"List databases for a connection.",
map[string]any{"connection_id": connID}, []string{"connection_id"})
register(aitools.ToolListTables,
"List tables/views (or engine equivalents) in a database.",
map[string]any{"connection_id": connID, "database": database}, []string{"connection_id"})
register(aitools.ToolDescribeTable,
"Describe columns and metadata for a table.",
map[string]any{
"connection_id": connID,
"database": database,
"table": map[string]any{"type": "string", "description": "Table name"},
}, []string{"connection_id", "table"})
register(aitools.ToolGetSchemaContext,
"Compact schema text for LLM context (capped ~4k chars).",
map[string]any{
"connection_id": connID,
"database": database,
"max_tables": map[string]any{"type": "integer", "description": "Max tables to include (default 40)"},
}, []string{"connection_id"})
register(aitools.ToolExecuteQuery,
"Execute a READ-ONLY SQL query (SELECT/SHOW/EXPLAIN/WITH…SELECT). Writes and DDL are rejected in P0. Default limit 100, max 500.",
map[string]any{
"connection_id": connID,
"sql": map[string]any{"type": "string", "description": "Read-only SQL"},
"database": database,
"limit": map[string]any{"type": "integer", "description": "Row limit (default 100, max 500)"},
}, []string{"connection_id", "sql"})
register(aitools.ToolExecuteRedisCommand,
"Execute a READ-ONLY Redis command (GET/SCAN/TYPE/TTL/…). FLUSH*/KEYS and writes are rejected in P0.",
map[string]any{
"connection_id": connID,
"command": map[string]any{"type": "string", "description": "Single Redis command line"},
"database": database,
}, []string{"connection_id", "command"})
if err := server.ServeStdio(s); err != nil {
fmt.Fprintf(os.Stderr, "opsxdb-mcp: %v\n", err)
os.Exit(1)