# Guide d'appel d'outils pour les LLMs locaux

L’appel d’outils consiste à permettre à un LLM de déclencher des fonctions spécifiques (comme « rechercher mes fichiers », « lancer une calculatrice » ou « appeler une API ») en émettant une requête structurée au lieu de deviner la réponse en texte. Vous utilisez les appels d’outils parce qu’ils rendent les sorties **plus fiables et plus à jour**, et ils permettent au modèle **d’entreprendre de vraies actions** (interroger des systèmes, valider des faits, imposer des schémas) plutôt que d’halluciner.

Dans ce tutoriel, vous apprendrez à utiliser des LLM locaux via l’appel d’outils avec des exemples de fonctions mathématiques, de narration, de code Python et de terminal. L’inférence est effectuée localement via llama.cpp, llama-server et des points de terminaison OpenAI.

{% columns %}
{% column %}
L’appel d’outils est configuré automatiquement lorsque vous utilisez [Unsloth Studio](https://unsloth.ai/docs/fr/nouveau/studio/chat#auto-healing-tool-calling). Sélectionnez simplement votre modèle et activez ou désactivez l’appel d’outils.

Voir à droite un exemple d’appel d’outils appliqué automatiquement pour [Gemma 4](https://unsloth.ai/docs/fr/modeles/gemma-4). Unsloth propose également un appel d’outils auto-réparateur, garantissant que vos appels d’outils fonctionnent toujours.
{% endcolumn %}

{% column %}

<figure><img src="https://550366147-files.gitbook.io/~/files/v0/b/gitbook-x-prod.appspot.com/o/spaces%2FxhOjnexMCB3dmuQFQ2Zq%2Fuploads%2FstfdTMsoBMmsbQsgQ1Ma%2Flandscape%20clip%20gemma.gif?alt=media&#x26;token=eec5f2f7-b97a-4c1c-ad01-5a041c3e4013" alt=""><figcaption></figcaption></figure>
{% endcolumn %}
{% endcolumns %}

Notre guide devrait fonctionner pour presque [n’importe quel modèle](https://unsloth.ai/docs/fr/commencer/unsloth-model-catalog) y compris :

* [**Qwen3**-Coder-Next](https://unsloth.ai/docs/models/qwen3-coder-next), [Qwen3-Coder](https://unsloth.ai/docs/models/qwen3-coder-how-to-run-locally), et d’autres **Qwen** modèles
* [**GLM**-4.7](https://unsloth.ai/docs/models/glm-4.7), 4.6, [GLM-4.7-Flash](https://unsloth.ai/docs/models/glm-4.7-flash) et [**Kimi K2.5**](https://unsloth.ai/docs/models/kimi-k2.5), [Kimi K2 Thinking](https://unsloth.ai/docs/models/tutorials/kimi-k2-thinking-how-to-run-locally)
* [**DeepSeek**-V3.1](https://unsloth.ai/docs/models/tutorials/deepseek-v3.1-how-to-run-locally), DeepSeek-V3.2 et **MiniMax**
* [**gpt-oss**](https://unsloth.ai/docs/models/gpt-oss-how-to-run-and-fine-tune) et [**NVIDIA Nemotron** 3 Nano](https://unsloth.ai/docs/models/tutorials/nemotron-3) et [**Devstral** 2](https://unsloth.ai/docs/models/tutorials/devstral-2)

<a href="#qwen3-coder-next-tool-calling" class="button primary">Tutoriel Qwen3-Coder-Next</a><a href="#glm-4.7-flash--glm-4.7-calling" class="button secondary">Tutoriel GLM-4.7-Flash</a>

### :hammer:Configuration de l’appel d’outils

Notre première étape consiste à obtenir la dernière version de `llama.cpp` sur [GitHub ici](https://github.com/ggml-org/llama.cpp). Vous pouvez également suivre les instructions de compilation ci-dessous. Remplacez `-DGGML_CUDA=ON` par `-DGGML_CUDA=OFF` si vous n’avez pas de GPU ou si vous souhaitez simplement une inférence sur CPU. **Pour les appareils Apple Mac / Metal**, définissez `-DGGML_CUDA=OFF` puis continuez comme d’habitude - la prise en charge de Metal est activée par défaut.

{% code overflow="wrap" %}

```bash
apt-get update
apt-get install pciutils build-essential cmake curl libcurl4-openssl-dev -y
git clone https://github.com/ggml-org/llama.cpp
cmake llama.cpp -B llama.cpp/build \\
    -DBUILD_SHARED_LIBS=OFF -DGGML_CUDA=ON
cmake --build llama.cpp/build --config Release -j --clean-first --target llama-cli llama-mtmd-cli llama-server llama-gguf-split
cp llama.cpp/build/bin/llama-* llama.cpp
```

{% endcode %}

Dans un nouveau terminal (si vous utilisez tmux, utilisez CTRL+B+D), nous créons quelques outils comme l’ajout de 2 nombres, l’exécution de code Python, l’exécution de fonctions Linux et bien plus encore :

{% code expandable="true" %}

```python
import json, subprocess, random
from typing import Any
def add_number(a: float | str, b: float | str) -> float:
    return float(a) + float(b)
def multiply_number(a: float | str, b: float | str) -> float:
    return float(a) * float(b)
def substract_number(a: float | str, b: float | str) -> float:
    return float(a) - float(b)
def write_a_story() -> str:
    return random.choice([
        "Il était une fois, dans une galaxie lointaine, très lointaine...",
        "Il y avait 2 amis qui aimaient les paresseux et le code...",
        "Le monde touchait à sa fin parce que chaque paresseux avait évolué pour acquérir une intelligence surhumaine...",
        "À l’insu de l’un des amis, l’autre avait accidentellement codé un programme pour faire évoluer les paresseux...",
    ])
def terminal(command: str) -> str:
    if "rm" in command or "sudo" in command or "dd" in command or "chmod" in command:
        msg = "Impossible d’exécuter les commandes 'rm, sudo, dd, chmod' car elles sont dangereuses"
        print(msg); return msg
    print(f"Exécution de la commande terminal `{command}`")
    try:
        return str(subprocess.run(command, capture_output = True, text = True, shell = True, check = True).stdout)
    except subprocess.CalledProcessError as e:
        return f"La commande a échoué : {e.stderr}"
def python(code: str) -> str:
    data = {}
    exec(code, data)
    del data["__builtins__"]
    return str(data)
MAP_FN = {
    "add_number": add_number,
    "multiply_number": multiply_number,
    "substract_number": substract_number,
    "write_a_story": write_a_story,
    "terminal": terminal,
    "python": python,
}
tools = [
    {
        "type": "function",
        "function": {
            "name": "add_number",
            "description": "Ajouter deux nombres.",
            "parameters": {
                "type": "object",
                "properties": {
                    "a": {
                        "type": "string",
                        "description": "Le premier nombre.",
                    },
                    "b": {
                        "type": "string",
                        "description": "Le deuxième nombre.",
                    },
                },
                "required": ["a", "b"],
            },
        },
    },
    {
        "type": "function",
        "function": {
            "name": "multiply_number",
            "description": "Multiplier deux nombres.",
            "parameters": {
                "type": "object",
                "properties": {
                    "a": {
                        "type": "string",
                        "description": "Le premier nombre.",
                    },
                    "b": {
                        "type": "string",
                        "description": "Le deuxième nombre.",
                    },
                },
                "required": ["a", "b"],
            },
        },
    },
    {
        "type": "function",
        "function": {
            "name": "substract_number",
            "description": "Soustraire deux nombres.",
            "parameters": {
                "type": "object",
                "properties": {
                    "a": {
                        "type": "string",
                        "description": "Le premier nombre.",
                    },
                    "b": {
                        "type": "string",
                        "description": "Le deuxième nombre.",
                    },
                },
                "required": ["a", "b"],
            },
        },
    },
    {
        "type": "function",
        "function": {
            "name": "write_a_story",
            "description": "Écrit une histoire aléatoire.",
            "parameters": {
                "type": "object",
                "properties": {},
                "required": [],
            },
        },
    },
    {
        "type": "function",
        "function": {
            "name": "terminal",
            "description": "Effectuer des opérations depuis le terminal.",
            "parameters": {
                "type": "object",
                "properties": {
                    "command": {
                        "type": "string",
                        "description": "La commande que vous souhaitez lancer, par ex. `ls`, `rm`, ...",
                    },
                },
                "required": ["command"],
            },
        },
    },
    {
        "type": "function",
        "function": {
            "name": "python",
            "description": "Appeler un interpréteur Python avec du code Python qui sera exécuté.",
            "parameters": {
                "type": "object",
                "properties": {
                    "code": {
                        "type": "string",
                        "description": "Le code Python à exécuter","required": ["code"],
                    },
                },
                "required": ["code"],
            },
        },
    },
]
```

{% endcode %}

Nous utilisons ensuite les fonctions ci-dessous (copier-coller puis exécuter), qui analyseront automatiquement les appels de fonctions et appelleront le point de terminaison OpenAI pour n’importe quel modèle :

{% hint style="info" %}
Dans cet exemple, nous utilisons Devstral 2 ; lorsque vous changez de modèle, assurez-vous d’utiliser les bons paramètres d’échantillonnage. Vous pouvez tous les voir dans nos [guides ici](https://unsloth.ai/docs/fr/modeles/tutorials).
{% endhint %}

{% code overflow="wrap" expandable="true" %}

```python
from openai import OpenAI
def unsloth_inference(
    messages,
    temperature = 0.7,
    top_p = 0.95,
    top_k = 40,
    min_p = 0.01,
    repetition_penalty = 1.0,
):
    messages = messages.copy()
    openai_client = OpenAI(
        base_url = "http://127.0.0.1:8001/v1",
        api_key = "sk-no-key-required",
    )
    model_name = next(iter(openai_client.models.list())).id
    print(f"Modèle utilisé = {model_name}")
    has_tool_calls = True
    original_messages_len = len(messages)
    while has_tool_calls:
        print(f"Messages actuels = {messages}")
        response = openai_client.chat.completions.create(
            model = model_name,
            messages = messages,
            temperature = temperature,
            top_p = top_p,
            tools = tools if tools else None,
            tool_choice = "auto" if tools else None,
            extra_body = {"top_k": top_k, "min_p": min_p, "repetition_penalty" :repetition_penalty,}
        )
        tool_calls = response.choices[0].message.tool_calls or []
        content = response.choices[0].message.content or ""
        tool_calls_dict = [tc.to_dict() for tc in tool_calls] if tool_calls else tool_calls
        messages.append({"role": "assistant", "tool_calls": tool_calls_dict, "content": content,})
        for tool_call in tool_calls:
            fx, args, _id = tool_call.function.name, tool_call.function.arguments, tool_call.id
            out = MAP_FN[fx](**json.loads(args))
            messages.append({"role": "tool", "tool_call_id": _id, "name": fx, "content": str(out),})
        else:
            has_tool_calls = False
    return messages
```

{% endcode %}

Nous allons maintenant présenter ci-dessous plusieurs méthodes d’exécution de l’appel d’outils pour de nombreux cas d’utilisation différents :

### Écriture d’une histoire :

```python
messages = [{
    "role": "user",
    "content": [{"type": "text", "text": "Pourriez-vous m’écrire une histoire ?"}],
}]
unsloth_inference(messages, temperature = 0.15, top_p = 1.0, top_k = -1, min_p = 0.00)
```

<figure><img src="https://550366147-files.gitbook.io/~/files/v0/b/gitbook-x-prod.appspot.com/o/spaces%2FxhOjnexMCB3dmuQFQ2Zq%2Fuploads%2F04clxomfFQjhIKiS5FAY%2Fimage.png?alt=media&#x26;token=299279c9-cca6-48d6-ab74-523edef04160" alt=""><figcaption></figcaption></figure>

### Opérations mathématiques :

{% code overflow="wrap" %}

```python
messages = [{
    "role": "user",
    "content": [{"type": "text", "text": "Quelle est la date d’aujourd’hui plus 3 jours ?"}],
}]
unsloth_inference(messages, temperature = 0.15, top_p = 1.0, top_k = -1, min_p = 0.00)
```

{% endcode %}

<figure><img src="https://550366147-files.gitbook.io/~/files/v0/b/gitbook-x-prod.appspot.com/o/spaces%2FxhOjnexMCB3dmuQFQ2Zq%2Fuploads%2Fi15WEhfSIPuFeZUWjrG1%2Fimage.png?alt=media&#x26;token=74818449-637b-442a-b1d6-aa72b09fb6b5" alt=""><figcaption></figcaption></figure>

### Exécuter du code Python généré

{% code overflow="wrap" %}

```python
messages = [{
    "role": "user",
    "content": [{"type": "text", "text": "Créez une fonction Fibonacci en Python et trouvez fib(20)."}],
}]
unsloth_inference(messages, temperature = 0.15, top_p = 1.0, top_k = -1, min_p = 0.00)
```

{% endcode %}

<figure><img src="https://550366147-files.gitbook.io/~/files/v0/b/gitbook-x-prod.appspot.com/o/spaces%2FxhOjnexMCB3dmuQFQ2Zq%2Fuploads%2FDsfcIrunKtsZ2RXRrjBo%2Fimage.png?alt=media&#x26;token=6aa2ab38-7def-4792-a2dc-c663329a41ff" alt=""><figcaption></figcaption></figure>

### Exécuter des fonctions de terminal arbitraires

{% code overflow="wrap" %}

```python
messages = [{
    "role": "user",
    "content": [{"type": "text", "text": "Écrivez 'Je suis un paresseux heureux' dans un fichier, puis affichez-le-moi."}],
}]
messages = unsloth_inference(messages, temperature = 0.15, top_p = 1.0, top_k = -1, min_p = 0.00)
```

{% endcode %}

<figure><img src="https://550366147-files.gitbook.io/~/files/v0/b/gitbook-x-prod.appspot.com/o/spaces%2FxhOjnexMCB3dmuQFQ2Zq%2Fuploads%2FMhmXE34IBuR8H8SnuSMe%2Fimage%20(3).png?alt=media&#x26;token=689114b7-5b50-41c9-8678-88f8f5da87a7" alt=""><figcaption></figcaption></figure>

## :stars: Appel d’outils Qwen3-Coder-Next

Dans un nouveau terminal, nous créons quelques outils comme l’ajout de 2 nombres, l’exécution de code Python, l’exécution de fonctions Linux et bien plus encore :

{% code expandable="true" %}

```python
import json, subprocess, random
from typing import Any
def add_number(a: float | str, b: float | str) -> float:
    return float(a) + float(b)
def multiply_number(a: float | str, b: float | str) -> float:
    return float(a) * float(b)
def substract_number(a: float | str, b: float | str) -> float:
    return float(a) - float(b)
def write_a_story() -> str:
    return random.choice([
        "Il était une fois, dans une galaxie lointaine, très lointaine...",
        "Il y avait 2 amis qui aimaient les paresseux et le code...",
        "Le monde touchait à sa fin parce que chaque paresseux avait évolué pour acquérir une intelligence surhumaine...",
        "À l’insu de l’un des amis, l’autre avait accidentellement codé un programme pour faire évoluer les paresseux...",
    ])
def terminal(command: str) -> str:
    if "rm" in command or "sudo" in command or "dd" in command or "chmod" in command:
        msg = "Impossible d’exécuter les commandes 'rm, sudo, dd, chmod' car elles sont dangereuses"
        print(msg); return msg
    print(f"Exécution de la commande terminal `{command}`")
    try:
        return str(subprocess.run(command, capture_output = True, text = True, shell = True, check = True).stdout)
    except subprocess.CalledProcessError as e:
        return f"La commande a échoué : {e.stderr}"
def python(code: str) -> str:
    data = {}
    exec(code, data)
    del data["__builtins__"]
    return str(data)
MAP_FN = {
    "add_number": add_number,
    "multiply_number": multiply_number,
    "substract_number": substract_number,
    "write_a_story": write_a_story,
    "terminal": terminal,
    "python": python,
}
tools = [
    {
        "type": "function",
        "function": {
            "name": "add_number",
            "description": "Ajouter deux nombres.",
            "parameters": {
                "type": "object",
                "properties": {
                    "a": {
                        "type": "string",
                        "description": "Le premier nombre.",
                    },
                    "b": {
                        "type": "string",
                        "description": "Le deuxième nombre.",
                    },
                },
                "required": ["a", "b"],
            },
        },
    },
    {
        "type": "function",
        "function": {
            "name": "multiply_number",
            "description": "Multiplier deux nombres.",
            "parameters": {
                "type": "object",
                "properties": {
                    "a": {
                        "type": "string",
                        "description": "Le premier nombre.",
                    },
                    "b": {
                        "type": "string",
                        "description": "Le deuxième nombre.",
                    },
                },
                "required": ["a", "b"],
            },
        },
    },
    {
        "type": "function",
        "function": {
            "name": "substract_number",
            "description": "Soustraire deux nombres.",
            "parameters": {
                "type": "object",
                "properties": {
                    "a": {
                        "type": "string",
                        "description": "Le premier nombre.",
                    },
                    "b": {
                        "type": "string",
                        "description": "Le deuxième nombre.",
                    },
                },
                "required": ["a", "b"],
            },
        },
    },
    {
        "type": "function",
        "function": {
            "name": "write_a_story",
            "description": "Écrit une histoire aléatoire.",
            "parameters": {
                "type": "object",
                "properties": {},
                "required": [],
            },
        },
    },
    {
        "type": "function",
        "function": {
            "name": "terminal",
            "description": "Effectuer des opérations depuis le terminal.",
            "parameters": {
                "type": "object",
                "properties": {
                    "command": {
                        "type": "string",
                        "description": "La commande que vous souhaitez lancer, par ex. `ls`, `rm`, ...",
                    },
                },
                "required": ["command"],
            },
        },
    },
    {
        "type": "function",
        "function": {
            "name": "python",
            "description": "Appeler un interpréteur Python avec du code Python qui sera exécuté.",
            "parameters": {
                "type": "object",
                "properties": {
                    "code": {
                        "type": "string",
                        "description": "Le code Python à exécuter","required": ["code"],
                    },
                },
                "required": ["code"],
            },
        },
    },
]
```

{% endcode %}

Nous utilisons ensuite les fonctions ci-dessous qui analyseront automatiquement les appels de fonctions et appelleront le point de terminaison OpenAI pour n’importe quel LLM :

{% code overflow="wrap" expandable="true" %}

```python
from openai import OpenAI
def unsloth_inference(
    messages,
    temperature = 1.0,
    top_p = 0.95,
    top_k = 40,
    min_p = 0.01,
    repetition_penalty = 1.0,
):
    messages = messages.copy()
    openai_client = OpenAI(
        base_url = "http://127.0.0.1:8001/v1",
        api_key = "sk-no-key-required",
    )
    model_name = next(iter(openai_client.models.list())).id
    print(f"Modèle utilisé = {model_name}")
    has_tool_calls = True
    original_messages_len = len(messages)
    while has_tool_calls:
        print(f"Messages actuels = {messages}")
        response = openai_client.chat.completions.create(
            model = model_name,
            messages = messages,
            temperature = temperature,
            top_p = top_p,
            tools = tools if tools else None,
            tool_choice = "auto" if tools else None,
            extra_body = {"top_k": top_k, "min_p": min_p, "repetition_penalty" :repetition_penalty,}
        )
        tool_calls = response.choices[0].message.tool_calls or []
        content = response.choices[0].message.content or ""
        tool_calls_dict = [tc.to_dict() for tc in tool_calls] if tool_calls else tool_calls
        messages.append({"role": "assistant", "tool_calls": tool_calls_dict, "content": content,})
        for tool_call in tool_calls:
            fx, args, _id = tool_call.function.name, tool_call.function.arguments, tool_call.id
            out = MAP_FN[fx](**json.loads(args))
            messages.append({"role": "tool", "tool_call_id": _id, "name": fx, "content": str(out),})
        else:
            has_tool_calls = False
    return messages
```

{% endcode %}

Nous allons maintenant présenter ci-dessous plusieurs méthodes d’exécution de l’appel d’outils pour de nombreux cas d’utilisation différents :

#### Exécuter du code Python généré

<pre class="language-python" data-overflow="wrap"><code class="lang-python"><strong>messages = [{
</strong>    "role": "user",
    "content": [{"type": "text", "text": "Créez une fonction Fibonacci en Python et trouvez fib(20)."}],
}]
unsloth_inference(messages, temperature = 1.0, top_p = 0.95, top_k = 40, min_p = 0.00)
</code></pre>

<figure><img src="https://550366147-files.gitbook.io/~/files/v0/b/gitbook-x-prod.appspot.com/o/spaces%2FxhOjnexMCB3dmuQFQ2Zq%2Fuploads%2F7fY3LSeNCjHXNjBwQkbI%2Fimage.png?alt=media&#x26;token=50eba62e-f8b2-424a-833b-be56696b4710" alt=""><figcaption></figcaption></figure>

#### Exécuter des fonctions de terminal arbitraires

{% code overflow="wrap" %}

```python
messages = [{
    "role": "user",
    "content": [{"type": "text", "text": "Écrivez 'Je suis un paresseux heureux' dans un fichier, puis affichez-le-moi."}],
}]
messages = unsloth_inference(messages, temperature = 1.0, top_p = 1.0, top_k = 40, min_p = 0.00)
```

{% endcode %}

Nous confirmons que le fichier a été créé et c’était bien le cas !

<figure><img src="https://550366147-files.gitbook.io/~/files/v0/b/gitbook-x-prod.appspot.com/o/spaces%2FxhOjnexMCB3dmuQFQ2Zq%2Fuploads%2FabplwVbEMlsCEJTmxzSA%2Fimage.png?alt=media&#x26;token=eb27f30a-c91e-4aec-8fb0-f4a35921d3db" alt=""><figcaption></figcaption></figure>

## :zap: GLM-4.7-Flash + Appel GLM 4.7

Nous téléchargeons d’abord [glm-4.7](https://unsloth.ai/docs/fr/modeles/tutorials/glm-4.7 "mention") ou [glm-4.7-flash](https://unsloth.ai/docs/fr/modeles/glm-4.7-flash "mention") via du code Python, puis le lançons via llama-server dans un terminal séparé (par exemple avec tmux). Dans cet exemple, nous téléchargeons le grand modèle GLM-4.7 :

```python
# !pip install huggingface_hub hf_transfer
import os
os.environ["HF_HUB_ENABLE_HF_TRANSFER"] = "1"
from huggingface_hub import snapshot_download
snapshot_download(
    repo_id = "unsloth/GLM-4.7-GGUF",
    local_dir = "unsloth/GLM-4.7-GGUF",
    allow_patterns = ["*UD-Q2_K_XL*",], # Pour Q2_K_XL
)
```

Si vous l’avez exécuté avec succès, vous devriez voir :

<figure><img src="https://550366147-files.gitbook.io/~/files/v0/b/gitbook-x-prod.appspot.com/o/spaces%2FxhOjnexMCB3dmuQFQ2Zq%2Fuploads%2FqZCvBkQPi7GZj50pPHsJ%2Fimage.png?alt=media&#x26;token=2e97888a-fafe-4477-b99c-c7f3e2e316bf" alt=""><figcaption></figcaption></figure>

Lancez-le maintenant via llama-server dans un nouveau terminal. Utilisez tmux si vous voulez :

{% code overflow="wrap" %}

```bash
./llama.cpp/llama-server \\
    --model unsloth/GLM-4.7-GGUF/UD-Q2_K_XL/GLM-4.7-UD-Q2_K_XL-00001-of-00003.gguf \\
    --alias "unsloth/GLM-4.7" \\
    --threads -1 \\
    --fit on \\
    --prio 3 \\
    --min_p 0.01 \\
    --ctx-size 16384 \\
    --port 8001 \\
    --jinja
```

{% endcode %}

Et vous obtiendrez :

<figure><img src="https://550366147-files.gitbook.io/~/files/v0/b/gitbook-x-prod.appspot.com/o/spaces%2FxhOjnexMCB3dmuQFQ2Zq%2Fuploads%2FMIqGMOXIMvl68jzDfyWy%2Fimage.png?alt=media&#x26;token=c5739da8-b9eb-4a31-9878-3f0d5f51416e" alt="" width="563"><figcaption></figcaption></figure>

Maintenant, dans un nouveau terminal et en exécutant du code Python, rappel de lancer [#tool-calling-setup](#tool-calling-setup "mention") Nous utilisons les paramètres optimaux de GLM 4.7 : temperature = 0.7 et top\_p = 1.0

#### Appel d’outil pour des opérations mathématiques pour GLM 4.7

{% code overflow="wrap" %}

```python
messages = [{
    "role": "user",
    "content": [{"type": "text", "text": "Quelle est la date d’aujourd’hui plus 3 jours ?"}],
}]
unsloth_inference(messages, temperature = 0.7, top_p = 1.0, top_k = -1, min_p = 0.00)
```

{% endcode %}

<figure><img src="https://550366147-files.gitbook.io/~/files/v0/b/gitbook-x-prod.appspot.com/o/spaces%2FxhOjnexMCB3dmuQFQ2Zq%2Fuploads%2FoFkZ20QOSGdzT4iz2SOB%2Fimage.png?alt=media&#x26;token=e4ca30b0-dcec-4a26-b019-dd33f0600949" alt=""><figcaption></figcaption></figure>

#### Appel d’outil pour exécuter du code Python généré pour GLM 4.7

{% code overflow="wrap" %}

```python
messages = [{
    "role": "user",
    "content": [{"type": "text", "text": "Créez une fonction Fibonacci en Python et trouvez fib(20)."}],
}]
unsloth_inference(messages, temperature = 0.7, top_p = 1.0, top_k = -1, min_p = 0.00)
```

{% endcode %}

<figure><img src="https://550366147-files.gitbook.io/~/files/v0/b/gitbook-x-prod.appspot.com/o/spaces%2FxhOjnexMCB3dmuQFQ2Zq%2Fuploads%2FhS8sWtZwjwerElezCc2C%2Fimage.png?alt=media&#x26;token=39032ef8-386e-4837-8dd2-c552c80a3ee3" alt="" width="563"><figcaption></figcaption></figure>

{% code expandable="true" %}

```python
import json, subprocess, random
from typing import Any
def add_number(a: float | str, b: float | str) -> float:
    return float(a) + float(b)
def multiply_number(a: float | str, b: float | str) -> float:
    return float(a) * float(b)
def substract_number(a: float | str, b: float | str) -> float:
    return float(a) - float(b)
def write_a_story() -> str:
    return random.choice([
        "Il était une fois, dans une galaxie lointaine, très lointaine...",
        "Il y avait 2 amis qui aimaient les paresseux et le code...",
        "Le monde touchait à sa fin parce que chaque paresseux avait évolué pour acquérir une intelligence surhumaine...",
        "À l’insu de l’un des amis, l’autre avait accidentellement codé un programme pour faire évoluer les paresseux...",
    ])
def terminal(command: str) -> str:
    if "rm" in command or "sudo" in command or "dd" in command or "chmod" in command:
        msg = "Impossible d’exécuter les commandes 'rm, sudo, dd, chmod' car elles sont dangereuses"
        print(msg); return msg
    print(f"Exécution de la commande terminal `{command}`")
    try:
        return str(subprocess.run(command, capture_output = True, text = True, shell = True, check = True).stdout)
    except subprocess.CalledProcessError as e:
        return f"La commande a échoué : {e.stderr}"
def python(code: str) -> str:
    data = {}
    exec(code, data)
    del data["__builtins__"]
    return str(data)
MAP_FN = {
    "add_number": add_number,
    "multiply_number": multiply_number,
    "substract_number": substract_number,
    "write_a_story": write_a_story,
    "terminal": terminal,
    "python": python,
}
tools = [
    {
        "type": "function",
        "function": {
            "name": "add_number",
            "description": "Ajouter deux nombres.",
            "parameters": {
                "type": "object",
                "properties": {
                    "a": {
                        "type": "string",
                        "description": "Le premier nombre.",
                    },
                    "b": {
                        "type": "string",
                        "description": "Le deuxième nombre.",
                    },
                },
                "required": ["a", "b"],
            },
        },
    },
    {
        "type": "function",
        "function": {
            "name": "multiply_number",
            "description": "Multiplier deux nombres.",
            "parameters": {
                "type": "object",
                "properties": {
                    "a": {
                        "type": "string",
                        "description": "Le premier nombre.",
                    },
                    "b": {
                        "type": "string",
                        "description": "Le deuxième nombre.",
                    },
                },
                "required": ["a", "b"],
            },
        },
    },
    {
        "type": "function",
        "function": {
            "name": "substract_number",
            "description": "Soustraire deux nombres.",
            "parameters": {
                "type": "object",
                "properties": {
                    "a": {
                        "type": "string",
                        "description": "Le premier nombre.",
                    },
                    "b": {
                        "type": "string",
                        "description": "Le deuxième nombre.",
                    },
                },
                "required": ["a", "b"],
            },
        },
    },
    {
        "type": "function",
        "function": {
            "name": "write_a_story",
            "description": "Écrit une histoire aléatoire.",
            "parameters": {
                "type": "object",
                "properties": {},
                "required": [],
            },
        },
    },
    {
        "type": "function",
        "function": {
            "name": "terminal",
            "description": "Effectuer des opérations depuis le terminal.",
            "parameters": {
                "type": "object",
                "properties": {
                    "command": {
                        "type": "string",
                        "description": "La commande que vous souhaitez lancer, par ex. `ls`, `rm`, ...",
                    },
                },
                "required": ["command"],
            },
        },
    },
    {
        "type": "function",
        "function": {
            "name": "python",
            "description": "Appeler un interpréteur Python avec du code Python qui sera exécuté.",
            "parameters": {
                "type": "object",
                "properties": {
                    "code": {
                        "type": "string",
                        "description": "Le code Python à exécuter","required": ["code"],
                    },
                },
                "required": ["code"],
            },
        },
    },
]
```

{% endcode %}

### :orange\_book: Appel d’outils Devstral 2

Nous téléchargeons d’abord [devstral-2](https://unsloth.ai/docs/fr/modeles/tutorials/devstral-2 "mention") via du code Python, puis lancez-le via llama-server dans un terminal séparé (par exemple avec tmux) :

```python
# !pip install huggingface_hub hf_transfer
import os
os.environ["HF_HUB_ENABLE_HF_TRANSFER"] = "1"
from huggingface_hub import snapshot_download
snapshot_download(
    repo_id = "unsloth/Devstral-Small-2-24B-Instruct-2512-GGUF",
    local_dir = "unsloth/Devstral-Small-2-24B-Instruct-2512-GGUF",
    allow_patterns = ["*UD-Q4_K_XL*", "*mmproj-F16*"], # Pour Q4_K_XL
)
```

Si vous l’avez exécuté avec succès, vous devriez voir :

<figure><img src="https://550366147-files.gitbook.io/~/files/v0/b/gitbook-x-prod.appspot.com/o/spaces%2FxhOjnexMCB3dmuQFQ2Zq%2Fuploads%2FC9M5eNGefCpi3bLe0Kbw%2Fimage.png?alt=media&#x26;token=727c22d5-368f-45ad-b698-ccb84e3bbbbf" alt=""><figcaption></figcaption></figure>

Lancez-le maintenant via llama-server dans un nouveau terminal. Utilisez tmux si vous voulez :

{% code overflow="wrap" %}

```bash
./llama.cpp/llama-server \\
    --model unsloth/Devstral-Small-2-24B-Instruct-2512-GGUF/Devstral-Small-2-24B-Instruct-2512-UD-Q4_K_XL.gguf \\
    --mmproj unsloth/Devstral-Small-2-24B-Instruct-2512-GGUF/mmproj-F16.gguf \\
    --alias "unsloth/Devstral-Small-2-24B-Instruct-2512" \\
    --threads -1 \\
    --fit on \\
    --prio 3 \\
    --min_p 0.01 \\
    --ctx-size 16384 \\
    --port 8001 \\
    --jinja
```

{% endcode %}

Vous verrez ce qui suit si cela a réussi :

<figure><img src="https://550366147-files.gitbook.io/~/files/v0/b/gitbook-x-prod.appspot.com/o/spaces%2FxhOjnexMCB3dmuQFQ2Zq%2Fuploads%2Fo0VjjsMTBQCsfMNXcbYG%2Fimage.png?alt=media&#x26;token=3f0d9c51-1fd7-4d8d-9532-1a190f1b5830" alt="" width="563"><figcaption></figcaption></figure>

Nous appelons ensuite le modèle avec le message suivant et uniquement avec les paramètres recommandés par Devstral, à savoir temperature = 0.15. Rappel de lancer [#tool-calling-setup](#tool-calling-setup "mention")
