Skip to main content

OpenSearch GenAI SDK

OTEL-native tracing and scoring for LLM applications. Instrument your AI workflows with standard OpenTelemetry spans and submit evaluation scores — all routed to OpenSearch through a single OTLP pipeline.

Features

  • One-line setup — register() configures the full OTEL pipeline (TracerProvider, exporter, auto-instrumentation)
  • Decorators — @workflow, @task, @agent, @tool wrap functions as OTEL spans with GenAI semantic convention attributes
  • Auto-instrumentation — automatically discovers and activates installed instrumentor packages (OpenAI, Anthropic, Bedrock, LangChain, etc.)
  • Scoring — score() emits evaluation metrics as OTEL spans at span, trace, or session level
  • AWS SigV4 — built-in SigV4 signing for AWS-hosted OpenSearch and Data Prepper endpoints
  • Zero lock-in — remove a decorator and your code still works; everything is standard OTEL

Requirements

  • Python: 3.10, 3.11, 3.12, or 3.13
  • OpenTelemetry SDK: ≥1.20.0, <2

Installation

pip install opensearch-genai-sdk-py

The core package includes the OTEL SDK and exporters. Auto-instrumentation of LLM libraries is opt-in — install only the providers you use:

# Single provider
pip install opensearch-genai-sdk-py[openai]
pip install opensearch-genai-sdk-py[anthropic]
pip install opensearch-genai-sdk-py[bedrock]
pip install opensearch-genai-sdk-py[langchain]

# Multiple providers
pip install "opensearch-genai-sdk-py[openai,anthropic]"

# All instrumentors at once
pip install opensearch-genai-sdk-py[instrumentors]

# AWS SigV4 signing for OpenSearch Ingestion / OpenSearch Service
pip install opensearch-genai-sdk-py[aws]

# Everything
pip install opensearch-genai-sdk-py[all]

Available extras: openai, anthropic, cohere, mistral, groq, ollama, google, bedrock, langchain, llamaindex, instrumentors (all of the above), aws, all

Quick Start

from opensearch_genai_sdk_py import register, workflow, agent, tool, score

# 1. Initialize tracing (one line)
register(endpoint="http://localhost:4318/v1/traces")

# 2. Decorate your functions
@tool("get_weather")
def get_weather(city: str) -> dict:
    """Fetch weather data for a city."""
    return {"city": city, "temp": 22, "condition": "sunny"}

@agent("weather_assistant")
def assistant(query: str) -> str:
    data = get_weather("Paris")
    return f"{data['condition']}, {data['temp']}C"

@workflow("weather_query")
def run(query: str) -> str:
    return assistant(query)

result = run("What's the weather?")

# 3. Submit scores (after workflow completes)
score(name="relevance", value=0.95, trace_id="...", source="llm-judge")

Architecture

┌─────────────────────────────────────────────────────┐
│                  Your Application                    │
│                                                      │
│  @workflow ─→ @agent ─→ @tool    score()            │
│     │            │         │        │                │
│     └────────────┴─────────┴────────┘                │
│                     │                                │
│            opensearch-genai-sdk-py                    │
├─────────────────────────────────────────────────────┤
│  register()                                          │
│  ┌─────────────────────────────────────────────┐    │
│  │  TracerProvider                              │    │
│  │  ├── Resource (service.name)                 │    │
│  │  ├── BatchSpanProcessor                      │    │
│  │  │   └── OTLPSpanExporter (HTTP or gRPC)     │    │
│  │  │       └── SigV4 signing (AWS endpoints)   │    │
│  │  └── Auto-instrumentation                    │    │
│  │      ├── openai, anthropic, bedrock, ...     │    │
│  │      ├── langchain, llamaindex, haystack     │    │
│  │      └── chromadb, pinecone, qdrant, ...     │    │
│  └─────────────────────────────────────────────┘    │
└──────────────────────┬──────────────────────────────┘
                       │ OTLP (HTTP/gRPC)
                       ▼
              ┌─────────────────┐
              │  Data Prepper /  │
              │  OTEL Collector  │
              └────────┬────────┘
                       │
                       ▼
              ┌─────────────────┐
              │   OpenSearch     │
              │  ├── traces      │
              │  └── scores      │
              └─────────────────┘

