Skip to content

Python: fix: preserve explicit null tool arguments - #5997

Closed
Yufeng He (he-yufeng) wants to merge 1 commit into
microsoft:mainfrom
he-yufeng:fix/preserve-null-tool-arguments
Closed

Python: fix: preserve explicit null tool arguments#5997
Yufeng He (he-yufeng) wants to merge 1 commit into
microsoft:mainfrom
he-yufeng:fix/preserve-null-tool-arguments

Conversation

@he-yufeng

Copy link
Copy Markdown
Contributor

Summary

  • preserve explicitly provided null tool arguments after Pydantic validation
  • cover both direct FunctionTool.invoke() and automatic function-call execution
  • keep the existing exclude_none behavior for fields that were not explicitly supplied

Fixes #5934.

Validation

python -m pytest tests/core/test_tools.py::test_tool_invoke_preserves_required_nullable_argument tests/core/test_function_invocation_logic.py::test_base_client_with_function_calling_preserves_null_arguments -q -p no:cacheprovider --basetemp .tmp\pytest-null-args
python -m pytest tests/core/test_tools.py -q -p no:cacheprovider --basetemp .tmp\pytest-tools
python -m ruff check packages/core/agent_framework/_tools.py packages/core/tests/core/test_tools.py packages/core/tests/core/test_function_invocation_logic.py
python -m ruff format --check packages/core/agent_framework/_tools.py packages/core/tests/core/test_tools.py packages/core/tests/core/test_function_invocation_logic.py
python -m py_compile packages/core/agent_framework/_tools.py packages/core/tests/core/test_tools.py packages/core/tests/core/test_function_invocation_logic.py
python -m pyright packages/core/agent_framework/_tools.py packages/core/tests/core/test_tools.py packages/core/tests/core/test_function_invocation_logic.py

Copilot AI review requested due to automatic review settings May 21, 2026 09:09
@moonbox3 Evan Mattson (moonbox3) added the python Usage: [Issues, PRs], Target: Python label May 21, 2026
@github-actions github-actions Bot changed the title fix: preserve explicit null tool arguments Python: fix: preserve explicit null tool arguments May 21, 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.

Pull request overview

This PR fixes a Python tool-invocation bug where explicitly provided null/None arguments were being dropped after Pydantic validation, causing required-but-nullable tool parameters to be omitted (notably in auto function-calling flows).

Changes:

  • Introduces _dump_tool_arguments() to keep exclude_none=True behavior while re-including explicitly-supplied None fields.
  • Updates FunctionTool.invoke() and the auto function-call execution path to use _dump_tool_arguments().
  • Adds regression tests covering both direct FunctionTool.invoke() and automatic function-call execution.

Reviewed changes

Copilot reviewed 3 out of 3 changed files in this pull request and generated 1 comment.

File Description
python/packages/core/agent_framework/_tools.py Adds _dump_tool_arguments() and uses it in tool invocation and auto function-call execution to preserve explicit null arguments.
python/packages/core/tests/core/test_tools.py Adds a regression test ensuring direct invoke() preserves explicitly provided None for a required nullable parameter.
python/packages/core/tests/core/test_function_invocation_logic.py Adds a regression test ensuring auto function calling preserves null arguments from model-generated function calls.

Comment on lines +242 to +243
for name in include_none_from if include_none_from is not None else model.model_fields_set:
if getattr(model, name, None) is None:
@moonbox3

Copy link
Copy Markdown
Contributor

Thanks for working on this, but we're going with #5944 - same root cause, but it handles the fix recursively, which matters since exclude_none=True itself recurses (nested cases like options.unit = null would still be dropped here).

Also worth flagging for next time: the getattr(model, name, None) is None check (Copilot caught this too) will re-inject any unknown key as None, since getattr returns None for missing attributes, so extra keys get forwarded as unexpected kwargs. Iterating model.model_fields_set directly avoids that.

Appreciate the effort as the diagnosis was spot on. Closing in favor of #5944.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

python Usage: [Issues, PRs], Target: Python

Projects

None yet

Development

Successfully merging this pull request may close these issues.

Python: [Bug]: Auto function calling removes null arguments

3 participants