Repository navigation
fix(items): strip output-only created_by when replaying model output as input - #4308
Merged
Merged
Conversation
…as input ModelResponse.to_input_items() replays each output item back as a Responses API input item. Several output item types (apply_patch/shell calls and the function/custom/computer tool-call outputs) carry a server-assigned created_by field that is not part of the input-item schema. The replay sanitizer only stripped it for tool_search items, so those other types leaked created_by back to the API on replay. Strip created_by for every replayed item, matching the existing tool_search behavior and the resolution-time stripping already done for shell/apply_patch calls. created_by is never read by SDK logic, so dropping it is safe.
seratch
requested changes
Aug 8, 2026
seratch
left a comment
Member
There was a problem hiding this comment.
One supported Responses shape is still left unsanitized: each entry in shell_call_output.output can carry its own output-only created_by. The current helper removes only the top-level field, so ModelResponse.to_input_items() still sends input[i].output[j].created_by. The normal runner path already removes both levels in turn_resolution.py.
Please sanitize the nested shell output chunks as well without mutating the original mapping input, and add a regression test covering both top-level and nested created_by. Once the replayed request contains neither field, this should be ready for another review.
…hunks shell_call_output carries created_by both at the item level and inside each chunk of its output list. The replay sanitizer only removed the top-level field, so ModelResponse.to_input_items() still leaked output[j].created_by. Rebuild the output list with fresh chunk copies (no mutation of the caller's original mapping), matching the two-level stripping the runner already does in turn_resolution.
seratch
approved these changes
Aug 9, 2026
seratch
enabled auto-merge (squash)
August 9, 2026 04:01
Member
|
@hsusul Can you resolve the typecheck error? |
auto-merge was automatically disabled
August 9, 2026 04:32
Head branch was pushed to by a user without write access
seratch
enabled auto-merge (squash)
August 9, 2026 04:54
6 of 8 tasks
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
Add this suggestion to a batch that can be applied as a single commit.This suggestion is invalid because no changes were made to the code.Suggestions cannot be applied while the pull request is closed.Suggestions cannot be applied while viewing a subset of changes.Only one suggestion per line can be applied in a batch.Add this suggestion to a batch that can be applied as a single commit.Applying suggestions on deleted lines is not supported.You must change the existing code in this line in order to create a valid suggestion.Outdated suggestions cannot be applied.This suggestion has been applied or marked resolved.Suggestions cannot be applied from pending reviews.Suggestions cannot be applied on multi-line comments.Suggestions cannot be applied while the pull request is queued to merge.Suggestion cannot be applied right now. Please check back later.
Summary
ModelResponse.to_input_items()replays each model output item back as a Responses API input item. Several output item types carry a server-assigned, output-onlycreated_byfield that is not part of the input-item schema:apply_patch_callandshell_call(supportedApplyPatchTool/ShellToolcalls)function_call_output,custom_tool_call_output,computer_call_output(tool-call outputs)tool_search_call/tool_search_outputThe replay sanitizer in
_output_item_to_input_itemonly strippedcreated_byfor the twotool_searchtypes, so every other type leakedcreated_bystraight back to the API on replay.created_byis not accepted by any input-item param in the OpenAI SDK schema, and the SDK already strips it at resolution time for shell/apply_patch calls (turn_resolution.py) and for tool_search (_tool_search_item_to_input_item). The directModelResponse.to_input_items()replay path bypassed that resolution-time stripping, leaving the field in place.Fix: strip
created_byfor every replayed item in_output_item_to_input_item, generalizing the existing tool_search behavior.created_byis never read by any SDK logic (it is only ever popped), so dropping it on replay is safe.Before:
After:
The behavior is otherwise unchanged: items are still converted via the same
dict(...)/model_dump(exclude_unset=True)logic, and theAgentsExceptionfallback for unexpected types is preserved. The only caller affected isModelResponse.to_input_items(); the two other callers (_fingerprint_for_tracker,_anonymous_tool_search_fingerprintinoai_conversation.py) only passtool_searchitems, which already routed through the created_by-stripping branch.Test plan
test_to_input_items_strips_created_by_for_non_tool_search_itemsintests/test_items_helpers.py, which builds anapply_patch_calland afunction_call_outputoutput item withcreated_byset and asserts the field is dropped on replay. It fails onmain(leakscreated_by) and passes with this change.test_to_input_items_for_tool_search_strips_created_byand all otherto_input_itemsround-trip tests still pass.uv run pytest tests/test_items_helpers.py→ 36 passeduv run pytest tests/test_items_helpers.py tests/memory tests/test_agent_runner.py tests/test_run_state.py tests/test_server_conversation_tracker.py tests/test_programmatic_tool_calling.py→ 903 passeduv run ruff format --checkanduv run ruff check→ cleanuv run python .github/scripts/check_optional_truthiness.py src/agents→ cleanuv run mypy src/agents/items.py→ Successuv run pyright src/agents/items.py tests/test_items_helpers.py→ 0 errorsNot run: the full test matrix and integration/coverage profiles (they require provider credentials / live services, which are unrelated to this change).
Issue number
N/A — no existing issue.
Checks
.agents/skills/code-change-verification/scripts/run.sh/reviewbefore submitting this PR