API Reference

register()

Configures the OTEL tracing pipeline. Call once at startup.

register(
    endpoint="https://pipeline.us-east-1.osis.amazonaws.com/v1/traces",
    service_name="my-app",
    auth="auto",           # "auto"/"none" = plain (default) | "sigv4" = AWS SigV4
    batch=True,            # BatchSpanProcessor (True) or Simple (False)
    auto_instrument=True,  # discover installed instrumentor packages
)

Endpoint formats:

URL scheme Transport
http:// / https:// HTTP (default)
grpc:// gRPC (insecure)
grpcs:// gRPC (TLS)

Auth:

  • auth="auto" (default) — auto-detects AWS endpoints (*.amazonaws.com) and enables SigV4; uses plain HTTP for everything else.
  • auth="sigv4" — always use SigV4 (requires pip install opensearch-genai-sdk-py[aws]).
  • auth="none" — always plain HTTP, no signing.

Decorators

Four decorators for tracing application logic. Each creates an OTEL span with gen_ai.* semantic convention attributes.

Decorator Use for Operation name Span name format
@workflow("name") Top-level orchestration invoke_agent name
@task("name") Units of work invoke_agent name
@agent("name") Autonomous agent logic invoke_agent invoke_agent name
@tool("name") Tool/function calls execute_tool execute_tool name

