Déploiement et service API de Qwen2.5-VL-7B-Instruct avec Docker Compose et Ollama

Introduction au modèle multimodal Qwen2.5-VL-7B-Instruct

Ce guide explique comment déployer efficacement le modèle multimodal Qwen2.5-VL-7B-Instruct en utilisant Docker Compose. Le modèle est ensuite exposé via une API RESTful grâce à Ollama, simplifiant ainsi le développement d'applications d'intelligence artificielle visuelle et linguistique.

Qwen2.5-VL-7B-Instruct est une solution avancée capable de comprendre des images et des vidéos. Ses fonctionnalités incluent :

  • Analyse de contenu visuel : identification d'objets, de textes, de diagrammes et de graphiques dans les images.
  • Compréhension vidéo : analyse de vidéos de plus d'une heure, avec localisation d'événements clés.
  • Localisation précise : détection d'objets dans des images via des boîtes englobantes ou des points.
  • Sortie structurée : génération de données au format JSON pour des applications professionnelles (finance, commerce).

Prérequis et configuration de l'environnement

Avant de commencer, assurez-vous que votre système répond aux exigences suivantes :

  • Système d'exploitation : Linux (Ubuntu 20.04+ recommandé) ou macOS.
  • Mémoire vive (RAM) : Minimum 16 Go (32 Go recommandés).
  • Espace disque : 20 Go disponibles.
  • Logiciels : Docker et Docker Compose installés.

Vérifiez votre installation Docker et Docker Compose :

docker --version
docker-compose --version

Si des informations de version s'affichent, votre environnement est prêt.

Déploiement du service Ollama

Création du fichier de configuration Docker Compose

Créez un répertoire pour votre projet et le fichier de configuration :

mkdir qwen2.5-vl-deploy && cd qwen2.5-vl-deploy

Créez le fichier docker-compose.yml avec le contenu suivant :

version: '3.8'

services:
 ollama:
   image: ollama/ollama:latest
   container_name: qwen-ollama
   ports:
     - "11434:11434" # Exposition de l'API Ollama
   volumes:
     - ollama_data:/root/.ollama # Persistance des données du modèle
   restart: unless-stopped
   deploy:
     resources:
       reservations:
         devices:
           - driver: nvidia # Utilisation du driver NVIDIA pour le GPU
             count: all # Utiliser tous les GPU disponibles
             capabilities: [gpu] # Activer les capacités GPU

volumes:
 ollama_data: # Définition du volume pour la persistance des données

Démarrage du service Ollama

Lancez les conteneurs en arrière-plan :

docker-compose up -d

Pour suivre les logs et vérifier le démarrage :

docker-compose logs -f

Une fois le service démarré, testez sa disponibilité :

curl http://localhost:11434/api/tags

Une réponse JSON valide indique que le service Ollama est opérationnel.

Téléchargement et configuration du modèle Qwen2.5-VL

Acquisition du modèle

Téléchargez le modèle Qwen2.5-VL-7B via Ollama. Vous pouvez le faire depuis l'extérieur du conteneur :

curl -X POST http://localhost:11434/api/pull -d '{
 "name": "qwen2.5-vl:7b"
}'

Le téléchargement du modèle (environ 7 milliards de paramètres) peut prendre entre 15 et 30 minutes en fonction de votre connexion Internet.

Vérification de l'installation du modèle

Après le téléchargement, vérifiez que le modèle est correctement enregistré :

curl http://localhost:11434/api/tags

Vous devriez voir une sortie similaire à : {"models":[{"name":"qwen2.5-vl:7b","modified_at":"2024-01-01T10:00:00.000Z"}]}.

Utilisation de l'API Ollama pour l'inférence multimodale

Test de réponse textuelle basique

Effectuez un test de génération de texte simple :

curl http://localhost:11434/api/generate -d '{
 "model": "qwen2.5-vl:7b",
 "prompt": "Explique le concept de deep learning.",
 "stream": false
}'

Démonstration de l'analyse d'images

Ollama permet l'envoi d'images encodées en Base64 pour l'analyse multimodale. Voici un exemple en Python :

import base64
import requests
import json

def encode_image_to_base64(image_path):
   """Encode une image en chaîne Base64."""
   with open(image_path, "rb") as image_file:
       return base64.b64encode(image_file.read()).decode('utf-8')

