Skip to main content
Glama
ARCHITECTURE.mdβ€’28.1 kB
# πŸ—οΈ Arquitectura del Sistema DiseΓ±o tΓ©cnico completo del sistema de memoria auto-evolutivo. --- ## πŸ“‹ Contenidos 1. [VisiΓ³n General](#visiΓ³n-general) 2. [Arquitectura de 3 Capas](#arquitectura-de-3-capas) 3. [Flujo de Datos](#flujo-de-datos) 4. [Componentes Principales](#componentes-principales) 5. [Sistema de Entidades y Relaciones](#sistema-de-entidades-y-relaciones) 6. [Decisiones de DiseΓ±o](#decisiones-de-diseΓ±o) --- ## VisiΓ³n General ### Principios ArquitectΓ³nicos **SOLID Principles:** - βœ… **Single Responsibility:** Cada componente tiene una responsabilidad clara - βœ… **Open/Closed:** Extensible mediante agentes y plugins sin modificar core - βœ… **Liskov Substitution:** VectorStore puede intercambiarse por otras implementaciones - βœ… **Interface Segregation:** Interfaces pequeΓ±as y especΓ­ficas - βœ… **Dependency Inversion:** KnowledgeStore depende de abstracciΓ³n, no implementaciΓ³n **Otros Principios:** - πŸ”„ **Separation of Concerns:** API, lΓ³gica, persistencia separadas - πŸ“¦ **Modular Design:** Componentes independientes y reutilizables - 🎯 **Single Source of Truth:** LanceDB es la ΓΊnica fuente de datos - πŸ”Œ **Plugin Architecture:** Agentes como plugins auto-contenidos --- ## Arquitectura de 3 Capas ``` β”Œβ”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β” β”‚ CAPA 1: INTERFACES β”‚ β”‚ β”Œβ”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β” β”Œβ”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β” β”Œβ”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β” β”‚ β”‚ β”‚ MCP Tools β”‚ β”‚ Slash β”‚ β”‚ CLI (terminal) β”‚ β”‚ β”‚ β”‚ (Claude) β”‚ β”‚ Commands β”‚ β”‚ memory-cli stats β”‚ β”‚ β”‚ β””β”€β”€β”€β”€β”€β”€β”¬β”€β”€β”€β”€β”€β”€β”˜ β””β”€β”€β”€β”€β”€β”€β”¬β”€β”€β”€β”€β”€β”€β”˜ β””β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”¬β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”˜ β”‚ β”‚ β”‚ β”‚ β”‚ β”‚ β””β”€β”€β”€β”€β”€β”€β”€β”€β”€β”Όβ”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”Όβ”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”Όβ”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”˜ β”‚ β”‚ β”‚ β””β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”΄β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”˜ β–Ό β”Œβ”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β” β”‚ CAPA 2: LΓ“GICA DE NEGOCIO β”‚ β”‚ β”Œβ”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β” β”‚ β”‚ β”‚ MCP Server (index.js) β”‚ β”‚ β”‚ β”‚ β€’ Transport Layer (StdioServerTransport) β”‚ β”‚ β”‚ β”‚ β€’ Tool Registration & Routing β”‚ β”‚ β”‚ β”‚ β€’ Request Validation (Zod schemas) β”‚ β”‚ β”‚ β”‚ β€’ Error Handling β”‚ β”‚ β”‚ β””β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”¬β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”˜ β”‚ β”‚ β”‚ β”‚ β”‚ β”Œβ”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β–Όβ”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β” β”‚ β”‚ β”‚ KnowledgeStore (class) β”‚ β”‚ β”‚ β”‚ β€’ Entity Management (CRUD) β”‚ β”‚ β”‚ β”‚ β€’ Relation Management β”‚ β”‚ β”‚ β”‚ β€’ Confidence System β”‚ β”‚ β”‚ β”‚ β€’ Search & Retrieval β”‚ β”‚ β”‚ β”‚ β€’ Stats & Analytics β”‚ β”‚ β”‚ β”‚ β€’ Export Functionality β”‚ β”‚ β”‚ β””β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”¬β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”˜ β”‚ β””β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”Όβ”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”˜ β”‚ β–Ό β”Œβ”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β” β”‚ CAPA 3: PERSISTENCIA β”‚ β”‚ β”Œβ”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β” β”‚ β”‚ β”‚ VectorStore (vector-store.js) β”‚ β”‚ β”‚ β”‚ β€’ Embedding Generation (Transformers.js) β”‚ β”‚ β”‚ β”‚ β€’ Vector Operations (add, search, update, delete) β”‚ β”‚ β”‚ β”‚ β€’ LanceDB Abstraction β”‚ β”‚ β”‚ β”‚ β€’ Schema Management β”‚ β”‚ β”‚ β””β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”¬β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”˜ β”‚ β”‚ β”‚ β”‚ β”‚ β”Œβ”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β–Όβ”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β” β”‚ β”‚ β”‚ LanceDB Storage β”‚ β”‚ β”‚ β”‚ β€’ Vector Database (.claude-memory/vectors/lancedb/) β”‚ β”‚ β”‚ β”‚ β€’ Persistent Storage β”‚ β”‚ β”‚ β”‚ β€’ Efficient Vector Search β”‚ β”‚ β”‚ β””β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”˜ β”‚ β””β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”˜ ``` --- ## Flujo de Datos ### 1. User Request β†’ Knowledge Capture ``` β”Œβ”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β” β”‚ Usuario β”‚ "Guarda decisiΓ³n: Usar PostgreSQL" β””β”€β”€β”€β”€β”¬β”€β”€β”€β”€β”€β”˜ β”‚ β–Ό β”Œβ”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β” β”‚ MCP Tool Call β”‚ save_knowledge({type: "decision", content: "..."}) β””β”€β”€β”€β”€β”¬β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”˜ β”‚ β–Ό β”Œβ”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β” β”‚ Input Validation β”‚ Zod schema validation β””β”€β”€β”€β”€β”¬β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”˜ β”‚ β–Ό β”Œβ”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β” β”‚ KnowledgeStore β”‚ addEntry({...}) β”‚ β€’ Generate UUID β”‚ β”‚ β€’ Set metadata β”‚ β”‚ β€’ Prepare for store β”‚ β””β”€β”€β”€β”€β”¬β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”˜ β”‚ β–Ό β”Œβ”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β” β”‚ VectorStore β”‚ add({...}) β”‚ β€’ Generate embeddingβ”‚ Transformers.js (384D vector) β”‚ β€’ Serialize arrays β”‚ tags β†’ JSON string β”‚ β€’ Insert to LanceDB β”‚ β””β”€β”€β”€β”€β”¬β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”˜ β”‚ β–Ό β”Œβ”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β” β”‚ LanceDB β”‚ Persistent storage β”‚ β€’ Write to disk β”‚ β”‚ β€’ Index vector β”‚ β””β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”˜ ``` ### 2. Knowledge Search ``` β”Œβ”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β” β”‚ Usuario β”‚ "Busca decisiones sobre database" β””β”€β”€β”€β”€β”¬β”€β”€β”€β”€β”€β”˜ β”‚ β–Ό β”Œβ”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β” β”‚ MCP Tool Call β”‚ search_knowledge({query: "database"}) β””β”€β”€β”€β”€β”¬β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”˜ β”‚ β–Ό β”Œβ”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β” β”‚ KnowledgeStore β”‚ search("database", {type: "decision"}) β””β”€β”€β”€β”€β”¬β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”˜ β”‚ β–Ό β”Œβ”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β” β”‚ VectorStore β”‚ search("database", limit: 10) β”‚ β€’ Generate embeddingβ”‚ Query β†’ 384D vector β”‚ β€’ Vector search β”‚ Cosine similarity β”‚ β€’ Filter results β”‚ By type, confidence β””β”€β”€β”€β”€β”¬β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”˜ β”‚ β–Ό β”Œβ”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β” β”‚ LanceDB β”‚ Vector similarity search β”‚ β€’ ANN search β”‚ Approximate Nearest Neighbors β”‚ β€’ Return top K β”‚ β””β”€β”€β”€β”€β”¬β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”˜ β”‚ β–Ό β”Œβ”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β” β”‚ Post-Processing β”‚ β”‚ β€’ Deserialize arraysβ”‚ JSON string β†’ array β”‚ β€’ Update metadata β”‚ accessCount++, lastAccessed β”‚ β€’ Format response β”‚ β””β”€β”€β”€β”€β”¬β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”˜ β”‚ β–Ό β”Œβ”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β” β”‚ Results β”‚ [{id, type, content, confidence, ...}, ...] β””β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”˜ ``` ### 3. Agent Workflow ``` β”Œβ”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β” β”‚ Trigger β”‚ Error occurs, task starts, etc. β””β”€β”€β”€β”€β”¬β”€β”€β”€β”€β”€β”˜ β”‚ β–Ό β”Œβ”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β” β”‚ Claude detects β”‚ Matches trigger condition in CLAUDE.md β”‚ trigger β”‚ β””β”€β”€β”€β”€β”¬β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”˜ β”‚ β–Ό β”Œβ”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β” β”‚ Task tool call β”‚ Launch agent (subagent_type: "general-purpose") β””β”€β”€β”€β”€β”¬β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”˜ β”‚ β–Ό β”Œβ”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β” β”‚ Agent executes β”‚ β”‚ 1. Search memory β”‚ mcp__memory__search_nodes β”‚ 2. Analyze findings β”‚ β”‚ 3. Create entities β”‚ mcp__memory__create_entities β”‚ 4. Create relations β”‚ mcp__memory__create_relations β””β”€β”€β”€β”€β”¬β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”˜ β”‚ β–Ό β”Œβ”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β” β”‚ Knowledge stored β”‚ Entities + Relations in LanceDB β””β”€β”€β”€β”€β”¬β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”˜ β”‚ β–Ό β”Œβ”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β” β”‚ Report β”‚ Brief confirmation to Claude β””β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”˜ ``` --- ## Componentes Principales ### 1. MCP Server (`index.js`) **Responsabilidad:** API Layer y Transport **Componentes:** ```javascript // Server initialization const server = new Server({ name: 'self-improving-memory', version: '2.0.0' }, { capabilities: { tools: {} // Expose MCP tools } }); // Transport (stdio para Claude Desktop) const transport = new StdioServerTransport(); // Tool registration server.setRequestHandler(ListToolsRequestSchema, async () => ({ tools: [ { name: 'create_entities', ... }, { name: 'search_nodes', ... }, ... ] })); // Tool execution server.setRequestHandler(CallToolRequestSchema, async (request) => { // Route to KnowledgeStore }); ``` **Herramientas Expuestas:** 1. `create_entities` - Crear entidades 2. `create_relations` - Crear relaciones 3. `add_observations` - Agregar observaciones 4. `search_nodes` - Buscar conocimiento 5. `open_nodes` - Abrir entidades especΓ­ficas 6. `read_graph` - Leer grafo completo 7. `delete_entities` - Eliminar entidades 8. `delete_observations` - Eliminar observaciones **Patterns Utilizados:** - **Factory Pattern:** Para crear entidades - **Strategy Pattern:** Routing de tools - **Facade Pattern:** Simplifica acceso a KnowledgeStore --- ### 2. KnowledgeStore (clase en `index.js`) **Responsabilidad:** Business Logic **MΓ©todos Principales:** ```javascript class KnowledgeStore { constructor(projectPath) { this.vectorStore = new VectorStore(projectPath); } // Entity Management async addEntry({ type, content, context, confidence, ... }) { const id = crypto.randomUUID(); const entry = { id, type, content, context, confidence, verified: false, tags: [], timestamp: new Date().toISOString(), accessCount: 0, lastAccessed: null, relatedIds: [] }; await this.vectorStore.add(entry); return id; } // Search with filters async search(query, { type, minConfidence, limit } = {}) { const results = await this.vectorStore.search(query, limit); // Filter by type if (type) { results = results.filter(r => r.type === type); } // Filter by confidence if (minConfidence) { results = results.filter(r => r.confidence >= minConfidence); } // Update access metadata for (const result of results) { await this.updateMetadata(result.id, { accessCount: result.accessCount + 1, lastAccessed: new Date().toISOString() }); } return results; } // Relation Management async linkEntries(fromId, toId, relationType) { const from = await this.getById(fromId); if (!from.relatedIds.includes(toId)) { from.relatedIds.push(toId); await this.updateEntry(fromId, { relatedIds: from.relatedIds }); } } // Analytics async getStats() { const allEntries = await this.vectorStore.getAll(); return { totalEntries: allEntries.length, byType: this.groupBy(allEntries, 'type'), byConfidence: this.groupByConfidence(allEntries), verified: allEntries.filter(e => e.verified).length, mostAccessedId: this.findMostAccessed(allEntries)?.id }; } // Export async exportMarkdown() { const entries = await this.vectorStore.getAll(); const grouped = this.groupBy(entries, 'type'); let md = '# Knowledge Base Export\n\n'; for (const [type, items] of Object.entries(grouped)) { md += `## ${type}\n\n`; for (const item of items) { md += `### ${item.content}\n`; md += `- Confidence: ${item.confidence}\n`; md += `- Tags: ${item.tags.join(', ')}\n\n`; } } return md; } } ``` **Patterns Utilizados:** - **Repository Pattern:** Abstrae acceso a datos - **Builder Pattern:** ConstrucciΓ³n de queries complejas - **Template Method:** Export en diferentes formatos --- ### 3. VectorStore (`vector-store.js`) **Responsabilidad:** Vector Operations & LanceDB Abstraction **Componentes:** ```javascript class VectorStore { constructor(projectPath) { this.dbPath = path.join(projectPath, '.claude-memory', 'vectors', 'lancedb'); this.db = null; this.table = null; this.model = null; // Transformers.js model } // Initialization async initialize() { this.db = await lancedb.connect(this.dbPath); // Check if table exists const tableNames = await this.db.tableNames(); if (tableNames.includes('knowledge')) { this.table = await this.db.openTable('knowledge'); } else { // Create table with schema this.table = await this.db.createTable('knowledge', SCHEMA); } // Warm-up embeddings model in background this.warmupModel(); } // Embedding generation async generateEmbedding(text) { if (!this.model) { const { pipeline } = await import('@xenova/transformers'); this.model = await pipeline( 'feature-extraction', 'Xenova/all-MiniLM-L6-v2' ); } const output = await this.model(text, { pooling: 'mean', normalize: true }); return Array.from(output.data); // 384D vector } // Add entry async add(entry) { const embedding = await this.generateEmbedding( `${entry.type} ${entry.content} ${entry.context || ''}` ); const record = { id: entry.id, vector: embedding, text: entry.content, type: entry.type, content: entry.content, context: entry.context || '', confidence: entry.confidence, verified: entry.verified, tags: JSON.stringify(entry.tags), // Serialize timestamp: entry.timestamp, accessCount: entry.accessCount, lastAccessed: entry.lastAccessed || '', relatedIds: JSON.stringify(entry.relatedIds), // Serialize indexed_at: new Date().toISOString() }; await this.table.add([record]); } // Vector search async search(query, limit = 10) { const queryEmbedding = await this.generateEmbedding(query); const results = await this.table .search(queryEmbedding) .limit(limit) .execute(); // Deserialize arrays return results.map(r => ({ ...r, tags: JSON.parse(r.tags || '[]'), relatedIds: JSON.parse(r.relatedIds || '[]') })); } // Update (delete + add pattern) async update(id, updates) { const existing = await this.getById(id); const merged = { ...existing, ...updates }; await this.delete(id); await this.add(merged); } // Metadata-only update (no re-embed) async updateMetadata(id, metadata) { // Direct SQL update for efficiency (no vector change) const sql = `UPDATE knowledge SET ${Object.keys(metadata).map(k => `${k} = ?`).join(', ')} WHERE id = ?`; await this.table.execute(sql, [...Object.values(metadata), id]); } } ``` **Patterns Utilizados:** - **Singleton Pattern:** Model instance reutilizada - **Lazy Loading:** Model se carga en primer uso - **Adapter Pattern:** Abstrae LanceDB specifics --- ### 4. CLI Tool (`memory-cli.js`) **Responsabilidad:** Terminal Interface **Comandos:** ```javascript const commands = { init: async () => { // Initialize .claude-memory directory }, stats: async () => { const store = new VectorStore(process.cwd()); const stats = await store.getStats(); console.log(formatStats(stats)); }, list: async (type) => { const entries = await store.getAll(); const filtered = type ? entries.filter(e => e.type === type) : entries; console.table(filtered.map(formatEntry)); }, search: async (query) => { const results = await store.search(query); console.log(formatResults(results)); }, show: async (id) => { const entry = await store.getById(id); console.log(formatDetail(entry)); }, export: async (format = 'md') => { if (format === 'md') { const md = await store.exportMarkdown(); fs.writeFileSync('knowledge-export.md', md); } }, analyze: async () => { // Quality analysis const entries = await store.getAll(); const lowConfidence = entries.filter(e => e.confidence < 0.5); const unverified = entries.filter(e => !e.verified); const unused = entries.filter(e => e.accessCount === 0); console.log(`Low confidence: ${lowConfidence.length}`); console.log(`Unverified: ${unverified.length}`); console.log(`Unused: ${unused.length}`); } }; ``` **Features:** - Acceso directo a VectorStore (no usa MCP) - Formateo con colores ANSI - Instalable globalmente (`npm link`) --- ## Sistema de Entidades y Relaciones ### Entity Schema ```typescript interface Entity { // Identity id: string; // UUID v4 name: string; // Human-readable name entityType: string; // Tipo de entidad (17 tipos) // Content observations: string[]; // Array de observaciones // Metadata (implicit) confidence?: number; // 0-1 (stored in observations) tags?: string[]; // (stored in observations) timestamp?: string; // ISO8601 verified?: boolean; // (stored in observations) } ``` ### Relation Schema ```typescript interface Relation { from: string; // Entity name (source) to: string; // Entity name (target) relationType: string; // Tipo de relaciΓ³n } ``` ### Entity Types (17 tipos) **CategorΓ­a: Proyecto & CΓ³digo** - `project` - InformaciΓ³n del proyecto - `component` - Componente/mΓ³dulo de cΓ³digo - `dependency` - LibrerΓ­a/herramienta externa **CategorΓ­a: Aprendizaje** - `error` - Error encontrado - `solution` - SoluciΓ³n exitosa - `pattern` - PatrΓ³n reutilizable - `insight` - Aprendizaje importante - `decision` - DecisiΓ³n tΓ©cnica **CategorΓ­a: Usuario** - `user-intent` - QuΓ© quiere lograr el usuario - `user-preference` - Preferencias del usuario - `requirement` - Requisito o constraint **CategorΓ­a: Estilo** - `style-rule` - Regla de estilo de cΓ³digo - `architectural-pattern` - PatrΓ³n arquitectΓ³nico - `tool-preference` - Herramienta/library preferida **CategorΓ­a: Sesiones** - `session-snapshot` - Estado completo de sesiΓ³n - `continuation-point` - Punto de continuaciΓ³n - `work-in-progress` - Trabajo incompleto ### Relation Types (ejemplos) ``` uses, depends on, fixes, implements, supersedes, applies to, guided by, causes, prevents, enhances, similar to, contradicts, requires, validates, extends ``` ### Knowledge Graph Structure ``` β”Œβ”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β” β”‚ PROJECT β”‚ β”‚ my-web-app β”‚ β””β”€β”€β”€β”€β”€β”€β”€β”¬β”€β”€β”€β”€β”€β”€β”˜ β”‚ uses β”Œβ”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”Όβ”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β” β”‚ β”‚ β”‚ β–Ό β–Ό β–Ό β”Œβ”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β” β”Œβ”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β” β”Œβ”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β” β”‚COMPONENT β”‚ β”‚COMPONENT β”‚ β”‚DEPENDENCYβ”‚ β”‚ Auth β”‚ β”‚ API β”‚ β”‚PostgreSQLβ”‚ β””β”€β”€β”€β”€β”¬β”€β”€β”€β”€β”€β”˜ β””β”€β”€β”€β”€β”¬β”€β”€β”€β”€β”€β”˜ β””β”€β”€β”€β”€β”¬β”€β”€β”€β”€β”€β”˜ β”‚ β”‚ β”‚ β”‚ implements β”‚ applies to β”‚ used in β–Ό β–Ό β–Ό β”Œβ”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β” β”Œβ”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β” β”Œβ”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β” β”‚ DECISION β”‚ β”‚ ERROR β”‚ β”‚DECISION β”‚ β”‚ Use JWT β”‚ β”‚ CORS failβ”‚ β”‚ Use PG β”‚ β””β”€β”€β”€β”€β”¬β”€β”€β”€β”€β”€β”˜ β””β”€β”€β”€β”€β”¬β”€β”€β”€β”€β”€β”˜ β””β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”˜ β”‚ β”‚ fixed by β”‚ guided by β–Ό β–Ό β”Œβ”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β” β”Œβ”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β” β”‚ SOLUTION β”‚ β”‚USER-PREF β”‚ β”‚Enable β”‚ β”‚Secure β”‚ β”‚CORS β”‚ β””β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”˜ β””β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”˜ ``` --- ## Decisiones de DiseΓ±o ### 1. ΒΏPor quΓ© LanceDB? **Alternativas consideradas:** - Pinecone (cloud-only, caro) - Weaviate (overhead alto) - ChromaDB (mΓ‘s lento) - JSON + manual search (no escala) **Razones para LanceDB:** - βœ… Persistencia local (no depende de cloud) - βœ… Vector search nativo y rΓ‘pido - βœ… Bajo overhead (embedded database) - βœ… Escalable (hasta millones de vectores) - βœ… IntegraciΓ³n fΓ‘cil con Node.js ### 2. ΒΏPor quΓ© Transformers.js? **Alternativas:** - OpenAI Embeddings API (requiere API key, costo) - Python sentence-transformers (requiere Python) - Manual TF-IDF (menos semΓ‘ntico) **Razones para Transformers.js:** - βœ… 100% JavaScript (no Python dependency) - βœ… Funciona offline (modelo local) - βœ… Gratis y open-source - βœ… Modelo pequeΓ±o pero efectivo (90MB) - βœ… RΓ‘pido despuΓ©s de warm-up ### 3. ΒΏPor quΓ© Modelo all-MiniLM-L6-v2? **Specs:** - TamaΓ±o: ~90MB - Dimensiones: 384 - Performance: 0.68 semantic similarity (benchmark) **Trade-offs:** - βœ… PequeΓ±o y rΓ‘pido - βœ… Buena precisiΓ³n para mayorΓ­a de casos - ❌ No tan preciso como modelos grandes (768D) **ConclusiΓ³n:** Sweet spot entre tamaΓ±o/velocidad/precisiΓ³n. ### 4. ΒΏPor quΓ© 3 Capas? **Separation of Concerns:** - **Layer 1 (Interfaces):** MΓΊltiples formas de interactuar - **Layer 2 (Logic):** Business rules independientes de storage - **Layer 3 (Persistence):** FΓ‘cil cambiar implementaciΓ³n **Benefits:** - Testeable (mock layers independientemente) - Mantenible (cambios localizados) - Extensible (agregar interfaces fΓ‘cilmente) ### 5. ΒΏPor quΓ© MCP Protocol? **Alternativas:** - REST API (overhead de servidor) - GraphQL (complejidad innecesaria) - Direct function calls (no portable) **Razones para MCP:** - βœ… Standard de Anthropic para Claude integrations - βœ… Stdio transport (simple, sin networking) - βœ… Schema validation built-in - βœ… Auto-discovery de tools ### 6. ΒΏPor quΓ© No JSON Storage? **Problemas con JSON:** - ❌ No search semΓ‘ntica (solo text match) - ❌ O(n) para bΓΊsquedas - ❌ No escala bien (>10k entries) - ❌ Require cargar todo en memoria **Benefits de Vector DB:** - βœ… O(log n) bΓΊsqueda con ANN - βœ… Semantic search (encuentra conceptos similares) - βœ… Escalable sin lΓ­mite prΓ‘ctico - βœ… Lazy loading (no todo en RAM) --- ## Performance Considerations ### Latency Breakdown ``` Total search time: ~300-500ms 1. Query embedding generation: ~100-200ms (primera vez) ~10-20ms (warm model) 2. Vector search (LanceDB): ~50-100ms (10k entries) ~200-300ms (100k entries) 3. Post-processing: ~10-20ms 4. Metadata update: ~20-50ms ``` ### Memory Usage ``` Base: ~50MB (Node.js runtime) Transformers.js: ~90MB (model in memory) LanceDB: ~20MB + (vectors * 384 * 4 bytes) Example for 10k entries: 10,000 * 384 * 4 = ~15MB Total: ~175MB (10k entries) ~265MB (100k entries) ``` ### Scalability Targets | Entries | DB Size | Search Latency | Memory | |---------|---------|----------------|---------| | 1k | ~5MB | <100ms | ~165MB | | 10k | ~50MB | <200ms | ~175MB | | 100k | ~500MB | <500ms | ~265MB | | 1M | ~5GB | <1s | ~500MB | --- ## Security Considerations ### Data Privacy - βœ… **Local-first:** Todo almacenado localmente - βœ… **No cloud:** No envΓ­a datos a servicios externos - βœ… **No tracking:** No telemetrΓ­a - βœ… **User control:** Usuario controla sus datos ### Input Validation ```javascript // Zod schemas para validaciΓ³n const EntitySchema = z.object({ name: z.string().min(1).max(200), entityType: z.enum([...17 entity types]), observations: z.array(z.string()).min(1) }); // SanitizaciΓ³n function sanitize(input) { return input .trim() .replace(/[<>]/g, '') // Remove HTML tags .slice(0, 10000); // Limit length } ``` ### Error Handling ```javascript try { await vectorStore.add(entity); } catch (error) { logger.error('Failed to add entity', { error: error.message, stack: error.stack, entity: sanitizeForLog(entity) }); throw new MCPError('Entity creation failed'); } ``` --- **DocumentaciΓ³n relacionada:** - [Agentes](AGENTS.md) - [API Reference](API.md) - [ROADMAP](../ROADMAP.md)

Latest Blog Posts

MCP directory API

We provide all the information about MCP servers via our MCP API.

curl -X GET 'https://glama.ai/api/mcp/v1/servers/SuperPiTT/self-improving-memory-mcp'

If you have feedback or need assistance with the MCP directory API, please join our Discord server