pub mod generic;
pub mod markdown;
pub mod mem0;
pub mod shodh;
use anyhow::Result;
use super::schema::MifDocument;
pub trait MifAdapter: Send + Sync {
fn name(&self) -> &str;
fn format_id(&self) -> &str;
fn detect(&self, data: &[u8]) -> bool;
fn to_mif(&self, data: &[u8]) -> Result<MifDocument>;
#[allow(clippy::wrong_self_convention)]
fn from_mif(&self, doc: &MifDocument) -> Result<Vec<u8>>;
}
pub struct AdapterRegistry {
adapters: Vec<Box<dyn MifAdapter>>,
}
impl AdapterRegistry {
pub fn new() -> Self {
Self {
adapters: vec![
Box::new(shodh::ShodhAdapter),
Box::new(mem0::Mem0Adapter),
Box::new(generic::GenericJsonAdapter),
Box::new(markdown::MarkdownAdapter),
],
}
}
pub fn auto_import(&self, data: &[u8]) -> Result<MifDocument> {
for adapter in &self.adapters {
if adapter.detect(data) {
return adapter.to_mif(data);
}
}
anyhow::bail!("No adapter could detect the input format. Supported: shodh (MIF JSON), mem0, generic JSON array, markdown.")
}
pub fn import_with(&self, format_id: &str, data: &[u8]) -> Result<MifDocument> {
for adapter in &self.adapters {
if adapter.format_id() == format_id {
return adapter.to_mif(data);
}
}
anyhow::bail!(
"Unknown format: '{}'. Available: {}",
format_id,
self.list_formats().join(", ")
)
}
pub fn export_with(&self, format_id: &str, doc: &MifDocument) -> Result<Vec<u8>> {
for adapter in &self.adapters {
if adapter.format_id() == format_id {
return adapter.from_mif(doc);
}
}
anyhow::bail!(
"Unknown format: '{}'. Available: {}",
format_id,
self.list_formats().join(", ")
)
}
pub fn list_formats(&self) -> Vec<&str> {
self.adapters.iter().map(|a| a.format_id()).collect()
}
pub fn list_adapters(&self) -> Vec<(&str, &str)> {
self.adapters
.iter()
.map(|a| (a.name(), a.format_id()))
.collect()
}
}
impl Default for AdapterRegistry {
fn default() -> Self {
Self::new()
}
}