⚡ You're viewing a live demo of ChimerAI. Data resets daily at midnight UTC.Get the CLI →

Web Search Tool

ChimerAI's Web Search Tool gives your AI app real-time web access using multiple search engines — no API key required for most backends.

What you get

  • Multi-engine search — DuckDuckGo, Brave, Mojeek, Yandex, Grokipedia — auto-selects the best available
  • Structured results — Title, URL, snippet for each result
  • No API key required — Uses open search endpoints by default
  • Rate limited — 20 searches/min per IP to prevent abuse
  • AI-ready — Results formatted for LLM context injection

Quick setup

npx chimerai add ai-tools

This adds the full AI Tools service including web search. Or add web search alone:

npx chimerai add ai-tools --only web-search

Scaffolds:

app/api/tools/web/search/route.ts    ← Search endpoint
services/ai/tools/web_tools.py       ← Python search implementation

Usage

const res = await fetch('/api/tools/web/search', {
  method: 'POST',
  headers: { 'Content-Type': 'application/json' },
  body: JSON.stringify({
    query: 'Next.js 15 new features',
    maxResults: 5,
    backend: 'auto', // or 'duckduckgo' | 'brave' | 'mojeek' | 'yandex' | 'grokipedia'
  }),
});

const { results } = await res.json();
// results: Array<{ title: string; url: string; snippet: string }>

Injecting results into an AI prompt

const { results } = await fetchWebSearch('latest AI news');

const context = results.map((r, i) => `[${i + 1}] ${r.title}\n${r.url}\n${r.snippet}`).join('\n\n');

const aiResponse = await openai.chat.completions.create({
  model: 'gpt-4o',
  messages: [
    { role: 'system', content: `Use the following search results:\n\n${context}` },
    { role: 'user', content: 'Summarise the latest AI news' },
  ],
});

Python implementation

The search is powered by ddgs with multi-engine support:

from ddgs import DDGS

def web_search(query: str, max_results: int = 5, backend: str = "auto"):
    engines = ["duckduckgo", "brave", "mojeek", "yandex", "grokipedia"]
    if backend != "auto":
        engines = [backend]

    for engine in engines:
        try:
            with DDGS() as ddgs:
                results = list(ddgs.text(query, max_results=max_results, backend=engine))
                if results:
                    return [{"title": r["title"], "url": r["href"], "snippet": r["body"]}
                            for r in results]
        except Exception:
            continue
    return []

Further reading

ChimerAI Docs · Back to Demo