> For the complete documentation index, see [llms.txt](https://unsloth.ai/docs/llms.txt). Markdown versions of documentation pages are available by appending `.md` to page URLs; this page is available as [Markdown](https://unsloth.ai/docs/fr/integrations/connecter-le-sdk-python-a-unsloth.md).

# Connecter le SDK Python à Unsloth

Guide pour appeler l'API locale d'Unsloth depuis Python à l'aide des SDK officiels OpenAI ou Anthropic, y compris le streaming, la vision, l'appel de fonctions et les outils côté serveur intégrés d'Unsloth.

Unsloth propose trois dialectes compatibles avec OpenAI à la même URL de base. Chat Completions, Responses et Anthropic Messages, donc tous les SDK Python grand public fonctionnent avec lui. \
\
Vous ne modifiez que le `base_url` et `api_key`  côté client ; tout le reste (streaming, appels d’outils, vision, sortie structurée) se comporte comme le documente le SDK. Cette page couvre les deux SDK vers lesquels la plupart des développeurs se tournent en premier : l’officiel **SDK Python OpenAI** et l’officiel **SDK Python Anthropic**.

{% hint style="info" %}
Si vous ne savez pas quelle URL / clé / nom de modèle utiliser, lisez d’abord la vue d’ensemble de l’API. Elle vous guide pour démarrer, charger un modèle et créer une `sk-unsloth-…` clé.
{% endhint %}

### 🔑 Prérequis

Avant d’exécuter les extraits ci-dessous, vous aurez besoin de :

* **d’Unsloth exécuté localement** avec un modèle chargé (notez le port : généralement `8000` ou `8888`).
* **Une `sk-unsloth-…` clé API** créée à partir de **Paramètres → API**.
* **Un nom de modèle.** Le nom du modèle GGUF dans Unsloth (par ex. `qwen-local`, `unsloth/Qwen3.6-27B-GGUF`). Si vous l’oubliez, exécutez :

  ```bash
  curl http://localhost:8888/v1/models -H "Authorization: Bearer sk-unsloth-…"
  ```

  et copiez le `id` champ.

Définissez la clé comme variable d’environnement afin de ne jamais la coller dans le code :

```bash
export UNSLOTH_STUDIO_AUTH_TOKEN=sk-unsloth-xxxxxxxxxxxx
```

#### 🤖 SDK OpenAI

d'Unsloth `/v1/chat/completions` Le point de terminaison est un remplacement direct pour le SDK Python OpenAI. Le client traite Unsloth comme n’importe quel autre fournisseur compatible OpenAI.

**1. Installez le SDK :**

```bash
pip install openai
```

**2. Créez un client** pointant vers Unsloth :

```python
import os
from openai import OpenAI

client = OpenAI(
    base_url="http://localhost:8888/v1",              # votre port Unsloth + /v1
    api_key=os.environ["UNSLOTH_STUDIO_AUTH_TOKEN"],     # votre clé sk-unsloth-…
)
```

#### Complétion de chat de base

```python
response = client.chat.completions.create(
    model="default",                               # le nom que vous avez donné au modèle dans Unsloth ou default
    messages=[
        {"role": "user", "content": "Donnez-moi deux faits sur Paris"}
    ],
)
print(response.choices[0].message.content)
```

<figure><img src="https://550366147-files.gitbook.io/~/files/v0/b/gitbook-x-prod.appspot.com/o/spaces%2FxhOjnexMCB3dmuQFQ2Zq%2Fuploads%2FZkxVYS7fcvwXZ8AxvaBF%2FScreenshot%202026-04-22%20at%202.38.44%E2%80%AFAM.png?alt=media&amp;token=06dece4e-dade-4c2d-bcdb-7c946cdd1290" alt=""><figcaption></figcaption></figure>

#### Diffusion en continu

Définissez `stream=True` et itérez sur le générateur renvoyé :

```python
stream = client.chat.completions.create(
    model="qwen-local",
    messages=[{"role": "user", "content": "Écris un haïku sur les LLM exécutés localement."}],
    stream=True,
)
for chunk in stream:
    if chunk.choices:
        delta = chunk.choices[0].delta.content
        if delta:
            print(delta, end="", flush=True)
```

<figure><img src="https://550366147-files.gitbook.io/~/files/v0/b/gitbook-x-prod.appspot.com/o/spaces%2FxhOjnexMCB3dmuQFQ2Zq%2Fuploads%2F0eItNT5zanSB8rXY4QHn%2Fopenai_streaming.png?alt=media&amp;token=2922bbf3-69da-409f-b954-76b6259233f8" alt=""><figcaption></figcaption></figure>

#### Images (vision)

Attachez une image comme un `image_url` élément de contenu. Unsloth accepte soit une URL HTTP(S), soit une `donnée :` URI base64 :

```python
import base64
from pathlib import Path

img_b64 = base64.b64encode(Path("test.jpg").read_bytes()).decode()

response = client.chat.completions.create(
    model="default",
    messages=[
        {
            "role": "user",
            "content": [
                {
                    "type": "image_url",
                    "image_url": {"url": f"data:image/jpeg;base64,{img_b64}"},
                },
                {"type": "text", "text": "Qu’y a-t-il dans cette image ?"},
            ],
        }
    ],
)
print(response.choices[0].message.content)
```

{% hint style="info" %}
Le modèle chargé doit être multimodal. Si vous chargez un modèle texte uniquement, la requête vision réussira structurellement, mais le modèle ne pourra pas « voir » l’image.
{% endhint %}

<figure><img src="https://550366147-files.gitbook.io/~/files/v0/b/gitbook-x-prod.appspot.com/o/spaces%2FxhOjnexMCB3dmuQFQ2Zq%2Fuploads%2FTNCX4qEMj8zFSAsOJw2Y%2Fopenai_sdk_vision_test.png?alt=media&amp;token=caa22501-66fc-4e3c-b4a0-636ebe5af4bf" alt=""><figcaption></figcaption></figure>

#### Appel de fonctions (outils OpenAI)

Passez des `outils` et (éventuellement) `tool_choice` et Unsloth les transmet au backend. Votre client est responsable d’exécuter chaque appel d’outil et de renvoyer le résultat au tour suivant :

```python
tools = [
    {
        "type": "function",
        "function": {
            "name": "get_weather",
            "description": "Obtenir la météo actuelle pour une ville",
            "parameters": {
                "type": "object",
                "properties": {
                    "city": {"type": "string", "description": "Nom de la ville, par ex. 'Paris'"},
                },
                "required": ["city"],
            },
        },
    }
]

response = client.chat.completions.create(
    model="default",
    messages=[{"role": "user", "content": "Quel temps fait-il à Perth en ce moment ?"}],
    tools=tools,
    tool_choice="auto",
)

tool_call = response.choices[0].message.tool_calls[0]
print(tool_call.function.name, tool_call.function.arguments)
```

<figure><img src="https://550366147-files.gitbook.io/~/files/v0/b/gitbook-x-prod.appspot.com/o/spaces%2FxhOjnexMCB3dmuQFQ2Zq%2Fuploads%2F8nzgxHsN8J23B6duQ3Zv%2Fopenai_sdk_function_calling.png?alt=media&amp;token=3551592d-31b2-4fa6-94a9-6a9f0974c21a" alt=""><figcaption></figcaption></figure>

#### Outils côté serveur d’Unsloth (raccourci)

En plus des outils côté client au style OpenAI, Unsloth peut exécuter **Python**, **bash**et **recherche web** côté serveur et renvoyer automatiquement les résultats en flux. Activez cette option via le `extra_body` paramètre afin que les champs soient transmis tels quels à Unsloth :

```python
stream = client.chat.completions.create(
    model="default",
    messages=[{"role": "user", "content": "Combien font 123 * 456 ? Utilisez Python pour le calculer."}],
    stream=True,
    extra_body={
        "enable_tools": True,
        "enabled_tools": ["python", "web_search"],
        "session_id": "my-session",
    },
)
for chunk in stream:
    if chunk.choices:
        delta = chunk.choices[0].delta.content
        if delta:
            print(delta, end="", flush=True)
```

<figure><img src="https://550366147-files.gitbook.io/~/files/v0/b/gitbook-x-prod.appspot.com/o/spaces%2FxhOjnexMCB3dmuQFQ2Zq%2Fuploads%2FvdZuLwIh7LT0C8y7AWaR%2FScreenshot%202026-04-22%20at%203.01.06%E2%80%AFAM.png?alt=media&amp;token=35ff3039-d941-406b-b3fc-5e1e564c7651" alt=""><figcaption></figcaption></figure>

<figure><img src="https://550366147-files.gitbook.io/~/files/v0/b/gitbook-x-prod.appspot.com/o/spaces%2FxhOjnexMCB3dmuQFQ2Zq%2Fuploads%2FnW60ezYCOJQmTjd52bnu%2FScreenshot%202026-04-22%20at%203.05.23%E2%80%AFAM.png?alt=media&amp;token=f7125db4-cb94-46f7-974d-abe58ec348a7" alt=""><figcaption></figcaption></figure>

Le `session_id` est facultatif. Utilisez-le pour conserver l’état des outils (par ex. un noyau Python) entre les appels.

{% hint style="info" %}
`enabled_tools` prend actuellement en charge `"python"`, `"bash"`et `"web_search"`. Les résultats des outils sont renvoyés en flux sous forme d’ `tool_result` événements afin que le modèle puisse les voir à son tour suivant.
{% endhint %}

**Liste des modèles**

```python
models = client.models.list()
for m in models.data:
    print(m.id)
```

<figure><img src="https://550366147-files.gitbook.io/~/files/v0/b/gitbook-x-prod.appspot.com/o/spaces%2FxhOjnexMCB3dmuQFQ2Zq%2Fuploads%2F6GKdrximwyplotWu3u5s%2FScreenshot%202026-04-22%20at%203.06.57%E2%80%AFAM.png?alt=media&amp;token=48d17278-e4b0-4437-a426-5f12c0c45b1e" alt=""><figcaption></figcaption></figure>

#### 🧠 SDK Anthropic

d'Unsloth `/v1/messages` Le point de terminaison est un remplacement direct pour le SDK Python Anthropic.

**1. Installez le SDK :**

```bash
pip install anthropic
```

**2. Créez un client** pointant vers Unsloth :

{% code overflow="wrap" %}

```python
import os
from anthropic import Anthropic

client = Anthropic(
    base_url="http://localhost:8888", # votre port Unsloth (pas de /v1 ici — le SDK l’ajoute)
    api_key="dummy", # une valeur aléatoire non vide
    default_headers={"Authorization": f"Bearer {os.environ['UNSLOTH_STUDIO_AUTH_TOKEN']}"} # votre clé sk-unsloth-…
)
```

{% endcode %}

#### Message de base

```python
message = client.messages.create(
    model="default",
    max_tokens=1024,
    messages=[
        {"role": "user", "content": "Dis bonjour en trois langues."}
    ],
)
print(message.content[0].text)
```

<figure><img src="https://550366147-files.gitbook.io/~/files/v0/b/gitbook-x-prod.appspot.com/o/spaces%2FxhOjnexMCB3dmuQFQ2Zq%2Fuploads%2Fc4yQCiRHjebKomV4H2Eh%2FScreenshot%202026-04-22%20at%202.29.04%E2%80%AFAM.png?alt=media&amp;token=4ad983da-83fd-48c0-8fa8-1fbe92fcfd40" alt=""><figcaption></figcaption></figure>

#### Diffusion en continu

Le SDK expose un gestionnaire de contexte qui produit des deltas de texte :

```python
with client.messages.stream(
    model="default",
    max_tokens=1024,
    messages=[{"role": "user", "content": "Expliquez LoRA en deux phrases."}],
) as stream:
    for text in stream.text_stream:
        print(text, end="", flush=True)
```

#### Images (vision)

Le contenu d’image au style Anthropic utilise un `code source` bloc avec des données base64 :

```python
import base64
from pathlib import Path

img_b64 = base64.standard_b64encode(Path("photo.jpg").read_bytes()).decode()

message = client.messages.create(
    model="default",
    max_tokens=1024,
    messages=[
        {
            "role": "user",
            "content": [
                {
                    "type": "image",
                    "source": {
                        "type": "base64",
                        "media_type": "image/jpeg",
                        "data": img_b64,
                    },
                },
                {"type": "text", "text": "Qu’y a-t-il dans cette image ?"},
            ],
        }
    ],
)
print(message.content[0].text)
```

<figure><img src="https://550366147-files.gitbook.io/~/files/v0/b/gitbook-x-prod.appspot.com/o/spaces%2FxhOjnexMCB3dmuQFQ2Zq%2Fuploads%2FKI75sgbWxmo8BNXQEP6s%2Fanthropic_sdk_vision_test.png?alt=media&amp;token=f72c2dd6-b811-41a7-82bb-a2a6f30513ac" alt=""><figcaption></figcaption></figure>

#### Appel d’outils (outils Anthropic)

Passez du style Anthropic `outils` avec un `input_schema` et Unsloth les transmet nativement :

```python
tools = [
    {
        "name": "get_weather",
        "description": "Obtenir la météo actuelle pour une ville",
        "input_schema": {
            "type": "object",
            "properties": {
                "city": {"type": "string", "description": "Nom de la ville, par ex. 'Tokyo'"},
            },
            "required": ["city"],
        },
    }
]

message = client.messages.create(
    model="default",
    max_tokens=1024,
    tools=tools,
    tool_choice={"type": "auto"},
    messages=[{"role": "user", "content": "Quel temps fait-il à Tokyo ?"}],
)

for block in message.content:
    if block.type == "tool_use":
        print(block.name, block.input)
```

<figure><img src="https://550366147-files.gitbook.io/~/files/v0/b/gitbook-x-prod.appspot.com/o/spaces%2FxhOjnexMCB3dmuQFQ2Zq%2Fuploads%2FWnWPZdZOtV2o1o5FIzlD%2Fanthropic_tool_use_get_weather_tokyo.png?alt=media&amp;token=39587916-f4c0-45cf-8e59-11245b3432b8" alt=""><figcaption></figcaption></figure>

#### Outils côté serveur d’Unsloth (raccourci)

Le même `enable_tools` / `enabled_tools` / `session_id` raccourci fonctionne avec `/v1/messages` transmettez-le `extra_body`:

```python
with client.messages.stream(
    model="default",
    max_tokens=1024,
    messages=[{"role": "user", "content": "Recherchez des fonctionnalités de Python 3.13 et résumez-les."}],
    extra_body={
        "enable_tools": True,
        "enabled_tools": ["web_search", "python"],
        "session_id": "my-session",
    },
) as stream:
    for text in stream.text_stream:
        print(text, end="", flush=True)
```

<figure><img src="https://550366147-files.gitbook.io/~/files/v0/b/gitbook-x-prod.appspot.com/o/spaces%2FxhOjnexMCB3dmuQFQ2Zq%2Fuploads%2F2wA6aleUHPJN1gAB3ClL%2Fserver_side_tool_call_backend.png?alt=media&amp;token=7440befb-d517-473a-a431-c6b4cb413ca5" alt=""><figcaption></figcaption></figure>

<figure><img src="https://550366147-files.gitbook.io/~/files/v0/b/gitbook-x-prod.appspot.com/o/spaces%2FxhOjnexMCB3dmuQFQ2Zq%2Fuploads%2FwcIerVboFjEZPkI2vU0L%2Fserver_side_tool_call_output.png?alt=media&amp;token=33800495-70d1-4a5f-9173-cde144abecb3" alt=""><figcaption></figcaption></figure>

Unsloth émet des `tool_result` événements SSE personnalisés pour la vue qu’a le modèle de la sortie de chaque appel d’outil. Le SDK Anthropic les relaie tels quels dans son flux d’événements.

#### Décodage JSON (`response_format`)

Unsloth prend en charge les sorties structurées au style OpenAI via `response_format`. Passez un schéma JSON et le modèle est contraint de produire du JSON conforme.

````python
import json
import os
import re
from openai import OpenAI

client = OpenAI(
    base_url="http://localhost:8888/v1",
    api_key=os.environ["UNSLOTH_STUDIO_AUTH_TOKEN"],
)

response = client.chat.completions.create(
    model="default",
    stream=False,
    temperature=0.0,
    max_tokens=1024,
    messages=[
        {
            "role": "user",
            "content": "Choisissez un pays : Japon, Égypte ou Pérou. Expliquez pourquoi en une phrase.",
        },
    ],
    response_format={
        "type": "json_schema",
        "json_schema": {
            "name": "country_pick",
            "schema": {
                "type": "object",
                "properties": {
                    "country": {"type": "string", "enum": ["Japan", "Egypt", "Peru"]},
                    "reason":  {"type": "string"},
                },
                "required": ["country", "reason"],
                "additionalProperties": False,
            },
            "strict": True,
        },
    },
)

raw = response.choices[0].message.content
# Supprimez la délimitation Markdown que Gemma 4 entoure autour du JSON, puis analysez-le.
cleaned = re.sub(r"^```(?:json)?\s*", "", raw)
cleaned = re.sub(r"\s*```$", "", cleaned)
parsed = json.loads(cleaned)

print(json.dumps(parsed, indent=2))
print()
print("country:", parsed["country"])
print("reason :", parsed["reason"])
````

Le `strict : True` indique à Unsloth d’imposer le schéma pendant le décodage plutôt que de compter sur le modèle pour s’y conformer de lui-même. `additionalProperties : False` et `required` fonctionnent comme dans le JSON Schema standard.

La sortie du terminal devrait ressembler à peu près à ceci :

<figure><img src="https://550366147-files.gitbook.io/~/files/v0/b/gitbook-x-prod.appspot.com/o/spaces%2FxhOjnexMCB3dmuQFQ2Zq%2Fuploads%2FmhPxaVA6sxkyF3nFf51f%2FScreenshot%202026-05-05%20at%201.46.44%E2%80%AFPM.png?alt=media&amp;token=50b1600d-9e5a-4d22-819a-274c6bfbf8f7" alt=""><figcaption></figcaption></figure>

### 🧪 Choisir un SDK

Les deux SDK fonctionnent avec Unsloth. Le bon choix dépend du reste de votre pile :

* Utilisez le **SDK OpenAI** si votre code dépend déjà du package Python OpenAI, que vous souhaitez un style OpenAI `outils` / `tool_choice`, ou que vous prévoyez d’appeler l’API Responses.
* Utilisez le **SDK Anthropic** si votre code dépend déjà du package Anthropic, que vous préférez le format d’outils `input_schema` Anthropic, ou que vous voulez les types d’événements de streaming natifs d’Anthropic.

Vous pouvez utiliser les deux dans le même projet. Unsloth les sert sur le même port, donc une seule `sk-unsloth-…` clé authentifie les deux.

### ❔ Dépannage

**`401 Non autorisé`**  Le `UNSLOTH_STUDIO_AUTH_TOKEN` la variable d’environnement n’est pas définie, ou la clé est incorrecte. Réexportez-la et confirmez avec `echo $UNSLOTH_STUDIO_AUTH_TOKEN`.

**`404 Not Found` du SDK OpenAI** Vérifiez que `base_url` se termine `/v1`par. Le SDK OpenAI ajoute les chemins de point de terminaison à l’URL de base tels quels.

**`404 Not Found` du SDK Anthropic** Vérifiez que `base_url` se termine **rend** par `/v1`. Le SDK Anthropic ajoute `/v1/messages` lui-même.

**`extra_body` les champs n’atteignent pas Unsloth** Assurez-vous d’utiliser une version récente du SDK `openai` / `anthropic` . Les anciennes versions ignorent silencieusement les champs inconnus. Mettez à niveau avec `pip install -U openai anthropic`.

**Le streaming « se bloque » puis affiche tout d’un coup** Ce qui encapsule votre sortie la met en tampon. Dans un script, `print(..., flush=True)`; dans un notebook, c’est généralement correct ; derrière un proxy, désactivez la mise en tampon des réponses sur le proxy.

Pour les problèmes au niveau du point de terminaison (mauvais port, modèle non chargé, connexion perdue, etc.), consultez la page d’aperçu de l’API.

### Facultatif : définir les valeurs par défaut du serveur

Vous pouvez configurer le comportement par défaut du serveur avant de vous connecter avec le SDK Python, lorsque vous utilisez le `unsloth run` commande.

```bash
# Démarrez le serveur avec des valeurs par défaut personnalisées
unsloth run \
  --model unsloth/Qwen3-1.7B-GGUF \
  --reasoning off \
  --temp 0.6 \
  -p 8888
```

Utilisez `--reasoning off` pour désactiver le raisonnement, ou `--reasoning on` pour l'activer pour les modèles qui prennent en charge le raisonnement.

```bash
# Exposez l'API sur votre réseau local
unsloth run \
  --model unsloth/Qwen3-1.7B-GGUF \
  -H 0.0.0.0 \
  -p 8888
```

Cela démarre le serveur sur `0.0.0.0:8888`, ce qui permet à d'autres appareils de votre réseau local de s'y connecter.

Ces paramètres deviennent les valeurs par défaut du serveur lorsque les requêtes ne spécifient pas leurs propres paramètres de génération.

Des valeurs au niveau de la requête comme `temperature`, `top_p`, `max_tokens`et `stream` peuvent toujours remplacer les valeurs par défaut pour cette requête.


---

# Agent Instructions
This documentation is published with GitBook. GitBook is the documentation platform designed so that both humans and AI agents can read, navigate, and reason over technical content effectively. Learn more at gitbook.com.

## Querying This Documentation
If you need additional information that is not directly available in this page, you can query the documentation by asking a question.

Perform an HTTP GET request on the following URL with the `ask` and `goal` query parameters:

```
GET https://unsloth.ai/docs/fr/integrations/connecter-le-sdk-python-a-unsloth.md?ask=<question>&goal=<user_goal>
```

`ask` is the immediate question: it should be specific, self-contained, and written in natural language.
`goal` is what the user is ultimately trying to achieve, the reason they need the answer. Sharing it helps GitBook give you a better, more relevant answer. A goal is most helpful when it describes the outcome the user wants rather than restating the question. For example, with `ask=how do I create an API token`, a goal like `automate deployments from our CI pipeline` lets GitBook tailor the answer to that use case.

The response will contain a direct answer to the question and relevant excerpts and sources from the documentation.

Use this mechanism when the answer is not explicitly present in the current page, you need clarification or additional context, or you want to retrieve related documentation sections.
