Skip to content

adds mcp cleanup support for bedrock models - #4573

Merged
akshaydeo merged 2 commits into
devfrom
06-20-adds_mcp_cleanup_support_for_bedrock_models
Jun 20, 2026
Merged

adds mcp cleanup support for bedrock models#4573
akshaydeo merged 2 commits into
devfrom
06-20-adds_mcp_cleanup_support_for_bedrock_models

Conversation

@akshaydeo

@akshaydeo akshaydeo commented Jun 20, 2026

Copy link
Copy Markdown
Contributor

Summary

Fixes a regression introduced in v1.5.0 (issue closes #3795) where a /v1/responses request carrying a Bifrost-hosted mcp server tool alongside function tools would fail with "tool type 'mcp' is not supported by provider 'bedrock'". The Responses path now silently strips provider-unsupported tools instead of rejecting the entire request, matching the existing behavior of the Chat path.

Changes

  • Introduced ValidateResponsesToolsForProvider in anthropic/utils.go — a Responses-path mirror of ValidateChatToolsForProvider. It partitions []schemas.ResponsesTool into a keep-set and a dropped-set using the same per-type feature flags as ValidateToolsForProvider, but returns both sets instead of erroring, leaving policy decisions to callers.
  • Updated ToBedrockResponsesRequest in bedrock/responses.go to call ValidateResponsesToolsForProvider and use the filtered keep-set for tool conversion, rather than calling ValidateToolsForProvider and returning an error on the first unsupported tool.
  • Updated BuildAnthropicResponsesRequestBody in anthropic/requestbuilder.go to strip unsupported tools via a shallow copy of the request (so the shared/pooled inbound request and its Params are never mutated) instead of failing the request.
  • Updated the ValidateTools field comment to reflect the new strip-silently policy.
  • Added validateresponsestools_test.go with a dedicated test table covering Bedrock, Vertex, Anthropic, Azure, unknown providers, and forward-compat cases.
  • Added regression tests in bedrock_test.go covering the mixed mcp+function case and the all-tools-dropped case.
  • Updated the existing requestbuilder_test.go test to assert that unsupported tools are stripped (not rejected) and that the inbound request is not mutated.

Type of change

  • Bug fix

Affected areas

  • Core (Go)
  • Providers/Integrations

How to test

go test ./core/providers/anthropic/... ./core/providers/bedrock/...

Expected: all tests pass, including the new regression guards for issue #3795. Specifically, a /v1/responses request to Bedrock with a mixed mcp + function tool list should succeed, with only the function tool forwarded to Bedrock and the mcp tool silently dropped. The inbound request's tool slice must remain unmodified.

Breaking changes

  • No

Related issues

Closes #3795

Security considerations

None. The change only affects which tools are forwarded to downstream providers. Unsupported tools are dropped rather than causing a hard failure; no secrets, auth, or PII handling is affected.

Checklist

  • I read docs/contributing/README.md and followed the guidelines
  • I added/updated tests where appropriate
  • I updated documentation where needed
  • I verified builds succeed (Go and UI)
  • I verified the CI pipeline passes locally if applicable

@CLAassistant

Copy link
Copy Markdown

CLA assistant check
Thank you for your submission! We really appreciate it. Like many open source projects, we ask that you sign our Contributor License Agreement before we can accept your contribution.
You have signed the CLA already but the status is still pending? Let us recheck it.

@coderabbitai

coderabbitai Bot commented Jun 20, 2026

Copy link
Copy Markdown
Contributor

Review Change Stack

No actionable comments were generated in the recent review. 🎉

ℹ️ Recent review info
⚙️ Run configuration

Configuration used: Path: .coderabbit.yaml

Review profile: CHILL

Plan: Pro Plus

Run ID: e4659338-3899-4727-8755-ca8268dd0a25

📥 Commits

Reviewing files that changed from the base of the PR and between 74c95ec and bf3aca1.

📒 Files selected for processing (12)
  • Makefile
  • core/providers/anthropic/requestbuilder.go
  • core/providers/anthropic/requestbuilder_test.go
  • core/providers/anthropic/utils.go
  • core/providers/anthropic/validateresponsestools_test.go
  • core/providers/bedrock/bedrock_test.go
  • core/providers/bedrock/responses.go
  • tests/config.json
  • tests/e2e/api/HARNESS_COVERAGE_BACKLOG.md
  • tests/e2e/api/collections/provider-harness.json
  • tests/integrations/python/config.json
  • tests/integrations/typescript/config.json
✅ Files skipped from review due to trivial changes (1)
  • tests/e2e/api/HARNESS_COVERAGE_BACKLOG.md
🚧 Files skipped from review as they are similar to previous changes (11)
  • core/providers/anthropic/validateresponsestools_test.go
  • tests/integrations/python/config.json
  • tests/integrations/typescript/config.json
  • core/providers/anthropic/requestbuilder_test.go
  • core/providers/bedrock/bedrock_test.go
  • core/providers/bedrock/responses.go
  • Makefile
  • core/providers/anthropic/utils.go
  • core/providers/anthropic/requestbuilder.go
  • tests/config.json
  • tests/e2e/api/collections/provider-harness.json

📝 Walkthrough

Summary by CodeRabbit

  • New Features

    • Added provider-aware Responses API tool filtering that keeps compatible tools and silently removes unsupported ones (including typed conversion paths).
  • Bug Fixes

    • Requests with mixed supported/unsupported tools no longer fail; unsupported tools are dropped.
    • Tool-choice pins are reconciled after filtering to avoid invalid pinned-tool behavior (including the all-tools-dropped case).
  • Tests

    • Added regression coverage for tool stripping and tool-choice reconciliation across providers, plus streaming/non-streaming scenarios.
  • Documentation

    • Updated harness coverage backlog notes for MCP tool stripping behavior.
  • Chores

    • Improved non-failure test report stream sanitization and refined Vertex test key model targeting.

Walkthrough

Introduces ValidateResponsesToolsForProvider, a new helper that partitions []schemas.ResponsesTool into keep and drop slices based on ProviderFeatures flags. Both the Anthropic typed-path request builder (BuildAnthropicResponsesRequestBody) and the Bedrock converter (ToBedrockResponsesRequest) are updated to use this helper, silently stripping unsupported server tools instead of returning errors. Comprehensive e2e regression tests covering Bedrock, Vertex, and routing variants validate MCP tool stripping with both isolated and mixed tool scenarios across streaming and non-streaming modes.

Changes

Responses API tool filtering: drop unsupported tools instead of failing

Layer / File(s) Summary
ValidateResponsesToolsForProvider helper and unit tests
core/providers/anthropic/utils.go, core/providers/anthropic/validateresponsestools_test.go
New exported function partitions []schemas.ResponsesTool into keep/dropped slices using ProviderFeatures[provider] flags; unknown providers keep all tools; function/custom/unknown tool types always survive. Table-driven tests verify keep/drop counts and ordered dropped-type strings across Bedrock, Vertex, Anthropic, Azure, and unknown providers.
Anthropic typed-path builder: filter instead of fail
core/providers/anthropic/requestbuilder.go, core/providers/anthropic/requestbuilder_test.go
ValidateTools doc updated to reflect silent-drop semantics. BuildAnthropicResponsesRequestBody replaces error-returning ValidateToolsForProvider call with ValidateResponsesToolsForProvider, shallow-copies request and request.Params to substitute the filtered tool set, and leaves the caller's original slice unmodified. Test replaces error-assertion case with strip-and-keep assertion that also verifies no mutation of inbound request.
Bedrock converter: filter instead of fail
core/providers/bedrock/responses.go, core/providers/bedrock/bedrock_test.go
ToBedrockResponsesRequest computes keepTools via ValidateResponsesToolsForProvider instead of returning an error on unsupported tools; ToolConfig construction iterates over keepTools and is skipped when the slice is empty. Tool-choice pins are reconciled against the filtered tool set: if the pinned tool was dropped, the tool-choice is cleared to avoid request rejection. Two regression tests cover the mixed-tools case (MCP dropped, function kept, ToolConfig non-nil) and the all-dropped case (ToolConfig == nil).
E2E regression harness and provider configuration for #3795
tests/e2e/api/collections/provider-harness.json, tests/config.json, tests/integrations/python/config.json, tests/integrations/typescript/config.json, tests/e2e/api/HARNESS_COVERAGE_BACKLOG.md, Makefile
Comprehensive provider-harness.json regression test matrix covering Bedrock/Vertex Claude opus/sonnet, /openai drop-in routing variants, and streaming SSE modes. Tests verify MCP tool stripping with text responses, mixed MCP+function scenarios with forced function tool invocation, and zero tool calls when all tools are dropped. Provider configuration updated with Vertex blacklisted_models and global-region Claude-specific keys. Coverage backlog marks MCP tool stripping as covered with regression reference #3795. Makefile stream-handling logic updated to unconditionally run trimstream for consistent test report output.

Estimated code review effort

🎯 3 (Moderate) | ⏱️ ~25 minutes

Possibly related issues

  • [Bug Report] #3795: Directly addresses the regression by replacing fail-fast validation with silent tool filtering, allowing requests with unsupported server tools (e.g., MCP) to succeed instead of returning a "tool type not supported by provider" error.

Possibly related PRs

  • maximhq/bifrost#3761: Overlaps with tool-support gating updates in Anthropic/Bedrock validation and test behavior that directly tie to the Responses-path tool filtering logic.

Suggested reviewers

  • danpiths

Poem

🐇 A tool came to knock, but the door said "no room"—
so I tucked it aside and let good tools through.
No error, no crash, just a tidy kept bloom,
unsupported friends quietly bid us adieu.
Soft copies, clean slices — the request sails true!

🚥 Pre-merge checks | ✅ 5
✅ Passed checks (5 passed)
Check name Status Explanation
Title check ✅ Passed The title 'adds mcp cleanup support for bedrock models' clearly summarizes the main change—adding tool filtering/cleanup for MCP tools in Bedrock Responses requests.
Description check ✅ Passed The pull request description comprehensively addresses all required template sections: summary, changes, type of change, affected areas, how to test, breaking changes, related issues, security considerations, and checklist items are all complete and well-documented.
Docstring Coverage ✅ Passed Docstring coverage is 81.82% which is sufficient. The required threshold is 80.00%.
Linked Issues check ✅ Passed Check skipped because no linked issues were found for this pull request.
Out of Scope Changes check ✅ Passed Check skipped because no linked issues were found for this pull request.

✏️ Tip: You can configure your own custom pre-merge checks in the settings.

✨ Finishing Touches
📝 Generate docstrings
  • Create stacked PR
  • Commit on current branch
🧪 Generate unit tests (beta)
  • Create PR with unit tests
  • Commit unit tests in branch 06-20-adds_mcp_cleanup_support_for_bedrock_models

Warning

There were issues while running some tools. Please review the errors and either fix the tool's configuration or disable the tool if it's a critical failure.

🔧 golangci-lint (2.12.2)

level=error msg="[linters_context] typechecking error: pattern ./...: directory prefix . does not contain main module or its selected dependencies"


Comment @coderabbitai help to get the list of available commands and usage tips.

akshaydeo commented Jun 20, 2026

Copy link
Copy Markdown
Contributor Author

This stack of pull requests is managed by Graphite. Learn more about stacking.

@akshaydeo
akshaydeo marked this pull request as ready for review June 20, 2026 08:51
@coderabbitai
coderabbitai Bot requested a review from danpiths June 20, 2026 08:52

@coderabbitai coderabbitai Bot 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.

Actionable comments posted: 1

🤖 Prompt for all review comments with AI agents
Verify each finding against current code. Fix only still-valid issues, skip the
rest with a brief reason, keep changes minimal, and validate.

Inline comments:
In `@core/providers/bedrock/responses.go`:
- Around line 2144-2153: After filtering unsupported tools into the keepTools
slice using anthropic.ValidateResponsesToolsForProvider, the code later
constructs tool_choice from the original unfiltered request parameters. If a
tool referenced in tool_choice was dropped during filtering, Bedrock will
receive a tool_choice reference to a tool that no longer exists in the converted
tools array, causing request rejection. Reconcile the tool_choice against
keepTools before assigning to bedrockReq.ToolConfig.ToolChoice by validating
that any pinned tool exists in keepTools, and either null out the tool_choice or
remap it if the referenced tool was filtered out. Apply this validation in both
locations where ToolChoice is assigned: around the initial construction and also
at lines 2417-2421.
🪄 Autofix (Beta)

Fix all unresolved CodeRabbit comments on this PR:

  • Push a commit to this branch (recommended)
  • Create a new PR with the fixes

ℹ️ Review info
⚙️ Run configuration

Configuration used: Path: .coderabbit.yaml

Review profile: CHILL

Plan: Pro Plus

Run ID: 530af14e-f792-4e59-a6cc-9b08fb2b3425

📥 Commits

Reviewing files that changed from the base of the PR and between 5f40c10 and 4c37ef8.

📒 Files selected for processing (6)
  • core/providers/anthropic/requestbuilder.go
  • core/providers/anthropic/requestbuilder_test.go
  • core/providers/anthropic/utils.go
  • core/providers/anthropic/validateresponsestools_test.go
  • core/providers/bedrock/bedrock_test.go
  • core/providers/bedrock/responses.go

Comment thread core/providers/bedrock/responses.go
@greptile-apps

greptile-apps Bot commented Jun 20, 2026

Copy link
Copy Markdown
Contributor

Confidence Score: 4/5

Safe to merge for the primary fix (mcp + function mixed tool list on Bedrock); one edge case in the tool_choice reconciliation path should be addressed before shipping.

The core fix is correct and well-tested: mcp tools are stripped, function tools survive, the inbound request is never mutated. The gap is in bedrock/responses.go's tool_choice reconciliation: when all tools are dropped and the caller sends tool_choice 'auto' or 'required', the code creates an empty BedrockToolConfig with only a ToolChoice and no Tools, which Bedrock rejects with HTTP 400. The named-tool reconciliation (lines 2505–2516) correctly nil-ifies a pinned choice whose tool was dropped, but it only fires for choices where .Tool.Name != '' — 'auto' and 'required' bypass it entirely.

core/providers/bedrock/responses.go — the tool_choice block at lines 2529–2534

Important Files Changed

Filename Overview
core/providers/bedrock/responses.go Switches from error-on-unsupported-tools to strip-silently; adds tool_choice reconciliation for named tools. The "auto"/"required" tool_choice with all-tools-dropped path creates an empty BedrockToolConfig with only a ToolChoice, which Bedrock rejects.
core/providers/anthropic/utils.go Adds ValidateResponsesToolsForProvider — clean mirror of ValidateChatToolsForProvider with partition instead of error-on-first-unsupported. Correct per-type gating and forward-compat defaults.
core/providers/anthropic/requestbuilder.go Switches Responses path from fail-on-unsupported to strip-silently with a shallow copy to avoid mutating the shared/pooled request. Correctly preserves the original Params.
core/providers/anthropic/validateresponsestools_test.go New table-driven test suite covering the key partition behavior: MCP dropped on Bedrock/Vertex, kept on Anthropic/Azure, function tools always kept, unknown-provider forward-compat.
core/providers/bedrock/bedrock_test.go Adds two regression tests: mcp+function mixed case (primary fix) and all-tools-dropped edge case. Both verify non-mutation of the inbound request's tool slice.
core/providers/anthropic/requestbuilder_test.go Updated test correctly asserts strip-silently behavior, verifies the function tool survives, the unsupported tool is absent, and the inbound request is not mutated.
Makefile Simplifies the jq sanitize function to always trimstream; the previously-used failed def is now dead code but does not affect behavior.

Flowchart

%%{init: {'theme': 'neutral'}}%%
flowchart TD
    A["/v1/responses request\ntools: [mcp, function, ...]"] --> B{bifrostReq.Params.Tools != nil?}
    B -- No --> C[keepTools = nil]
    B -- Yes --> D["ValidateResponsesToolsForProvider\n(new)"]
    D --> E{keepTools empty?}
    E -- No: some tools kept --> F["Convert keepTools → BedrockTools\nbedrockReq.ToolConfig = {Tools: bedrockTools}"]
    E -- Yes: all dropped --> G["keepTools = nil\nbedrockReq.ToolConfig = nil"]
    F --> H{ToolChoice set?}
    G --> H
    H -- No --> K[Send to Bedrock]
    H -- Yes: named tool --> I{pinPresent in\nbedrockReq.ToolConfig?}
    I -- Yes --> J[Keep toolChoice]
    I -- No --> L["bedrockToolChoice = nil"]
    J --> M["bedrockReq.ToolConfig.ToolChoice = toolChoice"]
    L --> K
    H -- "Yes: auto/required" --> N{bedrockReq.ToolConfig == nil?}
    N -- No: tools present --> M
    N -- "Yes: no tools ⚠️" --> O["Creates empty BedrockToolConfig\nwith only ToolChoice set\n→ Bedrock 400"]
    M --> K
    O --> K
    style O fill:#f88,stroke:#c00
    style N fill:#ffd,stroke:#cc0
Loading
%%{init: {'theme': 'base', 'themeVariables': {"darkMode": true, "background": "#0d1117", "primaryColor": "#21262d", "primaryTextColor": "#e6edf3", "primaryBorderColor": "#8b949e", "lineColor": "#8b949e", "textColor": "#e6edf3", "edgeLabelBackground": "#161b22", "actorBkg": "#21262d", "actorBorder": "#8b949e", "actorTextColor": "#e6edf3", "actorLineColor": "#8b949e", "signalColor": "#8b949e", "signalTextColor": "#e6edf3", "noteBkgColor": "#373320", "noteBorderColor": "#d4a72c", "noteTextColor": "#f0e6c0", "labelBoxBkgColor": "#21262d", "labelBoxBorderColor": "#8b949e", "labelTextColor": "#e6edf3", "loopTextColor": "#e6edf3", "activationBkgColor": "#30363d", "activationBorderColor": "#8b949e"}}}%%
flowchart TD
    A["/v1/responses request\ntools: [mcp, function, ...]"] --> B{bifrostReq.Params.Tools != nil?}
    B -- No --> C[keepTools = nil]
    B -- Yes --> D["ValidateResponsesToolsForProvider\n(new)"]
    D --> E{keepTools empty?}
    E -- No: some tools kept --> F["Convert keepTools → BedrockTools\nbedrockReq.ToolConfig = {Tools: bedrockTools}"]
    E -- Yes: all dropped --> G["keepTools = nil\nbedrockReq.ToolConfig = nil"]
    F --> H{ToolChoice set?}
    G --> H
    H -- No --> K[Send to Bedrock]
    H -- Yes: named tool --> I{pinPresent in\nbedrockReq.ToolConfig?}
    I -- Yes --> J[Keep toolChoice]
    I -- No --> L["bedrockToolChoice = nil"]
    J --> M["bedrockReq.ToolConfig.ToolChoice = toolChoice"]
    L --> K
    H -- "Yes: auto/required" --> N{bedrockReq.ToolConfig == nil?}
    N -- No: tools present --> M
    N -- "Yes: no tools ⚠️" --> O["Creates empty BedrockToolConfig\nwith only ToolChoice set\n→ Bedrock 400"]
    M --> K
    O --> K
    style O fill:#f88,stroke:#c00
    style N fill:#ffd,stroke:#cc0
Loading

Reviews (3): Last reviewed commit: "adds mcp cleanup support for bedrock mod..." | Re-trigger Greptile

Comment thread core/providers/anthropic/utils.go
@akshaydeo
akshaydeo force-pushed the 06-20-adds_mcp_cleanup_support_for_bedrock_models branch from 4c37ef8 to 3a0cdd5 Compare June 20, 2026 11:20
@akshaydeo
akshaydeo requested a review from a team as a code owner June 20, 2026 11:20

@coderabbitai coderabbitai Bot 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.

🧹 Nitpick comments (2)
tests/e2e/api/collections/provider-harness.json (1)

1925-2959: ⚡ Quick win

Streaming coverage gap for lone-mcp-dropped scenario.

The test description states "Covers native + /openai drop-in + streaming", but the explicit streaming tests (lines 2830-2959) only cover the forced function call scenario. The lone-mcp-dropped tests (e.g., lines 1934-1993, 2125-2183) only assert when ct.indexOf('event-stream') === -1, meaning they skip all assertions when the response is streamed.

This leaves the streaming behavior for the all-tools-dropped edge case (where only MCP tools are present and all are stripped) unverified. While the behavior is expected to be simpler (text answer, no tool calls), explicit streaming coverage would strengthen the regression suite and match the coverage claim.

📋 Add streaming variants for lone-mcp-dropped tests

Add streaming test cases similar to lines 2830-2893, but for the lone-mcp-dropped scenario. Example structure:

{
  "name": "bedrock/global.anthropic.claude-opus-4-7 · streaming · lone server-mcp dropped",
  "event": [
    {
      "listen": "test",
      "script": {
        "type": "text/javascript",
        "exec": [
          "var ct = (pm.response.headers.get('content-type') || '');",
          "var raw = pm.response.text() || '';",
          "pm.test('mcp server tool dropped, not rejected (`#3795`)', function () {",
          "  pm.expect(raw).to.not.include(\"tool type 'mcp'\");",
          "  pm.expect(raw.toLowerCase()).to.not.include('is not supported by provider');",
          "});",
          "pm.test('response body is non-empty', function () {",
          "  pm.expect(raw.length).to.be.above(0);",
          "});",
          "pm.test('streaming text answer, no tool call events (mcp dropped, zero tools left)', function () {",
          "  pm.expect(ct).to.include('event-stream');",
          "  pm.expect(raw).to.not.match(/\"type\"\\s*:\\s*\"function_call\"/);",
          "  pm.expect(raw).to.not.match(/\"type\"\\s*:\\s*\"tool_call\"/);",
          "});"
        ]
      }
    }
  ],
  "request": {
    "method": "POST",
    "header": [{"key": "Content-Type", "value": "application/json"}],
    "body": {
      "mode": "raw",
      "raw": "{...lone mcp payload with \"stream\": true...}"
    },
    "url": {"raw": "{{baseUrl}}/v1/responses", ...}
  }
}

Repeat for Bedrock sonnet, Vertex opus, and Vertex sonnet to match the forced-function-call streaming coverage.

🤖 Prompt for AI Agents
Verify each finding against current code. Fix only still-valid issues, skip the
rest with a brief reason, keep changes minimal, and validate.

In `@tests/e2e/api/collections/provider-harness.json` around lines 1925 - 2959,
The test suite claims to cover "native + /openai drop-in + streaming" for MCP
tool handling, but the lone-mcp-dropped scenario (where only MCP server tools
are present and all are stripped, leaving zero tools) only has non-streaming
test cases. The existing lone-mcp-dropped tests skip all assertions when the
response is streamed (checking `ct.indexOf('event-stream') === -1`). Add new
streaming test variants for the lone-mcp-dropped scenario by creating test items
following the pattern of the existing streaming forced-function-call tests
(around lines 2830-2893 and 2903-2959), but using the lone-mcp-dropped request
payloads with "stream": true added. Create one variant for each of the four
provider models (bedrock/global.anthropic.claude-opus-4-7,
bedrock/global.anthropic.claude-sonnet-4-6, vertex/claude-opus-4-7,
vertex/claude-sonnet-4-6) to match the coverage of the forced-function-call
streaming variants and verify that streaming responses correctly return text
without tool call events when all tools are dropped.
Makefile (1)

1978-1978: 💤 Low value

Optional: Remove unused failed function for clarity.

The sanitize function now unconditionally calls trimstream, which is the correct behavior for consistent report output. However, the failed function defined earlier in the jq expression is no longer used.

♻️ Simplify jq expression
-jq -s 'def failed: (((.assertions // []) | any(.error?)) or ((.response.code // 0) == 0) or ((.response.code // 0) >= 400) or (.response | not)); def trimstream: if (.response.stream.type? == "Buffer" and ((.response.stream.data // []) | length) > 20000) then (.response.stream.data = .response.stream.data[:20000] | .response.stream.truncated = true) else . end; def sanitize: trimstream; {collection: (.[0].collection // {}), environment: (.[0].environment // {}), run: {executions: [.[].run.executions[]? | sanitize], failures: [.[].run.failures[]?], stats: {iterations: {total: 1, pending: 0, failed: 0}, items: {total: ([.[].run.stats.items.total // 0] | add)}, requests: {total: ([.[].run.stats.requests.total // 0] | add), failed: ([.[].run.stats.requests.failed // 0] | add)}}, timings: (.[0].run.timings // {})}}' tmp/newman-report-*.json > tmp/newman-report.json || $(ECHO) "$(YELLOW)Report merge failed; per-provider reports remain at tmp/newman-report-*.json$(NC)"; \
+jq -s 'def trimstream: if (.response.stream.type? == "Buffer" and ((.response.stream.data // []) | length) > 20000) then (.response.stream.data = .response.stream.data[:20000] | .response.stream.truncated = true) else . end; def sanitize: trimstream; {collection: (.[0].collection // {}), environment: (.[0].environment // {}), run: {executions: [.[].run.executions[]? | sanitize], failures: [.[].run.failures[]?], stats: {iterations: {total: 1, pending: 0, failed: 0}, items: {total: ([.[].run.stats.items.total // 0] | add)}, requests: {total: ([.[].run.stats.requests.total // 0] | add), failed: ([.[].run.stats.requests.failed // 0] | add)}}, timings: (.[0].run.timings // {})}}' tmp/newman-report-*.json > tmp/newman-report.json || $(ECHO) "$(YELLOW)Report merge failed; per-provider reports remain at tmp/newman-report-*.json$(NC)"; \
🤖 Prompt for AI Agents
Verify each finding against current code. Fix only still-valid issues, skip the
rest with a brief reason, keep changes minimal, and validate.

In `@Makefile` at line 1978, The jq expression in the Makefile contains a defined
`failed` function that is never referenced or called anywhere in the remaining
jq pipeline. Remove the unused `failed` function definition from the jq
expression to simplify and clarify the code, keeping only the `trimstream` and
`sanitize` function definitions which are actively used in the data
transformation.
🤖 Prompt for all review comments with AI agents
Verify each finding against current code. Fix only still-valid issues, skip the
rest with a brief reason, keep changes minimal, and validate.

Nitpick comments:
In `@Makefile`:
- Line 1978: The jq expression in the Makefile contains a defined `failed`
function that is never referenced or called anywhere in the remaining jq
pipeline. Remove the unused `failed` function definition from the jq expression
to simplify and clarify the code, keeping only the `trimstream` and `sanitize`
function definitions which are actively used in the data transformation.

In `@tests/e2e/api/collections/provider-harness.json`:
- Around line 1925-2959: The test suite claims to cover "native + /openai
drop-in + streaming" for MCP tool handling, but the lone-mcp-dropped scenario
(where only MCP server tools are present and all are stripped, leaving zero
tools) only has non-streaming test cases. The existing lone-mcp-dropped tests
skip all assertions when the response is streamed (checking
`ct.indexOf('event-stream') === -1`). Add new streaming test variants for the
lone-mcp-dropped scenario by creating test items following the pattern of the
existing streaming forced-function-call tests (around lines 2830-2893 and
2903-2959), but using the lone-mcp-dropped request payloads with "stream": true
added. Create one variant for each of the four provider models
(bedrock/global.anthropic.claude-opus-4-7,
bedrock/global.anthropic.claude-sonnet-4-6, vertex/claude-opus-4-7,
vertex/claude-sonnet-4-6) to match the coverage of the forced-function-call
streaming variants and verify that streaming responses correctly return text
without tool call events when all tools are dropped.

ℹ️ Review info
⚙️ Run configuration

Configuration used: Path: .coderabbit.yaml

Review profile: CHILL

Plan: Pro Plus

Run ID: 12d94a87-a63c-49de-82a9-10a92c557cf7

📥 Commits

Reviewing files that changed from the base of the PR and between 4c37ef8 and 3a0cdd5.

📒 Files selected for processing (12)
  • Makefile
  • core/providers/anthropic/requestbuilder.go
  • core/providers/anthropic/requestbuilder_test.go
  • core/providers/anthropic/utils.go
  • core/providers/anthropic/validateresponsestools_test.go
  • core/providers/bedrock/bedrock_test.go
  • core/providers/bedrock/responses.go
  • tests/config.json
  • tests/e2e/api/HARNESS_COVERAGE_BACKLOG.md
  • tests/e2e/api/collections/provider-harness.json
  • tests/integrations/python/config.json
  • tests/integrations/typescript/config.json
✅ Files skipped from review due to trivial changes (1)
  • tests/e2e/api/HARNESS_COVERAGE_BACKLOG.md
🚧 Files skipped from review as they are similar to previous changes (6)
  • core/providers/anthropic/requestbuilder_test.go
  • core/providers/bedrock/bedrock_test.go
  • core/providers/anthropic/requestbuilder.go
  • core/providers/anthropic/validateresponsestools_test.go
  • core/providers/bedrock/responses.go
  • core/providers/anthropic/utils.go

@akshaydeo
akshaydeo force-pushed the 06-20-adds_mcp_cleanup_support_for_bedrock_models branch from 3a0cdd5 to 74c95ec Compare June 20, 2026 11:40
coderabbitai[bot]
coderabbitai Bot previously approved these changes Jun 20, 2026
@akshaydeo
akshaydeo force-pushed the 06-20-adds_mcp_cleanup_support_for_bedrock_models branch from 74c95ec to bf3aca1 Compare June 20, 2026 11:56
@akshaydeo
akshaydeo force-pushed the 06-20-extra_header_forwarding_for_mcp_tools branch from 5f40c10 to 411f221 Compare June 20, 2026 11:56

akshaydeo commented Jun 20, 2026

Copy link
Copy Markdown
Contributor Author

Merge activity

  • Jun 20, 12:05 PM UTC: A user started a stack merge that includes this pull request via Graphite.
  • Jun 20, 12:06 PM UTC: @akshaydeo merged this pull request with Graphite.

@akshaydeo
akshaydeo changed the base branch from 06-20-extra_header_forwarding_for_mcp_tools to graphite-base/4573 June 20, 2026 12:06
@akshaydeo
akshaydeo changed the base branch from graphite-base/4573 to dev June 20, 2026 12:06
@akshaydeo
akshaydeo dismissed coderabbitai[bot]’s stale review June 20, 2026 12:06

The base branch was changed.

@akshaydeo
akshaydeo merged commit ddb8de2 into dev Jun 20, 2026
11 of 12 checks passed
@akshaydeo
akshaydeo deleted the 06-20-adds_mcp_cleanup_support_for_bedrock_models branch June 20, 2026 12:06
@coderabbitai coderabbitai Bot mentioned this pull request Jun 21, 2026
18 tasks
akshaydeo added a commit that referenced this pull request Jun 21, 2026
## Summary

Fixes a regression introduced in v1.5.0 (issue closes #3795) where a `/v1/responses` request carrying a Bifrost-hosted `mcp` server tool alongside function tools would fail with `"tool type 'mcp' is not supported by provider 'bedrock'"`. The Responses path now silently strips provider-unsupported tools instead of rejecting the entire request, matching the existing behavior of the Chat path.

## Changes

- Introduced `ValidateResponsesToolsForProvider` in `anthropic/utils.go` — a Responses-path mirror of `ValidateChatToolsForProvider`. It partitions `[]schemas.ResponsesTool` into a keep-set and a dropped-set using the same per-type feature flags as `ValidateToolsForProvider`, but returns both sets instead of erroring, leaving policy decisions to callers.
- Updated `ToBedrockResponsesRequest` in `bedrock/responses.go` to call `ValidateResponsesToolsForProvider` and use the filtered keep-set for tool conversion, rather than calling `ValidateToolsForProvider` and returning an error on the first unsupported tool.
- Updated `BuildAnthropicResponsesRequestBody` in `anthropic/requestbuilder.go` to strip unsupported tools via a shallow copy of the request (so the shared/pooled inbound request and its `Params` are never mutated) instead of failing the request.
- Updated the `ValidateTools` field comment to reflect the new strip-silently policy.
- Added `validateresponsestools_test.go` with a dedicated test table covering Bedrock, Vertex, Anthropic, Azure, unknown providers, and forward-compat cases.
- Added regression tests in `bedrock_test.go` covering the mixed mcp+function case and the all-tools-dropped case.
- Updated the existing `requestbuilder_test.go` test to assert that unsupported tools are stripped (not rejected) and that the inbound request is not mutated.

## Type of change

- [x] Bug fix

## Affected areas

- [x] Core (Go)
- [x] Providers/Integrations

## How to test

```sh
go test ./core/providers/anthropic/... ./core/providers/bedrock/...
```

Expected: all tests pass, including the new regression guards for issue #3795. Specifically, a `/v1/responses` request to Bedrock with a mixed `mcp` + function tool list should succeed, with only the function tool forwarded to Bedrock and the `mcp` tool silently dropped. The inbound request's tool slice must remain unmodified.

## Breaking changes

- [x] No

## Related issues

Closes #3795

## Security considerations

None. The change only affects which tools are forwarded to downstream providers. Unsupported tools are dropped rather than causing a hard failure; no secrets, auth, or PII handling is affected.

## Checklist

- [x] I read `docs/contributing/README.md` and followed the guidelines
- [x] I added/updated tests where appropriate
- [x] I updated documentation where needed
- [x] I verified builds succeed (Go and UI)
- [x] I verified the CI pipeline passes locally if applicable
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.

[Bug Report]

2 participants