diff --git a/package.json b/package.json index 4551b04..f6d39b8 100644 --- a/package.json +++ b/package.json @@ -1,6 +1,6 @@ { "name": "@ztimson/ai-utils", - "version": "1.2.4", + "version": "1.2.5", "description": "AI Utility library", "author": "Zak Timson", "license": "MIT", diff --git a/src/llm.ts b/src/llm.ts index 2d10168..73c4e86 100644 --- a/src/llm.ts +++ b/src/llm.ts @@ -229,8 +229,8 @@ ${r.content} * Digest full conversation history into memory documents. * Call on session end to persist the conversation. */ - async updateMemory(history: LLMMessage[], memories: Memory[] | MemoryCache, options: LLMRequest = {}): Promise { - await this.memoryManager.memorize(history, memories, {model: this.defaultModel, ...options}); + async updateMemory(history: LLMMessage[], memories: Memory[] | MemoryCache, options: LLMRequest = {}): Promise { + return this.memoryManager.memorize(history, memories, {model: this.defaultModel, ...options}); } /** diff --git a/src/memory.ts b/src/memory.ts index 04842f1..9e2fc5a 100644 --- a/src/memory.ts +++ b/src/memory.ts @@ -355,68 +355,56 @@ ${conversation}`, return ordered.map(n => mem.find(m => m.name === n)!).filter(Boolean); } - async memorize(history: LLMMessage[], memories: Memory[] | MemoryCache, options: LLMRequest): Promise { + async memorize(history: LLMMessage[], memories: Memory[] | MemoryCache, options: LLMRequest): Promise { const conversation = history .filter(h => h.role === 'user' || h.role === 'assistant') .map(h => `[${h.role}]: ${h.content}`).join('\n\n').trim(); - - if (!conversation) return; - - const trackingId = `${Date.now()}_${Math.random()}`; + if(!conversation) return []; // Create and insert temp memory immediately + const trackingId = `${Date.now()}_${Math.random()}`; const tempMemory = await this.createTempMemory(conversation); const mem = memories instanceof MemoryCache ? memories.memories : memories; mem.push(tempMemory); - - if (memories instanceof MemoryCache) { - memories.rebuild(); - } - + if (memories instanceof MemoryCache) memories.rebuild(); this.pendingMemorizations.set(trackingId, { memories, tempMemoryName: tempMemory.name, timestamp: Date.now(), }); - this._memorizeBackground(conversation, memories, options, trackingId) - .catch(err => { - console.error('[memorize] Background memorization failed:', err); - }) - .finally(() => { - // Remove temp memory from the exact same memory array/cache - const pending = this.pendingMemorizations.get(trackingId); - if (pending) { - const cleanMem = pending.memories instanceof MemoryCache - ? pending.memories.memories - : pending.memories; - const idx = cleanMem.findIndex(m => m.name === pending.tempMemoryName); - if (idx !== -1) { - cleanMem.splice(idx, 1); - console.log(`[memorize] Removed temp memory: ${pending.tempMemoryName}`); - } - if (pending.memories instanceof MemoryCache) { - pending.memories.rebuild(); - } + try { + await this._memorizeBackground(conversation, memories, options); + // Return the final memories (excluding temp ones) + const finalMem = memories instanceof MemoryCache ? memories.memories : memories; + return finalMem.filter(m => !m.name.startsWith('_temp_')); + } catch (err) { + throw err; + } finally { + // Remove temp memory from the exact same memory array/cache + const pending = this.pendingMemorizations.get(trackingId); + if (pending) { + const cleanMem = pending.memories instanceof MemoryCache + ? pending.memories.memories + : pending.memories; + const idx = cleanMem.findIndex(m => m.name === pending.tempMemoryName); + if (idx !== -1) { + cleanMem.splice(idx, 1); } - this.pendingMemorizations.delete(trackingId); - }); + if (pending.memories instanceof MemoryCache) { + pending.memories.rebuild(); + } + } + this.pendingMemorizations.delete(trackingId); + } } - private async _memorizeBackground(conversation: string, memories: Memory[] | MemoryCache, options: LLMRequest, trackingId: string): Promise { + private async _memorizeBackground(conversation: string, memories: Memory[] | MemoryCache, options: LLMRequest): Promise { const mem = memories instanceof MemoryCache ? memories.memories : memories; const monday = getWeekMonday(); const sunday = getWeekSunday(monday); - const weekKey = monday; - - console.log('[memorize] Starting fact extraction...'); - const buckets = await this.factAgent(conversation, mem, options, weekKey); - console.log(`[memorize] Extracted ${buckets.length} buckets:`, buckets); - - if (!buckets.length) { - console.log('[memorize] No facts extracted, exiting'); - return; - } + const buckets = await this.factAgent(conversation, mem, options, monday); + if(!buckets.length) return; const runDocAgent = (node: Memory, bucket: FactBucket, embedding?: number[], week?: {monday: string, sunday: string}) => { if (memories instanceof MemoryCache) { @@ -443,11 +431,8 @@ ${conversation}`, await runDocAgent(node, bucket, embedding, week); })); - if (memories instanceof MemoryCache) { + if(memories instanceof MemoryCache) memories.rebuild(); - } - - console.log('[memorize] Completed successfully'); } private buildHeader(node: Memory, week?: {monday: string, sunday: string}, links: string[] = [], backlinks: string[] = []): string { @@ -587,9 +572,6 @@ ${node.content || '(empty — this is a new document)'} private async factAgent(conversation: string, memories: Memory[], options: LLMRequest, weekKey: string): Promise { const buckets: FactBucket[] = []; - - console.log('[factAgent] Starting extraction...'); - await this.llm.ask(conversation, { model: options.model, temperature: 0.2, @@ -618,7 +600,6 @@ ${this.listNodes(memories).map(n => `- ${n.name}: ${n.description}`).join('\n') create_new: {type: 'boolean', description: 'True if this is a new node that doesn\'t exist yet', required: true}, }, fn: (args: any) => { - console.log('[factAgent] Tool called with:', args); const subject = args.destination.trim().toLowerCase() === 'journal' ? `Journal/${weekKey}` : args.destination; @@ -631,8 +612,6 @@ ${this.listNodes(memories).map(n => `- ${n.name}: ${n.description}`).join('\n') }, }], }); - - console.log(`[factAgent] Extracted ${buckets.length} buckets:`, buckets); return buckets; } }