use core::fmt;
use core::time::Duration;
extern crate alloc;
use alloc::format;
use alloc::string::String;
use alloc::string::ToString;
#[derive(Default, Clone)]
pub struct Stats {
pub used_model: String,
pub provider: String,
pub cost_in_cents: f64, pub elapsed_time: Duration,
pub time_to_first_token: Option<Duration>,
pub inter_token_latency_ms: u128,
}
impl Stats {
pub fn provider(&self) -> &str {
&self.provider
}
}
impl fmt::Display for Stats {
fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result {
write!(
f,
"{} at {}. {:.4} cents. {} ({} TTFT, {}ms ITL)",
self.used_model,
self.provider,
self.cost_in_cents,
format_duration(self.elapsed_time),
format_duration(self.time_to_first_token.unwrap_or_default()),
self.inter_token_latency_ms,
)
}
}
fn format_duration(d: Duration) -> String {
let total_millis = d.as_millis();
let minutes = total_millis / 60_000;
let seconds = (total_millis % 60_000) / 1_000;
let milliseconds = total_millis % 1_000;
let mut result = String::new();
if minutes > 0 {
result.push_str(&format!("{minutes}m"));
}
if seconds > 0 {
if seconds <= 2 {
result.push_str(&format!(
"{seconds}.{}s",
(milliseconds as f64 / 100.0) as u32
));
} else {
result.push_str(&format!("{seconds}s"));
}
}
if milliseconds > 0 && minutes == 0 && seconds == 0 {
result.push_str(&format!("{milliseconds}ms"));
}
if result.is_empty() {
result = "0ms".to_string();
}
result
}