Infobroker
One server. Every source. Research that delivers.
Infobroker is a multi-provider MCP server that unifies web search,
structured knowledge, academic, archive, and content-extraction APIs
behind a single tool surface. Twenty-one zero-config providers ship in the
box — search the web, look up facts, fetch articles — with nothing to
configure. Five more providers unlock with an API key or self-hosting.
A built-in corroboration engine cross-references independent sources to
separate established facts from contested claims. Bundled client skills
transform raw research into polished writing. Free first. Privacy always.
[infobroker MCP server]
[M8ven Live Monitored]
North Star
Infobroker is the Bothan Spynet as a tool — a decentralized intelligence
network that queries independent sources and routes results through a
single, impartial interface. In intelligence-cycle terms, you supply the
direction and get the dissemination; the server handles the collection and
processing.
Quick Start
The npm package ships its default configuration. The server resolves it from
the installed package, so no environment variable is required. Your own
overrides live at ~/.config/infobroker/config.local.json, or at a path set
by INFOBROKER_CONFIG_LOCAL.
To run from a clone instead:
The configuration below is written for OpenCode. Other MCP clients connect the same way — a local server command plus the instruction and skill paths — but their config keys and file locations differ, so adapt the block to your client's schema.
Add this to your OpenCode config (~/.config/opencode/opencode.json):
For an npm install, point instructions and skills.paths at
node_modules/infobroker/... and use ["npx", "-y", "infobroker"] as the
command. On Windows, quote paths containing backslashes.
The mcp block starts the server; the instructions and skills blocks
are what activate the bundled client skills. Without them the skills ship
with the package but stay inert.
Most free providers work immediately; CORE needs a free API key. The keyed
providers — Exa, Tavily, Yep — unlock higher throughput and specialized
search when enabled, and self-hosted SearXNG gives full query privacy:
Requirements: Node.js 24+.
MCP Server
Your research backend. Seven tools, twenty-six providers, one
corroboration engine. The complete feature inventory is documented in the
feature taxonomy in the
spec.
Unified Search
"Search for the location of the second Death Star."
"Find scholarly papers on hyperspace travel theories."
"Search the latest astromech specs and show me the passages that answer: does the R2 unit pre-date the Clone Wars?"
search_web sends one query to every provider that can answer it. Search
across DuckDuckGo, Wikipedia, academic databases, news, code repositories —
or describe your task and the server picks the best source. Common operators
(site:, filetype:, quoted phrases) pass through to engines that support
them, a preferred language is honored where a provider allows it, and anything
the serving provider drops is reported rather than hidden. Pass an array of
queries to batch several searches in one call. Ask for a deep read and it
fetches the top results, then ranks each page's passages against your query,
so you get the specific text that answers the question instead of links. Pass
analyze: true and the same response carries topic terms, entity mentions,
semantic clusters, and a dated timeline derived from those results — computed
in-process, with no extra request. A query that names a measurable attribute —
attendance, population, a percentage, a date — resolves a sourced facts
entry from Wikidata or a Wikipedia infobox/table ahead of the prose results.
Failed providers fall back silently through a configurable chain so you get
results, not error messages. Other search tools lock you to one engine;
Infobroker routes every query to the right provider and keeps going when one
fails. Every tool also returns the same envelope as a machine-readable
object, so programmatic clients read fields instead of parsing text.
Content Extraction
"Fetch the article on the Battle of Yavin and summarize it."
"Get the text of that page about the Death Star plans."
"Where, in that report, does it mention the reactor core?"
fetch_page hands any URL to Jina Reader, which renders it as clean
Markdown optimized for LLM consumption. It falls back to native HTTP when
Jina is throttled. Wikipedia and Internet Archive have dedicated
renderers for source-specific extraction. Ask a page a question — pass
question to fetch_page and it returns the passages that answer it, each
scored and ranked, instead of the whole document. Fetch several URLs at once
and each result keeps its own renderer, ranked passages, and top score. Pass
raw: true to get the page text directly, without the JSON wrapper.
Built-in web fetchers return raw HTML; Infobroker gives you clean, readable
content from any source — ready for summarization or analysis. Fetch also
reports the page's last-updated date when it can determine one, so you know
how current your source is. When a page is paywalled, access-restricted, or
bot-blocked, fetch_page reports access_blocked and falls back to Crossref
metadata or an open-access copy for a DOI, and to an Internet Archive
snapshot when no metadata record exists.
Citations
"Give me BibTeX references for papers on hyperdrive field dynamics."
"Cite the paper that first described the hyperdrive field equations."
get_citations searches scholarly sources and returns each reference as a formatted
BibTeX entry with its fields — title, authors, year, venue, and URL — ready
to paste into a reference list.
Provider Intelligence
"Which source should I use to research the Death Star's weakness?"
"Show me all available sources and their quota status."
The server knows its own capabilities. search_web auto-selects the
best backend for your task, weighing capability, quota, and latency —
or routes by your intent when you ask for privacy, speed, or free-only
sources. When the automatic choice misses, pass task_type to force a
dispatch chain (for example academic), and meta.task_type reports the
chain that served the query. inspect_providers surfaces every configured
source, reports its
derived privacy posture, and drills into a single provider's uptime and error
history. The generated skills/infobroker/references/provider-privacy.md
documents query forwarding, retention, account requirements, and resale for
every provider, marking what configuration cannot establish as unknown rather
than assuming privacy. No other search MCP server gives you operational
visibility into every backend.
Multi-Source Verification
"Verify whether the Empire really destroyed Alderaan."
"Find the consensus on who fired first — Han or Greedo."
verify_claims runs a multi-pass truth-finding loop: broad
search across your highest-authority providers — search engines,
encyclopedias, and scholarly indexes — then claim extraction,
cross-source reconciliation, and targeted follow-up for gaps, dispatched
in parallel and stopping early once the truth is pinned down. Hand it a draft
and it takes a claim list, returning one finding per distinct claim in your
order — with every input index for a repeated claim — and an explicit
unverified row for a claim nothing supports, rather than dropping it. Claims
corroborated across independent sources score high
confidence, weighted
by each source's authority; every source is bound to the claim it
supports, with a span locating the supporting sentence and the claim's
modality (asserted, reported, speculative) so a hedged source is never
rendered as flat fact. A report that repeats a hedged claim must carry that
attribution in its body. Republished wire copy and mirrors are collapsed into one source
family, so confidence counts origins, not hosts, and a secondary-only
finding is capped rather than overstated. Contradictions are surfaced with
all perspectives. Gaps trigger refined queries that broaden to the rest of
your providers. It also remembers: prior findings in your knowledge base
participate as corroborating sources before it queries the network. You get a
structured report — confirmed, contested, and unverified findings — with
source provenance, per-source claims and spans, and confidence scores. Every
other search tool returns a list of links; Infobroker finds the truth and
tells you how sure it is.
Knowledge Base
"Search what you already found about the Rebel Alliance fleet."
"Ingest this article so it's cached for next time."
Every search, fetch, and corroboration run is cached. manage_kb
checks the cache before external providers, falling back only when cached
results aren't fresh or relevant enough. It ingests text or a URL, reports
what's cached, and removes content. Content is age-scored, expired on a
schedule, and deduplicated by source. Retrieval runs locally with a
configurable embedding model; your content never leaves the machine. Beyond
the cache, manage_kb archives generated reports: ingest with
source_type: "report", pass the Source Register URLs in the receipt, and the
ingest returns a report_id linking the report to them. Revisit them with
manage_kb list/get, or write them to a local directory. search_web scopes
recall to a named collection, and fresh: "blend" keeps cached results
beside fresh ones, reporting the kept count even when zero.
Corroboration results are also kept as claim records. Each verify_claims run
stores one ledger entry per finding, linked to the sources that supported it
with the time each source was retrieved, and re-verifying a claim updates that
entry in place instead of adding a duplicate. Cited sources are copied into
the knowledge base as retrievable, hashed snapshots, so a report can be
rechecked after the live page changes. Each snapshot reports its basis —
fetched document or supplied snippet — and whether it was truncated. Read them
with manage_kb action=claims, optionally filtered by query (claim text) or
source_url, newest first and capped by max_results (default 8, max 50).
The ledger is sealed at rest when encryption is on.
A watchlist runner records due-topic claim deltas; cron owns the schedule. A
report can carry a verification receipt: ingest claims, cited sources, and the
Source Register; the server hashes the report and every cached source.
verify_report rechecks it offline — no network call — and reports drift when
the report or a source changed, unverifiable for an uncached source, and a
digest mismatch for a tampered manifest. The manifest carries report metadata
and a revision chain; verify_report reports age and staleness alongside
drift, so monitoring can baseline, revalidate, and publish a delta revision.
The manifest is sealed at rest, and encryption transitions reseal it.
Research Pipeline
"Research the construction of the Death Star, then draft a summary."
"Fact-check these claims about Darth Vader's origin."
Infobroker doesn't stop at search results. Bundled client skills chain
its tools into writing pipelines, routing every request through a solved
workflow shape and the writing sub-skills until a finished document comes
out the other end. Everything lives in the repository — no external paths
or separate install. The full pipeline — the six skills, the workflow
shapes, and the escalation path — is detailed in the Skills
section. Other search MCP servers produce search results;
Infobroker produces finished work.
Operational Visibility
"Show server health."
"Hot-reload my config without restarting."
Quota counters persist to disk and survive restarts. Rate limits are
enforced per-provider, not globally. Configuration is hot-reloadable
via reload_config — change providers, adjust chains, or tweak
thresholds without dropping connections, or pass a patch to merge a
change into your user layer with a backup. search_web doubles as
DuckDuckGo query autocomplete. inspect_providers reports the server's build
health, request stats, and local state health — configuration drift,
pending migrations, backend capabilities, and update status. When something
needs your attention — configuration drift, a pending migration, or a
provider cooling down — successful tool responses carry a bounded notices
array with the condition and, where one exists, the fix, so a stale user
layer does not stay invisible. You always know what your search server is
doing and how much capacity remains.
Skills
The MCP server is one half of the product. The bundled skills are the
other. Six client skills ship in the repository and turn raw research into
finished work.
The orchestrator skill (infobroker) opens with a classify gate that
maps your request to a workflow shape: research-and-write, fact-check,
deep-dive, competitive evaluation, literature review, monitoring,
red-team, vetting, or gated analysis. Each shape composes the same
primitives — recall from the knowledge base, search, extract, verify,
write, validate, and cite — into its own sequence and ends with a grep-able
completion token. Every report carries a
machine-readable manifest and a graded Source Register; a validation gate
checks its sections, citations, and manifest values before delivery, and a
shared reference fixes one confidence, likelihood, and source-grade scale.
Four writing sub-skills execute the writing phases: summarization
condenses findings before writing, technical-writing drafts reports and
docs, proofreading polishes language, and translation produces
multilingual output.
The writing pipeline requires a client that loads bundled skills; without
skill loading, Infobroker provides tool-level research, not a finished report.
Gated analysis is the escalation shape. When a question is high-stakes or
decision-driving, the classify gate routes to the analysis-loop skill —
a disciplined path with confidence-scored findings, source-reliability
grading, and structured analytic techniques chosen by fit and named with a
rationale — rather than the lighter research-and-write route. It shares the
same primitives and Infobroker tools but runs its own gated workflow, so you
get the rigor without leaving the pipeline.
A single instruction file, search-preferences.md, routes your client
toward these tools: the knowledge base first, external providers only
when the cache falls short. Wire it and the skills directory into your
OpenCode config once — the Quick Start section shows the exact snippet —
and every research request follows the pipeline automatically.
Validated reports export as HTML, JSON, or CSV for reading and archiving. Write your own skill into skills/ to add a workflow shape of your own.
The pipeline diagram lives in references/pipeline-map.md and the
workflow-shape definitions in references/workflows.md. Other search MCP
servers return links; Infobroker ships the writers that turn them into
documented answers.
Providers
Twenty-six providers. Twenty-one work with zero configuration.
Built-in providers and most free-HTTP providers are active out of the box;
CORE needs a free API key. Exa, Tavily, and Yep ship disabled; set
"enabled": true in config.json for those, and export the matching key. A
keyed provider whose key is absent is excluded from dispatch, so nothing
changes for a keyless install. Self-hosted providers point at a server you run
yourself:
Keyed providers also accept an ordered credential pool via
INFOBROKER_<NAME>_API_KEYS (comma-separated). Infobroker rotates to the
next key when one is rejected or rate-limited, and reports per-key
availability through inspect_providers without ever surfacing key
material.
SearXNG is the only shipped self-hosted provider, and it is optional
through and through. Nothing in the server requires it, and nothing is
bundled or installed on its behalf — SearXNG runs as a container you
operate, and Infobroker queries its JSON endpoint like any other backend.
Leave it disabled (the default) and you lose nothing: the
privacy-critical chain still serves via Mojeek and DuckDuckGo. Enable it
only when you want full query privacy, in which case only your own
SearXNG instance sees your queries.
Configuration
Environment variables tune a deployment. INFOBROKER_CONFIG overrides
the shipped default config (resolved from the installed package when unset),
INFOBROKER_CONFIG_LOCAL points at a user config layer,
INFOBROKER_<NAME>_API_KEY supplies a keyed provider's credential, and
INFOBROKER_<NAME>_URL points at a self-hosted provider.
config.json ships with the package and the repository and holds the
defaults: which providers are enabled, their priority in fallback chains,
rate limits, corroboration parameters, and the task-to-provider dispatch
table. Hot-reloadable via reload_config — edit the file and call the tool,
or pass a patch to merge configuration programmatically; changes take
effect without a restart.
Your own overrides live in a separate user layer —
~/.config/infobroker/config.local.json by default, or a path you set via
INFOBROKER_CONFIG_LOCAL. An existing config.local.json beside the
resolved config still wins, so clone deployments keep their current layout.
The layer is preserved across updates. Values in the user layer take
precedence over the shipped defaults; anything left out falls back to
config.json.
config.json carries a schema stamp (config_version). If your user layer
was written for an older schema, or holds a key the current schema no longer
recognizes, the server reports the drift at startup and in every
reload_config response without changing your file. Apply the registered
migrations on demand by calling reload_config with migrate true: the
server first copies your layer to a timestamped *.bak-* file, then updates
it atomically, leaving anything it does not recognize untouched. Set
state.auto_migrate_config to true to apply those migrations automatically at
startup after the merged result validates; the same backup is written first.
If a user layer is invalid, the server starts on shipped defaults, leaves the
file untouched, and reports the error instead of refusing to start.
Provider entries are strict: a key outside the provider schema — for example
result_path where the schema expects results_path — makes the whole user
layer invalid instead of being ignored, so a single typo can suppress every
override in the file. The server reports the offending key and the invalid
value, and the fix belongs in config.local.json; a key the current schema no
longer recognizes is reported as drift rather than silently dropped.
state.update_check (off by default) enables an update-availability check
against the published npm package. When enabled, the check runs in the
background, caches its result for a day, and never downloads or applies an
update. The result appears in inspect_providers action spec and, when a
newer release exists, as a notice.
The knowledge base ships empty. Retrieval runs on a configurable in-process
embedding model selected by kb.embedding_model. By default, the store
writes to a user-scoped path (~/.local/share/infobroker/knowledge-base)
outside the repository, so the content you research and cache stays on your
machine and is never committed. Each deployed instance accumulates its own
store. A legacy vector-store.json store is migrated automatically on first
open and preserved as vector-store.json.migrated-<timestamp>; when encryption
is enabled the plaintext archive is removed instead. There is no legacy backend
to roll back to: recover with a key backup or rekey.
Knowledge base encryption
Research reports and cached pages can be sensitive, and the knowledge
base stores them in a SQLite database (plus -wal/-shm sidecars) in your
home directory. Enable optional
at-rest encryption by adding a kb.encryption block and supplying a key:
The key file (plain, 0600) is the most reliable source across MCP clients
and operating systems; INFOBROKER_KB_KEY (a 32-byte key) or
INFOBROKER_KB_PASSPHRASE (a passphrase) also work. Generate a key with
openssl rand -base64 32. Encryption protects the store and disk-saved
reports from anyone who obtains the files without the key — device theft,
backup or cloud-sync leaks, other local accounts. It does not protect
against a malicious MCP client on the same machine, or malware, which
full-disk encryption covers.
Two rules keep this safe. First, encryption is your opt-in: if the key is
missing or wrong, the knowledge base locks and reports an error rather
than touching your data — so back up the key (a forgotten key or
passphrase means the store is unrecoverable by design). Second, the server
never writes a partial file: every save is atomic, and an unrecognized or
newer store format is never overwritten.
The manage_kb tool's encryption action is the day-to-day surface for this
journey, and it never echoes secret material — generate_key and backup
return file paths, and rekey reads a key file rather than a raw key.
generate_key refuses a key-file path that already exists, so it can never
overwrite the only copy of a key.
Enable by generating a key, backing it up, adding the kb.encryption
block, and reloading; the store is encrypted in place immediately.
Disable by removing the block and reloading; the store is decrypted to
plaintext immediately (keep the key available during the transition so the
server can read the store to decrypt it). Recover a locked store with
status to see the state, verify to confirm a candidate key before
committing it, backup to restore a copy of your key file, and rekey to
move to a new key without losing content. After re-keying, point
kb.encryption.key_file at the new key, reload, then run verify again to
confirm the new key opens the store.
Tool-surface key operations (generate_key, backup, rekey's target)
are confined to the keys directory: kb.keys_dir when configured, else the
keys sibling of the knowledge base storage path
(~/.local/share/infobroker/keys by default). A path outside that
directory is refused. The kb.encryption.key_file configuration value is
operator-owned and not subject to the confinement.
Add the kb.encryption block to config.local.json before reloading to
enable, or remove it before reloading to disable. When the store is locked,
status, verify, and rekey remain reachable so you can recover without
first unlocking.
Content policy
Infobroker reads the open web and caches what it retrieves, so retrieved
content is assessed against a configurable policy before it is stored (and,
in the strictest mode, before it is returned). The policy flags content
that matches heuristic categories — prompt-injection instructions,
credential phishing, malware/exploit material, and adult content — and can
consult an external assessment service when one is configured. It is on by
default in flag mode: flagged content is still returned to you for
legitimate research, but it is never written to the knowledge base, and
every flag is recorded in the audit trail.
Modes: off disables assessment; flag (default) returns but never stores
flagged content; block refuses flagged content to the caller. threshold
tunes sensitivity (0–1, default 0.2 — a single match flags). patterns
extend or override the built-in categories per category name. external_url_env
names an environment variable holding the URL of an external assessor, and
external_api_key_env optionally names one holding its bearer key; when the
external service is unreachable the built-in assessment applies.
Security-relevant events — refused network targets, policy flags, config
reloads, encryption transitions, key operations, and quota exhaustion — are
appended to an owner-only audit log at output.audit_log_path (default
~/.local/share/infobroker/audit.log). Per-provider privacy posture is
generated from config.json into
skills/infobroker/references/provider-privacy.md; the gate fails when that
document drifts from configuration.
Operational records are separate: every tool call and outbound provider
request logs its name, status, and elapsed time, never the query, URL, or
content. A multi-query search or a verify_claims batch writes one record
per call plus one per provider request, so a batch multiplies the volume;
output.call_log_max_bytes (default 2 MB) bounds the file before rotation.
Set output.call_log to "stderr" (the default), "file", or
"off"; the file sink is owner-only and rotates at
output.call_log_max_bytes. inspect_providers action=spec reports the
session summary, and a successful response carries a provider_cooldown
notice while a provider is held off after a rate limit.
Bring your own endpoint
Any HTTP search endpoint can become an Infobroker provider without
touching the source tree. Declare it in config.local.json as a
generic_http provider, then append it to a dispatch chain: dispatch_append
adds the slug after the shipped providers instead of replacing the chain.
The server GETs endpoint?query_param=<query>, walks results_path
(dot-separated into the response JSON), and maps each result to the
common shape using field_map. field_map values are dot paths; besides
title, url, snippet, published_date, source_type, and
original_source, it accepts the scholarly keys authors (a string or
array), doi, venue, abstract, and citation_count. Relative result
URLs resolve against the endpoint.
Set auth_env to an environment variable name to send its value as
Authorization: Bearer …; the key never appears in configuration. For an API
that expects a different header or no scheme, set auth_header (default
Authorization) and auth_scheme (default Bearer; set "" to send the raw
key). For example, {"auth_header": "X-API-Key", "auth_scheme": ""} sends the
key alone in X-API-Key. Set
health_endpoint to a query-free URL so inspect_providers health does
not spend a real search against a metered API — without it the probe is a
search query. A generic provider's capabilities must be web_search or a
search task type such as academic; suggest and content_fetch are not
implemented by the shared generic backend. A slug that matches a built-in
provider is rejected. Add the entry to config.local.json and call
reload_config to use it immediately.
priority orders the first-pass provider pool for verify_claims; it does
not reorder search_web, which follows dispatch-chain order.
Per-provider status and provenance
Two optional keys tune per-provider behavior in config.json:
degraded_latency_ms — a provider whose recent average latency exceeds
this many milliseconds is reported degraded by the inspect_providers health
action, even while reachable. A global output.degraded_latency_ms acts
as the fallback when a provider omits its own.
resells — set true on aggregator/reseller backends (search engines
that surface other publishers' pages, like DuckDuckGo or
SearXNG). The server reports each result's original_source where the
backing API exposes one (e.g. Yep's source field); first-party
sources (Wikipedia, arXiv) leave it empty because the page is the
origin.
Source quality and blocklisting
Search results are ordered by relevance, then adjusted by a configurable
source-quality weight. Primary sources (default .gov, .mil, .edu, and
.int) and domains marked trusted rank higher; domains marked low-quality
rank lower. The default weight is small enough that relevance stays
dominant. A blocklist removes a host and its subdomains before ordering and
reports the count in meta.blocked_count; a *. pattern matches subdomains
only. The blocklist applies to search_web results, including a
knowledge-base recall used to answer a search, and does not apply to
fetch_page or verify_claims.
Set weight to 0 to keep pure semantic ordering, or enabled to false
to disable both ranking and blocklisting.
Hedged fallback
search_web and fetch_page fall back with a hedge instead of waiting
out a slow provider's full timeout: the primary (first-choice) provider
runs alone for a latency-derived window, then the remaining providers
race and the first result wins. The common path uses one provider call;
the hedge fires only when the primary is slow or failing. fetch_page
additionally prefers the primary renderer in a short grace window so a
marginally slow jina is not displaced by a lower-quality native_fetch.
A renderer whose content is an anti-bot challenge page (a CAPTCHA or
verification interstitial rather than the target page) is treated as a
failed render, so fetch_page falls through to the next renderer instead
of serving the challenge as content.
Tune the window with output.hedge_enabled, hedge_min_delay_ms,
hedge_max_delay_ms, and hedge_grace_ms; set hedge_enabled to
false for the sequential chain. A provider that returns a rate-limit
or anti-bot response is held in a per-provider cooldown (output.rate_limit_cooldown_ms)
so a burst of requests stops re-hammering it, and when a non-general_web
chain exhausts, the server retries the general_web chain before failing.
How It Compares
Every other search MCP server asks you to pick a provider and trust it.
Infobroker gives you a fleet — and picks the right one for each task.
When a provider fails, the next one takes over without you noticing.
When a claim matters, the corroboration engine finds agreement,
contradiction, and gaps. The bundled skills close the loop from raw
research to finished writing. One server. Every source. Research that
delivers.
Last updated: 2026-11-07.
Contribute
- Node.js 24+.
node --version. Get it at
nodejs.org.
npm install && npm run typecheck
- Bundle your own skill in
skills/ to extend the research pipeline.
- Validate README structure:
npm run validate-readme
- Versioning: CalVer (
YYYY.MM.DD). npm run version-bump stamps
today's date into the package, server manifest, and version stamps; update
the spec stamp and README citation alongside it. Pre-commit hooks verify
consistency. npm run push checks, tags, and pushes.
- MCP protocol: modelcontextprotocol.io
- Providers: DuckDuckGo ·
Jina Reader ·
Wikipedia API
Canonical origin: git.gay/flukeatzerocool/Infobroker. This GitHub repository is a read-only mirror.
License
MIT. Free to use, modify, and redistribute. The bundled client skills and
instruction files ship under the same license, so the full research pipeline
— server, skills, and documentation — is freely reusable in commercial and
open-source work alike. Third-party providers remain subject to their own
terms and API keys.
Spec
The server is built from a single source specification, infobroker.md
(v2026.11.07), which defines every requirement and the gates that verify it.
Each requirement traces to an implementation file, and npm run check
reconciles the code, the spec, and this README so what is documented is what
the server actually delivers. The routing gate resolves every cited tool and
operation against the live schema, and requires each registered tool to be
cited at least once.