Skip to main content

Installation & Configuration

Installation

Install the base package:

pip install waxell-observe

Optional Extras

For LangChain integration, install with the langchain extra:

pip install waxell-observe[langchain]

This installs langchain-core as an additional dependency.

Quick Setup: init()

The fastest way to get started -- call init() once at application startup:

import waxell_observe

waxell_observe.init(
api_key="wax_sk_...",
api_url="https://waxell.dev",
)

# Import LLM SDKs AFTER init() -- they're now auto-instrumented
from openai import OpenAI

This:

  1. Configures the API client
  2. Auto-instruments installed AI/ML libraries (OpenAI, Anthropic, LiteLLM, and many more)
  3. Auto-instruments installed infrastructure libraries (HTTP clients, databases, caches)
  4. Enables OpenTelemetry tracing

init() Parameters

ParameterTypeDefaultDescription
api_keystr""Waxell API key (wax_sk_...). Falls back to WAXELL_API_KEY env var.
api_urlstr""Waxell API URL. Falls back to WAXELL_API_URL env var.
capture_contentboolFalseInclude prompt/response content in traces.
instrumentlist[str] | NoneNoneExplicit list of AI/ML libraries to auto-instrument (e.g. ["openai", "anthropic"]). None means auto-detect all installed libraries.
instrument_infraboolTrueEnable auto-instrumentation of infrastructure libraries (HTTP clients, databases, caches, queues). Falls back to WAXELL_INSTRUMENT_INFRA env var.
infra_librarieslist[str] | NoneNoneOnly instrument these specific infra libraries (e.g. ["redis", "httpx"]). None means auto-detect all.
infra_excludelist[str] | NoneNoneInstrument all infra libraries except these (e.g. ["celery", "grpc"]). Falls back to WAXELL_INFRA_EXCLUDE env var (comma-delimited).
resource_attributesdict | NoneNoneCustom OTel resource attributes applied to all spans (e.g. {"deployment.environment": "production"}).
debugboolFalseEnable debug logging and console span export.
prompt_guardboolFalseEnable client-side prompt guard (regex PII/credential/injection detection). Falls back to WAXELL_PROMPT_GUARD env var.
prompt_guard_serverboolFalseAlso check server-side guard service (ML-powered detection). Falls back to WAXELL_PROMPT_GUARD_SERVER env var.
prompt_guard_actionstr"block"Action when violations are found: "block" (raise error), "warn" (log and continue), or "redact" (replace and continue). Falls back to WAXELL_PROMPT_GUARD_ACTION env var.

Supported Libraries

init() auto-instruments a wide range of AI/ML libraries. See Auto-Instrumentation for the full list and details.

Drop-in Imports

Alternative to init() -- import pre-instrumented modules:

from waxell_observe.openai import openai
from waxell_observe.anthropic import anthropic

Kill Switch

Disable all observability without code changes:

export WAXELL_OBSERVE="false"  # or "0" or "no"

Configuration

Waxell Observe requires two values to connect to your control plane:

SettingDescriptionExample
api_urlYour Waxell control plane URLhttps://acme.waxell.dev
api_keyYour API keywax_sk_abc123...

Configuration Priority

Configuration is resolved in the following order (highest priority first):

  1. Explicit constructor arguments -- passed directly to WaxellObserveClient()
  2. Global configure() -- set via WaxellObserveClient.configure()
  3. CLI config file -- ~/.waxell/config
  4. Environment variables -- WAXELL_API_URL / WAXELL_API_KEY

Higher-priority sources override lower-priority ones. You can mix methods -- for example, set the URL in an environment variable and override the API key per-instance.


Method 1: Environment Variables

The simplest approach for most deployments:

export WAXELL_API_URL="https://acme.waxell.dev"
export WAXELL_API_KEY="wax_sk_abc123..."

Both long-form and short-form variable names are supported:

Long FormShort Form
WAXELL_API_URLWAX_API_URL
WAXELL_API_KEYWAX_API_KEY

The long-form name takes precedence if both are set.


Method 2: CLI Config File

Create a config file at ~/.waxell/config in INI format:

[default]
api_url = https://acme.waxell.dev
api_key = wax_sk_abc123...

You can define multiple profiles by using different section names. The [default] section is used automatically. If no [default] section exists, the first section in the file is used.

warning

Keep your ~/.waxell/config file secure. It contains your API key in plain text. Set file permissions to owner-only: chmod 600 ~/.waxell/config


Method 3: Programmatic configure()

Call WaxellObserveClient.configure() once at application startup:

from waxell_observe import WaxellObserveClient

WaxellObserveClient.configure(
api_url="https://acme.waxell.dev",
api_key="wax_sk_abc123...",
)

All subsequent WaxellObserveClient() instances, @observe decorators, and WaxellContext managers will use this configuration automatically.

tip

This is the recommended approach for application code. Set it once in your application entry point and all observability calls pick it up.


Method 4: Per-Instance

Pass credentials directly when creating a client:

from waxell_observe import WaxellObserveClient

client = WaxellObserveClient(
api_url="https://acme.waxell.dev",
api_key="wax_sk_abc123...",
)

This overrides all other configuration sources for that specific client instance. You can also pass a client parameter to the decorator and context manager:

from waxell_observe import observe, WaxellContext

@observe(agent_name="my-agent", client=client)
async def my_function():
...

async with WaxellContext(agent_name="my-agent", client=client) as ctx:
...

Verifying Configuration

Check whether the client is properly configured:

from waxell_observe import WaxellObserveClient

# After calling configure()
print(WaxellObserveClient.is_configured()) # True or False

# Get the current global config
config = WaxellObserveClient.get_config()
if config:
print(config.api_url)
info

If the client is not configured when making API calls, it logs a warning and returns empty results instead of raising an error. This means missing configuration degrades gracefully rather than crashing your agent.

Next Steps