use allama::mock::MockProvider;
use allama::prelude::*;
use allama::schemars::{self, JsonSchema};
use serde::Deserialize;
use serde_json::json;
#[derive(Debug, Deserialize, JsonSchema)]
struct WeatherArgs {
city: String,
#[serde(default)]
units: Units,
}
#[derive(Debug, Default, Deserialize, JsonSchema)]
enum Units {
#[default]
Celsius,
Fahrenheit,
}
#[tokio::main]
async fn main() -> anyhow::Result<()> {
let provider = MockProvider::tool_round_trip(
"call_weather_1",
"lookup_weather",
json!({ "city": "San Francisco", "units": null }),
"The weather in San Francisco is cool and foggy.",
);
let weather = ToolDefinition::from_schema::<WeatherArgs>("lookup_weather")
.description("Look up the weather for a city.")
.strict(true);
let mut request = ChatRequest::new("demo-model")
.system("Use the weather tool when a city lookup is needed.")
.user("What is the weather in San Francisco?")
.tools([weather.clone()])
.tool_choice(ToolChoice::Required);
let first = provider.chat(&request).await?;
request.push_message(first.to_assistant_message());
for call in first.tool_calls() {
let args: WeatherArgs = call.parse_arguments_with(&weather)?;
println!(
"tool call {} -> {} ({:?})",
call.name, args.city, args.units
);
request.push_tool_result(call, format!("Weather for {}: cool and foggy.", args.city));
}
request.tool_choice = None;
let second = provider.chat(&request).await?;
println!("final text: {}", second.text_or_empty());
Ok(())
}