重构: tool_registry 声明式注册基础设施(declare_tool! 宏 + list_projects 试点,零回归)
This commit is contained in:
@@ -0,0 +1,57 @@
|
||||
//! 试点工具:`list_projects` 声明式注册(tool_registry 拆分第一步 · 迁移试点)
|
||||
//!
|
||||
//! 验证 `declare_tool!` 宏基础设施可行:从原 `register_project_tools` 第 1 个 register 调用
|
||||
//! (tool_registry.rs:524-541)迁移到声明式,行为逐字等价(schema/risk/handler body 同源)。
|
||||
//!
|
||||
//! 迁移策略(并存零回归):
|
||||
//! - 原 `register_project_tools` 内的 list_projects register 调用删除,改调本模块 `register`。
|
||||
//! - 其余 7 个项目工具(update/create/bind/delete/restore/purge/get_count)仍手写在原处,
|
||||
//! 不动(本步只迁 1 个试点,后续批次渐进)。
|
||||
//! - `MAX_LIST_RESULTS` 由 tool_registry.rs 改 `pub(crate)` 暴露,试点复用同一常量(单真相源,
|
||||
//! 避免字面量 50 漂移)。
|
||||
//!
|
||||
//! 等价性验证:基线测试 test_build_ai_tool_registry_baseline_tool_count 仍断言 48 总量;
|
||||
//! execute("list_projects", args) 行为不变(list_active 分页 + has_more 语义)。
|
||||
|
||||
use std::sync::Arc;
|
||||
|
||||
use df_ai::ai_tools::{object_schema, AiToolRegistry, RiskLevel};
|
||||
use df_ai::declare_tool;
|
||||
use df_storage::db::Database;
|
||||
|
||||
use crate::commands::ai::tool_registry::MAX_LIST_RESULTS;
|
||||
|
||||
/// 用声明式宏注册 `list_projects` 到 `$registry`。
|
||||
///
|
||||
/// 与原手写 register(name, desc, schema, risk, handler) 语义 1:1:
|
||||
/// - name/desc/schema 字符串与 JSON Schema 逐字照搬原定义
|
||||
/// - risk = RiskLevel::Low(只读,无副作用)
|
||||
/// - handler body 与原 async move 块逐字一致(list_active 排软删 + offset/limit 分页 +
|
||||
/// has_more 语义 + 默认/上限对齐 MAX_LIST_RESULTS)
|
||||
///
|
||||
/// 唯一差异:闭包包装(`{ let db = db.clone(); Box::new(move |args| { ... Box::pin(async move {...}) }) }`)
|
||||
/// 改由 `declare_tool!` 宏生成,handler body 直接写业务逻辑。
|
||||
pub fn register(registry: &mut AiToolRegistry, db: &Arc<Database>) {
|
||||
declare_tool!(
|
||||
registry,
|
||||
db: Arc<Database>,
|
||||
"list_projects",
|
||||
"列出所有项目,支持 offset/limit 分页。返回 items(项目列表)、total(总量)、has_more(是否有更多页)。默认 limit=50",
|
||||
RiskLevel::Low,
|
||||
schema: object_schema(vec![("offset", "integer", false), ("limit", "integer", false)]),
|
||||
args => {
|
||||
let repo = df_storage::crud::ProjectRepo::new(&db);
|
||||
// list_active 排除回收站(deleted_at),防 LLM 看到已软删项目
|
||||
let items = repo.list_active().await?;
|
||||
let total = items.len();
|
||||
let offset = args["offset"].as_u64().unwrap_or(0) as usize;
|
||||
let limit = args["limit"]
|
||||
.as_u64()
|
||||
.unwrap_or(MAX_LIST_RESULTS as u64)
|
||||
.min(MAX_LIST_RESULTS as u64) as usize;
|
||||
let page_items: Vec<_> = items.into_iter().skip(offset).take(limit).collect();
|
||||
let has_more = (offset + page_items.len()) < total;
|
||||
Ok(serde_json::json!({ "items": page_items, "total": total, "has_more": has_more }))
|
||||
}
|
||||
);
|
||||
}
|
||||
Reference in New Issue
Block a user