ararajuba_tools_coding/fs/
write.rs1use ararajuba_core::tools::tool::{tool, ToolDef};
4use serde_json::json;
5use std::path::Path;
6
7pub fn write_file_tool() -> ToolDef {
12 tool("write_file")
13 .description("Write content to a file. Creates parent directories if needed.")
14 .input_schema(json!({
15 "type": "object",
16 "properties": {
17 "path": { "type": "string", "description": "File path to write" },
18 "content": { "type": "string", "description": "Content to write" }
19 },
20 "required": ["path", "content"]
21 }))
22 .execute(|input| async move {
23 let path = input["path"]
24 .as_str()
25 .ok_or_else(|| "missing required field: path".to_string())?;
26 let content = input["content"]
27 .as_str()
28 .ok_or_else(|| "missing required field: content".to_string())?;
29
30 if let Some(parent) = Path::new(path).parent() {
32 tokio::fs::create_dir_all(parent)
33 .await
34 .map_err(|e| format!("failed to create directories: {e}"))?;
35 }
36
37 let bytes = content.as_bytes().len();
38 tokio::fs::write(path, content)
39 .await
40 .map_err(|e| format!("failed to write file: {e}"))?;
41
42 Ok(json!({
43 "ok": true,
44 "bytes_written": bytes
45 }))
46 })
47 .build()
48}
49
50#[cfg(test)]
51mod tests {
52 use super::*;
53
54 #[test]
55 fn tool_metadata() {
56 let t = write_file_tool();
57 assert_eq!(t.name, "write_file");
58 assert!(t.description.is_some());
59 assert!(t.execute.is_some());
60 }
61}