Remplacer GPT par un modèle open-source auto-hébergé : retour d'expérience avec l'extraction documentaire
En bref : migration réelle d'une stack d'extraction documentaire d'Azure (Document Intelligence + GPT-4o) vers un SLM open-source auto-hébergé sur un seul GPU. Résultat : qualité équivalente au cloud, traitement plus rapide, et jusqu'à 20× moins cher à l'échelle — sans qu'aucune donnée sensible ne quitte l'infrastructure. Pertinent dès quelques milliers de pages/mois, sous contrainte de souveraineté ou de rate limits.
L'extraction documentaire fait partie des tâches de l'IA générative que l'on peut facilement traiter avec les modèles propriétaires en API comme GPT, Claude et Gemini. Ces modèles sont rapides à intégrer, performants, et simples à opérer. Mais leur utilisation se heurte vite à la conjonction de plusieurs contraintes : la souveraineté des données, le coût facturé au token qui grimpe avec le volume, les rate limits qui plafonnent le débit, la modération qui bloque parfois des requêtes légitimes, et la dépendance à un fournisseur.
Or les performances des SLM open-source (small language models) atteignent aujourd'hui le niveau des grands modèles propriétaires sur les tâches classiques (OCR, segmentation, extraction structurée). Chez Galadrim, agence tech & IA française, nous avons mené cette migration pour un client soumis à de fortes contraintes de souveraineté. Cet article en détaille le retour d'expérience pas à pas : choix du modèle et du GPU, mise en production, garde-fous, et méthode d'évaluation pour valider qu'on ne perd rien en qualité.
Le contexte : pourquoi une API propriétaire ne tenait plus
Le projet est une application métier construite sur-mesure pour un bureau d'expertises médicales dont les clients sont des assureurs santé en Suisse. Un utilisateur y dépose un dossier PDF composite, souvent 50 à 500 pages, qui rassemble des pièces hétérogènes : rapports, formulaires, courriers, ordonnances, factures. L'application découpe ce PDF en sous-documents distincts, en extrait la date et le titre, produit un résumé, et sélectionne les pièces utiles au traitement.
En interne, ce pipeline enchaîne 7 étapes :
rendu des pages en images,
OCR,
segmentation (poser les frontières entre sous-documents),
fusion des blocs,
extraction des dates,
extraction du contenu (titre + résumé + sélection),
et déduplication.
La segmentation est l'étape pivot. Si on coupe mal, tout le reste est biaisé : un rapport éclaté en plusieurs morceaux fait exploser les dates extraites et fausse la sélection. C'est donc l'étape sur laquelle on a concentré nos tests en premier.
La protection des données privées a été au coeur des contraintes de développement du projet en raison des données sensibles traitées et régulées par la LPD suisse(Loi fédérale sur la protection des données), équivalent de la réglementation européenne. Plusieurs clients de la solution souhaitaient aller au-delà des garanties contractuelles fournies par Azure en Suisse en termes de souveraineté de la donnée.
À cette contrainte réglementaire, s'ajoutaient déjà un coût facturé au token qui croît avec le volume, et une dépendance à des fournisseurs hors de notre contrôle. Le client a donc demandé, en amont, une infrastructure 100 % suisse, sans tiers extra-européen dans la boucle. C'est le déclencheur de la migration.
Choisir son SLM : multimodalité et budget VRAM
Migrer vers de l'auto-hébergé GPU engage un coût d'infrastructure et une complexité opérationnelle et soulève principalement les questions suivantes : quelle infrastructure choisir pour l'inférence, en particulier la mémoire vive du GPU (VRAM) et quel modèle choisir pour chaque tâche (nombre de paramètres, quantification etc.) ?
Le LLM pour les tâches d'extraction et de synthèse
L'entrée de l'étape de segmentation est composée d'images de pages. Il faut donc un modèle multimodal, à fenêtre de contexte large, qui tienne sur un seul GPU.
Modèle
Params actifs
VRAM Q5
Multimodal
Choix
Llama 3.1 70B
70B
~50 GB
✗
✗pas de vision
Mistral Large 2 123B
123B
> 80 GB
✗
✗infaisable single-GPU
Qwen2.5-VL 32B
32B
~22 GB
✓
▲correct mais lent
Qwen3.6-35B-A3B (MoE)
3B actifs / 35B
~28 GB
✓
✓retenu
Pixtral 12B
12B
~10 GB
✓
✗écart de qualité
Tableau 1 — Choix du modèle multimodal (splitter) : Un seul GPU 48 Go, vision requise pour lire les pages.
On a retenu un Mixture-of-Experts (Qwen3.6-35B-A3B) : il n'active que 3 milliards de paramètres par token généré tout en disposant de la connaissance d'un modèle à 35 milliards de paramètres. On obtient donc le débit d'un petit modèle avec la qualité d'un gros. Sur notre tâche, il est au niveau de GPT-4o en segmentation et extraction de dates.
L'OCR
GLM-OCR est spécialisé OCR (pas généraliste) et lit bien les écritures manuscrites. C'est un point critique sur les formulaires où l'information utile est souvent une mention manuscrite.
Modèle
Qualité petit texte
Vitesse
Choix
Azure Document Intelligence
référence
1-2 s/p
✗cloud
Tesseract / PaddleOCR
dégradée sur tampons/écriture
< 1 s/p
✗insuffisant
Qwen2.5-VL OCR-mode
bonne
8-10 s/p
▲lent
GLM-OCR (THUDM)
≈ Azure DI
1-2 s/p
✓retenu
Tableau 2 — Choix du moteur OCR : Qualité proche d'Azure, sans le cloud.
Quantization : c'est avant tout une question de budget VRAM
Faire cohabiter deux modèles sur 48 GB est surtout un problème d'enveloppe mémoire. On a comparé plusieurs niveaux de quantization et retenu, pour notre cas et notre VRAM, du Q5_K_M pour le LLM et du Q8_0 pour l'OCR : c'est le point où la qualité reste indistingable du FP16 sur nos tâches tout en laissant assez de marge pour faire tourner plusieurs requêtes LLM concurrentes. Le bon niveau dépend du modèle, de la tâche et du GPU. Le Q4 dégradait l'extraction structurée et l'OCR des petits chiffres ; le FP16 ne rentrait tout simplement pas.
Figure 1 — Les deux modèles cohabitent sur un seul GPU 48 Go : ~38 Go alloués, ~10 Go conservés en marge pour absorber les pics de contexte.
Deux enseignements tirés de la mise en production des SLM
Couper le « thinking mode » : structurer la tâche plutôt que laisser le modèle réfléchir
Par défaut, le modèle émet plusieurs milliers de tokens de raisonnement (…) avant de produire son JSON. Sur une tâche à sortie structurée, ce raisonnement est du temps perdu : sur un batch de 10 pages, on passe de ~20 s à ~3 s en le désactivant, un gain × 5 à × 10.
Au-delà du flag : sur les tâches structurées, la qualité vient moins du raisonnement libre que de bien définir et structurer la tâche dans le prompt système. Et quand la qualité de sortie est critique, on remplace le raisonnement implicite par un dispositif explicite et contrôlé, typiquement plusieurs passes en réseau adversarial de LLM-as-a-judge pour durcir et valider le système de prompt. On garde le raisonnement uniquement là où il aide réellement (ici, la déduplication).
Toujours tester ses garde-fous : les modèles open-source hallucinent
Un SLM auto-hébergé n'a pas le filet de sécurité d'un fournisseur. Il faut construire ses propres garde-fous, et les tester en conditions réelles pour trouver les bonnes solutions.
Garde-fou
Déclenchement
Effet
Détection de boucle OCR
Sortie anormalement longue ou répétition phrase-level
Sauvegarde le préfixe valide, retry, fallback
Fallback per-page
Le parsing d'un batch OCR échoue
Re-OCR page par page
Fallback LLM sur OCR loop
Boucle OCR + retry échoué
Bascule sur le LLM vision pour cette page
Retry exponentiel
Erreur HTTP / timeout
Récupère les transients réseau ou saturation
Boundary resolver
Le splitter hésite entre 2 frontières
Réinjecte le contexte limitrophe pour trancher
Tableau 3 — Garde-fous du pipeline auto-hébergé : sans filet fournisseur, tout est géré côté pipeline.
Dans la pratique, ces garde-fous récupèrent la quasi-totalité des incidents : sur nos lots, environ 1 % des pages partent en boucle d'hallucination, et 100 % sont récupérées via sauvegarde du préfixe valide + fallback. L'objectif est de la détecter et d'avoir un plan B systématique.
Mesurer pour décider : comment on a validé qu'on ne perdait rien
Le risque numéro un d'une migration comme celle-ci, c'est de dégrader silencieusement la qualité. On a donc construit un harness d'évaluation qui compare chaque sortie du modèle local à une référence, sur un jeu de dossiers représentatifs annotés (plusieurs centaines de sous-documents).
Quelle référence ? La cible, c'est l'extraction faite en amont par GPT-4o (la stack de prod historique), consolidée par annotation. Point important : cette référence n'est pas une vérité absolue. Il subsiste des incertitudes métier et il arrive que le LLM-as-a-judge estime que le découpage ou l'extraction du modèle local sont meilleurs que la référence. Autrement dit, une partie des « écarts » mesurés ne sont pas des régressions mais des désaccords légitimes, ce qui plafonne mécaniquement les scores bruts vers le bas.
Séparer le mécanique du sémantique. Tout ce qui est comparable mécaniquement (frontières, dates, sélection, hallucinations) est calculé en Python pur, alignement par overlap de pages, F1, ce qui rend ces KPIsreproductibles bit-à-bit entre deux runs. Mais certains critères ne se réduisent pas à un exact-match : « Rapport médical Dr Martin » et « Rapport initial — Jean MARTIN » désignent le même document. Pour ces cas, un LLM-as-a-judge rend un verdict structuré ok | partial | ko + une raison courte. Seule cette couche dépend d'un LLM, donc elle reste auditable indépendamment.
KPI
Définition
Cible
Cut F1 (tol ±1)
Précision/rappel des frontières de découpe
≥ 90 %
Date exact rate
% de dates prédites exactes
≥ 80 %
is_selected F1
Sélection des pièces utiles
≥ 90 %
Hallucination rate
% de documents prédits sans correspondance
≤ 2 %
Title verdict
Qualité du titre, jugée par LLM
≥ 95 % ok
Tableau 4 — KPIs et cibles métier : séparer le mécanique du sémantique.
Astuce : le LLM-as-a-judge comme annotateur quand on n'a pas de golden set. Construire une ground truth à la main coûte cher. Avec les modèles actuels (on utilise aujourd'hui Claude Code avec Opus 4.8, ou Codex avec GPT-5.5), un LLM-as-a-judge fait un annotateur de départ étonnamment fiable : il pré-annote, on relit, et on itère. C'est un excellent moyen d'amorcer un jeu d'évaluation à moindre coût.
⚠️ Sur des données sensibles, anonymisez d'abord. Dès qu'on envoie des contenus à un LLM-as-a-judge ou à un modèle d'annotation — a fortiori via une API externe — il faut anonymiser en amont (caviardage des identités, identifiants). Sinon, on réintroduit par la petite porte exactement la fuite de données qu'on cherchait à éliminer en migrant on-premise. D'où l'importance d'un set de base anonymisé.
(Note transverse) Pour itérer vite, c'est un agent de code qui pilote la chaîne d'évaluation : il lance les pipelines, déclenche les passes de jugement, agrège les bilans et régénère un comparatif cross-runs — sans intervention manuelle. Un bon exemple d'usage d'agents de code pour accélérer une boucle de R&D.
Résultats : qualité, vitesse, coût
La qualité au rendez-vous
KPI
Score (local)
Verdict
Cut F1 (tol ±1)
89,8 %
✓au niveau cible
Date exact rate
81,3 %
✓
is_selected F1
85,1 %
✓
Hallucination rate
0,4 %
✓quasi nulle
Title verdict ok
68 % ok / 25 % partiel / 6 % ko
✓
Tableau 5 — Résultats du SLM local vs cibles : tous les indicateurs au niveau attendu.
Figure 2 — Le SLM local atteint ou approche les cibles métier sur tous les KPIs, avec un taux d'hallucination quasi nul (0,4 %).
Sur un dossier représentatif, la segmentation atteint un Cut F1 de 98 % : les frontières prédites coïncident presque toutes avec les frontières de référence, avec seulement deux sur-découpages mineurs sur 48.
Figure 3 — Frontières de référence et prédites sur un dossier de 79 pages. 46 des 48 frontières prédites sont exactes ; les deux sur-coupes entourées sont les seuls écarts.
La vitesse : plus rapide que le cloud
Mesure directe sur un même dossier de 530 pages :
Azure (DI + GPT-4o)
Local (GPU L40S)
Ratio
Temps wall-clock
45 min
30 min
× 1,5 plus rapide
Coût du run
$8.70
~$0.45 (estimé sur le coût horaire)
× ~20 moins cher
Tableau 6 — Azure vs local sur un même dossier de 530 pages.
Le coût local n'est pas nul : il s'estime en rapportant le temps machine au coût horaire du GPU (~$0.90/h). Un run de 30 min revient donc à ~$0.45 de compute, contre $8.70 facturés par le cloud sur le même dossier.
Figure 4 — DATES et SPLIT concentrent 92 % du temps de traitement : ce sont les deux postes à paralléliser en priorité.
À noter, une limite : un seul GPU ne tient pas une énorme charge parallèle : on plafonne autour de ~15 pages/min en charge maximale. C'est parfait pour du traitement asynchrone à volume modéré, moins adapté à un pic temps-réel massif.
Le coût : le vrai argument à l'échelle
C'est sur le coût que le gain est le plus net. Le GPU coûte un montant fixe (~$0.90/h, soit ~$650/mois en 24/24), indépendant du volume. Le cloud, lui, facture chaque page.
Métrique
Azure
Local (GPU 24/24)
Coût marginal / dossier (530 p)
$8.70
~$0.45 (en on-demand)
Coût fixe / mois
0 (pay-as-you-go)
~$650
Seuil de rentabilité
—
dès ~75 gros dossiers / mois
Tableau 7 — Coût — Azure vs GPU local 24/24.
En mode 24/24, le coût marginal d'un dossier supplémentaire tend vers zéro (la machine tourne de toute façon). Au-delà du seuil, tout volume supplémentaire est traité à coût marginal quasi nul côté infra IA, et l'écart se creuse linéairement.
Figure 5 — Le coût cloud croît avec le volume ; le GPU on-premise reste fixe. Au-delà de ~75 gros dossiers/mois, l'écart se creuse en faveur de l'on-premise.
Quand basculer vers un SLM on-premise
Cette migration n'est pas un dogme. Voici le cadre de décision qu'on en retire.
Basculez vers un SLM auto-hébergé quand :
vous avez une contrainte de souveraineté / conformité forte (données sensibles, secteur réglementé) ;
votre volume dépasse le seuil de rentabilité (typiquement quelques dizaines à centaines de dossiers/mois) ;
vous vous heurtez régulièrement aux rate limits des API : auto-héberger, c'est reprendre la main sur son throughput au lieu de subir les quotas du fournisseur ;
votre cas d'usage est « classique » (OCR, segmentation, extraction structurée, classification), là où les SLM ont rattrapé les gros modèles ;
votre charge est asynchrone et tolère une latence de l'ordre de la minute.
Ce qu'on a appris en chemin
La quantization est un arbitrage local, pas une recette : le bon niveau dépend du modèle, de la tâche et de votre VRAM.
MoE = qualité d'un gros modèle au débit d'un petit : un excellent profil pour de l'auto-hébergé.
Structurez la tâche plutôt que de laisser le modèle raisonner librement : prompt système soigné, et passes adversariales de LLM-as-a-judge quand la qualité est critique.
Testez vos garde-fous en conditions réelles : les modèles open-source hallucinent, l'enjeu est de détecter et de récupérer, pas de viser le zéro défaut illusoire.
Séparez l'évaluation mécanique (reproductible) du jugement sémantique (LLM) pour des KPIs auditables — et anonymisez avant tout passage par un juge externe.
Conclusion
Sur ce traitement documentaire, un SLM open-source en architecture MoE associé à un OCR spécialisé, sur un seul GPU à ~$650/mois, atteint la qualité du cloud, va plus vite, coûte jusqu'à 20 fois moins cher à l'échelle, et garde les données sensibles dans le périmètre. L'open-source ne remplace pas tout : il s'agit de choisir le bon modèle pour le bon usage. Pour les tâches classiques, à volume, sous contrainte de souveraineté ou de rate limits, les SLM sont prêts.
Par Maceo Duriez, Ingénieur IA chez Galadrim. Retour d'expérience issu d'un projet client réel.
FAQ
Un SLM open-source peut-il égaler GPT-4o sur l'extraction documentaire ?
Oui, sur les tâches classiques (OCR, segmentation, extraction structurée). Sur ce projet, le modèle MoE local atteint le niveau de GPT-4o en segmentation et extraction de dates. Les API propriétaires gardent l'avantage sur le raisonnement avancé et les tâches agentiques complexes.
À partir de quel volume l'auto-hébergement devient-il rentable ?
Typiquement quelques dizaines à centaines de dossiers/mois. Le GPU coûte un montant fixe (~650 $/mois en 24/24) ; au-delà du seuil de rentabilité (~3000 pages/mois ici), chaque dossier supplémentaire est traité à coût marginal quasi nul, là où le cloud facture chaque page.
Combien coûte le traitement d'un dossier en local vs cloud ?
Sur un même dossier de 530 pages : ~0,45 $ de compute en local (30 min à ~0,90 $/h de GPU) contre 8,70 $ (environ 16cts/pages) facturés par le cloud.
Quand rester sur une API propriétaire plutôt qu'un SLM on-premise ?
Quand le volume est faible, que vous avez besoin du raisonnement le plus avancé, que vous devez encaisser des pics de charge massifs sans provisionner d'infra, ou que la donnée n'a aucune contrainte de localisation.
Vous souhaitez être accompagné pour lancer votre projet digital ?