use std::{collections::BTreeMap, fmt};
use serde::Serialize;
use serde_json::Value;
use crate::RetrievalError;
#[derive(Clone, Debug, Eq, Hash, Ord, PartialEq, PartialOrd, Serialize)]
#[serde(transparent)]
pub struct DocumentId(String);
impl DocumentId {
pub fn new(value: impl Into<String>) -> Result<Self, RetrievalError> {
let value = value.into();
if value.trim().is_empty() {
return Err(RetrievalError::EmptyDocumentId);
}
Ok(Self(value))
}
pub fn as_str(&self) -> &str {
&self.0
}
}
impl fmt::Display for DocumentId {
fn fmt(&self, formatter: &mut fmt::Formatter<'_>) -> fmt::Result {
self.0.fmt(formatter)
}
}
impl TryFrom<String> for DocumentId {
type Error = RetrievalError;
fn try_from(value: String) -> Result<Self, Self::Error> {
Self::new(value)
}
}
impl TryFrom<&str> for DocumentId {
type Error = RetrievalError;
fn try_from(value: &str) -> Result<Self, Self::Error> {
Self::new(value)
}
}
#[derive(Clone, Debug, PartialEq, Serialize)]
pub struct Document {
pub id: DocumentId,
pub text: String,
pub metadata: BTreeMap<String, Value>,
}
impl Document {
pub fn new(id: impl Into<String>, text: impl Into<String>) -> Result<Self, RetrievalError> {
let id = DocumentId::new(id)?;
let text = text.into();
if text.trim().is_empty() {
return Err(RetrievalError::EmptyDocumentText { id });
}
Ok(Self {
id,
text,
metadata: BTreeMap::new(),
})
}
#[must_use]
pub fn with_metadata(mut self, metadata: BTreeMap<String, Value>) -> Self {
self.metadata = metadata;
self
}
}