def query_multimodal_model(image_path, user_question):
   """Interroge le modèle avec une image et une question."""
   encoded_image = encode_image_to_base64(image_path)
   
   payload = {
       "model": "qwen2.5-vl:7b",
       "prompt": user_question,
       "images": [encoded_image], # Liste des images encodées
       "stream": False
   }
   
   response = requests.post(
       "http://localhost:11434/api/generate",
       json=payload
   )
   
   return response.json()

# Exemple d'utilisation
image_file = "photo_chat.jpg"
question = "Décris le contenu de cette image."
analysis_result = query_multimodal_model(image_file, question)
print(analysis_result["response"])

Test de compréhension vidéo

Pour l'analyse vidéo, vous pouvez extraire des images clés et les envoyer au modèle. L'exemple suivant montre comment extraire des frames :

import cv2
import numpy as np

def extract_video_frames_as_base64(video_path, num_frames_to_extract=5):
   """Extrait des images clés d'une vidéo et les retourne en Base64."""
   video_capture = cv2.VideoCapture(video_path)
   extracted_frames = []
   total_frames = int(video_capture.get(cv2.CAP_PROP_FRAME_COUNT))
   
   if total_frames == 0:
       print("Erreur: Impossible de lire le nombre total d'images de la vidéo.")
       return []

   for i in range(num_frames_to_extract):
       frame_index = int(total_frames * (i / max(1, num_frames_to_extract - 1))) # Évite la division par zéro
       video_capture.set(cv2.CAP_PROP_POS_FRAMES, frame_index)
       success, frame = video_capture.read()
       
       if success:
           # Conversion de l'image en JPG puis en Base64
           _, buffer = cv2.imencode('.jpg', frame)
           encoded_frame = base64.b64encode(buffer).decode('utf-8')
           extracted_frames.append(encoded_frame)
       else:
           print(f"Avertissement: Impossible de lire l'image à l'index {frame_index}.")
           
   video_capture.release()
   return extracted_frames

def analyze_video_content(video_path, user_query):
   """Analyse le contenu d'une vidéo en utilisant des images extraites."""
   frames_base64 = extract_video_frames_as_base64(video_path)
   
   if not frames_base64:
       return {"error": "Aucune image vidéo n'a pu être extraite."}

   payload = {
       "model": "qwen2.5-vl:7b",
       "prompt": f"{user_query} Veuillez analyser le contenu à partir des images vidéo fournies.",
       "images": frames_base64,
       "stream": False
   }
   
   response = requests.post(
       "http://localhost:11434/api/generate",
       json=payload
   )
   
   return response.json()

# Exemple d'utilisation
# video_file = "ma_video.mp4"
# query = "Quel est le sujet principal de cette vidéo ?"
# video_analysis = analyze_video_content(video_file, query)
# print(video_analysis["response"])

Optimisation et configuration avancée

Configuration pour l'accélération GPU

Pour optimiser les performances avec une carte graphique NVIDIA, modifiez votre fichier docker-compose.yml comme suit :

version: '3.8'

services:
 ollama:
   image: ollama/ollama:latest
   container_name: qwen-ollama
   ports:
     - "11434:11434"
   volumes:
     - ollama_data:/root/.ollama
   restart: unless-stopped
   environment:
     - OLLAMA_NUM_GPU=1 # Spécifie le nombre de GPU à utiliser
   deploy:
     resources:
       reservations:
         devices:
           - driver: nvidia
             count: 1 # Utiliser un seul GPU
             capabilities: [gpu]

volumes:
 ollama_data:

Ajustement des paramètres du modèle

Vous pouvez personnaliser le comportement du modèle en créant un fichier Modelfile :

# Créez un fichier nommé Modelfile
cat > Modelfile << EOF
FROM qwen2.5-vl:7b

PARAMETER temperature 0.7
PARAMETER top_p 0.9
PARAMETER num_ctx 4096 # Augmente la taille du contexte si nécessaire
EOF

# Créez un nouveau modèle personnalisé depuis le Modelfile
docker exec -it qwen-ollama ollama create custom-qwen -f Modelfile

Pour utiliser ce modèle personnalisé, remplacez qwen2.5-vl:7b par custom-qwen dans vos appels API.

