Skip to main content

wigolo — Python client

pip install wigolo

A thin, dependency-free Python client for the wigolo local-first web intelligence server. It speaks the wigolo REST API and nothing more — no retries, no re-ranking, no interpretation, no caching. The server does all of that; this client just gets requests there and responses back with typed method signatures.

  • Zero runtime dependencies — stdlib only.
  • Sync and async clients with an identical surface.
  • Embedded local modelocal_client() probes or spawns a local server for you, no manual setup.
  • Fully typed (py.typed, PEP 561).

Tools

One method per tool: search, fetch, crawl, cache, extract, find_similar, research, agent, diff, watch, plus health(), list_tools(), and openapi().

Sync quickstart

from wigolo import Client

with Client(base_url="http://127.0.0.1:3333") as client:
    res = client.search(query="local first web search", max_results=5)
    for r in res.get("results", []):
        print(r.get("title"), r.get("url"))

    page = client.fetch(url="https://example.com")
    print(page.get("markdown", "")[:500])

    tables = client.extract(
        html="<table><tr><th>a</th></tr><tr><td>1</td></tr></table>",
        mode="tables",
    )
    print(tables["data"])

Async quickstart

import asyncio
from wigolo import AsyncClient

async def main():
    async with AsyncClient(base_url="http://127.0.0.1:3333") as client:
        res = await client.search(query="local first web search", max_results=5)
        print([r.get("url") for r in res.get("results", [])])

asyncio.run(main())

The async client runs each request on a bounded thread pool (max_workers, default 16). Cancelling an awaited call returns promptly but abandons the in-flight request — the worker thread runs to completion in the background (a blocking socket read cannot be portably aborted).

Embedded local mode (zero setup)

from wigolo import local_client

# Reuses a healthy local daemon if one is already listening; otherwise spawns
# one for you and waits for it to become healthy.
with local_client() as client:
    print(client.health())
    print(client.search(query="wigolo"))

local_client() (equivalently Client(local=True), or setting WIGOLO_LOCAL=1) resolves a port (WIGOLO_LOCAL_PORT, default 3333), probes /health, and either reuses an existing REST-capable daemon or spawns a new one via the wigolo CLI on your PATH (override with WIGOLO_CLI). A daemon this client spawns is stopped on close(); a daemon it merely reused is left running. In local mode base_url / WIGOLO_BASE_URL are ignored.

AsyncClient(local=True) accepts the same port / command overrides, but note the daemon probe-or-spawn runs synchronously in the constructor (it may block the calling thread up to ~20s while the daemon becomes healthy).

Security notes for embedded mode

  • WIGOLO_CLI is an exec-from-env vector. In embedded mode the SDK spawns the process named by WIGOLO_CLI (a JSON argv list, or a single executable path). Anything that can set this env var chooses what binary runs. When you hand the SDK untrusted environments, strip WIGOLO_CLI (and WIGOLO_LOCAL_PORT) before construction and pass the trusted argv through the explicit command= argument — the argument always overrides the env.
  • Point command at the server binary itself, not a wrapper. On POSIX, forced-kill escalation signals only the direct child. A wrapper such as ["npx", "wigolo"] makes the launcher the direct child, so a hung close() can kill the launcher while the real daemon it spawned is orphaned and keeps holding the port. Resolve to the actual wigolo executable so close() reaches the process that owns the socket.

Configuration

Resolution order for each option is explicit argument > environment variable > default. When an argument is passed explicitly, the corresponding env var is not consulted.

Option Argument Env var Default
Base URL base_url WIGOLO_BASE_URL http://127.0.0.1:3333
Bearer token token WIGOLO_API_TOKEN none
Local mode local WIGOLO_LOCAL=1 off
Local port port WIGOLO_LOCAL_PORT 3333
Spawn command command WIGOLO_CLI wigolo on PATH

The bearer token is only sent when set — the server requires it only when it runs with a token configured.

Timeouts

The timeout option (per client, or per call) is a per-socket-operation timeout — the maximum idle time on connect or read inactivity — not a total wall-clock deadline. When unset, each method uses its per-tool default, which mirrors the server's unscaled per-route deadline. If your server runs with WIGOLO_SERVE_TIMEOUT_SCALE set, its effective deadline scales but the client defaults do not — pass an explicit timeout to match.

Notes

  • stream on research / agent is accepted by the schema but has no effect over this transport — responses are returned whole.
  • A degraded call stays HTTP 200 with in-body warning / error fields; those are returned verbatim and never raise.
  • crawl(strategy="map") returns urls (no pages); the other strategies return pages.
  • The searxng field in health() is the search-aggregator sidecar status.

Errors

  • WigoloError — base class.
  • WigoloAPIError — a non-2xx HTTP response, carrying status, error, error_reason, stage, and retry_after (parsed from Retry-After on 429).
  • WigoloConnectionError — a transport-level failure (e.g. connection refused) with no HTTP response. Its message points at local_client() as the zero-setup path.

License

AGPL-3.0-only. See LICENSE.

Download files

Download the file for your platform. If you're not sure which to choose, learn more about installing packages.

Source Distribution

wigolo-0.2.1.tar.gz (29.3 kB view details)

Uploaded Source

Built Distribution

If you're not sure about the file name format, learn more about wheel file names.

wigolo-0.2.1-py3-none-any.whl (33.4 kB view details)

Uploaded Python 3

File details

Details for the file wigolo-0.2.1.tar.gz.

File metadata

  • Download URL: wigolo-0.2.1.tar.gz
  • Upload date:
  • Size: 29.3 kB
  • Tags: Source
  • Uploaded using Trusted Publishing? No
  • Uploaded via: twine/6.2.0 CPython/3.11.15

File hashes

Hashes for wigolo-0.2.1.tar.gz
Algorithm Hash digest
SHA256 45d04e46d3320f3bae7cfaf3df724ae6b5dffb1b262123c6e44c1219ea074ef0
MD5 83565a065c37d85483bb0c3228e759ca
BLAKE2b-256 7d38d25d31d7d6a765a9a89dce91132a0387484bad593746b5eeffe0749876cc

See more details on using hashes here.

File details

Details for the file wigolo-0.2.1-py3-none-any.whl.

File metadata

  • Download URL: wigolo-0.2.1-py3-none-any.whl
  • Upload date:
  • Size: 33.4 kB
  • Tags: Python 3
  • Uploaded using Trusted Publishing? No
  • Uploaded via: twine/6.2.0 CPython/3.11.15

File hashes

Hashes for wigolo-0.2.1-py3-none-any.whl
Algorithm Hash digest
SHA256 169a2243a2b663e7a9cb59cd898e8af98da0420b4265e903561ba4ed78508dd3
MD5 2aa2f60f5c6fb86f8f7faeafc48d6b88
BLAKE2b-256 8c3bacf7eff66975c28b55cd8ad02906d7989279b837464456e087daee0c66c5

See more details on using hashes here.

Release history Release notifications | RSS feed

This release

0.2.1 This release

2 files

0.2.0

2 files

Anthropic, PBC Visionary sponsor Bloomberg Visionary sponsor Hudson River Trading Visionary sponsor Meta Visionary sponsor NVIDIA Visionary sponsor Microsoft Sustainability sponsor Depot Continuous Integration AWS Cloud computing and Security Sponsor Datadog Monitoring Fastly CDN Google Download Analytics Sentry Error logging StatusPage Status page