Skip to main content

Official Python SDK for Onlist, the AI API marketplace. Access GPT, Claude, Gemini, DeepSeek and 40+ models through one OpenAI-compatible API.

Project description

Onlist Python SDK

The official Python client for Onlist, the AI API marketplace.

Onlist aggregates 40+ AI model providers behind a single OpenAI-compatible API. This SDK is a drop-in replacement for the OpenAI Python client, so you can switch with one line of code.

PyPI version Python versions License: MIT

Installation

pip install onlist

Quick Start

from onlist import Onlist

client = Onlist(api_key="sk-...")  # or set ONLIST_API_KEY env var

response = client.chat.completions.create(
    model="anthropic/claude-sonnet-4",
    messages=[{"role": "user", "content": "What is Onlist?"}],
)
print(response.choices[0].message.content)

Get your API key at onlist.io.

Authentication

The client reads your API key from:

  1. The api_key parameter
  2. The ONLIST_API_KEY environment variable
  3. The OPENAI_API_KEY environment variable (fallback, for easy migration)
export ONLIST_API_KEY="sk-..."

Context Manager

Both sync and async clients support use as context managers, which ensures the underlying HTTP connections are properly closed:

from onlist import Onlist

with Onlist(api_key="sk-...") as client:
    response = client.chat.completions.create(
        model="anthropic/claude-sonnet-4",
        messages=[{"role": "user", "content": "Hello!"}],
    )
    print(response.choices[0].message.content)
# Connections are automatically closed here
import asyncio
from onlist import AsyncOnlist

async def main():
    async with AsyncOnlist(api_key="sk-...") as client:
        response = await client.chat.completions.create(
            model="openai/gpt-4o",
            messages=[{"role": "user", "content": "Hello!"}],
        )
        print(response.choices[0].message.content)

asyncio.run(main())

Provider Routing

Onlist's marketplace lets you choose which provider serves your request. Use the provider field via extra_body:

# Pin to a specific provider
response = client.chat.completions.create(
    model="anthropic/claude-sonnet-4",
    messages=[{"role": "user", "content": "Hello"}],
    extra_body={"provider": "alice-shop"},
)

# Route to the cheapest provider
response = client.chat.completions.create(
    model="openai/gpt-4o",
    messages=[{"role": "user", "content": "Hello"}],
    extra_body={"provider": {"sort": "price"}},
)

# Full routing control
response = client.chat.completions.create(
    model="openai/gpt-4o",
    messages=[{"role": "user", "content": "Hello"}],
    extra_body={
        "provider": {
            "allow": ["alice-shop", "bob-relay"],
            "sort": "price",
            "allow_fallbacks": True,
            "max_price": {"prompt": 0.000003, "completion": 0.000015},
        }
    },
)

You can also use the typed helper:

from onlist import ProviderRouting

routing = ProviderRouting(
    allow=["alice-shop", "bob-relay"],
    sort="price",
)

response = client.chat.completions.create(
    model="openai/gpt-4o",
    messages=[{"role": "user", "content": "Hello"}],
    extra_body={"provider": routing.model_dump(exclude_none=True)},
)

Streaming

stream = client.chat.completions.create(
    model="anthropic/claude-sonnet-4",
    messages=[{"role": "user", "content": "Write a haiku about APIs"}],
    stream=True,
)

for chunk in stream:
    content = chunk.choices[0].delta.content
    if content:
        print(content, end="", flush=True)

Async Usage

import asyncio
from onlist import AsyncOnlist

async def main():
    client = AsyncOnlist(api_key="sk-...")

    response = await client.chat.completions.create(
        model="openai/gpt-4o",
        messages=[{"role": "user", "content": "Hello!"}],
    )
    print(response.choices[0].message.content)

asyncio.run(main())

Marketplace API

Query the Onlist marketplace for models and providers:

from onlist import Onlist

client = Onlist(api_key="sk-...")

# List available models with pricing
models = client.marketplace.models.list(limit=10)
for m in models.data:
    print(f"{m.id} - input: {m.pricing.prompt if m.pricing else 'N/A'}")

# Get detailed model info with all provider offers
detail = client.marketplace.models.get("anthropic/claude-sonnet-4")
print(f"{detail.id} - {len(detail.providers)} providers")

# Browse providers
providers = client.marketplace.providers.list()
for p in providers.data:
    print(f"{p.slug} - score: {p.score}")

# Get a specific provider's profile
provider = client.marketplace.providers.get("alice-shop")
print(f"{provider.display_name} - {provider.model_count} models")

Rankings API

View model usage rankings and app usage data:

from onlist import Onlist

client = Onlist(api_key="sk-...")

# Model usage leaderboard
rankings = client.marketplace.rankings.models(sort="popular", window="week")
for entry in rankings.leaderboard:
    print(f"#{entry.rank} {entry.model_name} by {entry.author} - {entry.total_tokens} tokens")

# Trending models
trending = client.marketplace.rankings.models(sort="trending", window="month")
for entry in trending.leaderboard:
    if entry.growth_pct is not None:
        print(f"{entry.model_name}: +{entry.growth_pct:.1f}%")

# App usage rankings
apps = client.marketplace.rankings.apps(sort="popular", window="month")
for app in apps.apps:
    print(f"#{app.rank} {app.title} ({app.domain}) - {app.total_requests} requests")

