Conversation
…cut-gated forgetting
ADR-345's nightly run rejected MincutGatedForgetting partly on a
1,800-2,700x compaction slowdown caused by RuVectorGraphAnalyzer's
per-call full edge-replay into MinCutWrapper's bounded-range instances.
Its own "next research" item 1 named ruvector_mincut::DynamicMinCut as
the untried, lower-level alternative.
Add MincutBackend::{Wrapper, Direct} with a shared k-NN graph builder so
both backends see byte-identical topology; Direct builds a DynamicMinCut
via MinCutBuilder (one exact solve) instead of replaying edges into the
wrapper. Wrapper remains the default; no existing caller's behavior
changes.
Co-Authored-By: claude-flow <ruv@ruv.net>
Claude-Session: https://claude.ai/code/session_01554na6bnFsvgTnQ4mBnX8y
Records the decision, measured evidence, and rejection criteria for MincutBackend::Direct (performance sub-hypothesis accepted; overall MincutGatedForgetting production use remains rejected per ADR-345). Regenerates docs/adr/INDEX.md via scripts/adr-index.mjs. Co-Authored-By: claude-flow <ruv@ruv.net> Claude-Session: https://claude.ai/code/session_01554na6bnFsvgTnQ4mBnX8y
…ct backend Full research report (hypothesis, capability-discovery table, benchmark methodology, raw benchmark output for the scaling/determinism/main/ scale-effectiveness probes, promotion decision, and next-research items) plus a standalone gist article, per the nightly research process. Co-Authored-By: claude-flow <ruv@ruv.net> Claude-Session: https://claude.ai/code/session_01554na6bnFsvgTnQ4mBnX8y
|
Reading that test: I attempted the one permitted re-run to confirm, but the workflow run was still in progress at the time ( Generated by Claude Code |
Hypothesis
Follow-up to ADR-345 (nightly 2026-09-05), which rejected
MincutGatedForgetting(a structural, min-cut-derived eviction signal for agent-memory compaction) on two axes: a 1,800-2,700x compaction slowdown, and a 0.0pp bridge-survival improvement. Its own "Next Research" item 1 namedruvector_mincut::DynamicMinCut, used directly instead of theRuVectorGraphAnalyzerconvenience wrapper, as the specific untried fix for the performance axis.This PR implements and tests exactly that, reusing ADR-345's corpus, hypothesis text, and acceptance thresholds unmodified (no goalpost moves):
Architecture
Added
MincutBackend::{Wrapper, Direct}to the existing feature-gatedgraph_forgetmodule. Both backends build the identical k-NN graph through one shared helper, so the only controlled variable is whichruvector-mincutAPI computes the partition.Wrapperremains the default; no existing caller's behavior changes.Files Changed
crates/ruvector-agent-memory/src/graph_forget.rs:MincutBackendenum,with_backend(), shared graph builder,partition_via_wrapper/partition_via_direct.crates/ruvector-agent-memory/src/lib.rs: re-exportMincutBackend.crates/ruvector-agent-memory/examples/: 4 new examples (mincut_direct_backend_bench,mincut_direct_scaling_probe,mincut_direct_determinism_probe,mincut_direct_scale_effectiveness_probe), registered inCargo.tomlunder the existingmincut-forgetfeature.docs/adr/ADR-346-mincut-direct-backend-for-gated-forgetting.md,docs/adr/INDEX.md(regenerated viascripts/adr-index.mjs).docs/research/nightly/2026-09-17-mincut-direct-backend/{README.md,gist.md}.Benchmark Command & Real Results
Scaling probe (ring k-NN, k=8) vs. ADR-345's own table on the same topology/sizes: n=50 76.8ms→0.708ms (~108x), n=100 481.3ms→1.895ms (~254x), n=200 2,712.9ms→5.466ms (~496x), n=400 11,415.0ms→18.620ms (~613x). Determinism probe (fixed 19-vertex graph, 30 trials): Wrapper gave 15/30 empty/unusable results at 841ms/call; Direct gave 0/30 empty results (1 distinct min-cut value across all 30) at 0.119ms/call.
An exploratory, explicitly non-gating follow-up (
mincut_direct_scale_effectiveness_probe) then asks whether the 0.0pp effectiveness gap was just a small-corpus artifact, now that Direct is cheap enough to test at scale: across 84→1,344 memories (16x), the gap stays at 0.0pp (briefly -6.2pp at n=336). Not a sampling artifact.Acceptance Result
ACCEPT for this PR's registered performance sub-hypothesis (Direct clears the 100x slowdown gate at 28.1-28.5x, vs. Wrapper's 1,569-1,589x; effectiveness numbers are bit-identical between backends as required). REJECT unchanged for the overall
MincutGatedForgettingproduction hypothesis — the bridge-survival gap is still 0.0pp against the required ≥15pp, now confirmed across a 16x corpus-size range, strengthening ADR-345's "global min-cut isolates an outlier, not the intended bridge" explanation.Darwin Result
No automated Darwin/MetaHarness tooling exists in this repository (verified:
npx ruvector harness doctor/status --json— no such executable resolvable;npx metaharness --helpresolves to an unrelated project-scaffolding generator). Framed manually: one generation, two candidates (Wrapperparent,Directchallenger), ADR-345's unmodified acceptance thresholds as the fitness function, one promotion (Directmerged as an opt-in addition;Wrapperretained as the unchanged default; the underlying policy itself stays unpromoted).Flywheel Result
This PR is a Flywheel-style follow-up: it reads ADR-345's raw numbers and named root causes, executes its "Next Research" item 1 without re-deriving anything, and records new evidence (the scale-effectiveness sweep) that materially strengthens one of ADR-345's still-open questions, so a future run doesn't have to re-ask "is the zero effect just a small-sample artifact?" from scratch.
Security Review
No new cryptographic primitive.
MincutBackend::Direct's disconnected-graph-to-empty-partition mapping is a documented correctness/parity choice, not a security control.witnessed_compaction(ADR-345's eviction-witness mechanism) is untouched. No new external dependency —ruvector-mincutwas already an optional dependency under the samemincut-forgetfeature.Main Limitations
ClusterHierarchy::boundary_size, ADR-345's other named alternative, does not exist under that name in this codebase (verified by source inspection) and was not tested;DynamicMinCutwas used instead.ruvector-mincut'sMinCutWrappernon-determinism is not fixed at its source, only routed around for this integration.ruvector-mincut::localkcutmodule) is the next thing to try, not attempted here.Production Recommendation
Merge
MincutBackend::Directas the additive, opt-in improvement it is — it is strictly better thanWrapperon every measured axis (speed, determinism) with no behavior change for existing callers. Do not promoteMincutGatedForgettingitself to a recommended or default compaction policy; the effectiveness gate is unmet independent of backend or corpus size.Research Document, ADR, and Gist
docs/research/nightly/2026-09-17-mincut-direct-backend/README.mddocs/adr/ADR-346-mincut-direct-backend-for-gated-forgetting.mddocs/research/nightly/2026-09-17-mincut-direct-backend/gist.mdTest Plan
cargo build --release -p ruvector-agent-memory --features mincut-forget(clean)cargo test -p ruvector-agent-memory --features mincut-forget(all tests pass, including existinggraph_forgetunit tests unaffected by the new default-Wrapperbackend)cargo fmt -p ruvector-agent-memory -- --check(clean)cargo clippy -p ruvector-agent-memory --features mincut-forget --all-targets(no new warnings)node scripts/adr-index.mjs --check(no duplicate ADR numbers)🤖 Generated with claude-flow
https://claude.ai/code/session_01554na6bnFsvgTnQ4mBnX8y
Generated by Claude Code