stellar-memory 0.5.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.
Files changed (197) hide show
  1. package/LICENSE +21 -0
  2. package/README.md +362 -0
  3. package/dist/api/routes/analytics.d.ts +15 -0
  4. package/dist/api/routes/analytics.js +131 -0
  5. package/dist/api/routes/analytics.js.map +1 -0
  6. package/dist/api/routes/conflicts.d.ts +12 -0
  7. package/dist/api/routes/conflicts.js +67 -0
  8. package/dist/api/routes/conflicts.js.map +1 -0
  9. package/dist/api/routes/consolidation.d.ts +11 -0
  10. package/dist/api/routes/consolidation.js +63 -0
  11. package/dist/api/routes/consolidation.js.map +1 -0
  12. package/dist/api/routes/constellation.d.ts +4 -0
  13. package/dist/api/routes/constellation.js +84 -0
  14. package/dist/api/routes/constellation.js.map +1 -0
  15. package/dist/api/routes/memories.d.ts +4 -0
  16. package/dist/api/routes/memories.js +219 -0
  17. package/dist/api/routes/memories.js.map +1 -0
  18. package/dist/api/routes/observations.d.ts +10 -0
  19. package/dist/api/routes/observations.js +42 -0
  20. package/dist/api/routes/observations.js.map +1 -0
  21. package/dist/api/routes/orbit.d.ts +4 -0
  22. package/dist/api/routes/orbit.js +71 -0
  23. package/dist/api/routes/orbit.js.map +1 -0
  24. package/dist/api/routes/projects.d.ts +15 -0
  25. package/dist/api/routes/projects.js +121 -0
  26. package/dist/api/routes/projects.js.map +1 -0
  27. package/dist/api/routes/scan.d.ts +4 -0
  28. package/dist/api/routes/scan.js +403 -0
  29. package/dist/api/routes/scan.js.map +1 -0
  30. package/dist/api/routes/sun.d.ts +4 -0
  31. package/dist/api/routes/sun.js +43 -0
  32. package/dist/api/routes/sun.js.map +1 -0
  33. package/dist/api/routes/system.d.ts +4 -0
  34. package/dist/api/routes/system.js +70 -0
  35. package/dist/api/routes/system.js.map +1 -0
  36. package/dist/api/routes/temporal.d.ts +13 -0
  37. package/dist/api/routes/temporal.js +82 -0
  38. package/dist/api/routes/temporal.js.map +1 -0
  39. package/dist/api/server.d.ts +2 -0
  40. package/dist/api/server.js +99 -0
  41. package/dist/api/server.js.map +1 -0
  42. package/dist/api/websocket.d.ts +53 -0
  43. package/dist/api/websocket.js +168 -0
  44. package/dist/api/websocket.js.map +1 -0
  45. package/dist/cli/index.d.ts +12 -0
  46. package/dist/cli/index.js +35 -0
  47. package/dist/cli/index.js.map +1 -0
  48. package/dist/cli/init.d.ts +10 -0
  49. package/dist/cli/init.js +163 -0
  50. package/dist/cli/init.js.map +1 -0
  51. package/dist/engine/analytics.d.ts +93 -0
  52. package/dist/engine/analytics.js +437 -0
  53. package/dist/engine/analytics.js.map +1 -0
  54. package/dist/engine/conflict.d.ts +54 -0
  55. package/dist/engine/conflict.js +322 -0
  56. package/dist/engine/conflict.js.map +1 -0
  57. package/dist/engine/consolidation.d.ts +83 -0
  58. package/dist/engine/consolidation.js +368 -0
  59. package/dist/engine/consolidation.js.map +1 -0
  60. package/dist/engine/constellation.d.ts +66 -0
  61. package/dist/engine/constellation.js +382 -0
  62. package/dist/engine/constellation.js.map +1 -0
  63. package/dist/engine/corona.d.ts +53 -0
  64. package/dist/engine/corona.js +181 -0
  65. package/dist/engine/corona.js.map +1 -0
  66. package/dist/engine/embedding.d.ts +44 -0
  67. package/dist/engine/embedding.js +168 -0
  68. package/dist/engine/embedding.js.map +1 -0
  69. package/dist/engine/gravity.d.ts +63 -0
  70. package/dist/engine/gravity.js +121 -0
  71. package/dist/engine/gravity.js.map +1 -0
  72. package/dist/engine/multiproject.d.ts +75 -0
  73. package/dist/engine/multiproject.js +241 -0
  74. package/dist/engine/multiproject.js.map +1 -0
  75. package/dist/engine/observation.d.ts +82 -0
  76. package/dist/engine/observation.js +357 -0
  77. package/dist/engine/observation.js.map +1 -0
  78. package/dist/engine/orbit.d.ts +91 -0
  79. package/dist/engine/orbit.js +249 -0
  80. package/dist/engine/orbit.js.map +1 -0
  81. package/dist/engine/planet.d.ts +64 -0
  82. package/dist/engine/planet.js +432 -0
  83. package/dist/engine/planet.js.map +1 -0
  84. package/dist/engine/procedural.d.ts +71 -0
  85. package/dist/engine/procedural.js +259 -0
  86. package/dist/engine/procedural.js.map +1 -0
  87. package/dist/engine/quality.d.ts +48 -0
  88. package/dist/engine/quality.js +245 -0
  89. package/dist/engine/quality.js.map +1 -0
  90. package/dist/engine/repository.d.ts +79 -0
  91. package/dist/engine/repository.js +13 -0
  92. package/dist/engine/repository.js.map +1 -0
  93. package/dist/engine/sun.d.ts +61 -0
  94. package/dist/engine/sun.js +240 -0
  95. package/dist/engine/sun.js.map +1 -0
  96. package/dist/engine/temporal.d.ts +67 -0
  97. package/dist/engine/temporal.js +283 -0
  98. package/dist/engine/temporal.js.map +1 -0
  99. package/dist/engine/types.d.ts +179 -0
  100. package/dist/engine/types.js +27 -0
  101. package/dist/engine/types.js.map +1 -0
  102. package/dist/index.d.ts +2 -0
  103. package/dist/index.js +60 -0
  104. package/dist/index.js.map +1 -0
  105. package/dist/mcp/connector-registry.d.ts +20 -0
  106. package/dist/mcp/connector-registry.js +35 -0
  107. package/dist/mcp/connector-registry.js.map +1 -0
  108. package/dist/mcp/server.d.ts +13 -0
  109. package/dist/mcp/server.js +242 -0
  110. package/dist/mcp/server.js.map +1 -0
  111. package/dist/mcp/tools/daemon-tool.d.ts +16 -0
  112. package/dist/mcp/tools/daemon-tool.js +58 -0
  113. package/dist/mcp/tools/daemon-tool.js.map +1 -0
  114. package/dist/mcp/tools/ingestion-tools.d.ts +20 -0
  115. package/dist/mcp/tools/ingestion-tools.js +34 -0
  116. package/dist/mcp/tools/ingestion-tools.js.map +1 -0
  117. package/dist/mcp/tools/memory-tools.d.ts +122 -0
  118. package/dist/mcp/tools/memory-tools.js +1037 -0
  119. package/dist/mcp/tools/memory-tools.js.map +1 -0
  120. package/dist/scanner/cloud/github.d.ts +34 -0
  121. package/dist/scanner/cloud/github.js +260 -0
  122. package/dist/scanner/cloud/github.js.map +1 -0
  123. package/dist/scanner/cloud/google-drive.d.ts +30 -0
  124. package/dist/scanner/cloud/google-drive.js +289 -0
  125. package/dist/scanner/cloud/google-drive.js.map +1 -0
  126. package/dist/scanner/cloud/notion.d.ts +33 -0
  127. package/dist/scanner/cloud/notion.js +231 -0
  128. package/dist/scanner/cloud/notion.js.map +1 -0
  129. package/dist/scanner/cloud/slack.d.ts +38 -0
  130. package/dist/scanner/cloud/slack.js +282 -0
  131. package/dist/scanner/cloud/slack.js.map +1 -0
  132. package/dist/scanner/cloud/types.d.ts +73 -0
  133. package/dist/scanner/cloud/types.js +9 -0
  134. package/dist/scanner/cloud/types.js.map +1 -0
  135. package/dist/scanner/index.d.ts +35 -0
  136. package/dist/scanner/index.js +420 -0
  137. package/dist/scanner/index.js.map +1 -0
  138. package/dist/scanner/local/filesystem.d.ts +33 -0
  139. package/dist/scanner/local/filesystem.js +203 -0
  140. package/dist/scanner/local/filesystem.js.map +1 -0
  141. package/dist/scanner/local/git.d.ts +24 -0
  142. package/dist/scanner/local/git.js +161 -0
  143. package/dist/scanner/local/git.js.map +1 -0
  144. package/dist/scanner/local/parsers/code.d.ts +3 -0
  145. package/dist/scanner/local/parsers/code.js +127 -0
  146. package/dist/scanner/local/parsers/code.js.map +1 -0
  147. package/dist/scanner/local/parsers/index.d.ts +11 -0
  148. package/dist/scanner/local/parsers/index.js +24 -0
  149. package/dist/scanner/local/parsers/index.js.map +1 -0
  150. package/dist/scanner/local/parsers/json-parser.d.ts +3 -0
  151. package/dist/scanner/local/parsers/json-parser.js +117 -0
  152. package/dist/scanner/local/parsers/json-parser.js.map +1 -0
  153. package/dist/scanner/local/parsers/markdown.d.ts +3 -0
  154. package/dist/scanner/local/parsers/markdown.js +120 -0
  155. package/dist/scanner/local/parsers/markdown.js.map +1 -0
  156. package/dist/scanner/local/parsers/text.d.ts +3 -0
  157. package/dist/scanner/local/parsers/text.js +41 -0
  158. package/dist/scanner/local/parsers/text.js.map +1 -0
  159. package/dist/scanner/metadata-scanner.d.ts +67 -0
  160. package/dist/scanner/metadata-scanner.js +356 -0
  161. package/dist/scanner/metadata-scanner.js.map +1 -0
  162. package/dist/scanner/types.d.ts +47 -0
  163. package/dist/scanner/types.js +19 -0
  164. package/dist/scanner/types.js.map +1 -0
  165. package/dist/service/daemon.d.ts +23 -0
  166. package/dist/service/daemon.js +105 -0
  167. package/dist/service/daemon.js.map +1 -0
  168. package/dist/service/scheduler.d.ts +73 -0
  169. package/dist/service/scheduler.js +281 -0
  170. package/dist/service/scheduler.js.map +1 -0
  171. package/dist/storage/database.d.ts +10 -0
  172. package/dist/storage/database.js +265 -0
  173. package/dist/storage/database.js.map +1 -0
  174. package/dist/storage/queries.d.ts +85 -0
  175. package/dist/storage/queries.js +865 -0
  176. package/dist/storage/queries.js.map +1 -0
  177. package/dist/storage/sqlite-repository.d.ts +32 -0
  178. package/dist/storage/sqlite-repository.js +68 -0
  179. package/dist/storage/sqlite-repository.js.map +1 -0
  180. package/dist/storage/vec.d.ts +62 -0
  181. package/dist/storage/vec.js +111 -0
  182. package/dist/storage/vec.js.map +1 -0
  183. package/dist/utils/config.d.ts +5 -0
  184. package/dist/utils/config.js +60 -0
  185. package/dist/utils/config.js.map +1 -0
  186. package/dist/utils/logger.d.ts +36 -0
  187. package/dist/utils/logger.js +86 -0
  188. package/dist/utils/logger.js.map +1 -0
  189. package/dist/utils/time.d.ts +21 -0
  190. package/dist/utils/time.js +42 -0
  191. package/dist/utils/time.js.map +1 -0
  192. package/dist/utils/tokenizer.d.ts +13 -0
  193. package/dist/utils/tokenizer.js +46 -0
  194. package/dist/utils/tokenizer.js.map +1 -0
  195. package/package.json +77 -0
  196. package/scripts/check-node.mjs +36 -0
  197. package/scripts/setup.mjs +157 -0
