Imported from reason-machines/mcp-skills (
skills/mcpsnoop-mcp-debugging/SKILL.md). Install upstream withnpx skills add reason-machines/mcp-skills --skill mcpsnoop-mcp-debugging. Copyright stays with the author.
mcpsnoop MCP Debugging Skill
Skill by ara.so — MCP Skills collection.
mcpsnoop is a transparent proxy for Model Context Protocol (MCP) that sits between your AI client (Claude Desktop, Cursor, Claude Code) and your MCP servers. Unlike the official MCP Inspector which connects as a separate client, mcpsnoop intercepts the actual traffic between your real client and server, showing every JSON-RPC frame live in your terminal.
Installation
Using Go
go install github.com/kerlenton/mcpsnoop/cmd/mcpsnoop@latest
Using Homebrew
brew tap kerlenton/mcpsnoop
brew install mcpsnoop
Pre-built Binaries
Download from the Releases page for your platform.
Core Concepts
mcpsnoop operates in two modes:
- Shim mode (
mcpsnoop -- <server-command>): Acts as a transparent proxy between client and server - UI mode (
mcpsnoop): Displays the captured traffic in an interactive TUI
The shim and UI communicate via a well-known socket and on-disk logs, so they can start in any order.
Configuration
Stdio Transport (Most Common)
Wrap your server command in your MCP client's configuration file. For Claude Desktop, edit ~/Library/Application Support/Claude/claude_desktop_config.json (macOS) or %APPDATA%\Claude\claude_desktop_config.json (Windows):
{
"mcpServers": {
"my-server": {
"command": "mcpsnoop",
"args": ["--", "node", "build/index.js"]
}
}
}
Everything after -- is your normal server launch command.
Examples:
Python server:
{
"mcpServers": {
"weather": {
"command": "mcpsnoop",
"args": ["--", "python", "-m", "weather_server"]
}
}
}
TypeScript server with npx:
{
"mcpServers": {
"filesystem": {
"command": "mcpsnoop",
"args": ["--", "npx", "-y", "@modelcontextprotocol/server-filesystem", "/path/to/allowed"]
}
}
}
Compiled binary:
{
"mcpServers": {
"custom": {
"command": "mcpsnoop",
"args": ["--", "/usr/local/bin/my-mcp-server", "--port", "8080"]
}
}
}
HTTP/SSE Transport
For servers using streamable HTTP, run mcpsnoop as a reverse proxy:
mcpsnoop http --target http://localhost:3000/mcp --listen :7000
Then point your client to http://localhost:7000.
Key Commands
CLI Commands
| Command | Description |
|---|---|
mcpsnoop |
Launch the interactive TUI to view traffic |
mcpsnoop -- <cmd> |
Wrap a server command (shim mode) |
mcpsnoop http |
Start HTTP reverse proxy |
mcpsnoop demo |
Run a scripted demo session |
mcpsnoop --help |
Show all options |
TUI Keybindings
| Key | Action |
|---|---|
enter |
Drill into frame details |
esc |
Go back |
r |
Replay selected tool call |
c |
View capability negotiation |
y |
Copy frame to clipboard |
/ |
Enter filter mode |
: |
Command mode |
p |
Pause/unpause stream |
f |
Follow mode (scroll to latest) |
ctrl-d |
Delete session |
j/k |
Move up/down |
ctrl-f/ctrl-b |
Page forward/back |
g/G |
Jump to top/bottom |
? |
Show help |
Filtering Traffic
Press / in the TUI to filter frames. Combine tokens with spaces (ANDed):
Filter Syntax
tool:search status:slow # Slow calls to search tool
dir:s2c kind:req # Server-to-client requests
method:tools/call id:123 # Specific method and ID
status:error tool:database # Failed database tool calls
kind:notif # All notifications
dir:c2s status:pending # Pending client requests
Available Filters
- tool: Filter by tool name (e.g.,
tool:search,tool:write_file) - method: JSON-RPC method (e.g.,
method:tools/call,method:initialize) - id: Request/response ID
- kind:
req(request),resp(response),notif(notification) - dir:
c2s(client-to-server),s2c(server-to-client) - status:
ok,error,slow,pending
Plain text searches match method, tool name, ID, and payload content.
Common Patterns
Debugging a Tool That Isn't Being Called
- Configure mcpsnoop wrapper in your client
- Restart the client
- Open mcpsnoop TUI:
mcpsnoop - Press
cto view capabilities - Verify your tool is listed in server capabilities
- Check if client accepted the capability
- Use filter:
/tool:your_tool_name - Attempt to use the tool in your client
- Look for
PENDINGstatus (indicates hung call) or absence of call
Inspecting Capability Negotiation
# Start your client with mcpsnoop wrapper
# Open TUI
mcpsnoop
# Press 'c' to view capabilities screen
# Navigate between:
# - Client capabilities (what the AI client supports)
# - Server capabilities (what your server advertises)
# - Handshake details
Replaying a Tool Call
# In TUI, navigate to a tools/call request
# Press 'r' to replay
# mcpsnoop spawns a fresh isolated server instance
# Executes the exact same call
# Shows the new response
This is useful for:
- Testing fixes without restarting your client
- Comparing responses after code changes
- Debugging non-deterministic behavior
Monitoring Slow Tools
# In TUI
/status:slow
# Shows only slow calls (threshold configurable)
# Each frame shows elapsed time
# PENDING calls show live timer
Debugging Server Stderr
Server stderr appears in the stream with special highlighting:
[STDERR] Warning: database connection slow
[STDERR] Error: timeout connecting to external API
Filter to see only stderr: /kind:notif
Real-World Examples
Example 1: Debugging a File System Server
{
"mcpServers": {
"filesystem": {
"command": "mcpsnoop",
"args": [
"--",
"npx",
"-y",
"@modelcontextprotocol/server-filesystem",
"/Users/dev/projects"
]
}
}
}
In TUI:
# Filter to file operations
/tool:read_file
# Or see all filesystem tools
/method:tools/call
# Check which directory was authorized
# Press 'c' for capabilities, look for "roots"
Example 2: Monitoring a Database Tool
{
"mcpServers": {
"database": {
"command": "mcpsnoop",
"args": ["--", "python", "db_server.py"],
"env": {
"DATABASE_URL": "postgresql://localhost/mydb"
}
}
}
}
In TUI:
# See only database queries
/tool:query
# Find slow queries
/status:slow tool:query
# Inspect a specific query
# Navigate with j/k, press enter to see full JSON
# Press 'y' to copy query details
Example 3: HTTP Server Debugging
# Terminal 1: Start your HTTP MCP server
python http_server.py --port 3000
# Terminal 2: Start mcpsnoop proxy
mcpsnoop http --target http://localhost:3000/mcp --listen :7000
# Terminal 3: View traffic
mcpsnoop
# Configure client to connect to http://localhost:7000
Example 4: Multi-Server Setup
{
"mcpServers": {
"weather": {
"command": "mcpsnoop",
"args": ["--", "python", "weather_server.py"]
},
"database": {
"command": "mcpsnoop",
"args": ["--", "node", "db-server.js"]
},
"filesystem": {
"command": "mcpsnoop",
"args": ["--", "npx", "-y", "@modelcontextprotocol/server-filesystem", "/home/user"]
}
}
}
The TUI shows all servers in separate sessions. Use :sessions command to switch between them.
Troubleshooting
UI Shows "No sessions"
Cause: Shim hasn't started or client hasn't launched the server yet.
Solution:
- Verify mcpsnoop is in your client config
- Restart your AI client completely
- Trigger an MCP action to start the server
- Wait a few seconds and refresh UI
Tool Call Hangs (Shows PENDING)
Symptoms: Request shows PENDING with increasing timer, no response.
Debug:
- Check server stderr in the frame list
- Press
enteron the PENDING frame to see full request - Look for resource locks or external API timeouts
- Press
rto replay with debug logging
Server Not Starting
Check:
# Test server command directly
node build/index.js # Or your actual command
# Check mcpsnoop can find the command
which node
which mcpsnoop
# Look at client logs
# Claude Desktop: ~/Library/Logs/Claude/
Capabilities Mismatch
Symptoms: Client doesn't see tool server advertises.
Debug:
- Press
cin TUI - Compare server capabilities vs client capabilities
- Check server's
initializeresponse - Verify tool schema matches MCP spec
Frames Not Appearing in TUI
Check:
- Socket connection:
ls -la ~/.config/mcpsnoop/(Linux/macOS) - Log directory: Check for
.jsonlfiles - Permissions: Ensure shim can write logs
- Try
mcpsnoop demoto verify TUI works
Replay Fails
Possible causes:
- Server has state dependencies
- External resources unavailable
- Non-idempotent operations
Solution: Check stderr in replay output and compare request parameters.
Advanced Usage
Custom Log Directory
mcpsnoop --log-dir /custom/path
Filtering in Shim Mode
# Only log specific tools (reduces disk usage)
mcpsnoop --filter tool:search -- python server.py
Exporting Sessions
# Sessions are stored as JSONL
cat ~/.config/mcpsnoop/sessions/*.jsonl | jq .
Performance Considerations
- mcpsnoop adds minimal latency (microseconds for copying frames)
- Disk I/O is async and buffered
- Large payloads (>1MB) may slow down TUI rendering
- Use filters to reduce noise in busy systems
Integration with Development Workflow
During Development
# Terminal 1: Your editor/IDE
code .
# Terminal 2: mcpsnoop TUI
mcpsnoop
# Terminal 3: Test client or manual testing
# Make changes to server code
# Restart client or use replay feature to test immediately
Testing Tools
# Capture a successful tool call
# Press 'y' to copy JSON
# Paste into your test suite as expected output
# Replay with modified server code
# Press 'r' repeatedly while iterating
CI/CD Integration
mcpsnoop logs are structured JSONL, suitable for automated testing:
# Run test, capture logs
mcpsnoop --log-dir ./test-logs -- python server.py &
# Run your MCP client test
# Parse logs
jq 'select(.kind == "response" and .status == "error")' test-logs/*.jsonl
Resources
- MCP Specification
- mcpsnoop GitHub
- MCP Inspector (alternative tool)
- Demo Walkthrough