mirror of
https://github.com/perstarkse/minne.git
synced 2026-04-24 17:58:31 +02:00
fix: graphmapper gracefully failing
This commit is contained in:
@@ -6,9 +6,12 @@ use tokio::task;
|
|||||||
|
|
||||||
use common::{
|
use common::{
|
||||||
error::AppError,
|
error::AppError,
|
||||||
storage::types::{
|
storage::{
|
||||||
knowledge_entity::{KnowledgeEntity, KnowledgeEntityType},
|
db::SurrealDbClient,
|
||||||
knowledge_relationship::KnowledgeRelationship,
|
types::{
|
||||||
|
knowledge_entity::{KnowledgeEntity, KnowledgeEntityType},
|
||||||
|
knowledge_relationship::KnowledgeRelationship,
|
||||||
|
},
|
||||||
},
|
},
|
||||||
utils::embedding::generate_embedding,
|
utils::embedding::generate_embedding,
|
||||||
};
|
};
|
||||||
@@ -56,13 +59,20 @@ impl LLMEnrichmentResult {
|
|||||||
source_id: &str,
|
source_id: &str,
|
||||||
user_id: &str,
|
user_id: &str,
|
||||||
openai_client: &async_openai::Client<async_openai::config::OpenAIConfig>,
|
openai_client: &async_openai::Client<async_openai::config::OpenAIConfig>,
|
||||||
|
db_client: &SurrealDbClient,
|
||||||
) -> Result<(Vec<KnowledgeEntity>, Vec<KnowledgeRelationship>), AppError> {
|
) -> Result<(Vec<KnowledgeEntity>, Vec<KnowledgeRelationship>), AppError> {
|
||||||
// Create mapper and pre-assign IDs
|
// Create mapper and pre-assign IDs
|
||||||
let mapper = Arc::new(Mutex::new(self.create_mapper()?));
|
let mapper = Arc::new(Mutex::new(self.create_mapper()?));
|
||||||
|
|
||||||
// Process entities
|
// Process entities
|
||||||
let entities = self
|
let entities = self
|
||||||
.process_entities(source_id, user_id, Arc::clone(&mapper), openai_client)
|
.process_entities(
|
||||||
|
source_id,
|
||||||
|
user_id,
|
||||||
|
Arc::clone(&mapper),
|
||||||
|
openai_client,
|
||||||
|
db_client,
|
||||||
|
)
|
||||||
.await?;
|
.await?;
|
||||||
|
|
||||||
// Process relationships
|
// Process relationships
|
||||||
@@ -88,6 +98,7 @@ impl LLMEnrichmentResult {
|
|||||||
user_id: &str,
|
user_id: &str,
|
||||||
mapper: Arc<Mutex<GraphMapper>>,
|
mapper: Arc<Mutex<GraphMapper>>,
|
||||||
openai_client: &async_openai::Client<async_openai::config::OpenAIConfig>,
|
openai_client: &async_openai::Client<async_openai::config::OpenAIConfig>,
|
||||||
|
db_client: &SurrealDbClient,
|
||||||
) -> Result<Vec<KnowledgeEntity>, AppError> {
|
) -> Result<Vec<KnowledgeEntity>, AppError> {
|
||||||
let futures: Vec<_> = self
|
let futures: Vec<_> = self
|
||||||
.knowledge_entities
|
.knowledge_entities
|
||||||
@@ -98,10 +109,18 @@ impl LLMEnrichmentResult {
|
|||||||
let source_id = source_id.to_string();
|
let source_id = source_id.to_string();
|
||||||
let user_id = user_id.to_string();
|
let user_id = user_id.to_string();
|
||||||
let entity = entity.clone();
|
let entity = entity.clone();
|
||||||
|
let db_client = db_client.clone();
|
||||||
|
|
||||||
task::spawn(async move {
|
task::spawn(async move {
|
||||||
create_single_entity(&entity, &source_id, &user_id, mapper, &openai_client)
|
create_single_entity(
|
||||||
.await
|
&entity,
|
||||||
|
&source_id,
|
||||||
|
&user_id,
|
||||||
|
mapper,
|
||||||
|
&openai_client,
|
||||||
|
&db_client.clone(),
|
||||||
|
)
|
||||||
|
.await
|
||||||
})
|
})
|
||||||
})
|
})
|
||||||
.collect();
|
.collect();
|
||||||
@@ -120,14 +139,14 @@ impl LLMEnrichmentResult {
|
|||||||
user_id: &str,
|
user_id: &str,
|
||||||
mapper: Arc<Mutex<GraphMapper>>,
|
mapper: Arc<Mutex<GraphMapper>>,
|
||||||
) -> Result<Vec<KnowledgeRelationship>, AppError> {
|
) -> Result<Vec<KnowledgeRelationship>, AppError> {
|
||||||
let mut mapper_guard = mapper
|
let mapper_guard = mapper
|
||||||
.lock()
|
.lock()
|
||||||
.map_err(|_| AppError::GraphMapper("Failed to lock mapper".into()))?;
|
.map_err(|_| AppError::GraphMapper("Failed to lock mapper".into()))?;
|
||||||
self.relationships
|
self.relationships
|
||||||
.iter()
|
.iter()
|
||||||
.map(|rel| {
|
.map(|rel| {
|
||||||
let source_db_id = mapper_guard.get_or_parse_id(&rel.source);
|
let source_db_id = mapper_guard.get_or_parse_id(&rel.source)?;
|
||||||
let target_db_id = mapper_guard.get_or_parse_id(&rel.target);
|
let target_db_id = mapper_guard.get_or_parse_id(&rel.target)?;
|
||||||
|
|
||||||
Ok(KnowledgeRelationship::new(
|
Ok(KnowledgeRelationship::new(
|
||||||
source_db_id.to_string(),
|
source_db_id.to_string(),
|
||||||
@@ -146,17 +165,13 @@ async fn create_single_entity(
|
|||||||
user_id: &str,
|
user_id: &str,
|
||||||
mapper: Arc<Mutex<GraphMapper>>,
|
mapper: Arc<Mutex<GraphMapper>>,
|
||||||
openai_client: &async_openai::Client<async_openai::config::OpenAIConfig>,
|
openai_client: &async_openai::Client<async_openai::config::OpenAIConfig>,
|
||||||
|
db_client: &SurrealDbClient,
|
||||||
) -> Result<KnowledgeEntity, AppError> {
|
) -> Result<KnowledgeEntity, AppError> {
|
||||||
let assigned_id = {
|
let assigned_id = {
|
||||||
let mapper = mapper
|
let mapper = mapper
|
||||||
.lock()
|
.lock()
|
||||||
.map_err(|_| AppError::GraphMapper("Failed to lock mapper".into()))?;
|
.map_err(|_| AppError::GraphMapper("Failed to lock mapper".into()))?;
|
||||||
mapper
|
mapper.get_id(&llm_entity.key)?.to_string()
|
||||||
.get_id(&llm_entity.key)
|
|
||||||
.ok_or_else(|| {
|
|
||||||
AppError::GraphMapper(format!("ID not found for key: {}", llm_entity.key))
|
|
||||||
})?
|
|
||||||
.to_string()
|
|
||||||
};
|
};
|
||||||
|
|
||||||
let embedding_input = format!(
|
let embedding_input = format!(
|
||||||
@@ -164,7 +179,7 @@ async fn create_single_entity(
|
|||||||
llm_entity.name, llm_entity.description, llm_entity.entity_type
|
llm_entity.name, llm_entity.description, llm_entity.entity_type
|
||||||
);
|
);
|
||||||
|
|
||||||
let embedding = generate_embedding(openai_client, &embedding_input).await?;
|
let embedding = generate_embedding(openai_client, &embedding_input, db_client).await?;
|
||||||
|
|
||||||
let now = Utc::now();
|
let now = Utc::now();
|
||||||
Ok(KnowledgeEntity {
|
Ok(KnowledgeEntity {
|
||||||
|
|||||||
@@ -1,5 +1,6 @@
|
|||||||
pub mod llm_instructions;
|
pub mod llm_instructions;
|
||||||
|
|
||||||
|
use common::error::AppError;
|
||||||
use std::collections::HashMap;
|
use std::collections::HashMap;
|
||||||
use uuid::Uuid;
|
use uuid::Uuid;
|
||||||
|
|
||||||
@@ -21,24 +22,39 @@ impl GraphMapper {
|
|||||||
key_to_id: HashMap::new(),
|
key_to_id: HashMap::new(),
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
/// Get ID, tries to parse UUID
|
/// Tries to get an ID by first parsing the key as a UUID,
|
||||||
pub fn get_or_parse_id(&mut self, key: &str) -> Uuid {
|
/// and if that fails, looking it up in the internal map.
|
||||||
|
pub fn get_or_parse_id(&self, key: &str) -> Result<Uuid, AppError> {
|
||||||
|
// First, try to parse the key as a UUID.
|
||||||
if let Ok(parsed_uuid) = Uuid::parse_str(key) {
|
if let Ok(parsed_uuid) = Uuid::parse_str(key) {
|
||||||
parsed_uuid
|
return Ok(parsed_uuid);
|
||||||
} else {
|
|
||||||
*self.key_to_id.get(key).unwrap()
|
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// If parsing fails, look it up in the map.
|
||||||
|
self.key_to_id
|
||||||
|
.get(key)
|
||||||
|
.map(|id| *id) // Dereference the &Uuid to get Uuid
|
||||||
|
// If `get` returned None, create and return an error.
|
||||||
|
.ok_or_else(|| {
|
||||||
|
AppError::GraphMapper(format!(
|
||||||
|
"Key '{}' is not a valid UUID and was not found in the map.",
|
||||||
|
key
|
||||||
|
))
|
||||||
|
})
|
||||||
}
|
}
|
||||||
|
|
||||||
/// Assigns a new UUID for a given key.
|
/// Assigns a new UUID for a given key. (No changes needed here)
|
||||||
pub fn assign_id(&mut self, key: &str) -> Uuid {
|
pub fn assign_id(&mut self, key: &str) -> Uuid {
|
||||||
let id = Uuid::new_v4();
|
let id = Uuid::new_v4();
|
||||||
self.key_to_id.insert(key.to_string(), id);
|
self.key_to_id.insert(key.to_string(), id);
|
||||||
id
|
id
|
||||||
}
|
}
|
||||||
|
|
||||||
/// Retrieves the UUID for a given key.
|
/// Retrieves the UUID for a given key, returning a Result for consistency.
|
||||||
pub fn get_id(&self, key: &str) -> Option<&Uuid> {
|
pub fn get_id(&self, key: &str) -> Result<Uuid, AppError> {
|
||||||
self.key_to_id.get(key)
|
self.key_to_id
|
||||||
|
.get(key)
|
||||||
|
.map(|id| *id)
|
||||||
|
.ok_or_else(|| AppError::GraphMapper(format!("Key '{}' not found in map.", key)))
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|||||||
Reference in New Issue
Block a user