Package Exports
This package does not declare an exports field, so the exports above have been automatically detected and optimized by JSPM instead. If any package subpath is missing, it is recommended to post an issue to the original package (@heyhuynhgiabuu/pi-search) to support the "exports" field. If that is not possible, create a JSPM override to customize the exports field for this package.
Readme
@heyhuynhgiabuu/pi-search
Six research tools for the Pi coding agent: websearch, codesearch, context7, deepwiki, web_fetch, get_fetch_content.
- Zero-config by default — works with no API key via the Exa MCP server
- Full feature access when configured — set
EXA_API_KEYto unlocksearchType: deep,recencyFilter,domainFilter,highlightsetc. via direct REST - Disable any tool you don't need via
disabledToolsconfig - Coded errors for reliable model reasoning on failure
- Streaming progress for multi-query research
Install
pi install npm:@heyhuynhgiabuu/pi-searchThat's it. No API key required.
If you also use pi-web-access, see Coexistence with pi-web-access below.
Tools
| Tool | Purpose | When to use |
|---|---|---|
websearch |
Search the open web | Exa discovery; includeContent: true fetches up to 5 result URLs for get_fetch_content. |
codesearch |
Code/library search | Looking for API references, library patterns, implementation examples. |
context7 |
Up-to-date library docs | Fetch current documentation for a library: libraryName: "react", topic: "hooks". |
deepwiki |
Ask about a public GitHub repo | repo: "facebook/react", question: "How does the reconciler work?". |
web_fetch |
Extract readable content from a URL | HTML, PDF text (no OCR), GitHub API; disk cache ~/.pi/pi-search-fetch-cache/ (7d). |
get_fetch_content |
Read stored fetch body | fetchId or list: true. Session JSONL (1h) + disk cache (7d). |
Configuration
Optional. Create ~/.pi/pi-search.json:
{
"exaApiKey": "your-exa-api-key",
"braveApiKey": "your-brave-api-key",
"disabledTools": ["codesearch"],
"mcpTimeoutMs": 30000,
"ssrf": {
"allowRanges": ["198.18.0.0/15"]
}
}ssrf.allowRanges exempts IPv4 CIDRs from the web_fetch SSRF guard (e.g. TUN fake-IP VPNs). 0.0.0.0/0 is rejected.
Or set environment variables:
export EXA_API_KEY=your-key
export BRAVE_API_KEY=your-brave-key # optional; failover (free key: https://brave.com/search/api/)
export PI_SEARCH_DISABLED_TOOLS=codesearch,deepwiki
export PI_SEARCH_USE_REST=true # force direct REST (default: false; auto-enabled when EXA_API_KEY is set)
export PI_SEARCH_CONFIG_PATH=/path/to/config.jsonResolution order (highest priority first):
- environment variables
~/.pi/pi-search.json(orPI_SEARCH_CONFIG_PATH)- defaults
Direct REST vs MCP
websearch and codesearch choose their provider at execution time:
- If
EXA_API_KEYis set (orPI_SEARCH_USE_REST=true), they callhttps://api.exa.ai/searchdirectly. This unlocks the full Exa feature surface. - Otherwise they fall back to
https://mcp.exa.ai/mcp(the public MCP server, no key required). Feature set is narrower.
context7, deepwiki, and web_fetch always use their respective providers regardless.
Architecture
src/
├── index.ts # extension entrypoint, wires the 5 tools
├── config.ts # env + ~/.pi/pi-search.json resolution
├── errors.ts # coded errors (validation_error, mcp_error, …)
├── types.ts # shared types
├── mcp/client.ts # JSON-RPC 2.0 MCP client
├── exa/client.ts # direct REST client for api.exa.ai
├── exa/params.ts # parameter normalization
├── fetch/ # web_fetch pipeline (html, github, jina, ssrf)
└── tools/ # one file per tool + shared citations.tsSee AGENTS.md for the change map.
Roadmap
Planned work (fetch fallbacks, GitHub URL routing, SSRF/proxy options, large-content retrieval) is in docs/ROADMAP.md. Rationale and rejected alternatives are in .pi/artifacts/DECISIONS.md.
Agent workflow (Pi)
- Discover:
websearch(Exa deep modes) →web_fetchorincludeContent: trueon search →get_fetch_contentwithfetchIdorlist: true. - Libraries / repos:
context7,codesearch,deepwiki; GitHub URLs inweb_fetchuse the API (GITHUB_TOKEN,GH_TOKEN, orgh auth token). - Doc site roots:
web_fetchonhttps://example.com/may load/llms.txtwhen present. - Brave: Used only when Exa fails if
BRAVE_API_KEY/braveApiKeyis set (also reads~/.config/ketch/config.json→brave_api_keyif unset).
Optional config: urlRewrites ([{ "match": "...", "replace": "..." }]), githubToken, ssrf.allowRanges.
Coexistence with pi-web-access
pi-web-access covers general web search (web_search), rich fetch (GitHub clone, video, PDF, anti-bot fallbacks), and optional search curation. pi-search focuses on Exa deep discovery, codesearch, context7, deepwiki, and a minimal web_fetch.
If you use both, disable overlapping tools to avoid duplicate calls and confused tool choice:
- Prefer pi-search for
websearch,codesearch,context7,deepwiki. - Prefer pi-web-access for heavy fetch and multimedia; set
"webSearch": { "enabled": false }in~/.pi/web-search.jsonif you only want its fetch tools, or addwebsearch/web_fetchto pi-searchdisabledTools.
Details: coexistence table in docs/ROADMAP.md.
Development
make install # npm ci
make check # biome + tsc + vitest --coverage
make test # vitest
make build # tsc → dist/
make format # biome format --write .
make lint # biome lint
make typecheck # tsc --noEmit
make release-dry-run
make version-packages
make releaseLicense
MIT