Skip to content

Remove Forwarding Methods & Fix SSE Parsing#2647

Merged
crivetimihai merged 2 commits intomainfrom
1595_sse_forwarding_fix
Feb 11, 2026
Merged

Remove Forwarding Methods & Fix SSE Parsing#2647
crivetimihai merged 2 commits intomainfrom
1595_sse_forwarding_fix

Conversation

@kevalmahajan
Copy link
Copy Markdown
Member

@kevalmahajan kevalmahajan commented Feb 2, 2026

🐛 Bug-fix PR

Closes #1595

📌 Summary

Addressed two distinct items:

  1. Federation Cleanup: Removes the deprecated forward_request, _forward_request_to_gateway, and _forward_request_to_all methods from gateway_service.py. This finalizes the removal of the unused "Federation" logic as tracked in Issue:
    [CHORE]: Cleanup unused Federation module and duplicate Forwarding logic #1912.

  2. SSE Parsing Fix: Updates the SSE parser in llm_proxy_service.py to correctly handle data: lines that are missing a space after the colon (e.g., data:{"key": "value"}).

🔁 Reproduction Steps

1. Federation/Forwarding Removal:

  • (Code Cleanup) Examine mcpgateway/services/gateway_service.py to see the methods are removed.
  • Attempt to call resources/read for a non-existent local resource. Previously, it might have attempted to forward. Now, it immediately returns a Resource not found (-32002) error.

2. SSE Parsing Bug:

  • Configure an LLM provider that returns SSE events formatted as data:{...} (no space) instead of data: {...}.
  • Initiate a streaming chat completion.
  • Before: The parser would fail or misinterpret the JSON payload.
  • After: The parser correctly handles the data regardless of the leading space.

🐞 Root Cause

1. Forwarding: The forwarding logic was legacy code from the "Federation" module which has been deprecated. It was duplicating logic handled by ToolService and was no longer wired correctly into the application lifecycle. This federation/forwarding logic is removed but some functions still existed in gateway_service.py for forwarding to other gateways (this feature is deprecated now.)

2. SSE Parsing: The existing parser assumed a strict data: prefix (with space). While the spec recommended a space, some providers/implementations omit it, causing orjson.loads to fail on the malformed string.

💡 Fix Description

  1. Removed Forwarding Logic:
  • Deleted forward_request, _forward_request_to_gateway, and _forward_request_to_all from gateway_service.py.
  • Updated main.py call sites to log a warning and return strict JSON-RPC errors (e.g., -32000 / -32002) when a local resource/tool is not found, rather than attempting a fallback.
  • Removed unit tests in test_gateway_service.py and test_gateway_service_oauth_comprehensive.py that covered this deprecated functionality.
  1. Robust SSE Parsing:
  • Updated llm_proxy_service.py (and translate.py) to inspect the line content after data:.
  • Added logic to conditionally strip the leading space only if it exists, ensuring both data: {...} and data:{...} are parsed correctly as valid JSON.

References:

  1. Issue for Federation: [CHORE]: Cleanup unused Federation module and duplicate Forwarding logic #1912
  2. PR for Federation: Cleanup Federation Redundant Code #1928

🧪 Verification

Check Command Status
Lint suite make lint
Unit tests make test
Coverage ≥ 80 % make coverage
Manual regression no longer fails steps / screenshots

📐 MCP Compliance (if relevant)

  • Matches current MCP spec
  • No breaking change to MCP clients

✅ Checklist

  • Code formatted (make black isort pre-commit)
  • No secrets/credentials committed

@crivetimihai
Copy link
Copy Markdown
Member

Good cleanup — removing the silent forward_request fallback in favor of explicit JSON-RPC errors is the right approach. The deleted forwarding code in gateway_service.py was significant dead weight. CI is all green.

LGTM — ready to merge.

@crivetimihai crivetimihai self-assigned this Feb 4, 2026
kevalmahajan and others added 2 commits February 11, 2026 11:32
Remove deprecated forward_request, _forward_request_to_gateway, and
_forward_request_to_all methods from gateway_service.py. Replace
forwarding fallbacks in main.py with proper JSON-RPC error responses.

Fix SSE parser in llm_proxy_service.py and translate.py to handle
data: lines with or without a space after the colon, per the SSE spec.

Closes #1595

Signed-off-by: Keval Mahajan <mahajankeval23@gmail.com>
Signed-off-by: Mihai Criveti <crivetimihai@gmail.com>
Simplify except (ValueError, Exception) to except Exception since
ValueError is a subclass of Exception. Update SSE data: line parsing
in integration and e2e tests to match the spec-correct pattern used
in production code.

Signed-off-by: Mihai Criveti <crivetimihai@gmail.com>
@crivetimihai crivetimihai force-pushed the 1595_sse_forwarding_fix branch from d09179d to 055e7c3 Compare February 11, 2026 11:49
@crivetimihai
Copy link
Copy Markdown
Member

Rebase & Review Notes

Rebased onto current main (resolved 3 merge conflicts) and squashed the original 5 commits into a single clean commit, preserving original authorship. Added a follow-up commit with additional cleanup.

Issues found and fixed