@@ -0,0 +1,322 @@
1
+ /**
2
+ * conflict.ts — Conflict Detection engine
3
+ *
4
+ * Finds contradictions between memories. When a new memory is stored,
5
+ * this module checks existing memories for semantic conflicts and creates
6
+ * MemoryConflict records for any detected issues.
7
+ *
8
+ * Detection is purely local — no LLM required. Heuristics use keyword
9
+ * overlap, negation patterns, and opposing action verbs.
10
+ *
11
+ * All functions are pure (no classes), following the project style.
12
+ */
13
+ import { randomUUID } from 'node:crypto';
14
+ import { searchMemories, createConflict as queriesCreateConflict, getConflicts, resolveConflict as queriesResolveConflict, } from '../storage/queries.js';
15
+ import { getDatabase } from '../storage/database.js';
16
+ import { supersedeMemory, extractKeyTerms } from './temporal.js';
17
+ import { createLogger } from '../utils/logger.js';
18
+ const log = createLogger('conflict');
19
+ // ---------------------------------------------------------------------------
20
+ // detectConflicts
21
+ // ---------------------------------------------------------------------------
22
+ /**
23
+ * Check for conflicts when storing a new memory.
24
+ *
25
+ * Searches for up to 5 similar existing memories via FTS5, then analyzes
26
+ * each pair for semantic contradictions. Detected conflicts are persisted
27
+ * and returned to the caller.
28
+ */
29
+ export async function detectConflicts(newMemory, project) {
30
+ // Build a representative search query from the new memory's content + tags
31
+ const queryTerms = [
32
+ newMemory.summary,
33
+ ...newMemory.tags,
34
+ ].join(' ').trim() || newMemory.content.slice(0, 100);
35
+ const candidates = searchMemories(project, queryTerms, 5);
36
+ const conflicts = [];
37
+ for (const candidate of candidates) {
38
+ // Skip self-comparison and already-superseded memories
39
+ if (candidate.id === newMemory.id)
40
+ continue;
41
+ if (candidate.superseded_by)
42
+ continue;
43
+ if (candidate.deleted_at)
44
+ continue;
45
+ const analysis = analyzeConflict(newMemory.content, candidate.content);
46
+ if (!analysis.isConflict)
47
+ continue;
48
+ // Further boost to high severity when both are 'decision' type
49
+ const severity = newMemory.type === 'decision' && candidate.type === 'decision'
50
+ ? 'high'
51
+ : analysis.severity;
52
+ const conflict = {
53
+ id: randomUUID(),
54
+ memory_id: newMemory.id,
55
+ conflicting_memory_id: candidate.id,
56
+ severity,
57
+ description: analysis.reason,
58
+ status: 'open',
59
+ project,
60
+ created_at: new Date().toISOString(),
61
+ };
62
+ queriesCreateConflict(conflict);
63
+ conflicts.push(conflict);
64
+ log.debug('Conflict detected', {
65
+ newId: newMemory.id,
66
+ existingId: candidate.id,
67
+ severity,
68
+ reason: analysis.reason,
69
+ });
70
+ }
71
+ return conflicts;
72
+ }
73
+ // ---------------------------------------------------------------------------
74
+ // analyzeConflict — local heuristics, no LLM
75
+ // ---------------------------------------------------------------------------
76
+ /**
77
+ * Analyze whether two memory contents contradict each other.
78
+ *
79
+ * Checks:
80
+ * 1. Shared key terms (minimum overlap threshold)
81
+ * 2. Negation of action verbs around shared terms
82
+ * 3. Opposing choice signals ("chose X" vs "chose Y" for same topic)
83
+ * 4. "Switched from X to Y" patterns (X = existing tech)
84
+ */
85
+ function analyzeConflict(newContent, existingContent) {
86
+ const newLower = newContent.toLowerCase();
87
+ const existingLower = existingContent.toLowerCase();
88
+ const newTerms = extractKeyTerms(newLower);
89
+ const existingTerms = extractKeyTerms(existingLower);
90
+ const sharedTerms = intersection(newTerms, existingTerms);
91
+ // Not enough shared context to conflict
92
+ if (sharedTerms.size === 0) {
93
+ return { isConflict: false, severity: 'low', reason: '' };
94
+ }
95
+ const overlapRatio = sharedTerms.size / Math.min(newTerms.size, existingTerms.size);
96
+ if (overlapRatio < 0.2) {
97
+ return { isConflict: false, severity: 'low', reason: '' };
98
+ }
99
+ // Check "switched from X" — X appears in existing
100
+ const switchMatch = newLower.match(/switched?\s+from\s+(\w+)/i)
101
+ ?? newLower.match(/migrat\w+\s+from\s+(\w+)/i)
102
+ ?? newLower.match(/replac\w+\s+(\w+)/i)
103
+ ?? newLower.match(/no\s+longer\s+using?\s+(\w+)/i);
104
+ if (switchMatch) {
105
+ const switchedFrom = switchMatch[1].toLowerCase();
106
+ if (existingLower.includes(switchedFrom)) {
107
+ return {
108
+ isConflict: true,
109
+ severity: 'high',
110
+ reason: `New memory indicates switching away from "${switchedFrom}" which appears in existing memory`,
111
+ };
112
+ }
113
+ }
114
+ // Check opposing action verbs around shared terms
115
+ const negationResult = checkNegationConflict(newLower, existingLower, sharedTerms);
116
+ if (negationResult.isConflict)
117
+ return negationResult;
118
+ // Check opposing choice signals ("chose X" / "selected X" vs "chose Y")
119
+ const choiceResult = checkChoiceConflict(newLower, existingLower);
120
+ if (choiceResult.isConflict)
121
+ return choiceResult;
122
+ // Check enable/disable toggles
123
+ const toggleResult = checkToggleConflict(newLower, existingLower, sharedTerms);
124
+ if (toggleResult.isConflict)
125
+ return toggleResult;
126
+ return { isConflict: false, severity: 'low', reason: '' };
127
+ }
128
+ /**
129
+ * Check if one text negates an action verb that appears with a shared term in the other.
130
+ * E.g., "use Redis" (existing) vs "not use Redis" (new).
131
+ */
132
+ function checkNegationConflict(newLower, existingLower, sharedTerms) {
133
+ const POSITIVE_VERBS = ['use', 'enable', 'add', 'adopt', 'choose', 'select', 'implement', 'deploy'];
134
+ const NEGATION_PREFIXES = ['not ', "don't ", "do not ", 'avoid ', 'stop ', 'remove ', 'disable ', 'never '];
135
+ for (const term of sharedTerms) {
136
+ for (const verb of POSITIVE_VERBS) {
137
+ const positivePattern = `${verb} ${term}`;
138
+ const existingPositive = existingLower.includes(positivePattern);
139
+ const newNegative = NEGATION_PREFIXES.some(neg => newLower.includes(neg + verb + ' ' + term));
140
+ if (existingPositive && newNegative) {
141
+ return {
142
+ isConflict: true,
143
+ severity: 'medium',
144
+ reason: `Existing memory says "${positivePattern}", new memory negates this`,
145
+ };
146
+ }
147
+ const newPositive = newLower.includes(positivePattern);
148
+ const existingNegative = NEGATION_PREFIXES.some(neg => existingLower.includes(neg + verb + ' ' + term));
149
+ if (newPositive && existingNegative) {
150
+ return {
151
+ isConflict: true,
152
+ severity: 'medium',
153
+ reason: `New memory says "${positivePattern}", but existing memory negates this`,
154
+ };
155
+ }
156
+ }
157
+ }
158
+ return { isConflict: false, severity: 'low', reason: '' };
159
+ }
160
+ /**
161
+ * Check for opposing choice signals.
162
+ * Detects: "chose/selected/decided on X" in one vs "chose/selected/decided on Y" in other.
163
+ */
164
+ function checkChoiceConflict(newLower, existingLower) {
165
+ const CHOICE_VERBS = ['chose', 'selected', 'decided on', 'picked', 'went with'];
166
+ const extractChoiceTarget = (text) => {
167
+ for (const verb of CHOICE_VERBS) {
168
+ const idx = text.indexOf(verb);
169
+ if (idx === -1)
170
+ continue;
171
+ const after = text.slice(idx + verb.length).trim();
172
+ const token = after.match(/^(\w+)/)?.[1];
173
+ if (token && token.length >= 3)
174
+ return token;
175
+ }
176
+ return null;
177
+ };
178
+ const newChoice = extractChoiceTarget(newLower);
179
+ const existingChoice = extractChoiceTarget(existingLower);
180
+ if (newChoice && existingChoice && newChoice !== existingChoice) {
181
+ return {
182
+ isConflict: true,
183
+ severity: 'high',
184
+ reason: `Conflicting decisions: existing chose "${existingChoice}", new chose "${newChoice}"`,
185
+ };
186
+ }
187
+ return { isConflict: false, severity: 'low', reason: '' };
188
+ }
189
+ /**
190
+ * Check for enable/disable or add/remove toggle conflicts on shared terms.
191
+ */
192
+ function checkToggleConflict(newLower, existingLower, sharedTerms) {
193
+ const TOGGLE_PAIRS = [
194
+ ['enabled', 'disabled'],
195
+ ['enable', 'disable'],
196
+ ['activated', 'deactivated'],
197
+ ['on', 'off'],
198
+ ];
199
+ for (const term of sharedTerms) {
200
+ for (const [pos, neg] of TOGGLE_PAIRS) {
201
+ const existingPos = existingLower.includes(`${pos} ${term}`) || existingLower.includes(`${term} ${pos}`);
202
+ const newNeg = newLower.includes(`${neg} ${term}`) || newLower.includes(`${term} ${neg}`);
203
+ if (existingPos && newNeg) {
204
+ return {
205
+ isConflict: true,
206
+ severity: 'medium',
207
+ reason: `Toggle conflict on "${term}": existing has "${pos}", new has "${neg}"`,
208
+ };
209
+ }
210
+ const newPos = newLower.includes(`${pos} ${term}`) || newLower.includes(`${term} ${pos}`);
211
+ const existingNeg = existingLower.includes(`${neg} ${term}`) || existingLower.includes(`${term} ${neg}`);
212
+ if (newPos && existingNeg) {
213
+ return {
214
+ isConflict: true,
215
+ severity: 'medium',
216
+ reason: `Toggle conflict on "${term}": new has "${pos}", existing has "${neg}"`,
217
+ };
218
+ }
219
+ }
220
+ }
221
+ return { isConflict: false, severity: 'low', reason: '' };
222
+ }
223
+ // ---------------------------------------------------------------------------
224
+ // autoResolveConflict
225
+ // ---------------------------------------------------------------------------
226
+ /**
227
+ * Attempt to auto-resolve a conflict without user intervention.
228
+ *
229
+ * Auto-resolves when the newer memory clearly supersedes the older one:
230
+ * - The conflict memory was created after the conflicting memory
231
+ * - Severity is high (strong signal of supersession)
232
+ *
233
+ * Returns true if resolved (and calls temporal.supersedeMemory),
234
+ * or false if user decision is needed.
235
+ */
236
+ export function autoResolveConflict(conflict) {
237
+ if (conflict.severity !== 'high')
238
+ return false;
239
+ // We auto-resolve only when the conflict description contains a switch signal
240
+ const switchSignals = ['switching away from', 'switched away from', 'conflicting decisions'];
241
+ const hasSwitch = switchSignals.some(s => conflict.description.toLowerCase().includes(s));
242
+ if (!hasSwitch)
243
+ return false;
244
+ // newMemory (memory_id) supersedes the existing (conflicting_memory_id)
245
+ supersedeMemory(conflict.conflicting_memory_id, conflict.memory_id);
246
+ queriesResolveConflict(conflict.id, `Auto-resolved: memory ${conflict.memory_id} supersedes ${conflict.conflicting_memory_id}`);
247
+ log.debug('Conflict auto-resolved', { conflictId: conflict.id });
248
+ return true;
249
+ }
250
+ // ---------------------------------------------------------------------------
251
+ // formatConflictWarnings
252
+ // ---------------------------------------------------------------------------
253
+ /**
254
+ * Format conflict warnings as human-readable text.
255
+ *
256
+ * Returns a warning string listing each conflict with memory summaries.
257
+ * Designed to be returned to the user as part of a remember tool response.
258
+ */
259
+ export function formatConflictWarnings(conflicts) {
260
+ if (conflicts.length === 0)
261
+ return '';
262
+ const lines = ['Warning: potential memory conflicts detected:'];
263
+ for (const conflict of conflicts) {
264
+ const severityLabel = conflict.severity.toUpperCase();
265
+ lines.push(` [${severityLabel}] Memory ${conflict.memory_id.slice(0, 8)} conflicts with ` +
266
+ `${conflict.conflicting_memory_id.slice(0, 8)}: ${conflict.description}`);
267
+ }
268
+ lines.push('Use resolveConflict() to dismiss or supersede the older memory.');
269
+ return lines.join('\n');
270
+ }
271
+ // ---------------------------------------------------------------------------
272
+ // getUnresolvedConflicts
273
+ // ---------------------------------------------------------------------------
274
+ /**
275
+ * Return all open (unresolved) conflicts for a project.
276
+ */
277
+ export function getUnresolvedConflicts(project) {
278
+ return getConflicts(project, 'open');
279
+ }
280
+ // ---------------------------------------------------------------------------
281
+ // resolveConflict
282
+ // ---------------------------------------------------------------------------
283
+ /**
284
+ * Resolve a conflict manually.
285
+ *
286
+ * Actions:
287
+ * - 'supersede': mark resolved and call temporal.supersedeMemory()
288
+ * (conflicting_memory_id superseded by memory_id)
289
+ * - 'dismiss': mark resolved without any memory changes
290
+ * - 'keep_both': mark resolved with a note that both are intentionally kept
291
+ */
292
+ export function resolveConflict(conflictId, resolution, action = 'dismiss') {
293
+ // We need the conflict details to call supersedeMemory if needed.
294
+ // Fetch it via getConflicts (no direct getConflictById, but we can filter).
295
+ // Since we only need it for supersede, we'll proceed directly.
296
+ if (action === 'supersede') {
297
+ const db = getDatabase();
298
+ const row = db.prepare(`SELECT memory_id, conflicting_memory_id FROM memory_conflicts WHERE id = ?`).get(conflictId);
299
+ if (row) {
300
+ supersedeMemory(row.conflicting_memory_id, row.memory_id);
301
+ }
302
+ }
303
+ const resolutionNote = action === 'keep_both'
304
+ ? `[keep_both] ${resolution}`
305
+ : action === 'dismiss'
306
+ ? `[dismissed] ${resolution}`
307
+ : `[superseded] ${resolution}`;
308
+ queriesResolveConflict(conflictId, resolutionNote);
309
+ log.debug('Conflict resolved', { conflictId, action, resolution });
310
+ }
311
+ // ---------------------------------------------------------------------------
312
+ // Internal utilities
313
+ // ---------------------------------------------------------------------------
314
+ function intersection(a, b) {
315
+ const result = new Set();
316
+ for (const item of a) {
317
+ if (b.has(item))
318
+ result.add(item);
319
+ }
320
+ return result;
321
+ }
322
+ //# sourceMappingURL=conflict.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"conflict.js","sourceRoot":"","sources":["../../src/engine/conflict.ts"],"names":[],"mappings":"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"}
@@ -0,0 +1,83 @@
1
+ /**
2
+ * consolidation.ts — Memory Consolidation ("Orbital Resonance")
3
+ *
4
+ * Finds groups of similar memories and merges them into richer, more
5
+ * comprehensive memories. Similar to how planets form from smaller bodies
6
+ * (planetesimals) combining in orbital resonance.
7
+ *
8
+ * Algorithm:
9
+ * 1. Load all memories in a project.
10
+ * 2. Group memories that share the same type and are within ±3 AU of each
11
+ * other, with cosine similarity > 0.80 between their embeddings.
12
+ * Falls back to Jaccard-based text similarity when embeddings are absent.
13
+ * 3. For each qualifying group (2+ memories):
14
+ * - Merge content by deduplicating sentences.
15
+ * - Create a new consolidated memory.
16
+ * - Mark sources as consolidated and push them to the Oort cloud.
17
+ */
18
+ import type { Memory } from './types.js';
19
+ /**
20
+ * Deduplicate an array of sentences using Jaccard similarity.
21
+ *
22
+ * For each new sentence, if it is too similar to one already kept (above
23
+ * JACCARD_DEDUP_THRESHOLD), keep the longer/more detailed version and discard
24
+ * the other.
25
+ *
26
+ * Returns the deduplicated array of sentences in original order.
27
+ */
28
+ export declare function deduplicateSentences(sentences: string[]): string[];
29
+ /**
30
+ * Find groups of memories that are candidates for consolidation.
31
+ *
32
+ * Criteria for grouping:
33
+ * - Same type
34
+ * - Within ±3 AU of each other (distance)
35
+ * - Cosine similarity > 0.80 (falls back to Jaccard if no embeddings)
36
+ *
37
+ * Returns groups sorted by average similarity (highest first).
38
+ * Each group contains 2+ memories.
39
+ */
40
+ export declare function findConsolidationCandidates(project: string): Promise<Array<{
41
+ memories: Memory[];
42
+ similarity: number;
43
+ }>>;
44
+ /**
45
+ * Consolidate a group of memories into a single new memory.
46
+ *
47
+ * Merge strategy:
48
+ * - Content: Combine unique sentences from all sources (Jaccard dedup).
49
+ * - Summary: Join all source summaries, deduplicated and truncated.
50
+ * - Tags: Union of all tags.
51
+ * - Type: Most important type by TYPE_PRIORITY ranking.
52
+ * - Impact: Max of all sources.
53
+ * - Distance: Min of all sources (closest orbit).
54
+ *
55
+ * After creating the new memory:
56
+ * - Source memories are marked as consolidated (consolidated_into set).
57
+ * - Source memories are pushed to the Oort cloud (distance = 95).
58
+ *
59
+ * Returns the newly created consolidated memory.
60
+ */
61
+ export declare function consolidateGroup(memories: Memory[], project: string): Memory;
62
+ /**
63
+ * Run a full consolidation pass for a project.
64
+ *
65
+ * Finds all candidate groups, consolidates each one, and returns statistics.
66
+ */
67
+ export declare function runConsolidation(project: string): Promise<{
68
+ groupsFound: number;
69
+ memoriesConsolidated: number;
70
+ newMemoriesCreated: number;
71
+ }>;
72
+ /**
73
+ * Return the source memories that were merged into the given memory ID.
74
+ * Returns an empty array if this memory was not created by consolidation.
75
+ */
76
+ export declare function getConsolidationSources(memoryId: string): Memory[];
77
+ /**
78
+ * Generate and compare embeddings for two text strings.
79
+ * Returns cosine similarity in [0, 1].
80
+ * Used internally when stored embeddings are unavailable.
81
+ */
82
+ export declare function computeEmbeddingSimilarity(textA: string, textB: string): Promise<number>;
83
+ //# sourceMappingURL=consolidation.d.ts.map