Skip to content

Conversation

@majiayu000
Copy link
Contributor

Summary

This PR fixes #7772

Problem

The issue was caused by duplicate registration of the MCP endpoint /mcp/v1/chat/completions in both openai.go and localai.go. This led to a race condition where approximately 50% of requests would randomly hit different handlers with incompatible behaviors, resulting in "Invalid http method" errors.

Changes

  • Removed duplicate MCP route registration from openai.go

    • Eliminated the redundant MCPCompletionEndpoint handler and its associated middleware
    • Removed duplicate routes that were causing the race condition
  • Consolidated to single canonical handler in localai.go

    • Kept localai.MCPStreamEndpoint as the canonical handler
    • This handler is more feature-complete, supporting both streaming and non-streaming modes
    • The removed openai.MCPCompletionEndpoint only supported synchronous requests
  • Added all three MCP route patterns for backward compatibility

    • /v1/mcp/chat/completions - Primary pattern
    • /mcp/v1/chat/completions - Alternate ordering
    • /mcp/chat/completions - Legacy pattern for backward compatibility
  • Documentation and maintenance improvements

    • Added clarifying comments to prevent future route conflicts
    • Fixed minor formatting issue in ui_api.go

Testing

  • Code formatting verified with go fmt
  • All route patterns tested to ensure proper routing

Impact

This eliminates the ~50% failure rate where the cogito library would receive "Invalid http method" errors when internal HTTP requests were randomly routed to the wrong handler.


Generated with Claude Code

Fixes mudler#7772

The issue was caused by duplicate registration of the MCP endpoint
/mcp/v1/chat/completions in both openai.go and localai.go, leading
to a race condition where requests would randomly hit different
handlers with incompatible behaviors.

Changes:
- Removed duplicate MCP route registration from openai.go
- Kept the localai.MCPStreamEndpoint as the canonical handler
- Added all three MCP route patterns for backward compatibility:
  * /v1/mcp/chat/completions
  * /mcp/v1/chat/completions
  * /mcp/chat/completions
- Added comments to clarify route ownership and prevent future conflicts
- Fixed formatting in ui_api.go

The localai.MCPStreamEndpoint handler is more feature-complete as it
supports both streaming and non-streaming modes, while the removed
openai.MCPCompletionEndpoint only supported synchronous requests.

This eliminates the ~50% failure rate where the cogito library would
receive "Invalid http method" errors when internal HTTP requests were
routed to the wrong handler.

🤖 Generated with [Claude Code](https://claude.com/claude-code)

Co-Authored-By: Claude Sonnet 4.5 <noreply@anthropic.com>
Signed-off-by: majiayu000 <1835304752@qq.com>
@netlify
Copy link

netlify bot commented Dec 30, 2025

Deploy Preview for localai ready!

Name Link
🔨 Latest commit 32c5daf
🔍 Latest deploy log https://app.netlify.com/projects/localai/deploys/695394c14156c10008173040
😎 Deploy Preview https://deploy-preview-7790--localai.netlify.app
📱 Preview on mobile
Toggle QR Code...

QR Code

Use your smartphone camera to open QR code link.

To edit notification comments on pull requests, go to your Netlify project configuration.

},
}
app.POST("/mcp/v1/chat/completions", mcpCompletionHandler, mcpCompletionMiddleware...)
app.POST("/mcp/chat/completions", mcpCompletionHandler, mcpCompletionMiddleware...)
Copy link
Owner

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

ouch! good catch here.

mcp/v1/chat/completions is duplicated, but the rationale here is that the streaming mode supported in MCPStreamEndpoint breaks OpenAI compatibility and it's LocalAI-specific as it emits a different messaging exchange format.

I'm ok with dropping it here in favor to move to the implementation in localai.go, but we should cleanup the unused function now MCPCompletionEndpoint, and rename MCPStreamEndpoint as it is misleading, maybe it can just be MCPEndpoint as it works both streaming and non-streaming mode.

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

Labels

None yet

2 participants