Skip to content

MCPServer status URL shows /sse instead of /mcp when using stdio transport with streamable-http proxyMode #2920

@jhrozek

Description

@jhrozek

Bug Description

When deploying an MCPServer with transport: stdio and proxyMode: streamable-http, the status URL incorrectly shows /sse instead of /mcp.

Steps to Reproduce

Deploy an MCPServer like this:

apiVersion: toolhive.stacklok.dev/v1alpha1
kind: MCPServer
metadata:
  name: arxiv
  namespace: toolhive-system
spec:
  image: ghcr.io/stacklok/dockyard/uvx/arxiv-mcp-server:0.3.1
  transport: stdio
  proxyMode: streamable-http
  proxyPort: 8080

Expected Behavior

Status URL should show /mcp endpoint (e.g., http://arxiv.toolhive-system.svc.cluster.local:8080/mcp)

Actual Behavior

Status URL shows /sse endpoint (e.g., http://arxiv.toolhive-system.svc.cluster.local:8080/sse#arxiv)

Root Cause

In pkg/transport/url.go, the GenerateMCPServerURL function treats stdio the same as sse:

isSSE := transportType == types.TransportTypeSSE.String() || transportType == types.TransportTypeStdio.String()

The MCPServer controller at cmd/thv-operator/controllers/mcpserver_controller.go:395-401 only passes the Transport field, ignoring ProxyMode:

mcpServer.Status.URL = transport.GenerateMCPServerURL(
    mcpServer.Spec.Transport,   // <-- Uses Transport, NOT ProxyMode
    host,
    int(mcpServer.GetProxyPort()),
    mcpServer.Name,
    "",
)

Impact

Transport ProxyMode Actual Endpoint Status Shows Match?
stdio sse /sse /sse
stdio streamable-http /mcp /sse BUG
sse (ignored) /sse /sse
streamable-http (ignored) /mcp /mcp

Since the default proxyMode is streamable-http, this bug affects the default stdio configuration.

Proposed Fix

Add a proxyMode parameter to GenerateMCPServerURL and update all callers:

  1. pkg/transport/url.go - Add proxyMode parameter:

    • For stdio transport: use proxyMode to determine endpoint
    • For stdio with empty proxyMode: default to streamable-http (matches CRD default)
    • For non-stdio transports: ignore proxyMode
  2. Update call sites (5 locations):

    • cmd/thv-operator/controllers/mcpserver_controller.go:395
    • pkg/runner/runner.go:283
    • pkg/workloads/manager.go:1392
    • pkg/workloads/types/types.go:75
    • pkg/vmcp/workloads/k8s.go:141
  3. Update tests in pkg/transport/url_test.go

Labels

bug, operator

Metadata

Metadata

Assignees

No one assigned

    Labels

    Type

    No type

    Projects

    No projects

    Milestone

    No milestone

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions