Skip to content

Repository files navigation

fearch

CI npm license

Web search and page reading for AI agents, as an MCP server and a CLI. Two tools:

  • search — real search engine result pages, read honestly. DuckDuckGo lite by default, with no key and no account. Google (and Google's AI Mode) when you list them, and then every Google query is shown to you first and runs only when you accept it.
  • fetch — a page as clean markdown that keeps code blocks and tables. Long pages by section, by relevance, or by regex. PDFs, feeds, GitHub, PyPI, npm and Stack Overflow read through their APIs.

It identifies itself, honours robots.txt, waits between requests, never solves a bot check, and treats a refusal as final — unless you, present, say "open it in my browser", in which case the page is your browsing, opened in an incognito tab and read back labelled. Your queries go from your own browser to the engine you chose and nowhere else. The full rules are in docs/POLICY.md.

Install

Node 22.5 or newer. Add to your MCP client's config:

{ "mcpServers": { "fearch": { "command": "npx", "args": ["-y", "fearch-mcp"] } } }

Claude Code: claude mcp add fearch -- npx -y fearch-mcp. For the fearch command on your PATH: npm install -g fearch-mcp. (The package is fearch-mcp because npm reserves names this close to fetch; the command is fearch.)

On macOS, pair the extension so that engine pages open quietly in your own Chrome:

npx fearch-mcp extension install      # or: fearch extension install

It registers fearch's native messaging host with your browsers, writes the pairing token, opens chrome://extensions, and tells you the three clicks: Developer mode, Load unpacked, choose the folder it printed (~/fearch-extension). (A Chrome Web Store listing is in preparation; see docs/extension/STORE.md and the extension's privacy policy.) Optional: allow it in Incognito, which is where Google result pages open by default. After upgrading fearch, run the command again and reload the extension. Without the extension, engine pages open in a background window of your installed Chrome, and on macOS that window comes forward on every search (a Chromium bug).

Use

From an agent, the two tools are enough; the server sends its own guidance to the model. From the shell:

fearch search "asyncio cancel task" --fetch-top 1
fearch fetch https://docs.python.org/3/library/asyncio-task.html --mode section --query Timeouts
fearch doctor                              # config, network, extension, one search, one render
fearch clear-profile --yes                 # forget the tool-owned browser profile

Every command takes --help and --json. Exit codes: 0 ok, 1 refused (with a Diagnosis), 2 failed.

Engines run in the order listed until one answers; an agent can ask for one (engine="google-ai"), or ask for the form on any query (ask=true). On fetch, ask=true reads a page as your own browsing with your yes. Your flags always win: the agent can add a question, never remove one. Google needs a person: --engines google,duckduckgo in the args, and each query then appears in your client as a form (edit it, pick the engine, incognito or not) before it runs. google-ai adds Google's AI Mode: its reply comes back labelled as Google's unverified text, and its cited pages are the results. Google shows those sources only to a signed-in session, so the form defaults AI Mode to your profile and plain Google to incognito; signed out, the reply comes without sources and the next engine supplies the links. From the CLI, which has no form, the search box opens in your browser and you press Enter; for AI Mode the question is put on your clipboard for you to paste.

Who does what, when

DuckDuckGo lite Google (Web tab) Google AI Mode fetch
Default (--engines duckduckgo) runs, no question not listed not listed plain client, then headless browser
Listed, you at the screen (MCP client with prompts) runs, no question form first: query, engine picker, incognito (default on), run on accept same form, incognito default off so sources come a bot check or a robots.txt "no" is offered to you (incognito or your profile, ask again or not); a sign-in wall in incognito earns a second offer, signed in
Listed, you away runs form waits 45 s, then the next engine runs and the result says so same refusal stands (Diagnosis, retryable)
Agent passes ask=true form for that query, whatever else is set form (also when "ask again" was turned off) same "open this page as your own browsing?" with the profile choice; no or nobody there means no read
"Ask me again next time" off runs runs as your remembered choice, no form same unchanged
--human-search form first too; unanswered runs nothing same as above same unchanged
Terminal (fearch search, no form) runs search box opens in your Chrome, you press Enter AI Mode opens, question on your clipboard, you paste and press Enter a robots.txt "no" is final
--incognito your Chrome, incognito incognito by default incognito by default: reply without sources escalations incognito (already the default)
--browser headless or no display no search no search no search headless only; checks and robots "no" final
--no-handoff runs not eligible not eligible checks final
A bot check appears you are asked, then you pass it or not same same same