Issue Severity Fix
~24 tests still calling removed methods (TestForwardRequestToGateway, TestForwardRequestDispatch, TestForwardRequestToAll, TestForwardRequestOAuthAuthCode in test_gateway_service.py) Critical Removed all 4 stale test classes
Stale test in test_main_extended.py (test_handle_rpc_fallback_forward_request_model_dump_and_internal_error still mocking gateway_service.forward_request) Critical Rewrote test for the new error behavior
Stale docstrings in gateway_service.py still listing "Request forwarding" as a feature Minor Removed
Unused imports (urljoin, get_db) left in gateway_service.py after method removal Minor Cleaned up
Spurious blank line in translate.py between if data: and print(data) Minor Removed
Redundant except (ValueError, Exception): in fallback handler (ValueError is a subclass of Exception) Minor Simplified to except Exception:
Inconsistent SSE parsing in test files — 19 occurrences in tests/e2e/ and tests/integration/ still using old startswith("data: ") pattern Minor Updated to spec-correct pattern matching production code

Review assessment

  • Forwarding removal: Correct — deprecated federation logic that duplicated ToolService functionality. Reduces attack surface (removes SSRF-capable code paths).
  • SSE parsing fix: Spec-correct — strips exactly one optional leading space per the SSE specification (HTML Living Standard Section 9.2).
  • Error codes: Acceptable — -32002 (resource not found) is a valid server-defined error; -32601 (tool not found) matches codebase convention; -32000 (invalid method fallback) is reasonable.
  • No security or performance concerns introduced.
  • All 699 affected unit tests pass.

@crivetimihai crivetimihai merged commit 0b0895f into main Feb 11, 2026
52 checks passed
@crivetimihai crivetimihai deleted the 1595_sse_forwarding_fix branch February 11, 2026 13:19
ja8zyjits pushed a commit that referenced this pull request Feb 13, 2026
* fix: remove deprecated forwarding methods and fix SSE data parsing

Remove deprecated forward_request, _forward_request_to_gateway, and
_forward_request_to_all methods from gateway_service.py. Replace
forwarding fallbacks in main.py with proper JSON-RPC error responses.

Fix SSE parser in llm_proxy_service.py and translate.py to handle
data: lines with or without a space after the colon, per the SSE spec.

Closes #1595

Signed-off-by: Keval Mahajan <mahajankeval23@gmail.com>
Signed-off-by: Mihai Criveti <crivetimihai@gmail.com>

* fix: clean up redundant except clause and align SSE parsing in tests

Simplify except (ValueError, Exception) to except Exception since
ValueError is a subclass of Exception. Update SSE data: line parsing
in integration and e2e tests to match the spec-correct pattern used
in production code.

Signed-off-by: Mihai Criveti <crivetimihai@gmail.com>

---------

Signed-off-by: Keval Mahajan <mahajankeval23@gmail.com>
Signed-off-by: Mihai Criveti <crivetimihai@gmail.com>
Co-authored-by: Mihai Criveti <crivetimihai@gmail.com>
vishu-bh pushed a commit that referenced this pull request Feb 18, 2026
* fix: remove deprecated forwarding methods and fix SSE data parsing

Remove deprecated forward_request, _forward_request_to_gateway, and
_forward_request_to_all methods from gateway_service.py. Replace
forwarding fallbacks in main.py with proper JSON-RPC error responses.

Fix SSE parser in llm_proxy_service.py and translate.py to handle
data: lines with or without a space after the colon, per the SSE spec.

Closes #1595

Signed-off-by: Keval Mahajan <mahajankeval23@gmail.com>
Signed-off-by: Mihai Criveti <crivetimihai@gmail.com>

* fix: clean up redundant except clause and align SSE parsing in tests

Simplify except (ValueError, Exception) to except Exception since
ValueError is a subclass of Exception. Update SSE data: line parsing
in integration and e2e tests to match the spec-correct pattern used
in production code.

Signed-off-by: Mihai Criveti <crivetimihai@gmail.com>

---------

Signed-off-by: Keval Mahajan <mahajankeval23@gmail.com>
Signed-off-by: Mihai Criveti <crivetimihai@gmail.com>
Co-authored-by: Mihai Criveti <crivetimihai@gmail.com>
Signed-off-by: Vishu Bhatnagar <vishu.bhatnagar@ibm.com>
kcostell06 pushed a commit to kcostell06/mcp-context-forge that referenced this pull request Feb 24, 2026
* fix: remove deprecated forwarding methods and fix SSE data parsing

Remove deprecated forward_request, _forward_request_to_gateway, and
_forward_request_to_all methods from gateway_service.py. Replace
forwarding fallbacks in main.py with proper JSON-RPC error responses.

Fix SSE parser in llm_proxy_service.py and translate.py to handle
data: lines with or without a space after the colon, per the SSE spec.

Closes IBM#1595

Signed-off-by: Keval Mahajan <mahajankeval23@gmail.com>
Signed-off-by: Mihai Criveti <crivetimihai@gmail.com>

* fix: clean up redundant except clause and align SSE parsing in tests

Simplify except (ValueError, Exception) to except Exception since
ValueError is a subclass of Exception. Update SSE data: line parsing
in integration and e2e tests to match the spec-correct pattern used
in production code.

Signed-off-by: Mihai Criveti <crivetimihai@gmail.com>

---------

Signed-off-by: Keval Mahajan <mahajankeval23@gmail.com>
Signed-off-by: Mihai Criveti <crivetimihai@gmail.com>
Co-authored-by: Mihai Criveti <crivetimihai@gmail.com>
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][SSE]: SSE transport incorrect endpoint and data parsing

2 participants