DuckDuckGo MCP Server

Model Context Protocol (MCP) server that exposes DuckDuckGo search as a tool for LLM clients (Claude Desktop, Cursor, VS Code, ...), backed by a self-hosted SearXNG metasearch instance.

SearXNG aggregates results from DuckDuckGo, Google, Brave, Wikipedia, and more with its own request handling — no browser fingerprinting, no API keys, fully self-hosted.

Part of the MCP Search Servers project:

Repo What it is
google-mcp Same design for Google search

Service

Service Port MCP tool Description
duckduckgo-mcp 3002 duckduckgo_search DuckDuckGo results via SearXNG
searxng Internal metasearch engine (not published)

The server exposes:

  • /sse + /messages/ — MCP SSE transport
  • /search?q=...&num=N — plain HTTP JSON endpoint
  • /health — liveness probe

Quick Start

cp .env.example .env        # fill in SEARXNG_SECRET
docker compose up -d --build

Generate a SearXNG secret:

python3 -c "import secrets; print(secrets.token_hex(32))"

Verify:

curl http://localhost:3002/health
curl "http://localhost:3002/search?q=python&num=3"

Then point your LLM client at http://localhost:3002/sse.

Tool Contract

{
  "name": "duckduckgo_search",
  "arguments": { "query": "Python programming language", "num_results": 5 }
}

Returns numbered results with title, URL, and snippet (max 20 results, queries capped at 500 characters).

Project Structure

.
├── duckduckgo-mcp/    # MCP server (SSE transport + tools)
│   ├── server.py
│   └── Dockerfile
├── lib/               # Shared search engine implementations
│   ├── duckduckgo_search.py
│   ├── google_search.py  # also used by the google-mcp sibling repo
│   ├── playwright_manager.py
│   └── rate_limiter.py
├── searxng-settings.yml
├── test_client.py
└── docker-compose.yml
Description
DuckDuckGo search as an MCP tool over self-hosted SearXNG (sibling: google-mcp)
Readme 38 KiB
Languages
Python 98.8%
Dockerfile 1.2%