Skip to content

Fix: drop trailing assistant message when rstrip leaves it empty - #8029

Open
Mayuri (mayuriphad) wants to merge 2 commits into
microsoft:mainfrom
mayuriphad:fix/issue-7768-rstrip-empty-assistant-message
Open

Fix: drop trailing assistant message when rstrip leaves it empty#8029
Mayuri (mayuriphad) wants to merge 2 commits into
microsoft:mainfrom
mayuriphad:fix/issue-7768-rstrip-empty-assistant-message

Conversation

@mayuriphad

Copy link
Copy Markdown

Fixes #7768

Root cause

_rstrip_last_assistant_message() is documented as removing the last assistant message when it is empty, but it only called .rstrip() on the content and left the (now possibly empty) message in the list. When the trailing AssistantMessage.content was whitespace-only, this produced an empty-string content block, which the Anthropic API rejects (text content blocks must be non-empty).

Fix

After stripping, if the content becomes an empty string, drop the message entirely — matching the function's documented behavior. Non-empty trailing assistant messages are still only whitespace-stripped, preserving the existing "prefill" behavior and pre-existing passing tests. Same fix applied to both the Anthropic and OpenAI clients, which share an identical copy of this helper.

Verification

Added regression tests in both test_anthropic_model_client.py and test_openai_model_client.py. Ran the full local suite: all pre-existing and new tests pass (unrelated failures due to missing OPENAI_API_KEY in this environment, confirmed unrelated via traceback inspection).

…rosoft#7768)

_rstrip_last_assistant_message() is documented as removing the last
assistant message when it is empty, but it only called .rstrip() on
the content and left the (now possibly empty) message in place. When
the last AssistantMessage content was whitespace-only, this produced
an empty-string content block, which the Anthropic API rejects (text
content blocks must be non-empty).

Now, after stripping, if the content becomes an empty string the
message is dropped from the returned list, matching the function's
documented behavior. Non-empty trailing assistant messages are still
only whitespace-stripped, preserving existing prefill behavior and
the pre-existing passing tests.

Same fix applied to both the Anthropic and OpenAI clients, which
share an identical copy of this helper.

Fixes microsoft#7768
Copilot AI lite review requested due to automatic review settings August 7, 2026 09:08

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.

Pull request overview

This PR fixes a bug in autogen-ext where _rstrip_last_assistant_message() could leave a trailing AssistantMessage in the history with content == "" after .rstrip(). That empty assistant content can be rejected by Claude/Anthropic message validation, so the helper now removes the assistant message entirely when stripping results in an empty string.

Changes:

  • Update _rstrip_last_assistant_message() in both the Anthropic and OpenAI clients to (a) handle empty messages safely and (b) drop the trailing assistant message if rstrip() produces "".
  • Add regression tests covering whitespace-only trailing assistant messages for both clients.

Reviewed changes

Copilot reviewed 4 out of 4 changed files in this pull request and generated no comments.

File Description
python/packages/autogen-ext/src/autogen_ext/models/openai/_openai_client.py Drops trailing assistant message when rstrip() leaves empty content (and avoids messages[-1] on empty input).
python/packages/autogen-ext/src/autogen_ext/models/anthropic/_anthropic_client.py Same helper fix applied to Anthropic client implementation.
python/packages/autogen-ext/tests/models/test_openai_model_client.py Adds regression test ensuring whitespace-only trailing assistant message is removed.
python/packages/autogen-ext/tests/models/test_anthropic_model_client.py Adds regression test ensuring whitespace-only trailing assistant message is removed.

Copy link
Copy Markdown

Choose a reason for hiding this comment

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

Correct — dropping a last assistant message that becomes empty after rstrip avoids the API rejection of empty text blocks, and guarding on a non-empty list fixes the prior index error. Two small notes: mutating messages then removing it changes the list identity returned, which is fine, but the same logic is now duplicated across the Anthropic and OpenAI clients — worth extracting the shared helper so the behavior cannot diverge; and confirm stripping affects only the trailing message, never an interleaved one.

@mayuriphad

Copy link
Copy Markdown
Author

@microsoft-github-policy-service agree

Addresses review feedback on microsoft#8029: the empty-trailing-assistant-message
handling was duplicated identically across the Anthropic and OpenAI
clients, risking divergence over time (the same codebase already has one
such duplicated helper, normalize_stop_reason, that diverged when only
one client was updated to import the shared version).

Moved the logic to autogen_ext.models._utils.rstrip_last_assistant_message
as a plain function, matching the existing _utils pattern used by
normalize_stop_reason and parse_r1_content, and updated both clients and
their tests to use it.

Also added a regression test confirming the strip only affects the
trailing message, not interleaved assistant messages earlier in the
sequence.
Mayuri (mayuriphad) pushed a commit to mayuriphad/autogen that referenced this pull request Aug 8, 2026
Addresses review feedback on microsoft#8029: the empty-trailing-assistant-message
handling was duplicated identically across the Anthropic and OpenAI
clients, risking divergence over time (the same codebase already has one
such duplicated helper, normalize_stop_reason, that diverged when only
one client was updated to import the shared version).

Moved the logic to autogen_ext.models._utils.rstrip_last_assistant_message
as a plain function, matching the existing _utils pattern used by
normalize_stop_reason and parse_r1_content, and updated both clients and
their tests to use it.

Also added a regression test confirming the strip only affects the
trailing message, not interleaved assistant messages earlier in the
sequence.

Co-Authored-By: Claude Sonnet 5 <noreply@anthropic.com>
@mayuriphad
Mayuri (mayuriphad) force-pushed the fix/issue-7768-rstrip-empty-assistant-message branch from 19afb96 to 0125134 Compare August 9, 2026 17:06
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

_rstrip_last_assistant_message only strips trailing whitespace from the content — it does not remove the assistant message.

4 participants