@rlabs-inc/memory 0.4.4 → 0.4.5

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@rlabs-inc/memory",
3
- "version": "0.4.4",
3
+ "version": "0.4.5",
4
4
  "description": "AI Memory System - Consciousness continuity through intelligent memory curation and retrieval",
5
5
  "type": "module",
6
6
  "main": "dist/index.js",
@@ -306,6 +306,8 @@ export async function ingest(options: IngestOptions) {
306
306
  // Accumulate all memories from this session for manager
307
307
  const sessionMemories: CuratedMemory[] = []
308
308
  let sessionSummary = ''
309
+ let interactionTone = ''
310
+ let projectSnapshot: CurationResult['project_snapshot'] = undefined
309
311
 
310
312
  const spinner = new Spinner()
311
313
 
@@ -330,16 +332,36 @@ export async function ingest(options: IngestOptions) {
330
332
  totalMemories++
331
333
  }
332
334
 
333
- // Keep the most recent session summary
335
+ // Keep the most recent session summary, tone, and snapshot
334
336
  if (result.session_summary) {
335
337
  sessionSummary = result.session_summary
336
338
  }
339
+ if (result.interaction_tone) {
340
+ interactionTone = result.interaction_tone
341
+ }
342
+ if (result.project_snapshot) {
343
+ projectSnapshot = result.project_snapshot
344
+ }
337
345
  } catch (error: any) {
338
346
  failedSegments++
339
347
  spinner.stop(` ${style('red', '✗')} Segment ${segment.segmentIndex + 1}/${segment.totalSegments}: ${error.message}`)
340
348
  }
341
349
  }
342
350
 
351
+ // Store session summary and project snapshot
352
+ if (sessionSummary) {
353
+ await store.storeSessionSummary(project.folderId, session.id, sessionSummary, interactionTone)
354
+ if (options.verbose) {
355
+ console.log(` ${style('dim', `Summary stored: ${sessionSummary.slice(0, 60)}...`)}`)
356
+ }
357
+ }
358
+ if (projectSnapshot) {
359
+ await store.storeProjectSnapshot(project.folderId, session.id, projectSnapshot)
360
+ if (options.verbose) {
361
+ console.log(` ${style('dim', `Snapshot stored: phase=${projectSnapshot.current_phase || 'none'}`)}`)
362
+ }
363
+ }
364
+
343
365
  // Run manager if we have memories and manager is enabled
