You can not select more than 25 topics
Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.
52 lines
1.5 KiB
52 lines
1.5 KiB
use crate::application::traits::{DictRepository, DictSource}; |
|
|
|
pub struct DictImporter<'a, R> { |
|
repo: &'a R, |
|
batch_size: usize, |
|
} |
|
|
|
impl<'a, R: DictRepository> DictImporter<'a, R> { |
|
pub fn new(repo: &'a R) -> Self { |
|
Self { |
|
repo, |
|
batch_size: 1000, // reasonable default |
|
} |
|
} |
|
|
|
pub fn import(&self, name: &str, mut source: impl DictSource) -> Result<(), anyhow::Error> { |
|
// 1. Ensure Dict exists (Logic: Create if new, or maybe clear existing?) |
|
self.repo.create(name)?; |
|
|
|
let mut batch = Vec::with_capacity(self.batch_size); |
|
|
|
// 2. Stream data |
|
while let Some(result) = source.next_entry() { |
|
match result { |
|
Ok(entry) => { |
|
// Optional: Domain Validation logic could go here |
|
// if entry.text.is_empty() { continue; } |
|
|
|
batch.push(entry); |
|
|
|
// 3. Batch Write |
|
if batch.len() >= self.batch_size { |
|
self.repo.save_entries(name, &batch)?; |
|
batch.clear(); |
|
} |
|
} |
|
Err(e) => { |
|
// Logic: Do we abort on malformed JSON or log and continue? |
|
// Here we abort for safety. |
|
return Err(e); |
|
} |
|
} |
|
} |
|
|
|
// 4. Flush remaining |
|
if !batch.is_empty() { |
|
self.repo.save_entries(name, &batch)?; |
|
} |
|
|
|
Ok(()) |
|
} |
|
}
|
|
|