use serde::{Deserialize, Serialize};
#[derive(Debug, Clone, Copy, PartialEq, Eq, Serialize, Deserialize)]
#[serde(rename_all = "lowercase")]
pub enum Role {
User,
Assistant,
}
#[derive(Debug, Clone, Serialize, Deserialize)]
#[serde(tag = "type", rename_all = "snake_case")]
pub enum ContentBlock {
Text {
text: String,
},
ToolUse {
id: String,
name: String,
input: serde_json::Value,
},
ToolResult {
tool_use_id: String,
content: String,
#[serde(default, skip_serializing_if = "is_false")]
is_error: bool,
},
}
fn is_false(b: &bool) -> bool {
!*b
}
#[derive(Debug, Clone, Serialize, Deserialize)]
pub struct Message {
pub role: Role,
pub content: Vec<ContentBlock>,
}
impl Message {
#[allow(dead_code)]
pub(crate) fn user_text(text: impl Into<String>) -> Self {
Self {
role: Role::User,
content: vec![ContentBlock::Text { text: text.into() }],
}
}
#[allow(dead_code)]
pub(crate) fn assistant(content: Vec<ContentBlock>) -> Self {
Self {
role: Role::Assistant,
content,
}
}
#[allow(dead_code)]
pub(crate) fn tool_results(results: Vec<ContentBlock>) -> Self {
Self {
role: Role::User,
content: results,
}
}
}
#[derive(Debug, Clone, Default, Serialize, Deserialize)]
pub struct Usage {
#[serde(default)]
pub input_tokens: u32,
#[serde(default)]
pub cache_creation_input_tokens: u32,
#[serde(default)]
pub cache_read_input_tokens: u32,
#[serde(default)]
pub output_tokens: u32,
}
impl Usage {
pub(crate) fn add(&mut self, other: &Usage) {
self.input_tokens += other.input_tokens;
self.cache_creation_input_tokens += other.cache_creation_input_tokens;
self.cache_read_input_tokens += other.cache_read_input_tokens;
self.output_tokens += other.output_tokens;
}
}