Salut à tous,
Je me suis récemment lancé dans l’auto-hébergement de LLM en local. Après avoir testé pas mal de configurations, je me suis rendu compte que faire tourner Ollama dans Docker avec accélération GPU, c’est parfois un parcours du combattant si on n’a pas les bons flags ou la bonne config Docker Compose.
Franchement, au début, je ne comprenais pas pourquoi mes temps de réponse étaient si catastrophiques. (Oui, j’ai testé sans GPU, et générer du texte à 1,5 token par seconde sur mon CPU, ça donne surtout envie de s’ouvrir les veines). Dès que le GPU est correctement sollicité, on passe direct à 50+ tokens/sec.
Voici un retour d’expérience complet, propre et fonctionnel pour configurer tout ça chez vous sans y passer la nuit.
1. Comprendre le “Bridge” entre Docker et votre GPU
Par défaut, Docker isole complètement vos conteneurs de votre matériel. Pour lui, le monde extérieur se résume à un CPU et de la RAM virtualisés. Pour que le conteneur Ollama puisse causer directement avec vos cœurs CUDA ou votre puce ROCm, on doit casser cette isolation de manière contrôlée.
- Le pont de pilotes (Driver Bridge) : Le conteneur n’embarque pas le pilote graphique physique. Il utilise une passerelle (comme le NVIDIA Container Toolkit) pour envoyer ses calculs de matrices directement au pilote installé sur votre machine hôte.
- La persistance des modèles : Les LLM sont de gros bébés (plusieurs gigas). Si vous montez un conteneur sans volume persistant (
-v ollama:/root/.ollama), vous allez devoir re-télécharger vos modèles de 8 Go à chaque fois que vous redémarrez le conteneur. Autant dire que votre connexion internet ne va pas apprécier.
2. Les prérequis sur la machine hôte
Avant même de lancer Docker, il faut préparer le terrain sur votre OS.
Pour NVIDIA :
Vous devez installer vos pilotes NVIDIA classiques, mais surtout le NVIDIA Container Toolkit.
- Sur Ubuntu/Debian : Un simple
sudo apt-get install nvidia-container-toolkitfait l’affaire. - Sur Windows : Assurez-vous d’utiliser WSL2 (Windows Subsystem for Linux) et d’avoir vos pilotes graphiques Windows à jour. C’est WSL2 qui fait le pont de manière transparente.
Pour AMD :
Pas besoin du toolkit propriétaire Nvidia ici, mais vous devez vous assurer que votre utilisateur système fait bien partie des groupes render et video pour donner l’accès matériel à Docker :
sudo usermod -aG render,video $USER
3. Lancer Ollama en ligne de commande (Docker CLI)
Si vous voulez juste tester rapidement à la volée, voici les commandes brutes :
Pour NVIDIA :
docker run -d \
--gpus all \
-v ollama:/root/.ollama \
-p 11434:11434 \
--name ollama \
ollama/ollama
Pour AMD (on utilise l’image spécifique ROCm et on mappe les devices) :
docker run -d \
--device /dev/kfd \
--device /dev/dri \
-v ollama:/root/.ollama \
-p 11434:11434 \
--name ollama \
ollama/ollama:rocm
Pour vérifier que le conteneur tourne, tapez un petit docker ps. Vous devriez voir le conteneur actif sur le port 11434.
4. La méthode propre : Docker Compose
Pour ma part, je gère tout via Docker Compose. C’est beaucoup plus propre pour maintenir ses configurations et y associer une interface graphique.
Voici la structure de base. Notez bien la section deploy.resources.reservations pour Nvidia, c’est elle qui indique à Docker de réserver les ressources du GPU.
Version NVIDIA (docker-compose.yml) :
version: "3.8"
services:
ollama:
image: ollama/ollama:latest
container_name: ollama
ports:
- "11434:11434"
volumes:
- ollama_data:/root/.ollama
deploy:
resources:
reservations:
devices:
- driver: nvidia
count: all
capabilities: [gpu]
restart: unless-stopped
volumes:
ollama_data:
Version AMD (docker-compose.yml) :
services:
ollama:
image: ollama/ollama:rocm
container_name: ollama
ports:
- "11434:11434"
volumes:
- ollama_data:/root/.ollama
devices:
- /dev/kfd:/dev/kfd
- /dev/dri:/dev/dri
restart: unless-stopped
volumes:
ollama_data:
Lancez ensuite la machine avec : docker compose up -d
5. Cibler un GPU spécifique (Multi-GPU)
Le truc piégeux avec count: all, c’est que si vous avez par exemple un GPU intégré (iGPU) et une grosse carte graphique dédiée, Ollama risque de s’emmêler les pinceaux ou d’allouer des ressources sur la mauvaise carte.
Pour forcer Ollama à n’utiliser qu’un seul GPU spécifique, récupérez d’abord l’UUID de votre carte sur l’hôte :
nvidia-smi --query-gpu=uuid --format=csv
Ensuite, remplacez count: all par l’ID de votre périphérique dans votre compose :
deploy:
resources:
reservations:
devices:
- driver: nvidia
device_ids: ['GPU-a1b2c3d4-e5f6-7a8b-9c0d-1e2f3a4b5c6d'] # Remplacez par votre UUID
capabilities: [gpu]
6. Comment Ollama gère la VRAM (Le “Layer Splitting”)
C’est là que réside toute l’intelligence (et parfois la frustration) d’Ollama. Quand vous lui demandez de charger un modèle, il calcule la VRAM disponible sur votre GPU.
- Le modèle rentre en entier : 100% des couches de calcul (layers) sont envoyées sur le GPU. Les temps de réponse sont ultra rapides.
- Le modèle est trop lourd (ex: essayer de faire tourner un modèle de 16 Go sur une carte de 8 Go) : Ollama ne va pas planter. Il va faire du partage hybride (CPU/GPU offloading). Il charge le maximum de couches possibles dans votre VRAM, et laisse le reste dans votre RAM système gérée par le CPU.
Le problème ? Les données doivent faire des allers-retours incessants sur votre bus PCIe. Vos performances vont chuter drastiquement. Choisissez donc toujours des modèles dont la taille globale est inférieure à votre VRAM disponible.
De plus, au démarrage de Docker, Ollama consomme pratiquement 0% de GPU. Il attend sagement une requête.
Dès que vous l’interrogez, il lance un sous-processus appelé ollama runner qui va réserver la VRAM et y charger les poids. Par défaut, Ollama garde le modèle en mémoire pendant 5 minutes (OLLAMA_KEEP_ALIVE=5m) après votre dernière question avant de vider la VRAM pour libérer votre machine.
7. Configurer l’écosystème complet avec Open WebUI
La CLI dans le terminal c’est sympa deux minutes, mais avoir une interface à la ChatGPT avec historique de discussion, gestion de fichiers et invites système, c’est quand même autre chose.
Voici mon fichier de prod qui lie Ollama et Open WebUI sur un réseau interne Docker isolé. Grâce à cette architecture, Open WebUI communique avec Ollama de manière sécurisée en utilisant le DNS interne de Docker, sans exposer directement le port d’Ollama sur votre réseau si vous ne le souhaitez pas.
services:
ollama:
image: ollama/ollama:latest
container_name: ollama
volumes:
- ollama_storage:/root/.ollama
ports:
- "11434:11434"
environment:
- OLLAMA_HOST=0.0.0.0:11434
- OLLAMA_KEEP_ALIVE=30m # Garde le modèle en VRAM pendant 30 minutes
- OLLAMA_NUM_PARALLEL=2 # Permet à deux personnes de requêter en même temps
- OLLAMA_FLASH_ATTENTION=1 # Optimise l'utilisation mémoire et accélère le traitement
deploy:
resources:
reservations:
devices:
- driver: nvidia
count: all
capabilities: [gpu]
restart: unless-stopped
open-webui:
image: ghcr.io/open-webui/open-webui:main
container_name: open-webui
ports:
- "3000:8080"
volumes:
- open-webui_storage:/app/backend/data
environment:
- OLLAMA_BASE_URL=http://ollama:11434
depends_on:
- ollama
restart: unless-stopped
volumes:
ollama_storage:
open-webui_storage:
Une fois déployé avec un petit docker compose up -d, rendez-vous sur http://localhost:3000 sur votre navigateur pour profiter de votre IA locale, 100% privée et hors-ligne.
8. Les Variables d’Environnement indispensables
Pour peaufiner votre installation, vous pouvez glisser ces variables sous la clé environment: de votre service Ollama :
OLLAMA_HOST=0.0.0.0:11434: Indispensable à l’intérieur de Docker pour que le serveur accepte les connexions provenant d’autres conteneurs (comme Open WebUI) ou d’autres machines de votre réseau local.OLLAMA_FLASH_ATTENTION=1: Active les optimisations de matrices mathématiques. Ça réduit l’empreinte VRAM et booste la vitesse sur les longues conversations.OLLAMA_MAX_LOADED_MODELS=2: Si vous avez assez de VRAM, cela évite de décharger votre modèle de code dès que vous posez une question à votre modèle de discussion générale.OLLAMA_ORIGINS=*ou liste d’IP : Pour gérer les partages CORS si vous connectez des applications tierces.HTTPS_PROXY: Pratique si votre serveur tourne derrière un proxy réseau pour récupérer les modèles viaollama pull.JETSON_JETPACK=5(ou6) : Si vous tournez sur un kit Nvidia Jetson, Ollama a du mal à détecter l’architecture GPU par défaut. Il faut lui spécifier la version de JetPack manuellement.OLLAMA_MODELS=/your/custom/path: Si vous avez monté vos volumes sur un chemin exotique dans votre conteneur et que vous voulez réorienter l’endroit où sont stockés les fichiers.gguf.
9. Vos modèles ne répondent pas ? Guide de dépannage rapide
- Erreur :
unknown flag: --gpus
Votre moteur Docker n’arrive pas à communiquer avec le matériel hôte. Vous avez très probablement oublié d’installer (ou de redémarrer après installation) le NVIDIA Container Toolkit. - Génération ultra lente (1 à 2 tokens/seconde) :
Ollama a sûrement basculé en mode CPU sans vous le dire. Pour valider que votre GPU tourne bien à l’intérieur du conteneur, ouvrez un autre terminal et lancez :docker exec -it ollama nvidia-smi
Si cette commande renvoie une erreur ou ne liste pas le processusollama/runneren train de saturer vos blocs de VRAM pendant une requête, c’est que la liaison de pilotes a échoué. (Sur AMD, surveillez les utilitaires hôtes commerocm-smiouradeontop). - Crash du conteneur au moment de charger un modèle :
Le fameux Out-of-Memory (OOM). Si le modèle dépasse à la fois votre VRAM ET la mémoire vive physique (RAM) allouée à votre conteneur Docker, le système coupe brutalement le processus. Solution : supprimez ce modèle trop lourd et optez pour une version quantifiée plus légère (comme un modèle au format8bou3bau lieu d’un énorme modèle non quantifié).
Pour tester rapidement, vous pouvez lancer le téléchargement et l’exécution de Llama 3.2 en interactif directement dans votre terminal avec :
docker exec -it ollama ollama run llama3.2
Si vous avez des questions sur vos configurations ou des comportements bizarres sur des architectures spécifiques, n’hésitez pas à les poser dans les commentaires !