# Filter by category
coding_apps = client.marketplace.rankings.apps(category="coding")
for app in coding_apps.apps:
    print(f"{app.title}: {app.categories}")

Other APIs

Since Onlist is fully OpenAI-compatible, all standard endpoints work:

# Embeddings
embedding = client.embeddings.create(
    model="openai/text-embedding-3-small",
    input="Hello world",
)

# Image generation
image = client.images.generate(
    model="openai/gpt-image-2",
    prompt="A sunset over Tokyo",
)

# Text-to-speech
audio = client.audio.speech.create(
    model="openai/tts-1",
    voice="alloy",
    input="Welcome to Onlist.",
)

Error Handling

For OpenAI-compatible API calls (chat.completions, embeddings, etc.), the standard openai exceptions are raised:

import openai
from onlist import Onlist

client = Onlist(api_key="sk-...")

try:
    response = client.chat.completions.create(
        model="openai/gpt-4o",
        messages=[{"role": "user", "content": "Hello"}],
    )
except openai.AuthenticationError:
    print("Invalid API key")
except openai.RateLimitError as e:
    print(f"Rate limited: {e.message}")

For marketplace API calls (client.marketplace.*), Onlist-specific exceptions are raised:

from onlist import Onlist, AuthenticationError, NotFoundError, APIError

client = Onlist(api_key="sk-...")

try:
    detail = client.marketplace.models.get("nonexistent/model")
except NotFoundError:
    print("Model not found")
except AuthenticationError:
    print("Invalid API key for marketplace")
except APIError as e:
    print(f"API error {e.status_code}: {e.message}")

Marketplace requests are automatically retried on transient errors (408, 429, 5xx) with exponential backoff. Configure the retry limit:

# Disable retries
client = Onlist(api_key="sk-...", max_retries=0)

# More retries
client = Onlist(api_key="sk-...", max_retries=5)

Migrate from OpenAI or OpenRouter

Already using the OpenAI SDK? Change one line:

- from openai import OpenAI
- client = OpenAI(api_key="sk-...")
+ from onlist import Onlist
+ client = Onlist(api_key="sk-...")

Or, if you prefer to keep using openai directly:

from openai import OpenAI

client = OpenAI(
    api_key="your-onlist-key",
    base_url="https://onlist.io/v1",
)

Routing Metadata

Onlist returns routing information in response headers. Access them to see which provider actually served your request:

# Use the with_raw_response pattern from the openai SDK:
raw_response = client.chat.completions.with_raw_response.create(
    model="openai/gpt-4o",
    messages=[{"role": "user", "content": "Hello"}],
)
print(raw_response.headers.get("x-onlist-route-id"))
print(raw_response.headers.get("x-onlist-provider"))

# Parse the completion as usual:
response = raw_response.parse()
print(response.choices[0].message.content)

Links

Project details


Download files

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

Source Distribution

onlist-0.2.0.tar.gz (15.9 kB view details)

Uploaded Source

Built Distribution

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

onlist-0.2.0-py3-none-any.whl (15.0 kB view details)

Uploaded Python 3

File details

Details for the file onlist-0.2.0.tar.gz.

File metadata

  • Download URL: onlist-0.2.0.tar.gz
  • Upload date:
  • Size: 15.9 kB
  • Tags: Source
  • Uploaded using Trusted Publishing? Yes
  • Uploaded via: twine/6.1.0 CPython/3.13.12

File hashes

Hashes for onlist-0.2.0.tar.gz
Algorithm Hash digest
SHA256 4c001b5c94c5a64c694376ffcd4d5af4ca07bd137292b4c53d5d1d2714d9e0f0
MD5 328bce14601138693c0cf60abf0614e0
BLAKE2b-256 a08e425cbf5e11dc9890a1beee54aa09ee0087151a113eeb4e971bbc892692c7

See more details on using hashes here.

Provenance

The following attestation bundles were made for onlist-0.2.0.tar.gz:

Publisher: publish.yml on OnlistTeam/python-sdk

Attestations: Values shown here reflect the state when the release was signed and may no longer be current.

File details

Details for the file onlist-0.2.0-py3-none-any.whl.

File metadata

  • Download URL: onlist-0.2.0-py3-none-any.whl
  • Upload date:
  • Size: 15.0 kB
  • Tags: Python 3
  • Uploaded using Trusted Publishing? Yes
  • Uploaded via: twine/6.1.0 CPython/3.13.12

File hashes

Hashes for onlist-0.2.0-py3-none-any.whl
Algorithm Hash digest
SHA256 dfa55b336a7e31847d9688ddc2b54fb5fe28aa426732e0bb437ded09fe029c97
MD5 e59ef4d0737cd97042cee425c90f4cde
BLAKE2b-256 5cd0f8022dcb745744a714f92205656c193d0727443048e0baff11d96f629fb8

See more details on using hashes here.

Provenance

The following attestation bundles were made for onlist-0.2.0-py3-none-any.whl:

Publisher: publish.yml on OnlistTeam/python-sdk

Attestations: Values shown here reflect the state when the release was signed and may no longer be current.

Supported by

AWS Cloud computing and Security Sponsor Datadog Monitoring Depot Continuous Integration Fastly CDN Google Download Analytics Pingdom Monitoring Sentry Error logging StatusPage Status page