Repository navigation
Conversation
LangchainTool only took tool.func or tool.coroutine for a StructuredTool. A plain langchain Tool fell through to Tool._run, whose keyword-only config parameter became the tool's only required argument, so the model was asked for config and every call failed. Treat a plain Tool the same way: use func, then coroutine, fall back to an overridden _run, and reject a Tool that has none of them. Fixes google#8035
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.
Link to Issue or Description of Change
1. Link to an existing issue (if applicable):
LangchainToolasks the model forconfigwhen it wraps a plain langchainTool#8035Problem:
LangchainTool.__init__only takestool.func/tool.coroutinefor aStructuredTool.ToolandStructuredToolare siblings (both subclassBaseTool), so a plainlangchain_core.tools.Toolskips that branch and falls back toTool._run(self, *args, config: RunnableConfig, run_manager=None, **kwargs).FunctionToolbuilds the declaration from that signature:run_manageris ignored and*args/**kwargsare dropped, leavingconfigas the only required parameter. The model is asked forconfig, never for the wrapped function's real arguments, and every call fails the mandatory-argument check.Solution:
Give a plain
Toolthe same resolution theStructuredToolbranch already uses:tool.func;tool.coroutine(async-only tools);_run, keep using_run(unchanged behavior);ValueError, asStructuredToolalready does.The change is the
isinstancecheck plus the "_runnot overridden" check, which now compares against bothStructuredTool._runandTool._run.One intentional behavior change:
Tool(func=None)with no coroutine and no_runoverride used to construct but could never run (it declaredconfigand every call failed). It now raises at construction, matchingStructuredTool.Testing Plan
Unit Tests:
New tests in
tests/unittests/integrations/langchain/test_langchain_tool.py. Following the review on #8036, they assert the declared parameters the model sees, not only therun_asyncresult:test_plain_tool_declares_func_params_not_config["text"], required["text"], noconfigtest_plain_tool_run_async_calls_funcrun_asyncreturns the function's resulttest_plain_tool_with_only_coroutine_worksTooldeclares["text"]and runstest_tool_subclass_overriding_run_uses_run_runoverride still usedtest_plain_tool_without_func_or_coroutine_raisesValueErrormatchingmust have a funcWithout the fix (src change stashed), the new tests fail as expected and the guard passes:
With the fix:
pre-commit runon both files passes (ruff, isort, pyink, addlicense, codespell, ADK compliance checks).Manual End-to-End (E2E) Tests:
The issue's repro script (no model or API key needed), Python 3.11.18, langchain-core 1.8.0:
Before:
After:
Checklist