What it will never do

  • Send a browser User-Agent from its own HTTP client, or hide navigator.webdriver in a browser it drives. It is fearch/<version> (+https://github.com/funkyfunc/fearch#bot-info), or your own Chrome.
  • Retry a refusal with different headers, cookies, an IP, a proxy, or a third-party reader.
  • Solve a CAPTCHA or any bot check. When one appears you are asked whether to see it, and you pass it or you don't.
  • Follow links on its own, or fetch more than one page per host at a time, faster than once a second.
  • Send a query anywhere but the engine you chose. No third-party search services, no telemetry.

Flags

Flags go in the MCP config's args; each is also a FEARCH_* environment variable. fearch --help has the full table.

--engines duckduckgo,google,google-ai   engines in order (default: duckduckgo)
--browser auto|headless|extension|off   who renders pages (default: auto)
--robots default|strict                 default: `*` and the fearch token; strict adds vendor AI-agent and training-crawler tokens
--incognito                             your own Chrome: engine pages in an incognito window
--human-search                          show every query in the form, DuckDuckGo included (an unanswered form then runs nothing)
--allow-domains a,b  --deny-domains c   host lists
--search off                            fetch only

Behind a corporate proxy: HTTPS_PROXY/NO_PROXY are honoured everywhere; behind a TLS-intercepting proxy, point NODE_EXTRA_CA_CERTS at the proxy's CA bundle for the plain client (the browser tier uses the OS trust store). GITHUB_TOKEN in the environment raises GitHub API limits.

Tool reference

search(query, max_results=8, recency?: d|w|m|y, site?, allowed_domains?, engine?, ask=false,
       fetch_top=0..3, raw=false)

fetch(url | urls[≤5], mode=read|focus|section|pattern|raw, query?, max_chars=12000,
      cursor?, include_links=false, context_chars=200, archive=false, fresh=false, ask=false)

A page comes back with a one-line header (source, robots decision, date, licence, char window), the content, and an outline of the sections not shown. A refusal comes back as a Diagnosis: the kind (captcha_or_challenge, paywall, robots_disallowed, …), what was attempted, and what to do instead.

Bot info

If you operate a website and see this agent in your logs:

  • User-Agent: fearch/<version> (+https://github.com/funkyfunc/fearch#bot-info) from the plain client; HeadlessChrome/… with From: and X-Agent: headers naming the tool when a page needed a browser. Engine result pages are opened in the person's own Chrome and carry no tool identity.
  • What it is: a locally-run tool fetching individual pages a person's AI assistant asked for right now. Agent traffic, not a crawler: it never follows links and never trains models.
  • Volume: one request at a time per host, at least a second apart, capped per session.
  • To block it: User-agent: fearch + Disallow: / in robots.txt. Crawl-delay and Content-Signal: ai-input=no are honoured; Claude-User/ChatGPT-User and GPTBot-class tokens are honoured under --robots strict. A 402/403 is final.
  • Content negotiation: it sends Accept: text/markdown, text/html;q=0.9, …. Serve markdown and it never touches your HTML.

Development

npm test              # unit, fixture and golden tests (no network)
npm run test:live     # live smoke tests
npm run audit:render  # per page: paragraphs, headings, code, tables kept vs. the page (live)
npm run lint && npm run format && npm run typecheck

Docs: POLICY.md (the rules, for reviewers), SPECTRUM.md (why), CASES.md, ROADMAP.md, AGENT-GUIDANCE.md, and the outside reviews under docs/reviews/.

About

Honest web search and page reading for AI agents — an MCP server and CLI that identify themselves truthfully, respect robots.txt, and hand bot-checks to a human in a visible browser. Headless until it matters.

Topics

Resources

Stars

0 stars

Watchers

0 watching

Forks

Releases

Packages

Contributors

Languages