feat: Implement semantic search and smart note linking with embedding generation, vector storage, and link persistence.

This commit is contained in:
2025-12-25 23:59:11 +01:00
parent 4cb398869d
commit 178d59540e
19 changed files with 2501 additions and 49 deletions

View File

@@ -11,10 +11,61 @@ pub enum FactoryError {
Database(#[from] sqlx::Error),
#[error("Not implemented: {0}")]
NotImplemented(String),
#[error("Infrastructure error: {0}")]
Infrastructure(#[from] notes_domain::DomainError),
}
pub type FactoryResult<T> = Result<T, FactoryError>;
#[derive(Debug, Clone)]
pub enum EmbeddingProvider {
FastEmbed,
// Ollama(String), // Url
// OpenAI(String), // ApiKey
}
#[derive(Debug, Clone)]
pub enum VectorProvider {
Qdrant { url: String, collection: String },
// InMemory,
}
pub async fn build_embedding_generator(
provider: &EmbeddingProvider,
) -> FactoryResult<Arc<dyn notes_domain::ports::EmbeddingGenerator>> {
match provider {
EmbeddingProvider::FastEmbed => {
let adapter = crate::embeddings::fastembed::FastEmbedAdapter::new()?;
Ok(Arc::new(adapter))
}
}
}
pub async fn build_vector_store(
provider: &VectorProvider,
) -> FactoryResult<Arc<dyn notes_domain::ports::VectorStore>> {
match provider {
VectorProvider::Qdrant { url, collection } => {
let adapter = crate::vector::qdrant::QdrantVectorAdapter::new(url, collection)?;
Ok(Arc::new(adapter))
}
}
}
#[cfg(feature = "sqlite")]
pub async fn build_link_repository(
pool: &DatabasePool,
) -> FactoryResult<Arc<dyn notes_domain::ports::LinkRepository>> {
match pool {
DatabasePool::Sqlite(pool) => Ok(Arc::new(
crate::link_repository::SqliteLinkRepository::new(pool.clone()),
)),
_ => Err(FactoryError::NotImplemented(
"LinkRepostiory for non-sqlite".to_string(),
)),
}
}
pub async fn build_database_pool(db_config: &DatabaseConfig) -> FactoryResult<DatabasePool> {
if db_config.url.starts_with("sqlite:") {
#[cfg(feature = "sqlite")]