gent/runtime/tools/
mod.rs1use async_trait::async_trait;
4use serde_json::Value as JsonValue;
5use std::collections::HashMap;
6use std::sync::Arc;
7
8use crate::runtime::llm::ToolDefinition;
9
10mod json_parse;
11mod read_file;
12mod user_tool;
13mod web_fetch;
14mod write_file;
15
16pub use json_parse::JsonParseTool;
17pub use read_file::ReadFileTool;
18pub use user_tool::UserToolWrapper;
19pub use web_fetch::WebFetchTool;
20pub use write_file::WriteFileTool;
21
22#[async_trait]
24pub trait Tool: Send + Sync {
25 fn name(&self) -> &str;
26 fn description(&self) -> &str;
27 fn parameters_schema(&self) -> JsonValue;
28 async fn execute(&self, args: JsonValue) -> Result<String, String>;
29
30 fn to_definition(&self) -> ToolDefinition {
31 ToolDefinition {
32 name: self.name().to_string(),
33 description: self.description().to_string(),
34 parameters: self.parameters_schema(),
35 }
36 }
37}
38
39pub struct ToolRegistry {
41 tools: HashMap<String, Arc<dyn Tool>>,
42}
43
44impl ToolRegistry {
45 pub fn new() -> Self {
46 Self {
47 tools: HashMap::new(),
48 }
49 }
50
51 pub fn with_builtins() -> Self {
52 let mut registry = Self::new();
53 registry.register(Box::new(WebFetchTool::new()));
54 registry.register(Box::new(ReadFileTool::new()));
55 registry.register(Box::new(WriteFileTool::new()));
56 registry.register(Box::new(JsonParseTool::new()));
57 registry
58 }
59
60 pub fn register(&mut self, tool: Box<dyn Tool>) {
61 self.tools.insert(tool.name().to_string(), Arc::from(tool));
62 }
63
64 pub fn get(&self, name: &str) -> Option<Arc<dyn Tool>> {
65 self.tools.get(name).cloned()
66 }
67
68 pub fn definitions_for(&self, names: &[String]) -> Vec<ToolDefinition> {
69 names
70 .iter()
71 .filter_map(|name| self.tools.get(name))
72 .map(|tool| tool.to_definition())
73 .collect()
74 }
75}
76
77impl Default for ToolRegistry {
78 fn default() -> Self {
79 Self::new()
80 }
81}