Dépannage

Gestion du manque de mémoire

Si vous recnontrez des erreurs liées à la mémoire insuffisante :

  • Assurez-vous que votre configuration Docker Compose inclut correctement les resosurces GPU.
  • Vous pouvez essayer de limiter l'utilisation de la mémoire GPU si nécessaire via des variables d'environnement Ollama spécifiques (consultez la documentation Ollama pour les détails).

Lenteur au chargement du modèle

Pour accélérer le chargement des modèles :

Modifiez docker-compose.yml pour ajuster les paramètres de gestion des modèles :

services:
 ollama:
   # ... autres configurations ...
   environment:
     - OLLAMA_MAX_LOADED_MODELS=2 # Limite le nombre de modèles chargés en mémoire
     - OLLAMA_KEEP_ALIVE=5m      # Définit le temps de rétention des modèles chargés

Problèmes de délai d'attente (timeout) API

Si les requêtes API échouent en raison d'un délai d'attente, augmentez le délai dans votre code client :

response = requests.post(
   "http://localhost:11434/api/generate",
   json=payload,
   timeout=300 # Définit un délai d'attente de 5 minutes (en secondes)
)

Cas d'usage pratiques

Modération de contenu intelligent

Utilisez le modèle pour vérifier la conformité des images :

def moderate_image_content(image_path):
   """Fonction pour la modération de contenu d'image."""
   moderation_query = "Cette image contient-elle du contenu inapproprié (violence, nudité, etc.) ? Répondez par oui ou non."
   result = query_multimodal_model(image_path, moderation_query)
   return result["response"]

# Exemple
# print(moderate_image_content("image_a_verifier.png"))

Extraction d'informations à partir de documents

Extrayez des données structurées à partir d'images de documents :

def extract_structured_data_from_document(image_path):
   """Extrait des informations spécifiques d'une image de document (facture, etc.)."""
   extraction_prompt = """Analysez cette image de document (facture). Extrayez les informations suivantes au format JSON :
   - numero_facture
   - date_emission
   - montant_total
   - nom_vendeur
   - liste_articles (nom, quantité, prix_unitaire)
   """
   
   result = query_multimodal_model(image_path, extraction_prompt)
   try:
       return json.loads(result["response"])
   except json.JSONDecodeError:
       print("Erreur lors du décodage JSON. Réponse brute :")
       return result["response"]

# Exemple
# invoice_data = extract_structured_data_from_document("facture.jpg")
# print(invoice_data)

Génération de résumés vidéo

Créez des résumés concis pour des vidéos longues :

def generate_video_summary(video_path):
   """Génère un résumé d'une vidéo en utilisant des images extraites."""
   summary_query = "Résumez le contenu principal de cette vidéo, en incluant les événements clés et les moments importants."
   return analyze_video_content(video_path, summary_query)

# Exemple
# video_summary_result = generate_video_summary("longue_presentation.mp4")
# print(video_summary_result["response"])

Conclusion

Ce tutoriel vous a guidé à travers le déploiement de Qwen2.5-VL-7B-Instruct via Docker Compose et Ollama, créant ainsi un service API multimodal puissant et accessible.

Points clés acquis :

  • Déploiement simplifié avec Docker Compose.
  • API standardisée fournie par Ollama pour une intégration aisée.
  • Capacités multimodales avancées du modèle Qwen2.5-VL.
  • Support de l'accélération GPU pour des performances accrues.

Prochaines étapes suggérées :

  • Explorer des cas d'usage supplémentaires (chatbots, génération de contenu, analyse de données).
  • Mettre en place une architecture scalable avec plusieurs instances et un équilibrage de charge.
  • Intégrer ce service AI dans vos flux de travail existants.
  • Surveiller les performances et ajuster la configuration des ressources si nécessaire.

En cas de problèmes, consultez la documentation officielle d'Ollama ou les forums communautaires. Vérifiez les logs du conteneur pour obtenir des informations de diagnostic détaillées :

docker-compose logs qwen-ollama

Vous disposez maintenant d'un service d'IA multimodale prêt à l'emploi pour vos projets innovants.

Étiquettes: Qwen2.5 multimodal Docker Docker Compose Ollama

Publié le 14 septembre à 23h45