Metadata-Version: 2.4
Name: pydantic-ai-searxng
Version: 0.1.0
Summary: A SearXNG web-search tool for Pydantic AI agents.
Project-URL: Homepage, https://github.com/joeychilson/pydantic-ai-searxng
Project-URL: Repository, https://github.com/joeychilson/pydantic-ai-searxng
Project-URL: Issues, https://github.com/joeychilson/pydantic-ai-searxng/issues
Author-email: Joey Chilson <joeychilson@outlook.com>
License-Expression: MIT
License-File: LICENSE
Keywords: ai,llm,pydantic-ai,search,searxng,tool
Classifier: Development Status :: 3 - Alpha
Classifier: Framework :: Pydantic
Classifier: Intended Audience :: Developers
Classifier: License :: OSI Approved :: MIT License
Classifier: Programming Language :: Python :: 3
Classifier: Programming Language :: Python :: 3.10
Classifier: Programming Language :: Python :: 3.11
Classifier: Programming Language :: Python :: 3.12
Classifier: Programming Language :: Python :: 3.13
Classifier: Programming Language :: Python :: 3.14
Classifier: Topic :: Software Development :: Libraries :: Python Modules
Classifier: Typing :: Typed
Requires-Python: >=3.10
Requires-Dist: httpx>=0.27
Requires-Dist: pydantic-ai-slim<2.0.0,>=1.0.0
Requires-Dist: typing-extensions>=4.12
Provides-Extra: dev
Requires-Dist: pydantic-ai-slim[openai]<2.0.0,>=1.0.0; extra == 'dev'
Requires-Dist: pytest-asyncio>=0.24.0; extra == 'dev'
Requires-Dist: pytest>=8.0.0; extra == 'dev'
Requires-Dist: respx>=0.21.0; extra == 'dev'
Requires-Dist: ruff>=0.14.0; extra == 'dev'
Requires-Dist: ty>=0.0.34; extra == 'dev'
Description-Content-Type: text/markdown

# pydantic-ai-searxng

A [SearXNG](https://docs.searxng.org/) web-search tool for [Pydantic AI](https://ai.pydantic.dev/) agents — modeled on the upstream `duckduckgo` and `tavily` common tools, but pointed at any SearXNG instance you control.

## Why SearXNG?

SearXNG is a self-hostable metasearch engine that aggregates results from Google, DuckDuckGo, Bing, Wikipedia, GitHub, arXiv, and ~200 other sources. Pointing your agent at your own instance gives you:

- No third-party API keys, rate limits, or per-query billing.
- Full control over which engines, categories, and SafeSearch level the agent sees.
- Privacy: queries don't leave your infrastructure.

## Deploy a SearXNG instance

Need an instance? One-click deploy on Railway:

[![Deploy on Railway](https://railway.com/button.svg)](https://railway.com/deploy/searxng-api)

## Important: enable JSON on your SearXNG instance

JSON output is **not enabled by default**. You must add it to `search.formats` in `settings.yml` on the instance:

```yaml
search:
  formats:
    - html
    - json
```

Without this, requests return HTML and this tool will raise a `RuntimeError`.

## Install

```bash
pip install pydantic-ai-searxng
# or
uv add pydantic-ai-searxng
```

## Usage

```python
from pydantic_ai import Agent
from pydantic_ai_searxng import searxng_search_tool

agent = Agent(
    'openai:gpt-4o',
    tools=[searxng_search_tool('https://searxng.example.com')],
    system_prompt='Use the search tool to ground answers in current sources.',
)

result = agent.run_sync('What did Pydantic AI release this month?')
print(result.output)
```

### Configuration

All keyword arguments are optional and are fixed at factory time (the LLM only sees `query`):

```python
searxng_search_tool(
    'https://searxng.example.com',
    max_results=5,
    categories='general,news',
    engines='google,duckduckgo,wikipedia',
    language='en',
    safesearch=1,           # 0 off, 1 moderate, 2 strict
    time_range='week',      # day | week | month | year
    timeout=20.0,
)
```

Pass your own `httpx.AsyncClient` if you want shared connection pooling, custom headers, or a proxy:

```python
import httpx

client = httpx.AsyncClient(headers={'User-Agent': 'my-agent/1.0'})
tool = searxng_search_tool('https://searxng.example.com', client=client)
```

### Result shape

Each result is a `TypedDict`:

```python
class SearxngResult(TypedDict):
    url: str
    title: str
    content: str
    engine: NotRequired[str]
    publishedDate: NotRequired[str]
    thumbnail: NotRequired[str]
```

## Development

This project uses [uv](https://docs.astral.sh/uv/), [ruff](https://docs.astral.sh/ruff/), and [ty](https://github.com/astral-sh/ty) (Astral's type checker).

```bash
uv sync --extra dev
uv run ruff format .
uv run ruff check .
uv run ty check
uv run pytest
uv build
```

## License

MIT
