Nous utilisons des cookies. Les cookies et le stockage du navigateur vous gardent connecté et mémorisent vos préférences. Avec votre accord, nous mesurons aussi l’utilisation du site. Vous pouvez à tout moment. Consultez notre politique relative aux cookies.

Python

Guides SDK

Python

Utilisez le paquet Python officiel openai avec api14 : client synchrone et asynchrone, chat, streaming, outils, sorties Pydantic et erreurs.

Utilisez le paquet Python officiel openai avec api14. Définissez base_url et api_key ; utilisez n'importe quel identifiant de modèle (par exemple openai/gpt-5-mini) comme model.

Installation

pip install openai
export API14_API_KEY="sk-api14-..."

Configuration

from openai import OpenAI
import os

client = OpenAI(
    base_url="https://api14.com/api/v1",
    api_key=os.environ["API14_API_KEY"],
)

Un client asynchrone existe aussi : from openai import AsyncOpenAI prend les mêmes arguments. Utilisez-le quand vous lancez beaucoup de requêtes à la fois, par exemple dans un serveur web ou un traitement par lots :

import asyncio
from openai import AsyncOpenAI

aclient = AsyncOpenAI(base_url="https://api14.com/api/v1", api_key=os.environ["API14_API_KEY"])

async def ask(q):
    r = await aclient.chat.completions.create(model="openai/gpt-5-mini", messages=[{"role": "user", "content": q}])
    return r.choices[0].message.content

async def main():
    return await asyncio.gather(*(ask(q) for q in ["What is RAG?", "What is a token?"]))

answers = asyncio.run(main())

Gardez la concurrence sous la limite de requêtes par minute de votre forfait. Voir Guide : traitement par lots.

Sans argument, OpenAI() lit OPENAI_BASE_URL et OPENAI_API_KEY, vous pouvez donc faire pointer une application existante vers api14 uniquement via l'environnement :

export OPENAI_BASE_URL="https://api14.com/api/v1"
export OPENAI_API_KEY="sk-api14-..."

Chat

result = client.chat.completions.create(
    model="openai/gpt-5-mini",
    messages=[{"role": "user", "content": "Explain vector databases in two sentences."}],
)
print(result.choices[0].message.content)

Streaming

stream = client.chat.completions.create(
    model="anthropic/claude-sonnet-4.5",
    messages=[{"role": "user", "content": "Write a haiku about APIs."}],
    stream=True,
)
for chunk in stream:
    if chunk.choices:
        print(chunk.choices[0].delta.content or "", end="")

Voir Streaming.

Appel d'outils

import json

tools = [{
    "type": "function",
    "function": {
        "name": "get_weather",
        "description": "Current weather for a city",
        "parameters": {
            "type": "object",
            "properties": {"city": {"type": "string"}},
            "required": ["city"],
        },
    },
}]
messages = [{"role": "user", "content": "What's the weather in Istanbul?"}]

while True:
    res = client.chat.completions.create(model="openai/gpt-5-mini", messages=messages, tools=tools)
    msg = res.choices[0].message
    if not msg.tool_calls:
        break
    messages.append(msg)
    for call in msg.tool_calls:
        args = json.loads(call.function.arguments)
        result = get_weather(**args)  # votre fonction
        messages.append({"role": "tool", "tool_call_id": call.id, "content": json.dumps(result)})

print(msg.content)

Voir Appel d'outils.

Sortie structurée

client.chat.completions.parse convertit un modèle Pydantic en JSON Schema strict et renvoie l'objet analysé. Il nécessite une version récente de openai ; les anciennes versions 1.x l'exposent sous client.beta.chat.completions.parse. Utilisez un modèle dont les supported_parameters incluent structured_outputs ou response_format :

from pydantic import BaseModel

class Person(BaseModel):
    name: str
    born: int
    city: str

res = client.chat.completions.parse(
    model="openai/gpt-5-mini",
    messages=[{"role": "user", "content": "Extract: Ada Lovelace, born 1815 in London."}],
    response_format=Person,
)
person = res.choices[0].message.parsed  # Person(name='Ada Lovelace', born=1815, city='London')

Voir Sorties structurées.

Image en entrée

import base64

image = base64.b64encode(open("photo.png", "rb").read()).decode()

res = client.chat.completions.create(
    model="google/gemini-2.5-flash",
    messages=[{
        "role": "user",
        "content": [
            {"type": "text", "text": "What is in this picture?"},
            {"type": "image_url", "image_url": {"url": f"data:image/png;base64,{image}"}},
        ],
    }],
)

Une URL publique https:// fonctionne aussi. Voir Vision et fichiers.

Images

result = client.images.generate(
    model="openai/gpt-5.4-image-2",
    prompt="A minimalist product photo of a ceramic mug on a wooden table",
    n=1,
    extra_body={"aspect_ratio": "1:1"},
)
open("image.png", "wb").write(base64.b64decode(result.data[0].b64_json))

Les paramètres que le SDK ne connaît pas (aspect_ratio, provider, models, reasoning) vont dans extra_body.

Voix et transcription

audio = client.audio.speech.create(
    model="openai/gpt-4o-mini-tts",
    input="Hello from api14!",
    voice="alloy",
)
audio.write_to_file("speech.mp3")

text = client.audio.transcriptions.create(
    model="openai/whisper-1",
    file=open("speech.mp3", "rb"),
)
print(text.text)

Erreurs

import openai

try:
    client.chat.completions.create(
        model="openai/gpt-5-mini",
        messages=[{"role": "user", "content": "Hi"}],
    )
except openai.APIStatusError as e:
    if e.status_code == 402:
        print("Balance too low, add funds:", e.code)  # insufficient_balance
    elif e.status_code == 429:
        print("Retry after", e.response.headers.get("retry-after"), "s:", e.code)  # rate_limited
    else:
        raise

Voir Erreurs.

Délais d'attente et nouvelles tentatives

Par défaut, le SDK réessaie deux fois les erreurs de connexion, 408, 409, 429 et 5xx avec un backoff exponentiel, en respectant Retry-After. Le délai par défaut est de 10 minutes. Configurez les deux sur le client, ou par appel avec with_options :

import httpx

client = OpenAI(
    base_url="https://api14.com/api/v1",
    api_key=os.environ["API14_API_KEY"],
    timeout=httpx.Timeout(60.0, connect=5.0),
    max_retries=4,
)

client.with_options(timeout=300, max_retries=0).chat.completions.create(...)

Réessayer n'aide pas face à daily_limit_reached ou insufficient_balance ; arrêtez-vous et alertez plutôt. Voir Limites de débit.

Toutes les capacités

import OpenAI from "openai";

const client = new OpenAI({
  baseURL: "https://api14.com/api/v1",
  apiKey: process.env.API14_API_KEY,
});

const result = await client.chat.completions.create({
  "model": "openai/gpt-5-mini",
  "messages": [
    {
      "role": "user",
      "content": "Explain vector databases in two sentences."
    }
  ]
});
console.log(result.choices[0].message.content);