use serde::{Deserialize, Serialize};
use serde_json::Value;
#[derive(Debug, Clone, PartialEq, Serialize, Deserialize)]
pub struct Tool {
pub name: String,
#[serde(default)]
pub description: String,
pub input_schema: Value,
}
impl Tool {
pub fn new(
name: impl Into<String>,
description: impl Into<String>,
input_schema: Value,
) -> Self {
Self { name: name.into(), description: description.into(), input_schema }
}
pub fn from_schema<T: ToolSchema>() -> Self {
Self {
name: T::tool_name().to_string(),
description: T::tool_description().to_string(),
input_schema: T::input_schema(),
}
}
}
#[derive(Debug, Clone, Default, PartialEq, Serialize, Deserialize)]
#[serde(rename_all = "snake_case")]
pub enum ToolChoice {
#[default]
Auto,
Any,
None,
Tool(String),
}
#[derive(Debug, Clone, PartialEq, Serialize, Deserialize)]
pub struct ToolCall {
pub id: String,
pub name: String,
pub input: Value,
}
impl ToolCall {
pub fn new(id: impl Into<String>, name: impl Into<String>, input: Value) -> Self {
Self { id: id.into(), name: name.into(), input }
}
}
#[derive(Debug, Clone, PartialEq, Serialize, Deserialize)]
pub struct ToolResult {
pub tool_use_id: String,
pub content: String,
#[serde(default)]
pub is_error: bool,
}
impl ToolResult {
pub fn ok(tool_use_id: impl Into<String>, content: impl Into<String>) -> Self {
Self { tool_use_id: tool_use_id.into(), content: content.into(), is_error: false }
}
pub fn error(tool_use_id: impl Into<String>, content: impl Into<String>) -> Self {
Self { tool_use_id: tool_use_id.into(), content: content.into(), is_error: true }
}
}
pub trait ToolSchema {
fn tool_name() -> &'static str;
fn tool_description() -> &'static str;
fn input_schema() -> Value;
}