Python SDK for Grepture — AI gateway with PII redaction, tracing, cost tracking, and prompt management. Works with any OpenAI-compatible SDK.
pip install grepturefrom openai import OpenAI
from grepture import Grepture
grepture = Grepture(api_key="gpt_abc123", proxy_url="https://proxy.grepture.com")
client = OpenAI(**grepture.client_options(
api_key="sk-openai-key",
base_url="https://api.openai.com/v1",
))
# Works exactly like normal — requests flow through Grepture
completion = client.chat.completions.create(
model="gpt-5.5",
messages=[{"role": "user", "content": "hi"}],
)grepture = Grepture(api_key="gpt_abc123", proxy_url="https://proxy.grepture.com", mode="trace")
client = OpenAI(**grepture.client_options(api_key="sk-openai-key", base_url="https://api.openai.com/v1"))
# Requests go DIRECT to the provider; traces are sent async in the background.
grepture.flush() # call before exit in serverless environments| Mode | Default | Traffic flow | Use case |
|---|---|---|---|
"proxy" |
Yes | App → Grepture → Provider | PII redaction, blocking, prompt management |
"trace" |
No | App → Provider (direct) | Observability and cost tracking without latency overhead |
In proxy mode (default), requests route through the Grepture proxy where detection rules are applied. In trace mode, requests go directly to the provider — the SDK captures metadata (tokens, model, latency, cost) asynchronously and sends it to the dashboard in the background.
Every feature has an async counterpart via AsyncGrepture, built on httpx.AsyncClient.
from openai import AsyncOpenAI
from grepture import AsyncGrepture
grepture = AsyncGrepture(api_key="gpt_abc123", proxy_url="https://proxy.grepture.com")
client = AsyncOpenAI(**grepture.client_options(
api_key="sk-openai-key",
base_url="https://api.openai.com/v1",
))
completion = await client.chat.completions.create(
model="gpt-5.5",
messages=[{"role": "user", "content": "hi"}],
)
await grepture.flush() # call before exit in serverless environmentsUse grepture.request() when you don't have (or don't want) a provider SDK in the loop. It routes through the same proxy/trace logic as client_options() and returns a GreptureResponse.
response = grepture.request(
"https://api.openai.com/v1/chat/completions",
headers={"Authorization": "Bearer sk-openai-key"},
json={"model": "gpt-5.5", "messages": [{"role": "user", "content": "hi"}]},
)
print(response.status_code) # 200
print(response.request_id) # proxy-assigned request id
print(response.rules_applied) # ["rule-uuid-1"]
print(response.json()) # parsed response bodyGroup related requests into a trace, label each step, attach metadata, and log custom events.
grepture = Grepture(api_key="gpt_abc123", proxy_url="https://proxy.grepture.com", trace_id="agent-run-42")
client = OpenAI(**grepture.client_options(api_key="sk-openai-key", base_url="https://api.openai.com/v1"))
# Attach metadata to all requests in this trace
grepture.set_metadata({"user_id": "u_123", "environment": "prod"})
# Label each step
grepture.set_label("extract-facts")
client.chat.completions.create(model="gpt-5.5", messages=[...])
# Log a custom event between AI calls
grepture.log("extract-facts-done", {"tokens": 174})
grepture.set_label("draft-response")
client.chat.completions.create(model="gpt-5.5", messages=[...])
grepture.flush() # call before exit in serverless environmentsAll trace data (labels, metadata, log events) is visible in the Grepture dashboard under Traffic Log > Traces, and on the dedicated trace detail page.
Fetch and resolve prompt templates managed in the Grepture dashboard.
# Proxy mode: attach a prompt reference to a request; the proxy resolves it server-side
messages = grepture.prompt.use("greeting", variables={"name": "Ada"})
client.chat.completions.create(model="gpt-5.5", messages=messages)
# Fetch a prompt template directly
template = grepture.prompt.get("greeting", version=3)
# Fetch + resolve variables locally (works in both proxy and trace mode)
assembled = grepture.prompt.assemble("greeting", variables={"name": "Ada"})
client.chat.completions.create(model="gpt-5.5", messages=assembled["messages"])
# Resolve a set of messages against variables without a network call
resolved = grepture.prompt.resolve(
[{"role": "system", "content": "Hi {{name}}"}], {"name": "Ada"}
)
# List all prompts
prompts = grepture.prompt.list()grepture.prompt.use() raises RuntimeError in trace mode, since it depends on the proxy to resolve the prompt server-side — use grepture.prompt.assemble() instead, which fetches the template and resolves it locally.
result = grepture.embeddings.create(
model="text-embedding-3-small",
input="hello world",
openai_key="sk-openai-key",
)
print(result["data"][0]["embedding"])
print(result["redactions"]) # {"count": 0, "categories": []}The SDK raises typed errors on non-OK responses from the proxy:
from grepture import Grepture, AuthError, BlockedError
try:
response = grepture.request(url, json=payload)
except BlockedError:
... # Request blocked by a Grepture rule (403)
except AuthError:
... # Invalid Grepture API key (401)| Error Class | Status | When |
|---|---|---|
BadRequestError |
400 | Malformed request |
AuthError |
401 | Invalid Grepture API key |
BlockedError |
403 | Request blocked by a rule |
ProxyError |
502/504 | Target unreachable or timed out |
GreptureError |
other | Any other non-OK status (base class for all of the above) |
| Parameter | Type | Description |
|---|---|---|
api_key |
str |
Your Grepture API key (gpt_xxx) |
proxy_url |
str |
Grepture proxy URL (e.g. https://proxy.grepture.com) |
mode |
"proxy" | "trace" |
Operating mode (default: "proxy") |
trace_id |
str | None |
Default trace ID for conversation tracing |
Returns {"base_url", "api_key", "http_client"} for use with OpenAI-shaped SDK constructors (OpenAI(**client_options(...))).
| Parameter | Type | Description |
|---|---|---|
base_url |
str |
Target base URL (e.g. https://api.openai.com/v1) |
api_key |
str | None |
Target API key (e.g. sk-openai-key); omit to use a key stored in the Grepture dashboard (proxy mode only) |
debug |
bool |
Attach debug headers to proxied requests |
grepture.request(target_url, *, method="POST", headers=None, json=None, content=None, trace_id=None, label=None, metadata=None, debug=False)
Issues a single request through the proxy (or direct, in trace mode) and returns a GreptureResponse. Pass either json (auto-serialized) or raw content bytes, not both.
Set or clear the default trace ID for all subsequent requests.
Set or clear the default label for all subsequent requests. Override per-request via request(..., label=...).
Set or clear default metadata (dict[str, str]) for all subsequent requests. Override per-request via request(..., metadata=...) (values merge, per-request wins on conflicts).
Log a custom event into the current trace. event is the event name (string), data is an optional payload (dict). Events appear in the trace timeline alongside AI calls.
Flushes any pending trace and log data. Call before process exit in serverless or short-lived environments.
Attach a prompt reference to a message list; the proxy resolves it server-side. Raises RuntimeError in trace mode.
grepture.prompt.get(slug, *, version=None) / grepture.prompt.assemble(slug, *, variables=None, version=None)
Fetch a raw prompt template, or fetch and resolve it against variables locally.
Resolve {{var}}, {{#if}}, and {{#each}} template syntax against a variable dict, without a network call.
List all prompts available to your API key.
grepture.embeddings.create(*, model, input, dimensions=None, encoding_format=None, user=None, on_pii=None, strategy=None, openai_key=None, trace_id=None)
Create embeddings through the Grepture proxy, with PII redaction applied to input before it reaches the provider.
Python 3.9+. Depends on httpx only.