Class: Llmemory::LongTerm::Procedural::Memory
- Inherits:
-
Object
- Object
- Llmemory::LongTerm::Procedural::Memory
- Includes:
- MemoryModule
- Defined in:
- lib/llmemory/long_term/procedural/memory.rb
Overview
Procedural long-term memory: a Voyager-style skill library. Agents register reusable skills (prompts, templates, code), retrieve them by relevance to the current task, and report outcomes so proven skills are preferred over unproven ones.
The success rate of each skill is surfaced as ‘importance`, so the retrieval Engine ranks battle-tested skills higher (P3). Semantic (embedding) retrieval is opt-in via `config.procedural_vector_enabled` or by injecting a `vector_store:`; when off, search is keyword-only.
Instance Attribute Summary collapse
-
#storage ⇒ Object
readonly
Returns the value of attribute storage.
-
#user_id ⇒ Object
readonly
Returns the value of attribute user_id.
Instance Method Summary collapse
- #count ⇒ Object
- #find_skill(query) ⇒ Object
- #forget(ids:, reason: nil) ⇒ Object
- #get_skill(id) ⇒ Object
-
#initialize(user_id:, storage: nil, vector_store: nil) ⇒ Memory
constructor
A new instance of Memory.
- #list(user_id: nil, limit: nil) ⇒ Object
-
#register_skill(name:, body:, description: nil, kind: Skill::DEFAULT_KIND, version: nil) ⇒ Object
Registers a skill.
-
#report_outcome(skill_id, success:) ⇒ Object
Records that applying a skill succeeded or failed.
-
#search_candidates(query, user_id: nil, top_k: 20) ⇒ Object
Retrieval Engine integration: skills ranked by relevance, recency and proven utility (success rate exposed as importance).
- #skills(limit: nil) ⇒ Object
- #stats(user_id: nil) ⇒ Object
-
#write(name:, body:, description: nil, kind: Skill::DEFAULT_KIND, version: nil, **_meta) ⇒ Object
— MemoryModule uniform interface —.
Methods included from MemoryModule
Constructor Details
#initialize(user_id:, storage: nil, vector_store: nil) ⇒ Memory
Returns a new instance of Memory.
25 26 27 28 29 30 |
# File 'lib/llmemory/long_term/procedural/memory.rb', line 25 def initialize(user_id:, storage: nil, vector_store: nil) @user_id = user_id @storage = storage || Storages.build @vector_store = vector_store @vector_explicit = !vector_store.nil? end |
Instance Attribute Details
#storage ⇒ Object (readonly)
Returns the value of attribute storage.
23 24 25 |
# File 'lib/llmemory/long_term/procedural/memory.rb', line 23 def storage @storage end |
#user_id ⇒ Object (readonly)
Returns the value of attribute user_id.
23 24 25 |
# File 'lib/llmemory/long_term/procedural/memory.rb', line 23 def user_id @user_id end |
Instance Method Details
#count ⇒ Object
59 60 61 |
# File 'lib/llmemory/long_term/procedural/memory.rb', line 59 def count @storage.count_skills(@user_id) end |
#find_skill(query) ⇒ Object
45 46 47 48 |
# File 'lib/llmemory/long_term/procedural/memory.rb', line 45 def find_skill(query) raw = @storage.search_skills(@user_id, query).first raw && Skill.from_h(raw) end |
#forget(ids:, reason: nil) ⇒ Object
98 99 100 101 102 103 104 105 |
# File 'lib/llmemory/long_term/procedural/memory.rb', line 98 def forget(ids:, reason: nil) requested = Array(ids).map(&:to_s) existing = @storage.list_skills(@user_id).map { |s| (s[:id] || s["id"]).to_s } removed = requested & existing @storage.delete_skills(@user_id, removed) forget_log.record(@user_id, memory_type: "procedural", ids: removed, reason: reason) removed.size end |
#get_skill(id) ⇒ Object
50 51 52 53 |
# File 'lib/llmemory/long_term/procedural/memory.rb', line 50 def get_skill(id) raw = @storage.get_skill(@user_id, id) raw && Skill.from_h(raw) end |
#list(user_id: nil, limit: nil) ⇒ Object
90 91 92 |
# File 'lib/llmemory/long_term/procedural/memory.rb', line 90 def list(user_id: nil, limit: nil) skills(limit: limit) end |
#register_skill(name:, body:, description: nil, kind: Skill::DEFAULT_KIND, version: nil) ⇒ Object
Registers a skill. If ‘version` is omitted and a skill with the same name exists, the version auto-increments (skill evolution).
34 35 36 37 38 39 40 41 42 43 |
# File 'lib/llmemory/long_term/procedural/memory.rb', line 34 def register_skill(name:, body:, description: nil, kind: Skill::DEFAULT_KIND, version: nil) version ||= next_version_for(name) skill = Skill.new( id: nil, user_id: @user_id, name: name, body: body, description: description, kind: kind, version: version ) id = @storage.save_skill(@user_id, skill.to_h) index_vector(id, skill.searchable_text) id end |
#report_outcome(skill_id, success:) ⇒ Object
Records that applying a skill succeeded or failed. Feeds retrieval ranking and adaptive retrieval (P8). Returns the updated Skill.
65 66 67 68 |
# File 'lib/llmemory/long_term/procedural/memory.rb', line 65 def report_outcome(skill_id, success:) raw = @storage.record_outcome(@user_id, skill_id, success: success) raw && Skill.from_h(raw) end |
#search_candidates(query, user_id: nil, top_k: 20) ⇒ Object
Retrieval Engine integration: skills ranked by relevance, recency and proven utility (success rate exposed as importance). Hybrid (vector + keyword) when a vector store is active; otherwise keyword-only.
73 74 75 76 77 78 79 80 81 82 |
# File 'lib/llmemory/long_term/procedural/memory.rb', line 73 def search_candidates(query, user_id: nil, top_k: 20) uid = user_id || @user_id return [] unless uid == @user_id keyword = @storage.search_skills(uid, query).first(top_k).map { |raw| candidate_for(raw, 1.0) } vs = vector_store return keyword unless vs merge_candidates(vector_candidates(query, top_k, vs), keyword, top_k) end |
#skills(limit: nil) ⇒ Object
55 56 57 |
# File 'lib/llmemory/long_term/procedural/memory.rb', line 55 def skills(limit: nil) @storage.list_skills(@user_id, limit: limit).map { |s| Skill.from_h(s) } end |
#stats(user_id: nil) ⇒ Object
94 95 96 |
# File 'lib/llmemory/long_term/procedural/memory.rb', line 94 def stats(user_id: nil) { skills: count } end |
#write(name:, body:, description: nil, kind: Skill::DEFAULT_KIND, version: nil, **_meta) ⇒ Object
— MemoryModule uniform interface —
86 87 88 |
# File 'lib/llmemory/long_term/procedural/memory.rb', line 86 def write(name:, body:, description: nil, kind: Skill::DEFAULT_KIND, version: nil, **) register_skill(name: name, body: body, description: description, kind: kind, version: version) end |