fix(compaction): 摘要收缩改按路由价并补齐定价访问路径

ds-review-bot 首轮意见修复:

- 摘要收缩比较改用所选节点的路由价 shadowedRouteTokenCount,修复图片消息启发式价低于带框摘要时压缩被误拒;日志影子价仍为启发式
- DeepSeek 定价经序列化器同一套 access 解析构建句柄与占位文本,消除逐图数十 token 的低估;uncatalogued 分支 JSDoc 指明复现 projectImagesForTextModel 替换
- llm-replay 在加载时拒绝纯文本模型上的 imageRequestTokens 声明
- contextBreakdown 的 README 与 JSDoc 改为等于 heuristicTokens 之和,不再声称等于路由价 surfaceTokens
This commit is contained in:
creatixchu
2026-08-24 19:48:52 +08:00
parent 42164508c8
commit 5183bc2b65
24 changed files with 154 additions and 42 deletions
@@ -4,6 +4,7 @@ import { AttachmentId } from '@deepseek-ai/dsh-attachment'
import BasicCompactionEngine from '@deepseek-ai/dsh-compaction-basic'
import type { BasicCompactionConfig } from '@deepseek-ai/dsh-compaction-basic'
import { selectCompactableRange } from '@deepseek-ai/dsh-compaction-basic/src/region.ts'
import { frameSummary } from '@deepseek-ai/dsh-compaction-basic/src/summarizer.ts'
import type { SummarizationInput, SummaryResult } from '@deepseek-ai/dsh-compaction-basic/src/summarizer.ts'
import { CompactionId, toolPairingBalancedAfter, toolPairingBalancedBefore } from '@deepseek-ai/dsh-compaction'
import {
@@ -1966,6 +1967,33 @@ describe('route-priced image pressure', () => {
expect(range).not.toBeNull()
})
it('accepts a summary larger than the span heuristic when the route price shrinks', async () => {
// A single short image message prices below a framed summary under the
// fixed heuristic but far above it under the route: the shrink comparison
// must ask whether the replacement lowers route pressure.
const ctx = pricedContext(1_000)
const session = imageConversation(1)
const before = ctx.tokenMeter.measure(session)
const imageNode = before.nodes[0]!
const compact = new TestCompactionEngine(ctx, { auto: false })
compact.summary = [{
type: 'text',
text: 'summary text sized between the heuristic and route prices of the shadowed image message, '
+ 'long enough that the fixed heuristic alone would reject it as not smaller '
+ 'while the route-priced comparison accepts the pressure reduction.',
}]
const framed = ctx.tokenMeter.estimateMessage(createUserMessage({
content: frameSummary(compact.summary),
source: { kind: 'plugin', plugin: 'test' },
}))
expect(framed).toBeGreaterThan(imageNode.heuristicTokens)
expect(framed).toBeLessThan(imageNode.tokens)
const result = await compact.compactRegion(imageNode.seq, imageNode.seq, agent(session), SIGNAL)
expect(result.shadowedSeqs).toEqual([imageNode.seq])
expect(result.shadowedTokenCount).toBe(imageNode.heuristicTokens)
})
it('triggers pressure compaction from routed visual tokens and logs heuristic shadow prices', async () => {
const ctx = pricedContext(1_000)
const session = imageConversation()