Repository navigation
Replies: 4 comments 6 replies
|
Thanks for the proposal. DeerFlow already moves tool outputs over 12k characters into files and keeps only a summary with the head and tail in context. Pruning older outputs later rewrites the earlier prompt prefix and breaks provider caching, so it can cost more on cache-priced models even with fewer tokens. Could you first share a paired comparison on the same tasks, with task success and cache-aware cost? |
|
For reference, we ran a paired test on long DeerFlow runs (DeepSeek Flash, 4 task pairs) that changed only how much history compaction keeps. Keeping less cut cumulative input by about 9%, yet the paired cost median was 0.995x, and 67 to 76% of input tokens were cache hits in both arms. One of the four pairs also regressed: the run with less context wrote a wrong main conclusion while Goal still marked it achieved. It is a small sample on one model, but it is why we would want task success and cache-aware cost before pruning more. |
|
Quick follow-up @Totoro-qaq — your point about prompt cache invalidation got me curious, so after my last reply I went back to inspect our raw I found a really interesting architectural nuance in how 1. Per-Turn Pruning vs. Compaction-Time PiggybackingWhen I simulated per-turn rolling pruning (mutating older tool outputs on regular turns), it 100% confirmed your warning: even though raw input tokens dropped, rewriting However, in our implementation,
2. Why the
|
| Live API Task Pair | Arm | Compactions | Compaction Turn cache_read |
Turn 3 cache_read (Hit %) |
Post-Compaction Cache Hit % | Total Cache Miss Tokens (incl. summary) | Cache-Aware Cost Ratio ($0.028 hit / $0.28 miss) | Conclusion Accuracy |
|---|---|---|---|---|---|---|---|---|
| Pair 1: 30-File Refund Audit | Baseline (prune=False) |
2 | 4,352 (38.1%) |
4,352 (38.5%, re-compacted) |
55.9% | 20,587 | 1.000x |
8/8 (100%) |
| Pair 1: 30-File Refund Audit | Compaction-Piggybacked | 1 | 4,352 (52.3%) |
9,728 (84.3%) |
74.9% (+19.0%) | 9,888 (-52.0%) | 0.549x |
8/8 (100%) |
| Pair 2: 12-Batch SKU Reconcile | Baseline (prune=False) |
2 | 4,352 (37.8%) |
4,352 (38.7%, re-compacted) |
55.9% | 20,585 | 1.000x |
5/5 (100%) |
| Pair 2: 12-Batch SKU Reconcile | Compaction-Piggybacked | 1 | 4,352 (51.7%) |
9,728 (84.8%) |
74.9% (+19.0%) | 9,956 (-51.6%) | 0.551x |
5/5 (100%) |
| Pair 3: Microservice 502 RCA | Baseline (prune=False) |
2 | 4,352 (39.9%) |
4,352 (39.9%, re-compacted) |
56.7% | 19,697 | 1.000x |
4/4 (100%) |
| Pair 3: Microservice 502 RCA | Compaction-Piggybacked | 1 | 4,352 (54.4%) |
9,472 (85.1%) |
75.8% (+19.1%) | 9,353 (-52.5%) | 0.545x |
4/4 (100%) |
(Across the broader 6-task 15-turn study, piggybacked compaction pruning raised post-compaction cache hit rate from 71.7% → 89.9%, cut cache-miss tokens by 66.7%, reduced cache-aware cost median to 0.648x [4x discount] / 0.506x [10x discount], and retained 28/28 ground-truth facts.)
I'm still completely happy to keep this tabled as we discussed! Just wanted to share the numbers since you asked for a paired cache-aware comparison earlier — and if you think an opt-in (prune_tool_outputs: false by default) compaction-only pass is worth having for tool-heavy runs, I'd be glad to submit a minimal PR anytime. Either way, thanks again for pushing me to measure the cache mechanics properly!
|
@Yakyou7 Saw your comment on #7884 — welcome aboard! That offline memory vs. project-context comparison is a great slice to start with. Following the deterministic offline pattern in backend/scripts/benchmark/deermem_scope_isolation (with pinned fixtures and no live model calls required) fits well here. For the first pass, I'd prioritize three checks: 1.Scope isolation between project context (instructions / document shelf) and global user/agent DeerMem facts across unrelated threads; |
Uh oh!
There was an error while loading. Please reload this page.
Motivation & Problem Statement
In long-horizon autonomous tasks (such as iterative code generation, deep file tree searches, and log diagnostics), tool executions frequently generate massive transient outputs (e.g., thousands of lines from
cat, largegit diffoutputs, or multi-step browser DOM dumps).While
SummarizationMiddlewareeffectively summarizes earlier conversation history when reaching the token threshold, we frequently observe two persistent friction points in extended sessions:Proposed Solution
We propose enhancing
SummarizationMiddlewarewith turn-aware ephemeral tool output pruning:Turn-Aware Execution Grouping:
ToolMessage.tool_call_idback to the initiatingAIMessageto group parallel tool executions into discrete logical turns.keep_recent_tool_turns(default 2) guarantees that all parallel calls in the most recent working steps remain 100% intact.Multimodal & Structured Content Block Pruning:
_prune_tool_message_contenttransparently handles bothstrand structuredlist[dict]payloads.... [Output truncated: X chars total, tool=...]) and preserving non-text blocks (such asimage_url) untouched.response_metadata,artifact, andadditional_kwargsfor downstream auditability.Defensive Dynamic Bounding & Metric Ingestion:
min(120, max(20, max_chars // 2))) to prevent reverse string expansion on low limits.usage_metadatavalues in token-budget evaluation.Impact & Benchmark
prune_tool_outputs: true), with zero external dependencies.Current Status
We have implemented this design with complete unit test coverage (parallel tool calls, multimodal structured blocks, dynamic prefix bounds, and malformed token handling).
We would love to hear feedback from @willem-bd, @Totoro-qaq, and the community. If the direction aligns with the project goals, I'd be more than happy to open a focused, reviewable PR!
All reactions