use serde::{Deserialize, Serialize};
#[derive(Debug, Clone, Deserialize, Serialize, PartialEq)]
#[serde(tag = "type", rename_all = "snake_case")]
pub enum ContentBlock {
Text { text: String },
Image {
data: String,
#[serde(rename = "mimeType")]
mime_type: String,
},
Audio {
data: String,
#[serde(rename = "mimeType")]
mime_type: String,
},
Resource(ResourceContent),
ResourceLink {
uri: String,
#[serde(skip_serializing_if = "Option::is_none")]
name: Option<String>,
#[serde(skip_serializing_if = "Option::is_none", rename = "mimeType")]
mime_type: Option<String>,
},
}
impl ContentBlock {
pub fn text(text: impl Into<String>) -> Self {
Self::Text { text: text.into() }
}
pub fn image(data: impl Into<String>, mime_type: impl Into<String>) -> Self {
Self::Image {
data: data.into(),
mime_type: mime_type.into(),
}
}
pub fn audio(data: impl Into<String>, mime_type: impl Into<String>) -> Self {
Self::Audio {
data: data.into(),
mime_type: mime_type.into(),
}
}
pub fn resource(resource: ResourceContent) -> Self {
Self::Resource(resource)
}
pub fn resource_link(
uri: impl Into<String>,
name: Option<String>,
mime_type: Option<String>,
) -> Self {
Self::ResourceLink {
uri: uri.into(),
name,
mime_type,
}
}
pub fn is_text(&self) -> bool {
matches!(self, Self::Text { .. })
}
pub fn is_image(&self) -> bool {
matches!(self, Self::Image { .. })
}
pub fn is_audio(&self) -> bool {
matches!(self, Self::Audio { .. })
}
pub fn is_resource(&self) -> bool {
matches!(self, Self::Resource(_))
}
pub fn is_resource_link(&self) -> bool {
matches!(self, Self::ResourceLink { .. })
}
}
#[derive(Debug, Clone, Deserialize, Serialize, PartialEq)]
pub struct ResourceContent {
pub uri: String,
#[serde(default, rename = "mimeType", skip_serializing_if = "Option::is_none")]
pub mime_type: Option<String>,
#[serde(default, skip_serializing_if = "Option::is_none")]
pub text: Option<String>,
#[serde(default, skip_serializing_if = "Option::is_none")]
pub blob: Option<String>,
}
impl ResourceContent {
pub fn new(uri: impl Into<String>) -> Self {
Self {
uri: uri.into(),
mime_type: None,
text: None,
blob: None,
}
}
pub fn with_mime_type(mut self, mime_type: impl Into<String>) -> Self {
self.mime_type = Some(mime_type.into());
self
}
pub fn with_text(mut self, text: impl Into<String>) -> Self {
self.text = Some(text.into());
self
}
pub fn with_blob(mut self, blob: impl Into<String>) -> Self {
self.blob = Some(blob.into());
self
}
pub fn with_optional_mime(mut self, mime_type: Option<String>) -> Self {
if mime_type.is_some() {
self.mime_type = mime_type;
}
self
}
}