344
366
  if (sessionMemories.length > 0 && managerEnabled) {
345
367
  try {
@@ -350,7 +372,8 @@ export async function ingest(options: IngestOptions) {
350
372
  const curationResult: CurationResult = {
351
373
  memories: sessionMemories,
352
374
  session_summary: sessionSummary,
353
- project_snapshot: undefined,
375
+ interaction_tone: interactionTone,
376
+ project_snapshot: projectSnapshot,
354
377
  }
355
378
 
356
379
  const managerResult = await manager.manageWithSDK(
@@ -7,6 +7,7 @@ import { homedir } from 'os'
7
7
  import { join } from 'path'
8
8
  import { existsSync } from 'fs'
9
9
  import type { CuratedMemory, CurationResult, CurationTrigger, ContextType } from '../types/memory.ts'
10
+ import { logger } from '../utils/logger.ts'
10
11
 
11
12
  /**
12
13
  * Get the correct Claude CLI command path
@@ -396,13 +397,14 @@ Focus ONLY on technical, architectural, debugging, decision, workflow, and proje
396
397
  // Try to extract JSON from response (same regex as Python)
397
398
  const jsonMatch = responseJson.match(/\{[\s\S]*\}/)?.[0]
398
399
  if (!jsonMatch) {
400
+ logger.debug('parseCurationResponse: No JSON object found in response', 'curator')
399
401
  throw new Error('No JSON object found in response')
400
402
  }
401
403
 
402
404
  // Simple parse - match Python's approach
403
405
  const data = JSON.parse(jsonMatch)
404
406
 
405
- return {
407
+ const result: CurationResult = {
406
408
  session_summary: data.session_summary ?? '',
407
409
  interaction_tone: data.interaction_tone,
408
410
  project_snapshot: data.project_snapshot ? {
@@ -417,7 +419,13 @@ Focus ONLY on technical, architectural, debugging, decision, workflow, and proje
417
419
  } : undefined,
418
420
  memories: this._parseMemories(data.memories ?? []),
419
421
  }
420
- } catch {
422
+
423
+ // Log what we extracted in verbose mode
424
+ logger.debug(`Curator parsed: ${result.memories.length} memories, summary: ${result.session_summary ? 'yes' : 'no'}, snapshot: ${result.project_snapshot ? 'yes' : 'no'}`, 'curator')
425
+
426
+ return result
427
+ } catch (error: any) {
428
+ logger.debug(`parseCurationResponse error: ${error.message}`, 'curator')
421
429
  return {
422
430
  session_summary: '',
423
431
  memories: [],
@@ -550,9 +558,17 @@ This session has ended. Please curate the memories from this conversation accord
550
558
  }
551
559
 
552
560
  if (!resultText) {
561
+ logger.debug('Curator SDK: No result text returned from Agent SDK', 'curator')
553
562
  return { session_summary: '', memories: [] }
554
563
  }
555
564
 
565
+ // Log raw response in verbose mode
566
+ logger.debug(`Curator SDK raw response (${resultText.length} chars):`, 'curator')
567
+ if (logger.isVerbose()) {
568
+ const preview = resultText.length > 3000 ? resultText.slice(0, 3000) + '...[truncated]' : resultText
569
+ console.log(preview)
570
+ }
571
+
556
572
  return this.parseCurationResponse(resultText)
557
573
  }
558
574
 
@@ -704,9 +720,21 @@ This session has ended. Please curate the memories from this conversation accord
704
720
  const exitCode = await proc.exited
705
721
 
706
722
  if (exitCode !== 0) {
723
+ logger.debug(`Curator CLI exited with code ${exitCode}`, 'curator')
724
+ if (stderr) {
725
+ logger.debug(`Curator stderr: ${stderr}`, 'curator')
726
+ }
707
727
  return { session_summary: '', memories: [] }
708
728
  }
709
729
 
730
+ // Log raw response in verbose mode
731
+ logger.debug(`Curator CLI raw stdout (${stdout.length} chars):`, 'curator')
732
+ if (logger.isVerbose()) {
733
+ // Show first 2000 chars to avoid flooding console
734
+ const preview = stdout.length > 2000 ? stdout.slice(0, 2000) + '...[truncated]' : stdout
735
+ console.log(preview)
736
+ }
737
+
710
738
  // Extract JSON from CLI output
711
739
  try {
712
740
  // First, parse the CLI JSON wrapper
@@ -718,6 +746,7 @@ This session has ended. Please curate the memories from this conversation accord
718
746
  // New format: array of events, find the one with type="result"
719
747
  resultObj = cliOutput.find((item: any) => item.type === 'result')
720
748
  if (!resultObj) {
749
+ logger.debug('Curator: No result object found in CLI output array', 'curator')
721
750
  return { session_summary: '', memories: [] }
722
751
  }
723
752
  } else {
@@ -727,6 +756,7 @@ This session has ended. Please curate the memories from this conversation accord
727
756
 
728
757
  // Check for error response FIRST (like Python does)
729
758
  if (resultObj.type === 'error' || resultObj.is_error === true) {
759
+ logger.debug(`Curator: Error response from CLI: ${JSON.stringify(resultObj).slice(0, 500)}`, 'curator')
730
760
  return { session_summary: '', memories: [] }
731
761
  }
732
762
 
@@ -735,9 +765,17 @@ This session has ended. Please curate the memories from this conversation accord
735
765
  if (typeof resultObj.result === 'string') {
736
766
  aiResponse = resultObj.result
737
767
  } else {
768
+ logger.debug(`Curator: result field is not a string: ${typeof resultObj.result}`, 'curator')
738
769
  return { session_summary: '', memories: [] }
739
770
  }
740
771
 
772
+ // Log the AI response in verbose mode
773
+ logger.debug(`Curator AI response (${aiResponse.length} chars):`, 'curator')
774
+ if (logger.isVerbose()) {
775
+ const preview = aiResponse.length > 3000 ? aiResponse.slice(0, 3000) + '...[truncated]' : aiResponse
776
+ console.log(preview)
777
+ }
778
+
741
779
  // Remove markdown code blocks if present (```json ... ```)
742
780
  const codeBlockMatch = aiResponse.match(/```(?:json)?\s*([\s\S]*?)```/)
743
781
  if (codeBlockMatch) {
@@ -747,10 +785,14 @@ This session has ended. Please curate the memories from this conversation accord
747
785
  // Now find the JSON object (same regex as Python)
748
786
  const jsonMatch = aiResponse.match(/\{[\s\S]*\}/)?.[0]
749
787
  if (jsonMatch) {
788
+ logger.debug(`Curator: Found JSON object (${jsonMatch.length} chars), parsing...`, 'curator')
750
789
  return this.parseCurationResponse(jsonMatch)
790
+ } else {
791
+ logger.debug('Curator: No JSON object found in AI response', 'curator')
751
792
  }
752
- } catch {
793
+ } catch (error: any) {
753
794
  // Parse error - return empty result
795
+ logger.debug(`Curator: Parse error: ${error.message}`, 'curator')
754
796
  }
755
797
 
756
798
  return { session_summary: '', memories: [] }