[BUG] Bedrock streaming drops native tool calls, so the tool never runs
Nobody has claimed this yet.
- Dominant language
- Python
- Stars
- 58.8k
- Forks
- 8.5k
- Avg merge
- 1d 15h
- Merged PRs (30d)
- 109
Description
Description
With a Bedrock model and streaming on (LLM(..., stream=True), or Crew(stream=True)), native tool calls are dropped. The tool never runs, and the task's answer becomes "I apologize, but I couldn't generate a response. Please try again." No error is raised.
The agent executor calls the LLM with available_functions=None and runs the returned tool calls itself. _handle_converse returns the tool uses in that case, but _handle_streaming_converse and _ahandle_streaming_converse only use a tool call when available_functions is set, then throw it away. The stream has no text, so the empty-content fallback string is returned as the final answer.
Steps to Reproduce
- Create an agent with a Bedrock LLM (
stream=True) and one tool. - Mock
converse_streamto return atoolUseblock, then a text answer on the next call. - Kick off a crew with one task for that agent.
Expected behavior
Same as stream=False: the tool runs and the crew returns the model's answer.
Screenshots/Code snippets
stream=False tool ran with=['Paris'] final answer='It is sunny in Paris.'
stream=True tool ran with=[] final answer="I apologize, but I couldn't generate a response. Please try again."
The Converse stream events are the same shape as _make_tool_use_stream() in tests/llms/bedrock/test_bedrock_streaming_tool_args.py.
Operating System
macOS
Python Version
3.12
crewAI Version
1.15.21 (main at 894898f)
crewAI Tools Version
not used
Virtual Environment
uv venv
Evidence
Non-streaming returns the calls at bedrock/completion.py:741-752. The streaming handlers only use them under if available_functions: (sync at 1096, async at 1707), and the executor always passes available_functions=None (experimental/agent_executor.py:1567). #6150 fixed the streamed arguments, but its tests always pass available_functions, so this path isn't covered.
Possible Solution
When available_functions is empty, collect the parsed tool uses in the streaming handlers and return them after the stream ends, the way the non-streaming path does. I have a fix with tests and will open a PR.
Additional context
This issue was written with AI assistance (Claude Code). I can't add the llm-generated label as an outside contributor; could a maintainer add it?
Contributor guide
First steps
- Read the whole issue, then the project's contributing guide.
- Comment on the issue to say you are picking it up — it saves two people doing the same work.
- Fork the repository and make your change on a branch.
- Open a pull request that references the issue number.
Research direction
Start in bedrock/completion.py at the streaming handlers around lines 1096 and 1707, then compare their behavior with the non-streaming path at lines 741-752 and the executor call in experimental/agent_executor.py:1567. Use the Converse stream shape from tests/llms/bedrock/test_bedrock_streaming_tool_args.py and verify both sync and async streaming return tool uses when available_functions is None, then confirm the tool runs and the final answer matches the non-streaming case.
Written by the indexing model from the issue text.
Assessment
- Tech stack
- aws, python
- Domain
- ai, backend-api-design, testing-qa
- Issue type
- Bug
- Difficulty
- 3/5
- Estimated time
- 1-2 days
- Activity status
- Active
- Clarity
- Clearly specified
- Newbie friendliness
- 68/100