feat(memory): système de mémoire projet model-agnostic (L14, LOT A+B+C)
Base de connaissance persistante par projet, indépendante de tout modèle/CLU
et de git. Cadrage archi en §14.5 (ARCHITECTURE.md), cycle Archi→Dev→Test.
LOT A — étage 1 (.md, source de vérité)
- domaine: entité Memory (+ MemorySlug, MemoryType, MemoryFrontmatter,
MemoryLink, MemoryIndexEntry), liens [[slug]], index MEMORY.md dérivé
- port MemoryStore + MemoryError, adapter FsMemoryStore (.ideai/memory/)
- application: 7 use cases (Create/Update/List/Get/Delete/ReadIndex/
ResolveLinks), From<MemoryError> for AppError
- app-tauri: commandes + DTO, events MemorySaved/MemoryDeleted
- suppression de la variante morte DomainError::MalformedFrontmatter
LOT B — rappel adaptatif (étage 1)
- port MemoryRecall + MemoryQuery, adapter NaiveMemoryRecall (troncature
au budget de tokens, court-circuit budget-0), use case RecallMemory
LOT C — étage 2 vectoriel (structure complète, zéro dépendance lourde)
- port Embedder + EmbedderError, profils déclaratifs EmbedderProfile/
EmbedderStrategy (embedder.json)
- VectorMemoryRecall (cosinus, cache .ideai/memory/.index/ gitignoré)
- AdaptiveMemoryRecall (bascule pure should_use_vector), défaut none
- HashEmbedder (déterministe, tests), StubEmbedder (onnx/server/api)
Tests: 57 binaires verts, build + clippy --workspace sans warning.
Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>
This commit is contained in:
@ -6,7 +6,8 @@
|
||||
//! with one error shape when building its `ErrorDTO`.
|
||||
|
||||
use domain::ports::{
|
||||
FsError, GitError, ProcessError, PtyError, RemoteError, RuntimeError, StoreError,
|
||||
EmbedderError, FsError, GitError, MemoryError, ProcessError, PtyError, RemoteError,
|
||||
RuntimeError, StoreError,
|
||||
};
|
||||
|
||||
/// Errors surfaced by application use cases.
|
||||
@ -84,6 +85,26 @@ impl From<StoreError> for AppError {
|
||||
}
|
||||
}
|
||||
|
||||
impl From<MemoryError> for AppError {
|
||||
fn from(e: MemoryError) -> Self {
|
||||
match e {
|
||||
MemoryError::NotFound => Self::NotFound("memory note".to_owned()),
|
||||
MemoryError::Frontmatter(m) => Self::Invalid(m),
|
||||
other => Self::Store(other.to_string()),
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
impl From<EmbedderError> for AppError {
|
||||
/// Maps to [`AppError::Store`] — an embedder is a *derived* recall detail; its
|
||||
/// failure must degrade the recall (fallback to naïve), never fail hard. This
|
||||
/// mapping exists for completeness; recall adapters degrade *before* an
|
||||
/// embedder error ever reaches a use case.
|
||||
fn from(e: EmbedderError) -> Self {
|
||||
Self::Store(e.to_string())
|
||||
}
|
||||
}
|
||||
|
||||
impl From<PtyError> for AppError {
|
||||
fn from(e: PtyError) -> Self {
|
||||
Self::Process(e.to_string())
|
||||
|
||||
Reference in New Issue
Block a user