Skip to content

Detect changes in hosted content types in compaction contentEqual - #1007

Open
PratikDhanave (PratikDhanave) wants to merge 1 commit into
microsoft:mainfrom
PratikDhanaveFork:compaction-equal-hosted-content-types
Open

Detect changes in hosted content types in compaction contentEqual#1007
PratikDhanave (PratikDhanave) wants to merge 1 commit into
microsoft:mainfrom
PratikDhanaveFork:compaction-equal-hosted-content-types

Conversation

@PratikDhanave

Copy link
Copy Markdown
Contributor

Problem

contentEqual (agent/compaction/equality.go) is the change-detection predicate that MessageIndex.Update uses (via contentsEqual/messageContentEqual) to locate the already-processed prefix, and that containsMessageByContent uses for source attribution. Its switch handles text/reasoning/data/uri/error/function-call/function-result/hosted-file and returns true (equal) for everything else.

So two messages that differ only in a registered hosted content type — MCPServerToolCallContent, MCPServerToolResultContent, CodeInterpreterToolCallContent, CodeInterpreterToolResultContent, or UsageContent — are reported equal. MessageIndex.Update then treats the changed message as unchanged and does not rebuild, preserving stale group/exclusion state and mis-locating the prefix boundary. The existing TestMessageIndexUpdate_MatchesKnownContentTypes encodes the intent that any differing value must trigger a rebuild; the default violated it for these types.

Fix

Add explicit equality cases for the hosted content types the framework actually produces, comparing their identity fields (recursing into Outputs/Inputs via the existing contentsEqual, and reflect.DeepEqual for UsageDetails). The default intentionally stays return true so a genuinely new, forward-compatible content type does not force an index rebuild — only the known hosted types get precise comparison.

Test

Extends TestMessageIndexUpdate_MatchesKnownContentTypes with rows for each hosted type: identical values still preserve the index; differing Arguments/Outputs/Inputs/usage now correctly rebuild. The differing rows fail before the fix (treated as equal) and pass after.

contentEqual is the change-detection predicate MessageIndex.Update uses to
locate the already-processed prefix. Its switch handled text/reasoning/data/
uri/error/function-call/function-result/hosted-file and returned true (equal)
for everything else. So two messages differing only in an
MCPServerToolCall/Result, CodeInterpreterToolCall/Result, or UsageContent were
treated as equal, and Update would not rebuild - preserving stale group and
exclusion state and mis-locating the prefix boundary.

Add explicit equality cases for the hosted content types the framework
produces (recursing into Outputs/Inputs via contentsEqual, DeepEqual for
UsageDetails). The default stays 'equal' so a genuinely new, forward-compatible
content type still does not force a rebuild.
Copilot AI lite review requested due to automatic review settings September 6, 2026 04:55
@github-actions github-actions Bot added area:agent Changes files in the agent area size:small At most 30 changed lines across at most 2 files pending-auto-risk Automatic risk classification is in progress labels Sep 6, 2026

Copilot AI left a comment

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

🟡 Changes recommended

The new contentsEqual(leftContent.Outputs/Inputs, ...) calls use message.Contents where contentsEqual expects []message.Content, which will not compile without explicit slice conversions.

Once you've addressed the issues Copilot identified, you can request another Copilot review.

Pull request overview

This PR fixes change detection in agent/compaction by teaching contentEqual how to compare several hosted/registered content types that were previously treated as equal via the default branch, which could cause MessageIndex.Update to preserve stale indexing state when hosted tool/usage content changes.

Changes:

  • Added explicit equality handling for MCPServerTool*, CodeInterpreterTool*, and UsageContent in contentEqual.
  • Kept default: return true for forward-compatible unknown content types, while ensuring known hosted types are compared precisely.
  • Extended TestMessageIndexUpdate_MatchesKnownContentTypes with new rows covering these hosted types.
File summaries
File Description
agent/compaction/equality.go Adds explicit equality cases for hosted tool-call/tool-result, code-interpreter, and usage content in contentEqual.
agent/compaction/equality_test.go Extends the existing compaction equality/update test table with cases for the hosted content types.
Review details

Suppressed comments (1)

agent/compaction/equality.go:87

  • Inputs/Outputs are message.Contents, but contentsEqual takes []message.Content; these calls need an explicit conversion to avoid a compile error.
	case *message.CodeInterpreterToolCallContent:
		rightContent := right.(*message.CodeInterpreterToolCallContent)
		return leftContent.CallID == rightContent.CallID && contentsEqual(leftContent.Inputs, rightContent.Inputs)
	case *message.CodeInterpreterToolResultContent:
		rightContent := right.(*message.CodeInterpreterToolResultContent)
		return leftContent.CallID == rightContent.CallID && contentsEqual(leftContent.Outputs, rightContent.Outputs)
  • Files reviewed: 2/2 changed files
  • Comments generated: 1
  • Review effort level: Lite

💡 Add a code-review agent skill or configure MCP servers for context-aware, tailored reviews. Learn more in the docs.

Comment on lines +79 to +81
return leftContent.CallID == rightContent.CallID && leftContent.Name == rightContent.Name &&
leftContent.ServerName == rightContent.ServerName && leftContent.Error == rightContent.Error &&
contentsEqual(leftContent.Outputs, rightContent.Outputs)
@github-actions

github-actions Bot commented Sep 6, 2026

Copy link
Copy Markdown
Contributor

Scope: internal-only

Changed Go contract: None. contentEqual, messageContentEqual, contentsEqual, and errorsEqual in agent/compaction/equality.go are all unexported. No exported types, functions, methods, fields, options, or documented behavior in agent/compaction's public surface change as a result of this PR.

Upstream evidence reviewed: Not applicable — this PR only extends an existing unexported switch in contentEqual with explicit comparison cases for *message.MCPServerToolCallContent, *message.MCPServerToolResultContent, *message.CodeInterpreterToolCallContent, *message.CodeInterpreterToolResultContent, and *message.UsageContent, following the exact same pattern already used for the adjacent *message.FunctionResultContent/*message.HostedFileContent cases in the same function. It corrects a bug (these hosted types previously fell through to the catch-all return true) rather than introducing new behavior, naming, or defaults that would require comparison against .NET/Python.

Result: out of scope — this is a self-contained internal bugfix restoring intended change-detection semantics within MessageIndex.Update's existing prefix-matching logic (already exercised by TestMessageIndexUpdate_MatchesKnownContentTypes). No public API or cross-language-observable behavior is added or altered, so no parity comparison applies. No public-api-change label needed.

Warning

Firewall blocked 2 domains

The following domains were blocked by the firewall during workflow execution:

  • github.com
  • patchdiff.githubusercontent.com

To allow these domains, add them to the network.allowed list in your workflow frontmatter:

network:
  allowed:
    - defaults
    - "github.com"
    - "patchdiff.githubusercontent.com"

See Network Configuration for more information.

Generated by Go API Consistency Review Agent · copilot · auto · 31.2 AIC · ⌖ 8.7 AIC · ⊞ 9.5K ·

@github-actions github-actions Bot added risk:medium Contained production impact requiring normal review depth and removed pending-auto-risk Automatic risk classification is in progress labels Sep 6, 2026
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

area:agent Changes files in the agent area risk:medium Contained production impact requiring normal review depth size:small At most 30 changed lines across at most 2 files

Projects

None yet

Development

Successfully merging this pull request may close these issues.

2 participants