Module 7 — Registre de modèles et versionnage
Une tâche a produit un modèle (module 5 ou 6). Il vit pour l'instant dans les sorties de cette tâche — un dossier outputs/modele/ sur le stockage. Cet emplacement ne suffit pas pour déployer, promouvoir, comparer ou auditer. Le registre de modèles enregistre ce dossier sous un nom, une version, des balises et un lignage vers la tâche qui l'a produit. C'est le seul objet qu'un point de terminaison (module 8) doit accepter en entrée.
Deux registres, un même vocabulaire
Azure ML distingue deux registres :
- Le registre du workspace : local à un espace, suffit pour un projet mono-équipe
- Le registre partagé (
shared registry) : traversant plusieurs espaces (dev, staging, prod), pensé pour les équipes multiples
Pour le fil rouge, on part sur le registre du workspace de dev, puis on promeut vers un registre partagé au moment de passer en production.
Enregistrer un modèle produit par une tâche
Un modèle sauvegardé au format MLflow par la tâche du module 5 s'enregistre en une commande :
az ml model create --name prev-demande-xgb --version 7 \
--type mlflow_model \
--path azureml://jobs/xgb-baseline-2026-09-06/outputs/modele/
Trois éléments importent.
Le nom prev-demande-xgb est stable dans le temps et sert de clé de rappel. Le numéro de version est incrémenté à chaque nouveau modèle enregistré sous ce nom — c'est Azure qui le gère si l'on omet --version.
Le type mlflow_model débloque le déploiement sans code du module 8 : Azure sait lire le fichier MLmodel, en tirer la signature, générer le script de scoring et l'environnement de service. Un modèle enregistré comme custom_model (format arbitraire, un dossier de poids et un Dockerfile) demandera un script score.py explicite au déploiement.
Le chemin azureml://jobs/… relie automatiquement le modèle à la tâche source. C'est cette référence qui matérialise le lignage : depuis le modèle, on remonte à la tâche ; depuis la tâche, aux entrées MLTable et à l'environnement, tous versionnés.
Balises : la métadonnée qui filtre
Les balises (tags) sont des paires clé-valeur libres. Elles portent l'essentiel de la vie opérationnelle d'un modèle :
az ml model update --name prev-demande-xgb --version 7 \
--set tags.stade=validation \
--set tags.mape_test=0.087 \
--set tags.responsable=alice.dupont@example.com \
--set tags.horizon_semaines=4
Deux conventions à installer dans l'équipe :
- Une balise
stadeavec quatre valeurs contrôlées :experimentation,validation,production,archive. C'est elle qui pilote quel modèle est éligible à un déploiement — le point de terminaison du module 8 lit uniquement les modèlesstade=production. - Une balise
mape_testou équivalent métrique, pour filtrer et comparer sans rouvrir chaque tâche.
Format MLflow contre format personnalisé
| Aspect | mlflow_model | custom_model |
|---|---|---|
| Signature | inférée du fichier MLmodel | à déclarer à la main |
| Déploiement sans code | oui | non |
| Portabilité hors Azure | oui, MLflow standard | dépend du script |
| Modèles supportés | scikit-learn, xgboost, pytorch, tensorflow, pyfunc | tout ce qui tient dans un dossier |
Le format mlflow_model est le choix par défaut. Le format custom_model s'impose pour un modèle propriétaire, un pipeline avec un prétraitement lourd non exprimable en pyfunc, ou un modèle en langage exotique (R, Julia).
Registre partagé : la promotion entre espaces
Un registre partagé se crée au niveau du groupe de ressources, indépendamment d'un workspace :
az ml registry create --name reg-prev-demande -g rg-prev-demande-shared \
--location westeurope --replication-locations westeurope,northeurope
Un modèle promu depuis le workspace de dev y devient accessible aux workspaces de staging et de production :
az ml model create --registry-name reg-prev-demande \
--name prev-demande-xgb --version 7 \
--path azureml://workspaces/mlw-prev-demande/models/prev-demande-xgb/versions/7
L'intérêt principal du registre partagé n'est pas technique — c'est la séparation des permissions. Les data scientists écrivent dans le workspace de dev, l'ingénieur MLOps seul a le droit d'importer dans le registre partagé, et l'ingénieur de déploiement seul a le droit de lire depuis la prod. La chaîne est auditable, chaque promotion produit une trace.
Lignage complet : de la prédiction au bit d'entrée
Une fois modèle enregistré, tâche remontée et données MLTable versionnées, le graphe de lignage est complet :
prev-demande-xgb:7
↳ job xgb-baseline-2026-09-06
↳ input ventes: azureml:ventes_magasins:3
↳ input environment: azureml:env-prev-demande:3
↳ code snapshot: sha 3f8a2b…
Cinq mois plus tard, si le contrôleur demande « rejouer la version 7 », la commande az ml job show retrouve toutes les briques et un nouveau lancement de la même définition YAML reproduit rigoureusement le modèle — c'est l'audit gratuit annoncé au module 3.
Un modèle enregistré avec --path ./local/, où ./local/ est un dossier posé à la main sur le poste d'un data scientist, casse le lignage : plus aucun lien avec une tâche, plus de trace des données. Refuser cet enregistrement en revue de code. La seule source légitime est une sortie de tâche ou une promotion depuis un autre registre.
En résumé
- Le registre transforme un artefact posé sur le stockage en objet nommé, versionné et lignagé
- Format
mlflow_modelpar défaut,custom_modelseulement quand la contrainte l'impose - Les balises
stadeetmétriquepilotent la promotion et la sélection sans rouvrir les tâches - Le registre partagé sépare les permissions entre dev, staging et prod, condition d'un audit crédible
Le module suivant utilise le modèle enregistré pour créer le premier point de terminaison en ligne du fil rouge.