claude_memory 0.7.1 → 0.9.0
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.
- checksums.yaml +4 -4
- data/.claude/memory.sqlite3 +0 -0
- data/.claude/rules/claude_memory.generated.md +32 -2
- data/.claude/settings.json +65 -15
- data/.claude/settings.local.json +5 -2
- data/.claude/skills/improve/SKILL.md +113 -25
- data/.claude/skills/upgrade-dependencies/SKILL.md +154 -0
- data/.claude-plugin/commands/distill-transcripts.md +98 -0
- data/.claude-plugin/commands/memory-recall.md +67 -0
- data/.claude-plugin/marketplace.json +2 -2
- data/.claude-plugin/plugin.json +3 -3
- data/.claude-plugin/scripts/hook-runner.sh +14 -0
- data/.claude-plugin/scripts/serve-mcp.sh +14 -0
- data/.ruby-version +1 -1
- data/CHANGELOG.md +90 -1
- data/CLAUDE.md +56 -18
- data/README.md +35 -0
- data/db/migrations/013_add_mcp_tool_calls.rb +26 -0
- data/db/migrations/014_canonicalize_predicates.rb +30 -0
- data/docs/improvements.md +74 -74
- data/docs/influence/claude-mem.md +1 -0
- data/docs/influence/claude-supermemory.md +1 -0
- data/docs/influence/episodic-memory.md +1 -0
- data/docs/influence/grepai.md +1 -0
- data/docs/influence/kbs.md +1 -0
- data/docs/influence/lossless-claw.md +1 -0
- data/docs/influence/qmd.md +1 -0
- data/docs/quality_review.md +119 -224
- data/hooks/hooks.json +39 -7
- data/lib/claude_memory/commands/checks/distill_check.rb +61 -0
- data/lib/claude_memory/commands/checks/hooks_check.rb +2 -2
- data/lib/claude_memory/commands/checks/vec_check.rb +2 -1
- data/lib/claude_memory/commands/completion_command.rb +149 -0
- data/lib/claude_memory/commands/doctor_command.rb +2 -0
- data/lib/claude_memory/commands/embeddings_command.rb +198 -0
- data/lib/claude_memory/commands/help_command.rb +12 -1
- data/lib/claude_memory/commands/hook_command.rb +2 -1
- data/lib/claude_memory/commands/index_command.rb +85 -78
- data/lib/claude_memory/commands/initializers/database_ensurer.rb +16 -0
- data/lib/claude_memory/commands/initializers/global_initializer.rb +2 -1
- data/lib/claude_memory/commands/initializers/hooks_configurator.rb +55 -11
- data/lib/claude_memory/commands/initializers/project_initializer.rb +2 -1
- data/lib/claude_memory/commands/install_skill_command.rb +78 -0
- data/lib/claude_memory/commands/registry.rb +47 -32
- data/lib/claude_memory/commands/reject_command.rb +62 -0
- data/lib/claude_memory/commands/restore_command.rb +77 -0
- data/lib/claude_memory/commands/skills/distill-transcripts.md +102 -0
- data/lib/claude_memory/commands/skills/memory-recall.md +67 -0
- data/lib/claude_memory/commands/stats_command.rb +98 -2
- data/lib/claude_memory/configuration.rb +14 -1
- data/lib/claude_memory/core/fact_ranker.rb +2 -2
- data/lib/claude_memory/core/rr_fusion.rb +23 -6
- data/lib/claude_memory/core/snippet_extractor.rb +7 -3
- data/lib/claude_memory/core/text_builder.rb +11 -0
- data/lib/claude_memory/distill/json_schema.md +8 -4
- data/lib/claude_memory/distill/null_distiller.rb +2 -0
- data/lib/claude_memory/domain/entity.rb +13 -1
- data/lib/claude_memory/domain/fact.rb +26 -2
- data/lib/claude_memory/domain/provenance.rb +0 -1
- data/lib/claude_memory/embeddings/api_adapter.rb +97 -0
- data/lib/claude_memory/embeddings/dimension_check.rb +23 -0
- data/lib/claude_memory/embeddings/fastembed_adapter.rb +46 -12
- data/lib/claude_memory/embeddings/generator.rb +4 -0
- data/lib/claude_memory/embeddings/inspector.rb +91 -0
- data/lib/claude_memory/embeddings/model_registry.rb +210 -0
- data/lib/claude_memory/embeddings/resolver.rb +44 -0
- data/lib/claude_memory/hook/context_injector.rb +58 -2
- data/lib/claude_memory/hook/distillation_runner.rb +46 -0
- data/lib/claude_memory/hook/handler.rb +11 -2
- data/lib/claude_memory/index/vector_index.rb +15 -2
- data/lib/claude_memory/infrastructure/schema_validator.rb +3 -3
- data/lib/claude_memory/ingest/ingester.rb +17 -0
- data/lib/claude_memory/mcp/handlers/context_handlers.rb +38 -0
- data/lib/claude_memory/mcp/handlers/management_handlers.rb +169 -0
- data/lib/claude_memory/mcp/handlers/query_handlers.rb +115 -0
- data/lib/claude_memory/mcp/handlers/setup_handlers.rb +211 -0
- data/lib/claude_memory/mcp/handlers/shortcut_handlers.rb +37 -0
- data/lib/claude_memory/mcp/handlers/stats_handlers.rb +205 -0
- data/lib/claude_memory/mcp/instructions_builder.rb +19 -1
- data/lib/claude_memory/mcp/query_guide.rb +10 -0
- data/lib/claude_memory/mcp/response_formatter.rb +1 -0
- data/lib/claude_memory/mcp/server.rb +22 -1
- data/lib/claude_memory/mcp/telemetry.rb +86 -0
- data/lib/claude_memory/mcp/text_summary.rb +26 -0
- data/lib/claude_memory/mcp/tool_definitions.rb +116 -4
- data/lib/claude_memory/mcp/tool_helpers.rb +43 -0
- data/lib/claude_memory/mcp/tools.rb +50 -679
- data/lib/claude_memory/publish.rb +40 -5
- data/lib/claude_memory/recall/dual_engine.rb +105 -0
- data/lib/claude_memory/recall/legacy_engine.rb +138 -0
- data/lib/claude_memory/recall/query_core.rb +371 -0
- data/lib/claude_memory/recall.rb +121 -673
- data/lib/claude_memory/resolve/predicate_policy.rb +63 -3
- data/lib/claude_memory/resolve/resolver.rb +43 -0
- data/lib/claude_memory/shortcuts.rb +4 -4
- data/lib/claude_memory/store/retry_handler.rb +61 -0
- data/lib/claude_memory/store/schema_manager.rb +68 -0
- data/lib/claude_memory/store/sqlite_store.rb +334 -201
- data/lib/claude_memory/store/store_manager.rb +50 -1
- data/lib/claude_memory/sweep/maintenance.rb +115 -1
- data/lib/claude_memory/sweep/sweeper.rb +3 -0
- data/lib/claude_memory/templates/hooks.example.json +26 -7
- data/lib/claude_memory/version.rb +1 -1
- data/lib/claude_memory.rb +16 -0
- metadata +48 -8
- data/.claude/memory.sqlite3-shm +0 -0
- data/.claude/memory.sqlite3-wal +0 -0
|
@@ -4,9 +4,25 @@ require "fileutils"
|
|
|
4
4
|
|
|
5
5
|
module ClaudeMemory
|
|
6
6
|
module Store
|
|
7
|
+
# Dual-database connection manager for global and project stores.
|
|
8
|
+
# Lazily opens SQLiteStore connections to the global database
|
|
9
|
+
# (~/.claude/memory.sqlite3) and the project database
|
|
10
|
+
# (.claude/memory.sqlite3 under the project root). Commands query
|
|
11
|
+
# both databases by default, with project facts taking precedence.
|
|
7
12
|
class StoreManager
|
|
8
|
-
|
|
13
|
+
# @return [SQLiteStore, nil] global store (nil until {#ensure_global!} is called)
|
|
14
|
+
attr_reader :global_store
|
|
9
15
|
|
|
16
|
+
# @return [SQLiteStore, nil] project store (nil until {#ensure_project!} is called)
|
|
17
|
+
attr_reader :project_store
|
|
18
|
+
|
|
19
|
+
# @return [String] project directory path
|
|
20
|
+
attr_reader :project_path
|
|
21
|
+
|
|
22
|
+
# @param global_db_path [String, nil] override path to the global database
|
|
23
|
+
# @param project_db_path [String, nil] override path to the project database
|
|
24
|
+
# @param project_path [String, nil] project directory (defaults to Configuration)
|
|
25
|
+
# @param env [Hash] environment variable hash (default: ENV)
|
|
10
26
|
def initialize(global_db_path: nil, project_db_path: nil, project_path: nil, env: ENV)
|
|
11
27
|
config = Configuration.new(env)
|
|
12
28
|
@project_path = project_path || config.project_dir
|
|
@@ -17,14 +33,23 @@ module ClaudeMemory
|
|
|
17
33
|
@project_store = nil
|
|
18
34
|
end
|
|
19
35
|
|
|
36
|
+
# Default global database path from Configuration.
|
|
37
|
+
# @param env [Hash] environment variable hash
|
|
38
|
+
# @return [String]
|
|
20
39
|
def self.default_global_db_path(env = ENV)
|
|
21
40
|
Configuration.new(env).global_db_path
|
|
22
41
|
end
|
|
23
42
|
|
|
43
|
+
# Default project database path for a given project directory.
|
|
44
|
+
# @param project_path [String] project directory (default: current working directory)
|
|
45
|
+
# @return [String]
|
|
24
46
|
def self.default_project_db_path(project_path = Dir.pwd)
|
|
25
47
|
Configuration.new.project_db_path(project_path)
|
|
26
48
|
end
|
|
27
49
|
|
|
50
|
+
# Open the global store, creating the directory and database if needed.
|
|
51
|
+
# No-op if already open.
|
|
52
|
+
# @return [SQLiteStore] the global store
|
|
28
53
|
def ensure_global!
|
|
29
54
|
return @global_store if @global_store
|
|
30
55
|
|
|
@@ -32,6 +57,9 @@ module ClaudeMemory
|
|
|
32
57
|
@global_store = SQLiteStore.new(@global_db_path)
|
|
33
58
|
end
|
|
34
59
|
|
|
60
|
+
# Open the project store, creating the directory and database if needed.
|
|
61
|
+
# No-op if already open.
|
|
62
|
+
# @return [SQLiteStore] the project store
|
|
35
63
|
def ensure_project!
|
|
36
64
|
return @project_store if @project_store
|
|
37
65
|
|
|
@@ -39,23 +67,33 @@ module ClaudeMemory
|
|
|
39
67
|
@project_store = SQLiteStore.new(@project_db_path)
|
|
40
68
|
end
|
|
41
69
|
|
|
70
|
+
# Open both global and project stores.
|
|
71
|
+
# @return [void]
|
|
42
72
|
def ensure_both!
|
|
43
73
|
ensure_global!
|
|
44
74
|
ensure_project!
|
|
45
75
|
end
|
|
46
76
|
|
|
77
|
+
# @return [String] filesystem path to the global database
|
|
47
78
|
attr_reader :global_db_path
|
|
48
79
|
|
|
80
|
+
# @return [String] filesystem path to the project database
|
|
49
81
|
attr_reader :project_db_path
|
|
50
82
|
|
|
83
|
+
# Check whether the global database file exists on disk.
|
|
84
|
+
# @return [Boolean]
|
|
51
85
|
def global_exists?
|
|
52
86
|
File.exist?(@global_db_path)
|
|
53
87
|
end
|
|
54
88
|
|
|
89
|
+
# Check whether the project database file exists on disk.
|
|
90
|
+
# @return [Boolean]
|
|
55
91
|
def project_exists?
|
|
56
92
|
File.exist?(@project_db_path)
|
|
57
93
|
end
|
|
58
94
|
|
|
95
|
+
# Close both database connections and reset store references.
|
|
96
|
+
# @return [void]
|
|
59
97
|
def close
|
|
60
98
|
@global_store&.close
|
|
61
99
|
@project_store&.close
|
|
@@ -63,6 +101,10 @@ module ClaudeMemory
|
|
|
63
101
|
@project_store = nil
|
|
64
102
|
end
|
|
65
103
|
|
|
104
|
+
# Return the appropriate store for a given scope string.
|
|
105
|
+
# @param scope [String] "global" or "project"
|
|
106
|
+
# @return [SQLiteStore]
|
|
107
|
+
# @raise [ArgumentError] if scope is not "global" or "project"
|
|
66
108
|
def store_for_scope(scope)
|
|
67
109
|
case scope
|
|
68
110
|
when "global"
|
|
@@ -76,6 +118,13 @@ module ClaudeMemory
|
|
|
76
118
|
end
|
|
77
119
|
end
|
|
78
120
|
|
|
121
|
+
# Copy a project-scoped fact (with its entities and provenance) into the
|
|
122
|
+
# global store, making it available across all projects. Runs the global
|
|
123
|
+
# writes in a single transaction for atomicity.
|
|
124
|
+
#
|
|
125
|
+
# @param fact_id [Integer] project fact row id to promote
|
|
126
|
+
# @return [Integer, nil] the new global fact id, or nil if the fact/subject
|
|
127
|
+
# was not found in the project store
|
|
79
128
|
def promote_fact(fact_id)
|
|
80
129
|
ensure_both!
|
|
81
130
|
|
|
@@ -8,10 +8,16 @@ module ClaudeMemory
|
|
|
8
8
|
#
|
|
9
9
|
# Source: QMD v2.0.1 Maintenance class pattern
|
|
10
10
|
class Maintenance
|
|
11
|
+
# Short / noise tokens dropped before Jaccard comparison.
|
|
12
|
+
# Intentionally minimal — we want conservative token extraction that
|
|
13
|
+
# still treats "Rails 8.0" and "Rails 8.1" as overlapping.
|
|
14
|
+
RESTORE_STOPWORDS = %w[for the and with via of in on to by is are].to_set.freeze
|
|
15
|
+
RESTORE_JACCARD_THRESHOLD = 0.5
|
|
11
16
|
DEFAULT_CONFIG = {
|
|
12
17
|
proposed_fact_ttl_days: 14,
|
|
13
18
|
disputed_fact_ttl_days: 30,
|
|
14
|
-
content_retention_days: 30
|
|
19
|
+
content_retention_days: 30,
|
|
20
|
+
mcp_tool_call_retention_days: 90
|
|
15
21
|
}.freeze
|
|
16
22
|
|
|
17
23
|
attr_reader :store
|
|
@@ -96,6 +102,85 @@ module ClaudeMemory
|
|
|
96
102
|
0
|
|
97
103
|
end
|
|
98
104
|
|
|
105
|
+
# Restore superseded facts in a (subject, predicate) slot that were
|
|
106
|
+
# only superseded because of an obsolete single-value classification.
|
|
107
|
+
# Uses Jaccard-based token overlap to distinguish bug-superseded facts
|
|
108
|
+
# (token-disjoint siblings) from legitimate corrections (overlapping
|
|
109
|
+
# siblings).
|
|
110
|
+
#
|
|
111
|
+
# Refuses to run on predicates still classified as single-value — they
|
|
112
|
+
# should stay superseded by design.
|
|
113
|
+
#
|
|
114
|
+
# Never touches status: "rejected" facts (explicit user decisions).
|
|
115
|
+
#
|
|
116
|
+
# @return [Hash] {inspected, restored, skipped_ambiguous, skipped_rejected, decisions}
|
|
117
|
+
def restore_multi_value_supersessions(predicate:, dry_run: false)
|
|
118
|
+
if ClaudeMemory::Resolve::PredicatePolicy.single?(predicate)
|
|
119
|
+
raise ArgumentError, "Predicate '#{predicate}' is still classified single-value; refusing to restore"
|
|
120
|
+
end
|
|
121
|
+
|
|
122
|
+
result = {inspected: 0, restored: 0, skipped_ambiguous: 0, skipped_rejected: 0, decisions: []}
|
|
123
|
+
|
|
124
|
+
rows_by_subject = @store.facts
|
|
125
|
+
.where(predicate: predicate)
|
|
126
|
+
.exclude(status: "rejected")
|
|
127
|
+
.select(:id, :subject_entity_id, :object_literal, :status)
|
|
128
|
+
.all
|
|
129
|
+
.group_by { |r| r[:subject_entity_id] }
|
|
130
|
+
|
|
131
|
+
rejected_by_subject = @store.facts
|
|
132
|
+
.where(predicate: predicate, status: "rejected")
|
|
133
|
+
.select(:id, :subject_entity_id, :object_literal)
|
|
134
|
+
.all
|
|
135
|
+
.group_by { |r| r[:subject_entity_id] }
|
|
136
|
+
|
|
137
|
+
@store.db.transaction do
|
|
138
|
+
rows_by_subject.each do |subject_id, rows|
|
|
139
|
+
rejected_rows = rejected_by_subject[subject_id] || []
|
|
140
|
+
siblings = rows + rejected_rows
|
|
141
|
+
|
|
142
|
+
rows.each do |candidate|
|
|
143
|
+
next unless candidate[:status] == "superseded"
|
|
144
|
+
result[:inspected] += 1
|
|
145
|
+
|
|
146
|
+
candidate_tokens = restore_tokenize(candidate[:object_literal])
|
|
147
|
+
ambiguous_against = find_overlapping_siblings(candidate, siblings, candidate_tokens)
|
|
148
|
+
|
|
149
|
+
if ambiguous_against.empty?
|
|
150
|
+
result[:restored] += 1
|
|
151
|
+
result[:decisions] << {
|
|
152
|
+
subject_entity_id: subject_id,
|
|
153
|
+
fact_id: candidate[:id],
|
|
154
|
+
object: candidate[:object_literal],
|
|
155
|
+
action: :restore
|
|
156
|
+
}
|
|
157
|
+
restore_fact!(candidate[:id]) unless dry_run
|
|
158
|
+
else
|
|
159
|
+
result[:skipped_ambiguous] += 1
|
|
160
|
+
result[:decisions] << {
|
|
161
|
+
subject_entity_id: subject_id,
|
|
162
|
+
fact_id: candidate[:id],
|
|
163
|
+
object: candidate[:object_literal],
|
|
164
|
+
action: :skip_ambiguous,
|
|
165
|
+
overlaps_with: ambiguous_against.map { |s| s[:object_literal] }
|
|
166
|
+
}
|
|
167
|
+
end
|
|
168
|
+
end
|
|
169
|
+
end
|
|
170
|
+
end
|
|
171
|
+
|
|
172
|
+
result
|
|
173
|
+
end
|
|
174
|
+
|
|
175
|
+
# Delete MCP tool-call telemetry rows older than retention window.
|
|
176
|
+
# Returns: Integer count of deleted rows (0 if table missing).
|
|
177
|
+
def prune_old_mcp_tool_calls
|
|
178
|
+
return 0 unless @store.db.table_exists?(:mcp_tool_calls)
|
|
179
|
+
|
|
180
|
+
cutoff = cutoff_time(@config[:mcp_tool_call_retention_days])
|
|
181
|
+
@store.mcp_tool_calls.where { called_at < cutoff }.delete
|
|
182
|
+
end
|
|
183
|
+
|
|
99
184
|
# Checkpoint the SQLite WAL file for compaction.
|
|
100
185
|
# Returns: true
|
|
101
186
|
def checkpoint_wal
|
|
@@ -112,6 +197,35 @@ module ClaudeMemory
|
|
|
112
197
|
|
|
113
198
|
private
|
|
114
199
|
|
|
200
|
+
def restore_tokenize(text)
|
|
201
|
+
return Set.new if text.nil?
|
|
202
|
+
text.downcase
|
|
203
|
+
.scan(/[a-z0-9]+/)
|
|
204
|
+
.reject { |t| t.length <= 2 || RESTORE_STOPWORDS.include?(t) }
|
|
205
|
+
.to_set
|
|
206
|
+
end
|
|
207
|
+
|
|
208
|
+
def restore_jaccard(a, b)
|
|
209
|
+
return 0.0 if a.empty? && b.empty?
|
|
210
|
+
intersection = (a & b).size
|
|
211
|
+
union = (a | b).size
|
|
212
|
+
return 0.0 if union.zero?
|
|
213
|
+
intersection.to_f / union
|
|
214
|
+
end
|
|
215
|
+
|
|
216
|
+
def find_overlapping_siblings(candidate, siblings, candidate_tokens)
|
|
217
|
+
siblings.select do |other|
|
|
218
|
+
next false if other[:id] == candidate[:id]
|
|
219
|
+
other_tokens = restore_tokenize(other[:object_literal])
|
|
220
|
+
restore_jaccard(candidate_tokens, other_tokens) >= RESTORE_JACCARD_THRESHOLD
|
|
221
|
+
end
|
|
222
|
+
end
|
|
223
|
+
|
|
224
|
+
def restore_fact!(fact_id)
|
|
225
|
+
@store.facts.where(id: fact_id).update(status: "active", valid_to: nil)
|
|
226
|
+
@store.fact_links.where(to_fact_id: fact_id, link_type: "supersedes").delete
|
|
227
|
+
end
|
|
228
|
+
|
|
115
229
|
def cutoff_time(days)
|
|
116
230
|
(Time.now - days * 86400).utc.iso8601
|
|
117
231
|
end
|
|
@@ -7,6 +7,7 @@ module ClaudeMemory
|
|
|
7
7
|
proposed_fact_ttl_days: 14,
|
|
8
8
|
disputed_fact_ttl_days: 30,
|
|
9
9
|
content_retention_days: 30,
|
|
10
|
+
mcp_tool_call_retention_days: 90,
|
|
10
11
|
default_budget_seconds: 5
|
|
11
12
|
}.freeze
|
|
12
13
|
|
|
@@ -29,6 +30,7 @@ module ClaudeMemory
|
|
|
29
30
|
disputed_facts_expired: 0,
|
|
30
31
|
orphaned_provenance_deleted: 0,
|
|
31
32
|
old_content_pruned: 0,
|
|
33
|
+
mcp_tool_calls_pruned: 0,
|
|
32
34
|
escalation_level: :normal
|
|
33
35
|
}
|
|
34
36
|
|
|
@@ -38,6 +40,7 @@ module ClaudeMemory
|
|
|
38
40
|
run_if_within_budget { @stats[:disputed_facts_expired] = maintenance.expire_disputed_facts }
|
|
39
41
|
run_if_within_budget { @stats[:orphaned_provenance_deleted] = maintenance.prune_orphaned_provenance }
|
|
40
42
|
run_if_within_budget { @stats[:old_content_pruned] = maintenance.prune_old_content }
|
|
43
|
+
run_if_within_budget { @stats[:mcp_tool_calls_pruned] = maintenance.prune_old_mcp_tool_calls }
|
|
41
44
|
run_if_within_budget { @stats[:vec_backfilled] = maintenance.backfill_vec_index }
|
|
42
45
|
run_if_within_budget { @stats[:vec_cleaned] = maintenance.cleanup_vec_expired }
|
|
43
46
|
run_if_within_budget { @stats[:wal_checkpointed] = maintenance.checkpoint_wal }
|
|
@@ -6,7 +6,20 @@
|
|
|
6
6
|
{
|
|
7
7
|
"type": "command",
|
|
8
8
|
"command": "claude-memory hook ingest",
|
|
9
|
-
"timeout": 10
|
|
9
|
+
"timeout": 10,
|
|
10
|
+
"statusMessage": "Saving memory..."
|
|
11
|
+
}
|
|
12
|
+
]
|
|
13
|
+
}
|
|
14
|
+
],
|
|
15
|
+
"StopFailure": [
|
|
16
|
+
{
|
|
17
|
+
"hooks": [
|
|
18
|
+
{
|
|
19
|
+
"type": "command",
|
|
20
|
+
"command": "claude-memory hook ingest",
|
|
21
|
+
"timeout": 10,
|
|
22
|
+
"statusMessage": "Saving memory..."
|
|
10
23
|
}
|
|
11
24
|
]
|
|
12
25
|
}
|
|
@@ -17,7 +30,8 @@
|
|
|
17
30
|
{
|
|
18
31
|
"type": "command",
|
|
19
32
|
"command": "claude-memory hook ingest",
|
|
20
|
-
"timeout": 10
|
|
33
|
+
"timeout": 10,
|
|
34
|
+
"statusMessage": "Saving memory..."
|
|
21
35
|
}
|
|
22
36
|
]
|
|
23
37
|
}
|
|
@@ -28,12 +42,14 @@
|
|
|
28
42
|
{
|
|
29
43
|
"type": "command",
|
|
30
44
|
"command": "claude-memory hook ingest",
|
|
31
|
-
"timeout": 30
|
|
45
|
+
"timeout": 30,
|
|
46
|
+
"statusMessage": "Saving memory..."
|
|
32
47
|
},
|
|
33
48
|
{
|
|
34
49
|
"type": "command",
|
|
35
50
|
"command": "claude-memory hook sweep",
|
|
36
|
-
"timeout": 30
|
|
51
|
+
"timeout": 30,
|
|
52
|
+
"statusMessage": "Sweeping memory..."
|
|
37
53
|
}
|
|
38
54
|
]
|
|
39
55
|
}
|
|
@@ -44,12 +60,14 @@
|
|
|
44
60
|
{
|
|
45
61
|
"type": "command",
|
|
46
62
|
"command": "claude-memory hook ingest",
|
|
47
|
-
"timeout": 30
|
|
63
|
+
"timeout": 30,
|
|
64
|
+
"statusMessage": "Saving memory..."
|
|
48
65
|
},
|
|
49
66
|
{
|
|
50
67
|
"type": "command",
|
|
51
68
|
"command": "claude-memory hook sweep",
|
|
52
|
-
"timeout": 30
|
|
69
|
+
"timeout": 30,
|
|
70
|
+
"statusMessage": "Sweeping memory..."
|
|
53
71
|
}
|
|
54
72
|
]
|
|
55
73
|
}
|
|
@@ -61,7 +79,8 @@
|
|
|
61
79
|
{
|
|
62
80
|
"type": "command",
|
|
63
81
|
"command": "claude-memory hook sweep",
|
|
64
|
-
"timeout": 10
|
|
82
|
+
"timeout": 10,
|
|
83
|
+
"statusMessage": "Sweeping memory..."
|
|
65
84
|
}
|
|
66
85
|
]
|
|
67
86
|
}
|
data/lib/claude_memory.rb
CHANGED
|
@@ -38,6 +38,7 @@ require_relative "claude_memory/commands/checks/claude_md_check"
|
|
|
38
38
|
require_relative "claude_memory/commands/checks/hooks_check"
|
|
39
39
|
require_relative "claude_memory/commands/checks/reporter"
|
|
40
40
|
require_relative "claude_memory/commands/checks/vec_check"
|
|
41
|
+
require_relative "claude_memory/commands/checks/distill_check"
|
|
41
42
|
require_relative "claude_memory/commands/help_command"
|
|
42
43
|
require_relative "claude_memory/commands/version_command"
|
|
43
44
|
require_relative "claude_memory/commands/doctor_command"
|
|
@@ -67,6 +68,11 @@ require_relative "claude_memory/commands/recover_command"
|
|
|
67
68
|
require_relative "claude_memory/commands/compact_command"
|
|
68
69
|
require_relative "claude_memory/commands/export_command"
|
|
69
70
|
require_relative "claude_memory/commands/git_lfs_command"
|
|
71
|
+
require_relative "claude_memory/commands/install_skill_command"
|
|
72
|
+
require_relative "claude_memory/commands/completion_command"
|
|
73
|
+
require_relative "claude_memory/commands/embeddings_command"
|
|
74
|
+
require_relative "claude_memory/commands/reject_command"
|
|
75
|
+
require_relative "claude_memory/commands/restore_command"
|
|
70
76
|
require_relative "claude_memory/commands/registry"
|
|
71
77
|
require_relative "claude_memory/cli"
|
|
72
78
|
require_relative "claude_memory/configuration"
|
|
@@ -77,9 +83,16 @@ require_relative "claude_memory/domain/fact"
|
|
|
77
83
|
require_relative "claude_memory/domain/entity"
|
|
78
84
|
require_relative "claude_memory/domain/provenance"
|
|
79
85
|
require_relative "claude_memory/domain/conflict"
|
|
86
|
+
require_relative "claude_memory/embeddings/model_registry"
|
|
87
|
+
require_relative "claude_memory/embeddings/inspector"
|
|
80
88
|
require_relative "claude_memory/embeddings/generator"
|
|
89
|
+
require_relative "claude_memory/embeddings/fastembed_adapter"
|
|
90
|
+
require_relative "claude_memory/embeddings/api_adapter"
|
|
91
|
+
require_relative "claude_memory/embeddings/dimension_check"
|
|
92
|
+
require_relative "claude_memory/embeddings/resolver"
|
|
81
93
|
require_relative "claude_memory/embeddings/similarity"
|
|
82
94
|
require_relative "claude_memory/hook/context_injector"
|
|
95
|
+
require_relative "claude_memory/hook/distillation_runner"
|
|
83
96
|
require_relative "claude_memory/hook/exit_codes"
|
|
84
97
|
require_relative "claude_memory/hook/handler"
|
|
85
98
|
require_relative "claude_memory/hook/error_classifier"
|
|
@@ -110,6 +123,9 @@ require_relative "claude_memory/mcp/tools"
|
|
|
110
123
|
require_relative "claude_memory/publish"
|
|
111
124
|
require_relative "claude_memory/recall/dual_query_template"
|
|
112
125
|
require_relative "claude_memory/recall/expansion_detector"
|
|
126
|
+
require_relative "claude_memory/recall/query_core"
|
|
127
|
+
require_relative "claude_memory/recall/legacy_engine"
|
|
128
|
+
require_relative "claude_memory/recall/dual_engine"
|
|
113
129
|
require_relative "claude_memory/recall"
|
|
114
130
|
require_relative "claude_memory/shortcuts"
|
|
115
131
|
require_relative "claude_memory/resolve/predicate_policy"
|
metadata
CHANGED
|
@@ -1,7 +1,7 @@
|
|
|
1
1
|
--- !ruby/object:Gem::Specification
|
|
2
2
|
name: claude_memory
|
|
3
3
|
version: !ruby/object:Gem::Version
|
|
4
|
-
version: 0.
|
|
4
|
+
version: 0.9.0
|
|
5
5
|
platform: ruby
|
|
6
6
|
authors:
|
|
7
7
|
- Valentino Stoll
|
|
@@ -15,14 +15,14 @@ dependencies:
|
|
|
15
15
|
requirements:
|
|
16
16
|
- - "~>"
|
|
17
17
|
- !ruby/object:Gem::Version
|
|
18
|
-
version: '5.
|
|
18
|
+
version: '5.102'
|
|
19
19
|
type: :runtime
|
|
20
20
|
prerelease: false
|
|
21
21
|
version_requirements: !ruby/object:Gem::Requirement
|
|
22
22
|
requirements:
|
|
23
23
|
- - "~>"
|
|
24
24
|
- !ruby/object:Gem::Version
|
|
25
|
-
version: '5.
|
|
25
|
+
version: '5.102'
|
|
26
26
|
- !ruby/object:Gem::Dependency
|
|
27
27
|
name: extralite
|
|
28
28
|
requirement: !ruby/object:Gem::Requirement
|
|
@@ -44,6 +44,9 @@ dependencies:
|
|
|
44
44
|
- - "~>"
|
|
45
45
|
- !ruby/object:Gem::Version
|
|
46
46
|
version: '0.1'
|
|
47
|
+
- - ">="
|
|
48
|
+
- !ruby/object:Gem::Version
|
|
49
|
+
version: 0.1.9
|
|
47
50
|
type: :runtime
|
|
48
51
|
prerelease: false
|
|
49
52
|
version_requirements: !ruby/object:Gem::Requirement
|
|
@@ -51,8 +54,13 @@ dependencies:
|
|
|
51
54
|
- - "~>"
|
|
52
55
|
- !ruby/object:Gem::Version
|
|
53
56
|
version: '0.1'
|
|
54
|
-
|
|
55
|
-
|
|
57
|
+
- - ">="
|
|
58
|
+
- !ruby/object:Gem::Version
|
|
59
|
+
version: 0.1.9
|
|
60
|
+
description: Gives Claude Code persistent memory across sessions. Claude recalls your
|
|
61
|
+
codebase architecture without file traversal, enforces project conventions during
|
|
62
|
+
code generation, tracks decisions with rationale, and remembers your preferences
|
|
63
|
+
across all projects. Zero-config via Hooks + MCP.
|
|
56
64
|
email:
|
|
57
65
|
- v@codenamev.com
|
|
58
66
|
executables:
|
|
@@ -60,13 +68,15 @@ executables:
|
|
|
60
68
|
extensions: []
|
|
61
69
|
extra_rdoc_files: []
|
|
62
70
|
files:
|
|
71
|
+
- ".claude-plugin/commands/distill-transcripts.md"
|
|
72
|
+
- ".claude-plugin/commands/memory-recall.md"
|
|
63
73
|
- ".claude-plugin/marketplace.json"
|
|
64
74
|
- ".claude-plugin/plugin.json"
|
|
75
|
+
- ".claude-plugin/scripts/hook-runner.sh"
|
|
76
|
+
- ".claude-plugin/scripts/serve-mcp.sh"
|
|
65
77
|
- ".claude.json"
|
|
66
78
|
- ".claude/CLAUDE.md"
|
|
67
79
|
- ".claude/memory.sqlite3"
|
|
68
|
-
- ".claude/memory.sqlite3-shm"
|
|
69
|
-
- ".claude/memory.sqlite3-wal"
|
|
70
80
|
- ".claude/output-styles/memory-aware.md"
|
|
71
81
|
- ".claude/rules/claude_memory.generated.md"
|
|
72
82
|
- ".claude/settings.json"
|
|
@@ -86,6 +96,7 @@ files:
|
|
|
86
96
|
- ".claude/skills/study-repo/SKILL.md"
|
|
87
97
|
- ".claude/skills/study-repo/analysis-template.md"
|
|
88
98
|
- ".claude/skills/study-repo/focus-examples.md"
|
|
99
|
+
- ".claude/skills/upgrade-dependencies/SKILL.md"
|
|
89
100
|
- ".gitattributes"
|
|
90
101
|
- ".lefthook/map_specs.rb"
|
|
91
102
|
- ".mcp.json"
|
|
@@ -112,6 +123,8 @@ files:
|
|
|
112
123
|
- db/migrations/010_add_llm_cache.rb
|
|
113
124
|
- db/migrations/011_add_tool_call_summaries.rb
|
|
114
125
|
- db/migrations/012_add_vec_indexing_support.rb
|
|
126
|
+
- db/migrations/013_add_mcp_tool_calls.rb
|
|
127
|
+
- db/migrations/014_canonicalize_predicates.rb
|
|
115
128
|
- docs/EXAMPLES.md
|
|
116
129
|
- docs/GETTING_STARTED.md
|
|
117
130
|
- docs/RELEASE_NOTES_v0.2.0.md
|
|
@@ -151,14 +164,17 @@ files:
|
|
|
151
164
|
- lib/claude_memory/commands/changes_command.rb
|
|
152
165
|
- lib/claude_memory/commands/checks/claude_md_check.rb
|
|
153
166
|
- lib/claude_memory/commands/checks/database_check.rb
|
|
167
|
+
- lib/claude_memory/commands/checks/distill_check.rb
|
|
154
168
|
- lib/claude_memory/commands/checks/hooks_check.rb
|
|
155
169
|
- lib/claude_memory/commands/checks/reporter.rb
|
|
156
170
|
- lib/claude_memory/commands/checks/snapshot_check.rb
|
|
157
171
|
- lib/claude_memory/commands/checks/vec_check.rb
|
|
158
172
|
- lib/claude_memory/commands/compact_command.rb
|
|
173
|
+
- lib/claude_memory/commands/completion_command.rb
|
|
159
174
|
- lib/claude_memory/commands/conflicts_command.rb
|
|
160
175
|
- lib/claude_memory/commands/db_init_command.rb
|
|
161
176
|
- lib/claude_memory/commands/doctor_command.rb
|
|
177
|
+
- lib/claude_memory/commands/embeddings_command.rb
|
|
162
178
|
- lib/claude_memory/commands/explain_command.rb
|
|
163
179
|
- lib/claude_memory/commands/export_command.rb
|
|
164
180
|
- lib/claude_memory/commands/git_lfs_command.rb
|
|
@@ -173,13 +189,18 @@ files:
|
|
|
173
189
|
- lib/claude_memory/commands/initializers/mcp_configurator.rb
|
|
174
190
|
- lib/claude_memory/commands/initializers/memory_instructions_writer.rb
|
|
175
191
|
- lib/claude_memory/commands/initializers/project_initializer.rb
|
|
192
|
+
- lib/claude_memory/commands/install_skill_command.rb
|
|
176
193
|
- lib/claude_memory/commands/promote_command.rb
|
|
177
194
|
- lib/claude_memory/commands/publish_command.rb
|
|
178
195
|
- lib/claude_memory/commands/recall_command.rb
|
|
179
196
|
- lib/claude_memory/commands/recover_command.rb
|
|
180
197
|
- lib/claude_memory/commands/registry.rb
|
|
198
|
+
- lib/claude_memory/commands/reject_command.rb
|
|
199
|
+
- lib/claude_memory/commands/restore_command.rb
|
|
181
200
|
- lib/claude_memory/commands/search_command.rb
|
|
182
201
|
- lib/claude_memory/commands/serve_mcp_command.rb
|
|
202
|
+
- lib/claude_memory/commands/skills/distill-transcripts.md
|
|
203
|
+
- lib/claude_memory/commands/skills/memory-recall.md
|
|
183
204
|
- lib/claude_memory/commands/stats_command.rb
|
|
184
205
|
- lib/claude_memory/commands/sweep_command.rb
|
|
185
206
|
- lib/claude_memory/commands/uninstall_command.rb
|
|
@@ -214,10 +235,16 @@ files:
|
|
|
214
235
|
- lib/claude_memory/domain/entity.rb
|
|
215
236
|
- lib/claude_memory/domain/fact.rb
|
|
216
237
|
- lib/claude_memory/domain/provenance.rb
|
|
238
|
+
- lib/claude_memory/embeddings/api_adapter.rb
|
|
239
|
+
- lib/claude_memory/embeddings/dimension_check.rb
|
|
217
240
|
- lib/claude_memory/embeddings/fastembed_adapter.rb
|
|
218
241
|
- lib/claude_memory/embeddings/generator.rb
|
|
242
|
+
- lib/claude_memory/embeddings/inspector.rb
|
|
243
|
+
- lib/claude_memory/embeddings/model_registry.rb
|
|
244
|
+
- lib/claude_memory/embeddings/resolver.rb
|
|
219
245
|
- lib/claude_memory/embeddings/similarity.rb
|
|
220
246
|
- lib/claude_memory/hook/context_injector.rb
|
|
247
|
+
- lib/claude_memory/hook/distillation_runner.rb
|
|
221
248
|
- lib/claude_memory/hook/error_classifier.rb
|
|
222
249
|
- lib/claude_memory/hook/exit_codes.rb
|
|
223
250
|
- lib/claude_memory/hook/handler.rb
|
|
@@ -240,22 +267,34 @@ files:
|
|
|
240
267
|
- lib/claude_memory/ingest/transcript_reader.rb
|
|
241
268
|
- lib/claude_memory/logging/logger.rb
|
|
242
269
|
- lib/claude_memory/mcp/error_classifier.rb
|
|
270
|
+
- lib/claude_memory/mcp/handlers/context_handlers.rb
|
|
271
|
+
- lib/claude_memory/mcp/handlers/management_handlers.rb
|
|
272
|
+
- lib/claude_memory/mcp/handlers/query_handlers.rb
|
|
273
|
+
- lib/claude_memory/mcp/handlers/setup_handlers.rb
|
|
274
|
+
- lib/claude_memory/mcp/handlers/shortcut_handlers.rb
|
|
275
|
+
- lib/claude_memory/mcp/handlers/stats_handlers.rb
|
|
243
276
|
- lib/claude_memory/mcp/instructions_builder.rb
|
|
244
277
|
- lib/claude_memory/mcp/query_guide.rb
|
|
245
278
|
- lib/claude_memory/mcp/response_formatter.rb
|
|
246
279
|
- lib/claude_memory/mcp/server.rb
|
|
247
280
|
- lib/claude_memory/mcp/setup_status_analyzer.rb
|
|
281
|
+
- lib/claude_memory/mcp/telemetry.rb
|
|
248
282
|
- lib/claude_memory/mcp/text_summary.rb
|
|
249
283
|
- lib/claude_memory/mcp/tool_definitions.rb
|
|
250
284
|
- lib/claude_memory/mcp/tool_helpers.rb
|
|
251
285
|
- lib/claude_memory/mcp/tools.rb
|
|
252
286
|
- lib/claude_memory/publish.rb
|
|
253
287
|
- lib/claude_memory/recall.rb
|
|
288
|
+
- lib/claude_memory/recall/dual_engine.rb
|
|
254
289
|
- lib/claude_memory/recall/dual_query_template.rb
|
|
255
290
|
- lib/claude_memory/recall/expansion_detector.rb
|
|
291
|
+
- lib/claude_memory/recall/legacy_engine.rb
|
|
292
|
+
- lib/claude_memory/recall/query_core.rb
|
|
256
293
|
- lib/claude_memory/resolve/predicate_policy.rb
|
|
257
294
|
- lib/claude_memory/resolve/resolver.rb
|
|
258
295
|
- lib/claude_memory/shortcuts.rb
|
|
296
|
+
- lib/claude_memory/store/retry_handler.rb
|
|
297
|
+
- lib/claude_memory/store/schema_manager.rb
|
|
259
298
|
- lib/claude_memory/store/sqlite_store.rb
|
|
260
299
|
- lib/claude_memory/store/store_manager.rb
|
|
261
300
|
- lib/claude_memory/sweep/maintenance.rb
|
|
@@ -296,5 +335,6 @@ required_rubygems_version: !ruby/object:Gem::Requirement
|
|
|
296
335
|
requirements: []
|
|
297
336
|
rubygems_version: 4.0.6
|
|
298
337
|
specification_version: 4
|
|
299
|
-
summary: Long-term
|
|
338
|
+
summary: Long-term memory for Claude Code — architecture recall, convention enforcement,
|
|
339
|
+
decision tracking
|
|
300
340
|
test_files: []
|
data/.claude/memory.sqlite3-shm
DELETED
|
Binary file
|
data/.claude/memory.sqlite3-wal
DELETED
|
Binary file
|