Understanding MCP Gateway Architecture¶
This guide demonstrates how to explore and understand MCP Gateway's architecture by examining its components, configuration, and request flows in a running cluster.
About MCP Gateway Components¶
You should read the overview first to understand the high-level components and design.
Prerequisites¶
Required Setup: This guide assumes you have a running MCP Gateway cluster.
See the installation guide for setup instructions.
Step 1: Understanding Configuration and State¶
Before observing the system in action, let's understand how it's configured.
MCPServerRegistration Resources¶
MCPServer custom resources define backend servers:
# View all MCPServerRegistration resources
kubectl get mcpsr -A
# Describe a specific MCPServerRegistration
kubectl describe mcpserver api-key-server -n mcp-test
Example MCPServerRegistration spec:
spec:
prefix: test1_
targetRef:
group: gateway.networking.k8s.io
kind: HTTPRoute
name: mcp-server1-route
namespace: mcp-test
Key fields:
prefix: Prefix added to all tools from this servertargetRef: Reference to HTTPRoute that defines the backend
Generated Configuration¶
The controller generates a ConfigMap that the broker/router consumes:
Configuration structure:
data:
config.yaml: |
servers:
- name: mcp-test/mcp-server1-route
url: http://mcp-test-server1.mcp-test.svc.cluster.local:9090/mcp
hostname: server1.mcp.local
prefix: test1_
enabled: true
What each server entry contains:
name: Unique identifier (namespace/route-name)url: Full URL to backend MCP serverhostname: Used for routing decisions by Envoyprefix: Prefix for tool federationenabled: Whether this server is active
HTTPRoute Configuration¶
HTTPRoutes define how to reach backend services:
# View all routes
kubectl get httproute -A
# Describe a backend server route
kubectl describe httproute mcp-server1-route -n mcp-test
What to examine:
spec.hostnames: Used by router for routing decisions (e.g.,server1.mcp.local)spec.rules.backendRefs: Service and port to route tostatus: Whether the route is accepted and programmed
Envoy Configuration¶
Envoy's configuration is generated by Istio from Gateway and HTTPRoute resources:
# View full Envoy configuration (large output)
make istio-config
# Check specific backend clusters
istioctl proxy-config clusters $(kubectl get pods -l istio=ingressgateway -n gateway-system -o jsonpath='{.items[0].metadata.name}') -n gateway-system
# Check routing configuration
istioctl proxy-config routes $(kubectl get pods -l istio=ingressgateway -n gateway-system -o jsonpath='{.items[0].metadata.name}') -n gateway-system
Key Envoy concepts:
- Clusters: Backend service definitions (e.g.,
mcp-test-server1.mcp-test.svc.cluster.local:9090) - Listeners: Entry points for traffic (e.g., port 8080)
- Routes: Mapping from hostnames/paths to clusters
- ext_proc filter: External processor that calls the router for tools/call requests
Step 2: Understanding Session Management¶
The router maintains two types of session mappings:
- Client sessions: Created by the broker when clients initialize
- Backend sessions: Created by the router when first calling a tool on a backend server
Session mapping structure:
Example flow:
- Client initializes → broker creates session
client-abc-123 - Client calls
test1_hiwith sessionclient-abc-123 - Router checks: Does
client-abc-123/server1mapping exist? - If no: Router initializes connection to backend, gets session
backend-xyz-789 - Router stores:
client-abc-123/server1→backend-xyz-789 - Router forwards request with session
backend-xyz-789 - Future calls from same client to server1 reuse session
backend-xyz-789
Step 3: Using MCP Inspector for Interactive Testing¶
The MCP Inspector provides a web interface for exploring the gateway:
This opens http://localhost:6274/?transport=streamable-http&serverUrl=http://mcp.127-0-0-1.sslip.io:8001/mcp
What you can do:
- View all tools: Navigate to Tools → List Tools to see all available tools with their prefixes
- Execute tools: Click on any tool (e.g.,
test1_greet) and provide arguments to execute it - View request/response: See full JSON payloads for each interaction
Step 4: Examining Component Layout and Logs¶
Now that you understand the configuration, let's observe the running system.
View Cluster Status¶
This shows:
- Running components and their status
- Local processes (if any)
Inspect Component Pods¶
# MCP Gateway components
kubectl get pods -n mcp-system
kubectl describe pods -n mcp-system
# Test MCP servers
kubectl get pods -n mcp-test
# Gateway infrastructure (Istio)
kubectl get pods -n istio-system
MCP Broker Logs: Tool Aggregation¶
The broker is responsible for:
- Connecting to all configured backend MCP servers
- Aggregating tools from all servers with prefixes
- Handling client
initializeandtools/listrequests - Caching the aggregated tool list
View broker logs:
# Watch all logs in real-time
kubectl logs -f deployment/mcp-gateway -n mcp-system
# View recent broker activity (filter by key patterns)
kubectl logs deployment/mcp-gateway -n mcp-system --tail=100 | grep -E "(Registering|Discovered|Federating)"
Key log patterns:
| Pattern | Meaning |
|---|---|
Registering server mcpURL=... prefix=... |
Broker connecting to backend MCP server |
Discovered tools mcpURL=... #tools=N |
Successfully connected and discovered tools |
Federating tool mcpURL=... "federated name"=... |
Adding tool with prefix to aggregated list |
Server registered url=... totalServers=N |
Backend server successfully registered |
MCP Router Logs: Tool Call Routing¶
The router is responsible for:
- Intercepting
tools/callrequests via Envoy ext_proc - Parsing tool names to determine target server (based on prefix)
- Setting routing headers (
:authority) for Envoy - Managing backend MCP server sessions
- Stripping prefixes from tool names before forwarding
View router logs:
Note: The router operates as an Envoy external processor (ext_proc) and intercepts requests at the proxy level. Router logs are generated when processing tool calls.
To see router activity, use the MCP Inspector (from Step 3) to make tool calls.
For detailed routing logs, enable debug logging:
MCP Gateway Controller Logs: Dynamic Discovery¶
The controller is responsible for:
- Watching MCPServerRegistration custom resources
- Resolving HTTPRoute references to backend URLs
- Updating ConfigMap with server configuration
- Triggering broker/router reloads
View controller logs:
Key log patterns:
| Pattern | Meaning |
|---|---|
Reconciling MCPServerRegistration |
Processing MCPServerRegistration resource change |
Updated HTTPRoute status |
HTTPRoute discovered and status updated |
Config push completed |
Configuration pushed to broker/router |
Successfully regenerated aggregated configuration |
Configuration successfully updated with server count |
Successfully got status from endpoint |
Backend server health check passed |
Step 5: Tracing Request Flows¶
This section demonstrates how different request types flow through the system.
Setup: Log Monitoring¶
Open two terminals to monitor logs simultaneously:
# Terminal 1 - MCP Gateway logs (broker and router combined)
kubectl logs -f deployment/mcp-gateway -n mcp-system
# Terminal 2 - Envoy access logs (optional)
kubectl logs -f -n gateway-system -l istio=ingressgateway
Flow 1: Initialize Request¶
The initialize method establishes a client session and returns capabilities.
How to test: Use the MCP Inspector (Step 3) - when you first connect, it sends an initialize request automatically.
What happens:
The initialize request is handled by the broker.
Expected logs with debug logging enabled:
INFO Processing request method=initialize
INFO [EXT-PROC] Response backend session: mcp-session-xxxxx
INFO [EXT-PROC] Session ID doesn't need reverse mapping
Flow 2: Tools List Request¶
The tools/list method returns all available tools from all servers.
How to test: In the MCP Inspector (Step 3), navigate to Tools → List Tools.
What happens:
The broker returns the cached aggregated tool list.
Expected logs:
DEBUG [EXT-PROC] HandleRequestBody None tool call setting method header onlytools/list
INFO Sending MCP routing instructions to Envoy: request_body:{response:{header_mutation:{set_headers:{header:{key:"x-mcp-method" raw_value:"tools/list"}}}}}
INFO [EXT-PROC] Processing response body...
Example tools returned:
test1_greet(from server1 with prefixtest1_)test2_greet(from server2 with prefixtest2_)apikey_greet(from api-key-server with prefixapikey_)
Flow 3: Tool Call Request (The Routing Magic)¶
The tools/call method is where routing happens - this is the most complex flow.
How to test: In the MCP Inspector (Step 3):
- Navigate to Tools → List Tools to see available tools
- Click on a tool (e.g.,
test1_greet) - Provide any required arguments
- Click Execute
- Watch the logs in your terminal to see the routing activity
What happens:
The router intercepts the request via Envoy ext_proc, strips the prefix, and routes to the appropriate backend server.
Expected logs with debug logging enabled:
INFO [EXT-PROC] Found matching server toolName=test1_greet serverPrefix=test1_ serverName=mcp-test/mcp-server1-route
INFO Stripped tool name tool=greet originalPrefix=test1_
INFO Completed MCP processing with routing target=mcp-test/mcp-server1-route
INFO Sending MCP routing instructions to Envoy: request_body:{response:{header_mutation:{set_headers:{header:{key:"x-mcp-toolname" raw_value:"test1_greet"}}
INFO [EXT-PROC] Processing response body... (size: 136, end_of_stream: true)
INFO [EXT-PROC] Response body content: event: message
id: 3_0
data: {"jsonrpc":"2.0","id":3,"result":{"content":[{"type":"text","text":"Hi Patryk"}],"structuredContent":{}}}
Step 6: Troubleshooting Common Scenarios¶
Scenario 1: Tool Not Found¶
Symptoms:
Investigation:
-
Check if tool exists in aggregated list using MCP Inspector (Step 3) or:
-
Check MCPServerRegistration status:
-
Check broker logs for connection issues:
Scenario 2: Backend Server Unreachable¶
Symptoms:
- Router logs show connection failures
- 503 Service Unavailable responses
- Tools list is missing tools from a specific server
Investigation:
-
Check backend pod health:
-
Check service exists:
-
Check HTTPRoute is valid:
Scenario 3: Routing to Wrong Server¶
Symptoms:
- Tool calls timeout or return unexpected results
- Router logs show incorrect authority headers
- Tools work when calling backend directly but fail through gateway
Investigation:
-
Check logs for routing activity:
-
Verify prefix mappings in configuration:
-
Check Envoy routing configuration: