nexusmem 0.6.0 → 0.8.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.
- package/CHANGELOG.md +56 -1
- package/README.md +39 -17
- package/dist/cli/index.js +464 -29
- package/dist/cli/index.js.map +1 -1
- package/package.json +1 -1
package/CHANGELOG.md
CHANGED
|
@@ -9,6 +9,59 @@ built from, matched by publish timestamp: `v0.1.0` → `67a4776`, `v0.1.1` → `
|
|
|
9
9
|
|
|
10
10
|
## [Unreleased]
|
|
11
11
|
|
|
12
|
+
No unreleased changes yet.
|
|
13
|
+
|
|
14
|
+
## [0.8.0] — 2026-08-22
|
|
15
|
+
|
|
16
|
+
### Added
|
|
17
|
+
|
|
18
|
+
- Provenance widened from 2 tiers to a 4-tier trust hierarchy: `observed` (commits, diffs, shell
|
|
19
|
+
exit codes) > `authored` (doc sections — human-written claims) > `recorded` (conversation turns —
|
|
20
|
+
verbatim discourse) > `derived` (session summaries — a model's distillation). Schema V7 backfills
|
|
21
|
+
existing databases by kind. The ranker decays each tier at its own rate (lower trust fades
|
|
22
|
+
faster); the ordering is the design claim, the exact ratios are documented judgment calls.
|
|
23
|
+
- Contradiction checking now runs automatically during `sync`: at most 3 new SLM judgments per run
|
|
24
|
+
(`contradictions.maxPerSync`; `contradictions.autoCheck: false` turns it off), gated on the
|
|
25
|
+
embedding provider already being reachable. Every judgment — either verdict — is memoized in a new
|
|
26
|
+
`contradiction_checks` table (schema V8), so a judged pair is never sent to the model again and
|
|
27
|
+
repeat syncs converge to zero model calls. Measured live against this repo's own database: 5.4s
|
|
28
|
+
for the first 10 judgments, 0.5s for the identical re-run. Still suggest-only: nothing ever writes
|
|
29
|
+
`supersedes` automatically.
|
|
30
|
+
- Standing suggestions now surface everywhere without a model in the loop: plain `nexusmem stale`
|
|
31
|
+
decorates flagged candidates from the memoized judgments (instant, offline), `nexusmem status`
|
|
32
|
+
gains a `flagged` line, and the sync summary reports new/open suggestion counts.
|
|
33
|
+
- `stale --check-contradictions` reuses each candidate's stored embedding instead of re-embedding
|
|
34
|
+
it, and stops after two consecutive null SLM replies so a down provider costs at most two timeouts
|
|
35
|
+
rather than one per candidate.
|
|
36
|
+
|
|
37
|
+
## [0.7.0] — 2026-08-21
|
|
38
|
+
|
|
39
|
+
### Added
|
|
40
|
+
|
|
41
|
+
- `nexusmem stale --check-contradictions`: for each stale candidate, finds the most similar newer
|
|
42
|
+
node (local embedding search) and asks a local SLM (Ollama, `qwen2.5:3b` by default) whether it
|
|
43
|
+
actually contradicts the older one, instead of only surfacing by age. Suggest-only — nothing is
|
|
44
|
+
written, same as plain `stale`. Live-dogfooded against this repo's own real database and Ollama
|
|
45
|
+
instance; found and fixed a real gap along the way (below) before the feature surfaced anything
|
|
46
|
+
useful.
|
|
47
|
+
- Import graph: bare Python imports with no leading dot (`import foo`, `from foo import bar`)
|
|
48
|
+
now resolve to a same-directory sibling file too, alongside the existing relative-dot support.
|
|
49
|
+
Found dogfooding two real local projects: neither used a single PEP 328 relative import, both
|
|
50
|
+
relied entirely on this flat-script style. Guarded by a static list of stdlib module names so a
|
|
51
|
+
bare `import os`/`import queue`/etc. is never mistaken for a same-named local file.
|
|
52
|
+
|
|
53
|
+
### Fixed
|
|
54
|
+
|
|
55
|
+
- Import graph: a Java wildcard import (`import a.b.*;`) no longer merges files from two
|
|
56
|
+
unrelated packages that happen to share a directory-name suffix (e.g. two Gradle/Maven modules
|
|
57
|
+
each with their own `.../foo`) — it now refuses to guess, same as the single-class-import case.
|
|
58
|
+
- `stale --check-contradictions`'s neighbor search now looks past same-timestamp sibling nodes
|
|
59
|
+
(e.g. the many chunks one long conversation gets split into) to reach genuinely newer content.
|
|
60
|
+
Found live-dogfooding against this repo's own database: the first real candidate's closest 15
|
|
61
|
+
neighbors were all same-conversation siblings sharing its exact timestamp, so the original
|
|
62
|
+
5-neighbor default silently found zero suggestions for every candidate, regardless of what the
|
|
63
|
+
SLM would have said.
|
|
64
|
+
|
|
12
65
|
## [0.6.0] — 2026-08-20
|
|
13
66
|
|
|
14
67
|
### Added
|
|
@@ -451,7 +504,9 @@ First public release.
|
|
|
451
504
|
there is no local-model summarization pass, and the conversation collector has never been audited
|
|
452
505
|
for the stale-node bug that was found and fixed in the docs collector.
|
|
453
506
|
|
|
454
|
-
[Unreleased]: https://github.com/yaminbkk/NexusMem/compare/v0.
|
|
507
|
+
[Unreleased]: https://github.com/yaminbkk/NexusMem/compare/v0.8.0...HEAD
|
|
508
|
+
[0.8.0]: https://github.com/yaminbkk/NexusMem/compare/v0.7.0...v0.8.0
|
|
509
|
+
[0.7.0]: https://github.com/yaminbkk/NexusMem/compare/v0.6.0...v0.7.0
|
|
455
510
|
[0.6.0]: https://github.com/yaminbkk/NexusMem/compare/v0.5.4...v0.6.0
|
|
456
511
|
[0.5.4]: https://github.com/yaminbkk/NexusMem/compare/v0.5.3...v0.5.4
|
|
457
512
|
[0.5.3]: https://github.com/yaminbkk/NexusMem/compare/v0.5.2...v0.5.3
|
package/README.md
CHANGED
|
@@ -24,7 +24,7 @@ exists nowhere else, and it disappears when your terminal scrollback rolls over.
|
|
|
24
24
|
**Contents:** [Try it](#try-it) · [Exact shell capture](#optional-exact-shell-capture) ·
|
|
25
25
|
[Failure → fix chains](#failure--fix-chains-opt-in) · [How retrieval works](#how-retrieval-works) ·
|
|
26
26
|
[Session summaries](#session-summaries-optional-local-model) · [Use it from an agent](#use-it-from-an-agent)
|
|
27
|
-
· [What it costs you](#what-it-costs-you) · [
|
|
27
|
+
· [What it costs you](#what-it-costs-you) · [Staleness & provenance](#staleness--provenance) ·
|
|
28
28
|
[Where it breaks](#where-it-breaks) · [Commands](#commands) · [Cross-project recall](#recall-across-projects)
|
|
29
29
|
· [On disk](#on-disk) · [Development](#development)
|
|
30
30
|
|
|
@@ -48,11 +48,11 @@ Relevant history for: windows spawn failure
|
|
|
48
48
|
readRepoInfo collapsed three unrelated failures into one error: git running and reporting
|
|
49
49
|
the path is not a work tree, git not being installed, and the process failing to spawn at
|
|
50
50
|
all. Dogfooding hit the third case in two separate sessions...
|
|
51
|
-
- 2026-08-09 [
|
|
51
|
+
- 2026-08-09 [authored] README.md — Before a tagged release
|
|
52
52
|
- [ ] Retry on transient process-spawn failures on Windows
|
|
53
53
|
```
|
|
54
54
|
|
|
55
|
-
`[observed]`/`[
|
|
55
|
+
`[observed]`/`[authored]` is the provenance tag (see [Staleness & provenance](#staleness--provenance))
|
|
56
56
|
— a commit is a directly observed event, a doc section is a written claim that could go stale.
|
|
57
57
|
|
|
58
58
|
A commit and a docs section, ranked against each other, inside whatever token budget you gave it.
|
|
@@ -269,19 +269,23 @@ Two things a memory layer needs and this one only partly has: a way to tell an o
|
|
|
269
269
|
guess, and a way to retire a conclusion once something contradicts it. This section is what exists
|
|
270
270
|
and what doesn't.
|
|
271
271
|
|
|
272
|
-
Every node carries a `provenance
|
|
273
|
-
|
|
274
|
-
|
|
275
|
-
|
|
276
|
-
|
|
272
|
+
Every node carries a `provenance`, a four-tier trust hierarchy set once per collector at ingest
|
|
273
|
+
time: `observed` (a commit that landed, a shell command's real exit code) > `authored` (a doc
|
|
274
|
+
section — a human's own written claim) > `recorded` (a conversation turn — verbatim, but talk about
|
|
275
|
+
events rather than the events) > `derived` (a session summary — a model's distillation). The tier is
|
|
276
|
+
shown as a tag on every query result and decays retrieval weight — the lower the trust, the faster a
|
|
277
|
+
node fades from ranking as it ages. The ordering is the design claim; the exact decay ratios are
|
|
278
|
+
judgment calls, not measured optima.
|
|
277
279
|
|
|
278
280
|
```bash
|
|
279
281
|
nexusmem stale
|
|
280
282
|
```
|
|
281
283
|
|
|
282
|
-
Lists `
|
|
283
|
-
a heuristic on age and provenance, not on content. It writes nothing; you decide which
|
|
284
|
-
actually wrong.
|
|
284
|
+
Lists non-`observed` nodes old enough (45+ days by default) that nothing has confirmed they still
|
|
285
|
+
hold — a heuristic on age and provenance, not on content. It writes nothing; you decide which
|
|
286
|
+
candidates are actually wrong. Any candidate the SLM has already flagged (see below) is decorated
|
|
287
|
+
with its standing `likely superseded by` suggestion — reading those costs nothing, so the plain
|
|
288
|
+
command stays instant and offline.
|
|
285
289
|
|
|
286
290
|
```bash
|
|
287
291
|
nexusmem mark-stale <oldNodeId> --supersedes <newNodeId>
|
|
@@ -290,10 +294,27 @@ nexusmem mark-stale <oldNodeId> --supersedes <newNodeId>
|
|
|
290
294
|
Links `newNodeId` as the replacement for `oldNodeId`. The ranker down-weights the old node from then
|
|
291
295
|
on (it stays queryable, just usually loses to its replacement) — nothing is deleted, unlike `forget`.
|
|
292
296
|
|
|
293
|
-
|
|
294
|
-
|
|
295
|
-
|
|
296
|
-
|
|
297
|
+
```bash
|
|
298
|
+
nexusmem stale --check-contradictions
|
|
299
|
+
```
|
|
300
|
+
|
|
301
|
+
For each candidate, finds the most similar newer node (local embedding search) and asks a local SLM
|
|
302
|
+
(Ollama, `qwen2.5:3b` by default) whether it actually contradicts the older one — real content
|
|
303
|
+
comparison, not just age. A match is printed as `likely superseded by <id> <title> -- <reason>`
|
|
304
|
+
under the candidate. Every judgment (either verdict) is memoized, so a judged pair is never sent to
|
|
305
|
+
the model again; nothing else is written — `supersedes` stays yours to set via `mark-stale`.
|
|
306
|
+
|
|
307
|
+
**This also runs automatically during `sync`** — at most 3 new judgments per run (configurable via
|
|
308
|
+
the `contradictions` block in `.nexusmem/config.json`; set `autoCheck: false` to turn it off), only
|
|
309
|
+
when the embedding provider was reachable anyway, and free on repeat syncs thanks to the
|
|
310
|
+
memoization. New and open suggestions show up in the sync summary, `nexusmem status` (a `flagged`
|
|
311
|
+
line), and plain `nexusmem stale`.
|
|
312
|
+
|
|
313
|
+
**What this doesn't do:** it is one small model's yes/no judgment on one older/newer pair, not a
|
|
314
|
+
verified fact — treat a match as a lead to check, not a conclusion. It also only ever compares a
|
|
315
|
+
candidate against nodes *found by embedding similarity*; a contradiction from an unrelated-sounding
|
|
316
|
+
node would never surface. Comprehensive contradiction detection (not just for the pair the vector
|
|
317
|
+
search happens to surface) is still an open problem, and nothing here supersedes a node on its own.
|
|
297
318
|
|
|
298
319
|
## Where it breaks
|
|
299
320
|
|
|
@@ -361,8 +382,9 @@ just how old one is) is still an open problem.
|
|
|
361
382
|
## Commands
|
|
362
383
|
|
|
363
384
|
`init`, `sync`, `query <text>`, `status` (add `--share` for a plain-text summary worth pasting
|
|
364
|
-
somewhere), `projects`, `mcp`, `forget <value>`, `stale
|
|
365
|
-
`mark-stale <nodeId> --supersedes <newNodeId>`, and
|
|
385
|
+
somewhere), `projects`, `mcp`, `forget <value>`, `stale` (add `--check-contradictions` for a local-SLM
|
|
386
|
+
content check, see above), `mark-stale <nodeId> --supersedes <newNodeId>`, and
|
|
387
|
+
`hook install|remove|status`.
|
|
366
388
|
|
|
367
389
|
There are also five dry-run previews (`scan-git`, `scan-diff`, `scan-shell`, `scan-docs`,
|
|
368
390
|
`scan-conversation`)
|