Research MCP
Provides read-only GitHub API access for searching code, issues, repositories, and inspecting repository contents.
Click on "Deploy Server".
Wait a few minutes for the server to deploy. Once ready, it will show a "Started" state.
In the chat, type
@followed by the MCP server name and your instructions, e.g., "@Research MCPfind detailed information about the James Webb Space Telescope"
That's it! The server will respond to your query, and you can continue using it as needed.
Here is a step-by-step guide with screenshots.
Private Search Gateway
This project is a deterministic, self-hosted search and page-retrieval backend for AI frontends. It exposes a fast SearXNG-compatible discovery endpoint, a bounded integrated search route, and Firecrawl-compatible scrape/search routes. The gateway starts with the user's exact query and a small healthy set of broad search engines. It stops when that evidence is already good, or runs one bounded fallback wave when relevance, entity coverage, or source diversity is weak. It opens pages only when the selected route asks for it, extracts their actual contents, reranks evidence locally, and returns source URLs and page-derived text.
Search results also carry deterministic evidence metadata: an inferred source type and tier, an authority score, normalized page-declared dates, version markers, a stable citation ID/URL, and exact character spans for selected passages. These are ranking and coverage aids, not claims that the gateway has proved source ownership or verified every claim.
It does not require a paid search API or an internal language model. The gateway always performs deterministic query planning first. When the first search wave has weak entity coverage, relevance, or source diversity, an optional OpenAI-compatible planner can add at most two validated alternatives. The planner is never used on a strong first pass; invalid, slow, or unavailable output falls back to deterministic planning. The frontend's model receives the retrieved evidence and writes the answer. This keeps the service usable by any frontend that accepts a custom SearXNG or JSON search provider.
What runs
search-gateway: the only client-facing service, on internal port8080searxng: web, technical, news, image, and research discoveryreranker: localBAAI/bge-reranker-baserelevance rankingcrawl4ai: JavaScript-aware crawling for difficult pagesweb-runner: isolated Crawl4AI and Playwright control over a Unix socketpdf-runner: network-isolated PDF extractionsafe-egress: blocks private-network and metadata destinations for browsersredis: response cache, stale-result fallback, and learned per-domain fetch strategy
The stack publishes no host ports. A frontend reaches it over a shared Docker network at:
http://search-gateway:8080/searchEvery container attached to that shared network can call the gateway. Use a dedicated shared network if other unrelated containers should not have access.
Related MCP server: deep-research
Requirements
64-bit Linux VPS
Docker Engine and Docker Compose v2.24.4 or newer
About 10 GB free disk for images, Chromium, and the reranker model
16 GB RAM recommended for the complete stack
The supplied ceilings total about 10.5 GB, excluding shared memory and normal Docker overhead. They are limits, not reservations, but leave useful headroom on a 16 GB host. The first build is slow because it downloads Chromium, the Crawl4AI image, and the reranker model.
Clean installation
Create the Docker network once if it does not already exist:
docker network inspect docker-stacks_app-network >/dev/null 2>&1 || \
docker network create docker-stacks_app-networkClone and configure the project:
git clone https://github.com/ZDOSt/Research-MCP.git
cd Research-MCP
cp .env.example .env
chmod 600 .envGenerate three different secrets:
openssl rand -hex 32
openssl rand -hex 32
openssl rand -hex 32Edit .env and replace SEARXNG_SECRET, CRAWL4AI_API_TOKEN, and
FIRECRAWL_API_KEY with three different values. Change
CLIENT_DOCKER_NETWORK only if your frontend uses a different external Docker
network.
Validate and start the complete stack:
docker compose config --quiet
docker compose up -d --build --wait
docker compose psNo ports: entries are needed. Do not add one unless you intentionally want to
expose the gateway outside Docker.
Verify it
Run a health check from the gateway container:
docker compose exec -T search-gateway python -c \
"import urllib.request; print(urllib.request.urlopen('http://127.0.0.1:8080/healthz').read().decode())"Run a real search from any container on the shared network. Replace
your-frontend-container with anythingllm, librechat, or another container
name:
docker exec your-frontend-container sh -lc \
"wget -qO- 'http://search-gateway:8080/search?q=how+to+install+docker+compose&format=json' | head -c 1000"The response should contain results, source URLs, search snippets, and
diagnostics. This endpoint intentionally does not crawl pages, so it returns
quickly and is suitable for standard SearXNG integrations.
Frontend setup
Use the following base URL wherever the frontend asks for a SearXNG URL:
http://search-gateway:8080If it asks for the complete search path, use:
http://search-gateway:8080/searchAnythingLLM requires the complete discovery path even though its field is
labeled SearXNG API Base URL. Configure it as:
http://search-gateway:8080/searchUse http://search-gateway:8080/integrated/search in that field instead when
you specifically want AnythingLLM's search request to include a bounded crawl.
The standard request is:
GET /search?q=your+question&format=jsonSupported query parameters include:
language=autotime_range=day|week|month|yearcategories=general,it,news,science,imagesmax_results=1..8mode=auto|quick|balanced|deep
When no category is supplied, the gateway infers useful SearXNG categories from
the request. auto uses quick mode for simple unanchored lookups and balanced
mode for technical questions, recommendations, and identifiable subjects.
quick performs one search wave;
balanced conditionally adds one fallback query and a small crawl budget. When
an identifiable subject has no matching candidates, that fallback relaxes the
request to the subject plus preserved proper names or identifiers, then to the
subject alone when the mode permits another variant;
deep permits two bounded fallback variants and wider evidence. The discovery
route never crawls.
Broad web search remains primary. Rate-limited or CAPTCHA-blocked engines enter a temporary cooldown, duplicate URLs are combined with reciprocal-rank and multi-engine consensus signals, and weak searches may receive keyless supplemental candidates from Stack Exchange, Wikipedia, Crossref, or GitHub when the request explicitly asks for repository information. Supplemental sources never replace broad search or exclude ordinary web results.
To enable the optional planner, set GATEWAY_PLANNER_BASE_URL,
GATEWAY_PLANNER_MODEL, and, when required, GATEWAY_PLANNER_API_KEY in
.env. GATEWAY_PLANNER_MODES=balanced,deep is the default. The planner is
called only after a weak first search wave, has a three-second default timeout,
and is guarded by entity-preservation checks. Leave the URL and model empty for
fully deterministic operation.
Integrated search and Firecrawl compatibility
For a frontend that has one combined search/scraper setting, use the bounded integrated route:
http://search-gateway:8080/integrated/searchIt performs adaptive discovery, crawls a small initial batch, replaces failed
or blocked pages from the remaining ranked candidates, and returns page-derived
content. Its default timeout and crawl budget are intentionally smaller than
/v1/research.
Learned browser preferences are not permanent. After the configured re-probe interval, the gateway retries direct retrieval so temporary blocks do not keep a recovered domain on the slower browser path.
For LibreChat, Open WebUI, or LobeChat Firecrawl settings, use this API base:
http://search-gateway:8080The gateway implements POST /v2/scrape and POST /v2/search. Set the
frontend's Firecrawl API key to the same value as FIRECRAWL_API_KEY in the
gateway .env. The scraper accepts the common Markdown request and returns
success, data.markdown, and data.metadata.sourceURL. The Firecrawl routes
require a Bearer token and use the existing URL validation, direct extraction,
Crawl4AI, Playwright, and PDF isolation controls.
The gateway also implements a Jina-compatible POST /v1/rerank endpoint backed
by the stack's local BGE reranker. It uses the same Bearer credential as the
Firecrawl routes. This adapter lets LibreChat include relevant passages from
scraped pages in the model-visible Web Search result without a hosted reranking
service. Frontend requests larger than the local model's 32-text client limit
are split into bounded batches and their scores are merged. The integrated
route uses CPU-friendly 16-text batches and caps passage reranking at 32
page-diverse passages. If the local model is unavailable or exceeds its bounded
deadline, the adapter returns lexical fallback passages instead of an empty
result.
Crawl4AI runs without direct public DNS or Internet access. Its redundant
in-container destination precheck is disabled because it cannot resolve public
targets in that topology. URL syntax is checked by web-runner, and every
actual browser connection still passes through the pinning proxy and
safe-egress, which resolves the hostname and rejects private, loopback,
link-local, metadata, and otherwise non-public destinations.
Queries containing an explicit HTTP or HTTPS URL bypass SearXNG discovery. The supplied URL is returned as the deterministic direct discovery result and then passes through the same authenticated Firecrawl-compatible scraper. This prevents direct-page requests from depending on whether a search engine happens to index the supplied URL.
The /v1/research and /integrated/search responses include an
evidence_summary with independent-domain coverage, likely primary-source
coverage, date and extraction coverage, version context, and explicit warnings
when evidence is thin. Each extracted result also includes an evidence list
with stable passage IDs, exact source character spans, section labels when
available, and passage scores. Source classification is based on transparent
domain, path, and query-affinity heuristics. It never represents itself as
claim-level verification or proof that two domains are organizationally
independent.
Use these internal Docker URLs:
Frontend | Search setting | Scraper setting | Reranker setting |
AnythingLLM |
| Use the integrated route when its separate scraper cannot be changed | Included in integrated search |
LibreChat | SearXNG base | Firecrawl base | Jina URL |
Open WebUI | SearXNG query URL |
| Configure separately in the frontend |
LobeChat | Configure its preferred search provider separately |
| Configure separately in the frontend |
For Open WebUI select the Firecrawl web loader and set FIRECRAWL_API_KEY.
For LobeChat include Firecrawl in CRAWLER_IMPLS and set the same key. For
LibreChat select SearXNG as the search provider and Firecrawl as the scraper;
permit the private search-gateway address in its web-search allowlist.
Examples:
POST /v2/scrape
Authorization: Bearer <FIRECRAWL_API_KEY>
Content-Type: application/json
{"url":"https://example.com","formats":["markdown"]}POST /v2/search
Authorization: Bearer <FIRECRAWL_API_KEY>
Content-Type: application/json
{"query":"how to install Docker Compose","limit":5}POST /v1/rerank
Authorization: Bearer <FIRECRAWL_API_KEY>
Content-Type: application/json
{
"model": "jina-reranker-v2-base-multilingual",
"query": "Docker Engine Ubuntu installation commands",
"documents": ["first passage", "second passage"],
"top_n": 5,
"return_documents": true
}For direct integrations, the full bounded research endpoint is also available:
POST /v1/research
Content-Type: application/json
{
"query": "What are the recommended settings for an AW3426DW?",
"mode": "balanced",
"max_results": 5,
"language": "auto",
"categories": []
}Updating
From the repository directory on the VPS:
git pull --ff-only
docker compose config --quiet
docker compose up -d --build --remove-orphans --wait
docker compose psYou do not need to run docker compose down for a normal update. Existing Redis
cache and reranker downloads remain in named volumes.
If the existing .env file already defines reranker settings, set
GATEWAY_RERANKER_TIMEOUT_SECONDS=8,
GATEWAY_RERANKER_MAX_BATCH_SIZE=16, and
GATEWAY_RERANKER_MAX_DOCUMENTS=32; values in .env override the Compose
defaults.
Operations
Useful commands:
docker compose ps
docker compose logs --tail=200 search-gateway searxng reranker
docker compose logs --tail=200 crawl4ai web-runner safe-egress pdf-runner
docker compose restart search-gateway
docker compose down
docker compose up -d --waitRepeatable quality baseline
The opt-in live evaluation suite covers installation guides, errors, hardware settings, recommendations, version-sensitive questions, direct URLs, multi-source comparisons, gaming, academic material, and current news. It is not run automatically and adds no latency to normal gateway requests.
From inside the running gateway container:
docker compose exec -T search-gateway python evaluate_search_quality.py \
--base-url http://127.0.0.1:8080Run one case while tuning with --case docker-compose-install, or retain the
JSON report with --output /tmp/search-quality-report.json. See
evals/README.md for the measured fields and limitations.
docker compose down preserves named volumes. docker compose down -v deletes
the cache and downloaded reranker model and should be used only for a deliberate
full reset.
Limitations
This can approach hosted search tools for documentation, troubleshooting, product settings, games, current information, and general research, but it cannot guarantee the same coverage as commercial providers. Keyless engines may rate-limit datacenter IPs, some sites block all automated browsers, and no single VPS has the proprietary search indexes used by Google, Brave, or paid answer engines. The gateway compensates with adaptive engine cooldowns, source-neutral query fallbacks, consensus fusion, keyless supplemental indexes, learned extraction strategies, local reranking, bounded browser fallbacks, caching, and honest partial results rather than inventing an answer.
This server cannot be deployed
Maintenance
Related MCP Connectors
AI Reasoning Cache & Consensus Layer with 11 MCP tools via Streamable HTTP.
Scrape, crawl and search the web for AI agents via MCP.
Stealth web browser for agents: search, fetch, click, download and type in persistent MCP sessions.
Read-only MCP tools for AI agent discovery, structured resources, and NIULAI information.
Related MCP Servers
- AlicenseAqualityAmaintenanceProvides local-first web intelligence over MCP with tools for search, fetch, crawl, extract, cache, find-similar, research, and autonomous agent loops, requiring no API keys.10940 npm5,284AGPL 3.0
- AlicenseNot gradedqualityDmaintenanceEnables deep research tasks using a multi-agent architecture that integrates any LLM and MCP tools. Available via MCP stdio, streamable HTTP, and SSE transports.17MIT
- AlicenseAqualityAmaintenanceEnables AI agents to run local deep-research workflows via a single MCP stdio server, combining web search, page extraction, query-aware distillation, and caching without cloud quotas. It exposes tools for deep research, search, and single or batch URL reading.6MIT
- AlicenseAqualityCmaintenanceGives MCP-capable agents live web access: search the web, scrape pages into Markdown (including JavaScript-heavy and bot-protected sites), and extract named fields as JSON, with job polling, token-aware content offloading, and built-in research guidance. Ships as a self-hostable stdio or HTTP service with spend caps and per-request key support.7MIT