siyuan-note/siyuan · error

agent context cannot be compacted enough: current user turn

Error message

agent context cannot be compacted enough: current user turn not found

What it means

currentTurnTail(checkpointMsgs, userEntryID, userMessage) fails to locate the messages belonging to the current user turn in the checkpoint message list, so compactContext returns errContextCannotBeCompacted with "current user turn not found". The runtime expects the pending user entry to correspond to messages at the tail of the checkpoint history; an inconsistency means the compaction tail cannot be reconstructed.

Source

Thrown at kernel/agent/agent.go:788

			estimatedMessages, _ := projectImageMessages(messages)
			if !force && estimateProtocolRequestTokens(model, protocol, estimatedMessages, checkpointMsgs,
				compaction, requestTools) <= inputBudget {
				return false, nil
			}

			coveredEntryCount := 0
			previousSummary := ""
			if compaction != nil {
				coveredEntryCount = compaction.CoveredEntryCount
				previousSummary = compaction.Summary
			}
			candidates := compactionCandidateEntryCounts(sessionEntries, coveredEntryCount, userEntryID)
			if len(candidates) == 0 {
				return false, fmt.Errorf("%w: the current turn is too large", errContextCannotBeCompacted)
			}
			tail, ok := currentTurnTail(checkpointMsgs, userEntryID, userMessage)
			if !ok {
				return false, fmt.Errorf("%w: current user turn not found", errContextCannotBeCompacted)
			}

			nativeResponsesCompaction := util.IsOpenAIResponsesProtocol(protocol) &&
				util.SupportsOpenAIResponsesCompaction(ctx)
			// 原生 compact 无法限制输出长度,覆盖所有已完成轮次,避免 opaque window 返回后仍超出预算。
			selectedCandidateIndex := len(candidates) - 1
			if !nativeResponsesCompaction {
				selectedCandidateIndex = sort.Search(len(candidates), func(i int) bool {
					candidate := candidates[i]
					candidateCheckpointMsgs := checkpointMessagesAfterCompaction(sessionEntries, candidate, tail)
					candidateMessages := checkpointMessagesToOpenAIWithSummary(
						candidateCheckpointMsgs, language, capabilities, nil)
					candidateMessages, _ = projectImageMessages(candidateMessages)
					baseTokens := estimateProtocolRequestTokens(model, protocol, candidateMessages,
						candidateCheckpointMsgs, nil, requestTools)
					return compactionSummaryMinTokens <= inputBudget-baseTokens-compactionSummaryOverhead
				})
			}

View on GitHub (pinned to 8641553a1f)

Solutions

  1. Verify the user entry was recorded before compaction runs (entry ordering/id consistency between session entries and checkpointMsgs)
  2. Restore the session from a consistent backup or start a new session if the files are corrupted
  3. Do not hand-edit session history files
  4. If reproducible, debug currentTurnTail inputs: confirm userEntryID and userMessage match the latest checkpoint messages

Example fix

// before
compact(entries, staleUserEntryID, msg) // id from a previous send attempt
// after
entry := session.AppendUserEntry(msg)
compact(entries, entry.ID, msg) // use the id of the entry actually appended
Defensive patterns

Strategy: validation

Validate before calling

found := false
for _, m := range checkpointMsgs {
    if m.SessionEntryID == userEntryID {
        found = true
        break
    }
}
if !found {
    return fmt.Errorf("userEntryID %s has no matching checkpoint message; refusing to compact", userEntryID)
}

Try / catch

if err := agent.Send(ctx, msg); errors.Is(err, errContextCannotBeCompacted) &&
    strings.Contains(err.Error(), "current user turn not found") {
    // session state is inconsistent; restore from backup or start a new session
}

Prevention

When it happens

Trigger: userEntryID does not match any entry in checkpointMsgs — e.g. the session entry list and the checkpoint message list got out of sync, the user entry was not yet appended, or session/history files were edited or corrupted.

Common situations: Manually editing or restoring session files; a bug or interrupted write leaving checkpoint messages inconsistent with session entries; passing an already-consumed or wrong userEntryID into the compaction path.

Understand the failure class

Background: "This is a bug, please report it": internal invariant violations, unreachable panics, and SNH errors explained — this error's family across 47 libraries.

Related errors


AI-assisted analysis of siyuan-note/siyuan@8641553a1f (2026-09-11). Data as JSON: /api/errors/8345e11eef2fdb8c. Report an issue: GitHub.