mcp server
argos-engine
Token-efficient, local-first web research MCP server in Rust: keyless multi-profile metasearch. Built on FlojoMCP.
Set up
Runs on your computer. Pick your agent and operating system.
This project does not publish an install method we can turn into a config. Follow the README instead.
README
synced Oct 26, 2026Argos Engine
Token-efficient, local-first web research MCP server in Rust. Keyless multi-engine search with parallel fanout, dedup and automatic failover — no API keys, no runtime, no VM required. Built on FlojoMCP over the official Rust MCP SDK (rmcp).
Keywords: MCP server, web search, deep research, metasearch, keyless, token efficiency, AI agents, Model Context Protocol, local-first, Rust, DuckDuckGo, Bing.
Why
Search MCPs force a bad trade: scrape fragile engines yourself, rent an API key, or run a container farm — and either way the agent pays for it in tokens and timeouts.
- Keyless by default: DuckDuckGo, Bing and Brave HTML endpoints queried directly from Rust for compatibility. No accounts, no cards, no Docker, no WSL. The direct HTML set is experimental: see the measured quality and policy caveats below before treating it as a durable index.
- Browser impersonation: the HTTP layer (primp, same crate ddgs uses) masquerades as Chrome153/Windows — measured difference: without it Bing serves a
302to its homepage and Brave returns429; with it all three engines answer200. - Fanout with failover: all providers queried in parallel, results fused with weighted RRF and deduplicated by canonical URL. When one engine rate-limits your IP (202/403/429 happen — see below), the others still answer: research degrades, it doesn't die.
- Tokens are a feature: compact results, server-side truncation budgets (
src/limits.rs), dedup before the agent ever sees duplicates. - No silent failures: every
searchresponse carries the per-provider status (ok,empty,filtered,rate_limited,unreachable) and the warnings. If all engines were throttled, the tool returns a typedAllProvidersRateLimitederror; if providers answered but every result failed Argos' domain/relevance gate, it returnsNoUsableResultsinstead of pretending the topic had no hits. - Honest, typed errors:
rate_limited,unreachable,all_providers_rate_limited,no_usable_results— each with an actionable hint, never a genericError executing toolghost. - Per-provider visibility: every
searchresponse carries{ results, providers: [{name, kind}], warnings }so the agent knows exactly which engines contributed, which were empty or filtered, and which errored. - One small binary: ~7 MB exe, ~5 ms startup, ~4 MB RAM — no Python/Node runtime.
Status
Early development — Milestone 1: keyless multi-provider search. Not production-ready yet.
| Feature | Status |
|---|---|
search via five keyless profiles: general web (DuckDuckGo/Bing/Brave), academic (OpenAlex, Crossref, arXiv, Europe PMC, PubMed, DOAJ, Semantic Scholar), code (GitHub, crates.io, npm, Packagist), news (GDELT) and knowledge (Wikipedia). Weighted RRF fusion, canonical dedup, failover | ✅ |
| Browser impersonation (primp / Chrome153) — Bing & Brave pass | ✅ |
status with per-provider reachability probes | ✅ |
Typed errors with hints (rate_limited, all_rate_limited, unreachable, ...) | ✅ |
| Real-markup fixture tests (captured HTML from live engines) | ✅ |
| More keyless providers | 📋 provider audit first; see PROVIDER_AUDIT.md |
| research tool: multi-query fan-out, progress + cancellation, compact digest | 📋 M2 |
| Content extraction (readability → markdown, no XPath) | 📋 M3 |
| Optional cloud providers (Serper/Tavily/Exa) behind SearchProvider | 📋 M3+ |
Requirements
- Rust 1.89+ (rustup) — primp's floor
- Windows: VS Build Tools (the
.batscripts set upVsDevCmd); plaincargo buildworks on any platform. - Nothing else: no Docker, no WSL, no VM, no API keys.
Quick start
cargo build --release # or build.bat on Windows (release + tests)
Connect from opencode.jsonc:
"argos": {
"type": "local",
"command": ["D:\\Mis Juegos\\ClaudeMCPs\\argos-engine\\target\\release\\argos-engine.exe"]
}
Or any MCP client (Claude Desktop, Cursor, Inspector…): command = the argos-engine binary, stdio transport.
Tools
| Tool | Arguments | Returns |
|---|---|---|
search | query, limit? (1-50, default 10), page?, profile? (general, academic, code, news, knowledge), domains? ([String], e.g. ["kvrforums.com", "reddit.com"]) | `{ results: [{ url, source, title, snippet, engine }], providers: [{name, kind: "ok" |
status | profile? (same values) | { name, version, profile, providers: [{name, reachable}] } |
Both tools declare all four MCP annotations, so a client can tell before invoking that they are read-only, non-destructive, idempotent and open-world:
{ "readOnlyHint": true, "destructiveHint": false, "idempotentHint": true, "openWorldHint": true }
search only reads: nothing the caller can observe is mutated, so a host can invoke it without warning.
Configuration
| Env var | Default | Meaning |
|---|---|---|
ARGOS_PROVIDERS | 16 implemented adapters | Enabled adapters; the profile decides which family spends quota |
ARGOS_CONTACT_EMAIL | (unset) | Optional contact address for the OpenAlex/Crossref/PubMed polite pools. Not a key, no account |
ARGOS_GITHUB_TOKEN | (unset) | Optional token; raises the GitHub Search quota from 60/h |
ARGOS_SEMANTIC_SCHOLAR_KEY | (unset) | Optional key; anonymous traffic is throttled hard |
ARGOS_META_INITIAL | 2 | Maximum providers in the first native metasearch wave |
ARGOS_META_TOTAL | 5 | Maximum providers considered across fallback waves |
The rate-limit reality (measured, not guessed)
Anti-bot limits live in the upstream engines, not in your client — and every keyless approach shares that wall — SearXNG's own docs admit it gets CAPTCHAs too, which is why the optional adapter was dropped. Measurements from one residential IP,2026-09-24:
| Endpoint | Plain client (reqwest, rustls and schannel) | With primp (Chrome153 impersonation) |
|---|---|---|
html.duckduckgo.com | 200 with browser UA / 403 with PowerShell UA | 200,10-12 organic results |
www.bing.com/search | 302 → homepage (same headers/HTTP1.1 that curl passes — pure ClientHello discrimination) | 200,10 b_algo |
search.brave.com/search | 429 | 200,20 web results |
www.mojeek.com/search | CAPTCHA | CAPTCHA (IP/consent-based — out of the set) |
Argos raises the ceiling with design instead of hoping: browser impersonation at the transport layer, parallel fanout across independent rate budgets, weighted RRF fusion + canonical URL dedup (fewer redundant queries for the agent), a short-lived cache with single-flight, per-request timeouts and typed rate-limit errors with failover.
Quality reality (measured 2026-09-24)
HTTP 200 is not a quality result. A controlled live audit found that DDG and Brave can return highly relevant niche results on their first request and then quickly return 202/429 from the same IP. Bing returned valid HTML with b_algo entries but poor semantic coverage for the same queries: free piano VST produced free-game pages, and one Spitfire Audio LABS free run produced Macao travel pages. The query itself was present in Bing's final URL, so this was not a URL-encoding failure.
Argos therefore applies a conservative result-side quality gate:
domainsis validated and enforced against the returned host;site:text is only a ranking hint, never the security boundary.- Results with no meaningful query terms are rejected as obvious entity drift.
- A provider whose entire result set was rejected is
filtered, notok. - If no provider contributes a usable result, the tool returns typed
NoUsableResults.
The full matrix and policy notes are in PROVIDER_AUDIT.md. The direct HTML endpoints remain a compatibility set, not a guarantee of quality or long-term provider availability.
Comparison (researched 2026-09-23)
| Argos Engine | ddgs MCP (Python) | Cloud search MCPs (Tavily / Serper / Exa) | |
|---|---|---|---|
| Runtime | single ~7 MB exe | Python ≥3.10 + pip package | binary + API key |
| Startup / RAM | ~5 ms / ~4 MB | ~324 ms / ~50-76 MB¹ | n/a |
| Keys & cost | none | none (direct scraping) | keys, free tiers then paid |
| Multi-engine failover | ✅ parallel fanout | sequential per-call engines | provider-dependent |
| Deadlines / typed errors | ✅ | ❌ blocking threads, opaque errors | provider-dependent |
| Engine maintenance | sync from ddgs reference + own parsers | per-engine XPath, constant upstream fixes | provider's problem |
| Deep-research fan-out | roadmap (M2) | no — N sequential LLM calls | partial (their own APIs) |
¹ FastMCP/Python figures from FlojoMCP benchmarks; ddgs behavior from source inspection of v9.16.0.
Roadmap
- M1 — keyless fanout (DDG + Bing + Brave, primp impersonation), dedup, typed errors, fixtures, per-provider outcome and validated
domainsscoping ← current - M1.1 — provider quality gates, result-side scope enforcement and
NoUsableResults; see PROVIDER_AUDIT.md ← current - M1.2 — Native Metasearch Engine: provider registry, profiles, index-family diversity, circuit breaker, quota/cooldown state, RRF fusion and compact token-aware output; see PROVIDERS.md ← current
- M1.3 — keyless and public API adapters (academic, code, news and local verticals)
- M1.4 — user-key/free-tier adapters, with provider-owned keys and quotas
- M2 —
researchtool: multi-query fan-out with reformulation, optional source allowlist, progress + cancellation, compact digest (ChatGPT/Qwen deep-research style) - M3 — content extraction (Rust readability, no XPath) and optional structured remote providers behind the same trait
Decisions and progress live in AGENTS.md.
License
GPL-3.0 — see LICENSE.