All decorators accept name (defaults to function's __qualname__) and version.

Attributes set automatically:

Attribute Set by
gen_ai.operation.name All decorators
gen_ai.agent.name / gen_ai.tool.name All decorators
gen_ai.input.messages / gen_ai.output.messages @workflow, @task, @agent
gen_ai.tool.call.arguments / gen_ai.tool.call.result @tool
gen_ai.tool.type @tool (always "function")
gen_ai.tool.description @tool (from docstring, if present)
gen_ai.agent.version All decorators (when version is set)

Supported function types: sync, async, generators, async generators. Errors are captured as span status + exception events.

@agent("research_agent", version=2)
async def research(query: str) -> str:
    """Agents create invoke_agent spans with gen_ai.agent.* attributes."""
    result = await search_tool(query)
    return summarize(result)

@tool("search")
def search_tool(query: str) -> list:
    """Docstring becomes gen_ai.tool.description. Input/output use gen_ai.tool.call.* attributes."""
    return api.search(query)

score()

Submits evaluation scores as OTEL spans. Use any evaluation framework you prefer (autoevals, RAGAS, custom) and submit the results through score().

Three scoring levels:

# Span-level: score a specific LLM call or tool execution
score(
    name="accuracy",
    value=0.95,
    trace_id="abc123",
    span_id="def456",
    explanation="Weather data matches ground truth",
    source="heuristic",
)

# Trace-level: score an entire workflow
score(
    name="relevance",
    value=0.92,
    trace_id="abc123",
    explanation="Response addresses the user's query",
    source="llm-judge",
)

# Session-level: score across multiple traces in a conversation
score(
    name="user_satisfaction",
    value=0.88,
    conversation_id="session-123",
    label="satisfied",
    source="human",
)

Parameters:

Parameter Type Description
name str Metric name (e.g., "relevance", "factuality")
value float Numeric score
trace_id str Trace being scored (span/trace-level)
span_id str Span being scored (span-level)
conversation_id str Session being scored (session-level)
label str Human-readable label ("pass", "relevant")
explanation str Evaluator justification (truncated to 500 chars)
response_id str LLM completion ID for correlation
source str Score origin: "sdk", "human", "llm-judge", "heuristic"
metadata dict Arbitrary key-value metadata

Scores are emitted as gen_ai.evaluation.result spans with gen_ai.evaluation.* attributes, following the OTEL GenAI semantic conventions.

Auto-Instrumented Libraries

register() automatically discovers and activates any installed instrumentor packages via OTEL entry points. No code changes needed — install the extras for the providers you use and their calls are traced automatically.

Category Extras / packages
LLM providers [openai], [anthropic], [cohere], [mistral], [groq], [ollama]
Cloud AI [bedrock], [google] (Vertex AI + Generative AI)
Frameworks [langchain], [llamaindex]
All of the above [instrumentors]

Additional instrumentors (Together, Replicate, Writer, Voyage AI, Aleph Alpha, SageMaker, watsonx, Haystack, CrewAI, Agno, MCP, Transformers, ChromaDB, Pinecone, Qdrant, Weaviate, Milvus, LanceDB, Marqo) are included in [instrumentors] but do not have individual extras.

Configuration

Environment Variable Description Default
OPENSEARCH_OTEL_ENDPOINT OTLP endpoint URL http://localhost:21890/opentelemetry/v1/traces
OTEL_SERVICE_NAME Service name for spans "default"
OPENSEARCH_PROJECT Project/service name (fallback) "default"
AWS_DEFAULT_REGION AWS region for SigV4 auto-detected

License

Apache-2.0

Metadata

Release files for opensearch-genai-o11y-sdk-py 0.2.5

For a detailed explanation of source distributions (sdists) and built distributions (wheels), please see the package formats documentation.

Source distribution (sdist)

Source distribution for opensearch-genai-o11y-sdk-py 0.2.5
File Size Uploaded Provenance Actions
opensearch_genai_o11y_sdk_py-0.2.5.tar.gz 5.6 kB Without provenance Details for opensearch_genai_o11y_sdk_py-0.2.5.tar.gz

Built distribution (wheel)

Table of built distributions (wheels) for opensearch-genai-o11y-sdk-py 0.2.5
File Interpreter ABI Platform Actions
opensearch_genai_o11y_sdk_py-0.2.5-py3-none-any.whl Python 3 none any Details for opensearch_genai_o11y_sdk_py-0.2.5-py3-none-any.whl

Total release size: 10.9 kB

Release files / opensearch_genai_o11y_sdk_py-0.2.5.tar.gz

Download URL opensearch_genai_o11y_sdk_py-0.2.5.tar.gz
Size 5.6 kB
Tags Source
SHA-256 checksum
How to use checksums
351d9b443266c8ae1e4ef2e4b7199575e0a8ff9c02c6bfb18d3be4b42d8d9414
BLAKE2b-256 checksum
How to use checksums
71d16f3f8fd9a481b945acd4d75aeead25db02e9cf1eff2be1247ba4aa27b009
Upload date
Uploaded using Trusted Publishing?
What is trusted publishing?
No
Uploaded via twine/6.2.0 CPython/3.13.5

Release files / opensearch_genai_o11y_sdk_py-0.2.5-py3-none-any.whl

Download URL opensearch_genai_o11y_sdk_py-0.2.5-py3-none-any.whl
Size 5.3 kB
Tags Python 3
SHA-256 checksum
How to use checksums
057705afe0fa88dc323729dc426a5574eb27f98e91c433b08f780e234b12f143
BLAKE2b-256 checksum
How to use checksums
05360082757359834f88724fbb513508cbf2867b851789fcb073128110adcaac
Upload date
Uploaded using Trusted Publishing?
What is trusted publishing?
No
Uploaded via twine/6.2.0 CPython/3.13.5

Security for opensearch-genai-o11y-sdk-py 0.2.5

Provenance

Provenance describes where a file came from. On PyPI, provenance is shared via attestations, which provide a verifiable record of the build or publishing details. View details, limitations and caveats.

No provenance found

None of the files in this release were uploaded with provenance metadata.

A note on package security

PyPI is a repository for distributing packages, not a service for auditing them. While third-party security researchers and our staff do their best to detect and remove malicious packages, PyPI cannot guarantee the quality, security or suitability of any given package.

To learn more about protecting yourself from malicious actors, visit our package security documentation.

Release history Release notifications | RSS feed

This release

0.2.5 This release

2 release files No provenance

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