AgentScope-Java is an open-source project. To involve a broader community, we recommend asking your questions in English.
Describe the bug
AutoContextMemory#summaryPreviousRoundMessages implementation and comment inconsistent.
Original comment:
/**
* Summarize all previous rounds of conversation messages before the latest assistant.
*
*
This method finds the latest assistant message and summarizes all conversation rounds
* before it. Each round consists of messages between a user message and its corresponding
* assistant message (typically including tool calls/results and the assistant message itself).
*
*
Example transformation:
* Before: "user1-tools-assistant1, user2-tools-assistant2, user3-tools-assistant3, user4"
* After: "user1-summary, user2-summary, user3-summary, user4"
* Where each summary contains the compressed information from tools and assistant of that round.
*
*
Strategy:
* 1. Find the latest assistant message (this is the current round, not to be summarized)
* 2. From the beginning, find all user-assistant pairs before the latest assistant
* 3. For each pair, summarize messages between user and assistant (including assistant message)
* 4. Replace those messages (including assistant) with summary (process from back to front to avoid index shifting)
*
* @param rawMessages the list of messages to process
* @return true if summary was actually performed, false otherwise
*/
According to 'Summarize all previous rounds of conversation messages before the latest assistant' in comment and code implementation, for 'the 'Example transformation', 'user3-tools-assistant3' will not be summarized. The correct content is as follows:
- Before: "user1-tools-assistant1, user2-tools-assistant2, user3-tools-assistant3, user4"
* After: "user1-summary, user2-summary, user3-tools-assistant3, user4"
AutoContextMemory#summaryPreviousRoundMessages will not summary last <user, assistant> pair, when last <user, assistant> pair has too many messages, it will trigger a large amount of context.
To Reproduce
Steps to reproduce the behavior:
Branch: release/1.0.10
Method: AutoContextMemory#summaryPreviousRoundMessages
- You code
private boolean summaryPreviousRoundMessages(List<Msg> rawMessages) {
if (rawMessages == null || rawMessages.isEmpty()) {
return false;
}
// Step 1: Find the latest assistant message that is a final response (not a tool call)
int latestAssistantIndex = -1;
for (int i = rawMessages.size() - 1; i >= 0; i--) {
Msg msg = rawMessages.get(i);
if (MsgUtils.isFinalAssistantResponse(msg)) {
latestAssistantIndex = i;
break;
}
}
// If no assistant message found, nothing to summarize
if (latestAssistantIndex < 0) {
return false;
}
// Step 2: Find all user-assistant pairs before the latest assistant
// We'll collect them as pairs: (userIndex, assistantIndex)
List<Pair<Integer, Integer>> userAssistantPairs = new ArrayList<>();
int currentUserIndex = -1;
for (int i = 0; i < latestAssistantIndex; i++) {
Msg msg = rawMessages.get(i);
if (msg.getRole() == MsgRole.USER) {
currentUserIndex = i;
} else if (MsgUtils.isFinalAssistantResponse(msg) && currentUserIndex >= 0) {
// Found a user-assistant pair (assistant message is a final response, not a tool
// call)
if (i - currentUserIndex != 1) {
userAssistantPairs.add(new Pair<>(currentUserIndex, i));
}
currentUserIndex = -1; // Reset to find next pair
}
}
// If no pairs found, nothing to summarize
if (userAssistantPairs.isEmpty()) {
return false;
}
log.info(
"Found {} user-assistant pairs to summarize before latest assistant at index {}",
userAssistantPairs.size(),
latestAssistantIndex);
// Step 3: Process pairs from back to front to avoid index shifting issues
boolean hasSummarized = false;
for (int pairIdx = userAssistantPairs.size() - 1; pairIdx >= 0; pairIdx--) {
Pair<Integer, Integer> pair = userAssistantPairs.get(pairIdx);
int userIndex = pair.first();
int assistantIndex = pair.second();
// Messages to summarize: from user to assistant (inclusive of both)
// Include user message for context, but we'll only remove messages after user
int startIndex = userIndex + 1; // Messages to remove start after user
int endIndex = assistantIndex; // Include assistant message in removal
// If no messages between user and assistant (including assistant), skip
if (startIndex > endIndex) {
log.info(
"No messages to summarize between user at index {} and assistant at index"
+ " {}",
userIndex,
assistantIndex);
continue;
}
// Include user message in messagesToSummarize for context, but keep it in the final
// list
List<Msg> messagesToSummarize = new ArrayList<>();
messagesToSummarize.add(rawMessages.get(userIndex)); // Include user message for context
for (int i = startIndex; i <= endIndex; i++) {
messagesToSummarize.add(rawMessages.get(i));
}
log.info(
"Summarizing round {}: user at index {}, messages [{}, {}], totalCount={}"
+ " (includes user message for context)",
pairIdx + 1,
userIndex,
startIndex,
endIndex,
messagesToSummarize.size());
// Step 4: Check if original token count is sufficient for compression
// Skip compression if tokens are below threshold to avoid compression overhead
int originalTokens = TokenCounterUtil.calculateToken(messagesToSummarize);
int threshold = autoContextConfig.getMinCompressionTokenThreshold();
if (originalTokens < threshold) {
log.info(
"Skipping conversation summary for round {}: original tokens ({}) is below"
+ " threshold ({})",
pairIdx + 1,
originalTokens,
threshold);
continue;
}
log.info(
"Proceeding with conversation summary for round {}: original tokens: {},"
+ " threshold: {}",
pairIdx + 1,
originalTokens,
threshold);
// Step 5: Offload original messages if contextOffLoader is available
String uuid = UUID.randomUUID().toString();
offload(uuid, messagesToSummarize);
log.info("Offloaded messages to be summarized: uuid={}", uuid);
// Step 6: Generate summary
Msg summaryMsg = summaryPreviousRoundConversation(messagesToSummarize, uuid);
// Build metadata for compression event
Map<String, Object> metadata = new HashMap<>();
if (summaryMsg.getChatUsage() != null) {
metadata.put("inputToken", summaryMsg.getChatUsage().getInputTokens());
metadata.put("outputToken", summaryMsg.getChatUsage().getOutputTokens());
metadata.put("time", summaryMsg.getChatUsage().getTime());
}
// Record compression event (before removing messages to preserve indices)
recordCompressionEvent(
CompressionEvent.PREVIOUS_ROUND_CONVERSATION_SUMMARY,
startIndex,
endIndex,
rawMessages,
summaryMsg,
metadata);
// Step 7: Remove the messages between user and assistant (including assistant), then
// replace with summary
// Since we're processing from back to front, the indices are still accurate
// for the current pair (indices of pairs after this one have already been adjusted)
// Remove messages from startIndex to endIndex (including assistant, from back to front
// to avoid index shifting)
int removedCount = endIndex - startIndex + 1;
rawMessages.subList(startIndex, endIndex + 1).clear();
// After removal, the position where assistant was is now: assistantIndex - removedCount
// + 1
// But since we removed everything including assistant, we insert summary at the
// position after user
int insertIndex = userIndex + 1;
// Insert summary after user (replacing the removed messages including assistant)
rawMessages.add(insertIndex, summaryMsg);
log.info(
"Replaced {} messages [indices {}-{}] with summary at index {}",
removedCount,
startIndex,
endIndex,
insertIndex);
hasSummarized = true;
}
return hasSummarized;
}
- How to execute
- See error
Expected behavior
According to 'Summarize all previous rounds of conversation messages before the latest assistant' in comment and code implementation, for 'the 'Example transformation', 'user3-tools-assistant3' will not be summarized. The correct content is as follows:
- Before: "user1-tools-assistant1, user2-tools-assistant2, user3-tools-assistant3, user4"
* After: "user1-summary, user2-summary, user3-tools-assistant3, user4"
AutoContextMemory#summaryPreviousRoundMessages will not summary last <user, assistant> pair, when last <user, assistant> pair has too many messages, it will trigger a large amount of context.
Error messages
Detailed error messages.
Environment (please complete the following information):
- AgentScope-Java Version: release/1.0.10
- Java Version: [e.g. 17]
- OS: [e.g. macos]
Additional context
Add any other context about the problem here.
AgentScope-Java is an open-source project. To involve a broader community, we recommend asking your questions in English.
Describe the bug
AutoContextMemory#summaryPreviousRoundMessages implementation and comment inconsistent.
Original comment:
According to 'Summarize all previous rounds of conversation messages before the latest assistant' in comment and code implementation, for 'the 'Example transformation', 'user3-tools-assistant3' will not be summarized. The correct content is as follows:
AutoContextMemory#summaryPreviousRoundMessages will not summary last <user, assistant> pair, when last <user, assistant> pair has too many messages, it will trigger a large amount of context.
To Reproduce
Steps to reproduce the behavior:
Branch: release/1.0.10
Method: AutoContextMemory#summaryPreviousRoundMessages
Expected behavior
According to 'Summarize all previous rounds of conversation messages before the latest assistant' in comment and code implementation, for 'the 'Example transformation', 'user3-tools-assistant3' will not be summarized. The correct content is as follows:
AutoContextMemory#summaryPreviousRoundMessages will not summary last <user, assistant> pair, when last <user, assistant> pair has too many messages, it will trigger a large amount of context.
Error messages
Detailed error messages.
Environment (please complete the following information):
Additional context
Add any other context about the problem here.