L’erreur ZFS la plus coûteuse n’est pas un mauvais checksum ni un resilver qui dure tout le week-end.
C’est celle qui survient quand l’activité attend et que le pool refuse de s’importer : « fonctionnalités non prises en charge ».
Si vous avez déjà traité un pool ZFS comme un disque dur portable — « on déplace juste le JBOD vers le nouvel hôte » — vous avez déjà marché sur ce râteau.
Les flags de fonctionnalités ZFS sont excellents jusqu’au moment où vous oubliez qu’ils existent. Ensuite, ils deviennent une serrure que vous avez installée vous-même.
Ce que sont réellement les flags de fonctionnalités (et pourquoi ils bloquent les imports)
Les « flags de fonctionnalités » ZFS sont des capacités du format sur disque, suivies au niveau du pool. Ils ont remplacé l’ancien modèle de « version du pool »
où un unique numéro croissant cherchait à représenter tout. Les flags sont plus granulaires :
un pool peut supporter certaines fonctionnalités et pas d’autres ; différentes implémentations peuvent ajouter de nouvelles fonctionnalités sans coordonner un compteur de version global.
Voici le piège de portabilité : une fois qu’une fonctionnalité devient active sur un pool (ou parfois seulement activée),
vous pouvez avoir besoin d’une implémentation ZFS qui la comprend pour importer le pool. Si vous déplacez les disques vers un hôte avec un ZFS plus ancien,
ou une build fournie par un vendeur qui n’intègre pas la fonctionnalité, ZFS peut refuser l’import. Ce n’est pas ZFS qui fait la difficile : c’est pour éviter une corruption silencieuse.
Activée vs active : le petit détail qui ruine des week-ends
ZFS suit les fonctionnalités dans des états qui ressemblent généralement à : disabled, enabled, active.
La présentation exacte varie légèrement selon la plateforme, mais l’idée est la même :
- Enabled : le pool est autorisé à utiliser la fonctionnalité si nécessaire.
- Active : le pool l’a effectivement utilisée ; des structures sur disque existent et nécessitent la fonctionnalité pour une interprétation correcte.
Le risque de portabilité augmente fortement lorsqu’une fonctionnalité devient active. Parfois, le simple fait d’être « enabled » suffit à bloquer l’import sur un ZFS ancien ;
d’autres fois, seul « active » compte. Vous ne voulez pas découvrir lequel au moment d’une fenêtre de migration.
Pourquoi on ne peut pas simplement « la désactiver »
La plupart des flags de fonctionnalités sont des portes à sens unique. Une fois qu’un pool a utilisé une fonctionnalité, la supprimer exigerait de réécrire les métadonnées
et peut‑être les structures de données sur tout le pool. ZFS ne fournit généralement pas d’outils de « rétrogradation » des fonctionnalités. Le chemin pratique de rétrogradation
est généralement : répliquer les données vers un nouveau pool créé avec des fonctionnalités plus anciennes/compatibles.
C’est le premier point de décision vers lequel cet article vous poussera : la portabilité se conçoit et se teste. Ce n’est pas une propriété
que vous découvrez plus tard en regardant les erreurs de zpool import.
La réalité sèchement drôle
Blague #1 : Un pool ZFS est portable comme un piano à queue est « déplaçable ». Oui, techniquement—mais ne soyez pas surpris quand il faudra planifier.
Une citation à coller sur votre écran
« L’espoir n’est pas une stratégie. » — Général Gordon R. Sullivan
Traitez la compatibilité des flags de fonctionnalités exactement comme les sauvegardes : si vous ne l’avez pas testée, vous ne l’avez pas.
Faits et courte histoire : comment on en est arrivé là
Les détails comptent parce que des gens continuent de répéter d’anciennes sagesses ZFS qui n’étaient vraies que pour une époque spécifique.
Voici des faits concrets et des points de contexte qui vous aideront à raisonner sur la portabilité aujourd’hui.
-
Les « versions » de pool étaient un compteur unique. Les premiers ZFS utilisaient un numéro de version de pool ; le fait d’upgrader l’incrémentait et pouvait bloquer les imports sur les versions plus anciennes.
Les flags de fonctionnalités ont été introduits pour éviter ce modèle tout‑ou‑rien. -
Les flags de fonctionnalités sont enregistrés sur disque. Ce n’est pas un réglage à l’exécution ; c’est une partie de la description du pool à travers les redémarrages.
C’est excellent pour la récupération — jusqu’à ce que vous changiez la description vers un dialecte que vos autres hôtes ne comprennent pas. - OpenZFS a unifié ce qui était fragmenté. ZFS dérivé de Solaris/Illumos et les différents downstreams avaient divergé ; OpenZFS a rendu la coordination des flags plus réaliste, mais pas parfaite entre les packages des vendeurs.
-
Linux ZFS (aujourd’hui OpenZFS on Linux) a popularisé les flottes mixtes. Beaucoup d’organisations exécutent maintenant ZFS sur Linux, FreeBSD et des appliances en même temps,
et la portabilité entre eux est une préoccupation opérationnelle quotidienne, pas une curiosité. -
« zpool upgrade » change le contrat. Sur de nombreux systèmes,
zpool upgraden’active pas juste des fonctionnalités ; il peut activer un ensemble
que des systèmes plus anciens ne peuvent pas importer. Les gens le traitent comme « appliquer les mises à jour de sécurité » et le regrettent. -
Certaines fonctionnalités sont au niveau dataset, d’autres au niveau pool, mais le blocage d’import est au niveau pool. Si le pool nécessite une fonctionnalité, l’import du pool entier
est affecté même si un seul dataset l’utilise. -
Le chiffrement a modifié les discussions sur la portabilité. Le chiffrement natif ZFS a introduit la gestion des clés et des intégrations de keystore différentes selon les OS,
plus des flags requis pour les datasets chiffrés. -
Les appliances vendeurs prennent parfois du retard. Les systèmes de stockage « basés sur ZFS » fournis par des vendeurs peuvent expédier des sets de fonctionnalités conservateurs ou des versions OpenZFS mises à jour plus tard,
ce qui en fait le membre le moins compatible de votre flotte. -
L’import en lecture seule peut quand même échouer. Certains pensent que
zpool import -o readonly=oncontournera les exigences de fonctionnalités. Ce n’est pas le cas si
le format sur disque ne peut pas être interprété en toute sécurité.
Conclusion : les flags de fonctionnalités sont la bonne solution d’ingénierie, mais ils exigent de la discipline opérationnelle. Si votre processus est « mettre à niveau quand c’est proposé »,
vous laissez essentiellement vos pools écrire des chèques que vos autres machines ne pourront pas encaisser.
Modes d’échec qui mènent à « impossible d’importer »
1) Le pool a été mis à niveau sur un hôte, puis déplacé sur un hôte plus ancien
Scénario classique : vous avez un pool parfois importé sur l’hôte A (nouvel OpenZFS) et parfois sur l’hôte B (plus ancien). Quelqu’un lance
zpool upgrade sur l’hôte A parce que ça ressemble à une étape de maintenance sans risque. Maintenant l’hôte B ne peut plus importer.
2) Une fonctionnalité est devenue active parce qu’une propriété de dataset a été changée
Certaines propriétés de dataset peuvent activer des fonctionnalités au niveau du pool indirectement. Vous n’avez pas exécuté d’upgrade ; vous avez « juste activé xattr=sa » ou « activé le chiffrement »
ou « activé special_small_blocks ». Cela peut activer des fonctionnalités. Maintenant votre site DR ne peut plus importer, ou votre cible de réplication refuse de recevoir.
3) Versions OpenZFS hétérogènes dans une flotte, avec packaging incohérent
Même au sein d’« OpenZFS », les distributions et vendeurs peuvent livrer des versions, des backports ou des sets de fonctionnalités différents. Vous pouvez avoir deux systèmes « 2.1.x » où l’un supporte
une fonctionnalité et l’autre non à cause du choix de patchs. Partir du principe que la parité de version sémantique équivaut à la parité des fonctionnalités est une excellente façon d’écrire des rapports d’incident.
4) Quelqu’un a utilisé une voie de snapshot/réplication pratique qui a traîné des fonctionnalités
Le send brut pour datasets chiffrés, le support de gros blocs, les données embarquées — tout cela peut lier la compatibilité de votre réplication au support de fonctionnalités. Vous pouvez répliquer des données
et quand même être coincé si le récepteur ne supporte pas le format sur disque impliqué par le flux de send.
5) Le pool a été créé en ignorant la « compatibilité »
OpenZFS moderne a une propriété compatibility (sur certaines plateformes) qui peut contraindre les fonctionnalités à la création du pool pour correspondre à un ensemble cible.
Si vous ne la définissez pas et découvrez plus tard que vous en aviez besoin, vous êtes dans le territoire de la reconstruction.
Playbook de diagnostic rapide
Quand un pool refuse de s’importer et que des gens regardent, vous n’avez pas le temps de redécouvrir ZFS. Vous avez besoin d’un chemin de triage rapide qui distingue
« flags de fonctionnalités non pris en charge » vs « périphérique/chemin manquant » vs « dommage ». Voici l’ordre qui vous mène le plus vite à la vérité.
Première étape : confirmer que c’est un problème de flag et pas des disques manquants
- Exécutez
zpool importet lisez la sortie complète. Si elle indique « unsupported feature(s) », arrêtez de deviner et commencez à collecter des informations. - Vérifiez que l’OS voit tous les disques (par les chemins by-id). Si le pool est incomplet, vous pouvez obtenir du bruit trompeur.
Deuxième étape : identifier quelles fonctionnalités sont requises et quel ZFS vous exécutez
- Récupérez l’implémentation ZFS locale et les infos de version (
zfs versionsur Linux ;uname/kldstatet info paquet sur BSD). - Extrait la liste des fonctionnalités requises par le pool depuis la sortie d’import, puis comparez-la aux fonctionnalités prises en charge localement.
Troisième étape : décider si vous pouvez importer quelque part, même temporairement
- Trouvez un hôte (ou un média de démarrage) avec une version ZFS qui supporte les fonctionnalités requises.
- Si vous pouvez y importer, vos options s’élargissent : répliquer ailleurs, revenir à des snapshots pré-activation (parfois), ou laisser le pool sur l’hôte plus récent.
Quatrième étape : choisir une voie de récupération sûre
- Si le pool doit rester portable vers des systèmes plus anciens, planifiez une migration : créez un nouveau pool avec des fonctionnalités contraintes et utilisez
zfs send | zfs receive. - Si l’ancien système doit rester en service, mettez à niveau son ZFS (si possible et sûr) plutôt que de forcer une rétrogradation du pool (généralement impossible).
Blague #2 : L’expression « on l’importera sur l’autre machine » a interrompu plus de fenêtres de changement que la caféine.
Tâches pratiques : commandes, sorties, décisions
Ces tâches sont écrites comme si vous étiez en astreinte : commande, sortie réaliste, et la décision que vous prenez à partir de celle-ci.
Les exemples partent du principe d’un Linux avec les utilitaires OpenZFS installés. Les mêmes concepts s’appliquent sur FreeBSD/Illumos, mais certaines commandes diffèrent.
Tâche 1 : Lister les pools importables et repérer immédiatement les « fonctionnalités non prises en charge »
cr0x@server:~$ zpool import
pool: data
id: 13462978123456789012
state: UNAVAIL
status: The pool was last accessed by another system.
action: The pool cannot be imported due to missing or damaged devices.
see: zpool import -F for recovery
config:
data UNAVAIL insufficient replicas
raidz1-0 UNAVAIL insufficient replicas
sda UNAVAIL cannot open
sdb UNAVAIL cannot open
sdc UNAVAIL cannot open
pool: backup
id: 998877665544332211
state: UNAVAIL
status: The pool uses the following feature(s) not supported on this system:
com.delphix:spacemap_histogram
com.delphix:extensible_dataset
action: The pool cannot be imported. Access the pool on a system that supports
the required feature(s), then migrate the data.
config:
backup UNAVAIL unsupported feature(s)
Décision : « data » ressemble à un problème de visibilité de périphériques/réplicas insuffisants. « backup » est un problème de compatibilité par flags.
Ne perdez pas de temps à changer des câbles pour « backup » ; allez chercher un hôte ZFS plus récent.
Tâche 2 : Tenter un import en lecture seule (pour confirmer que ça échoue toujours à cause des fonctionnalités)
cr0x@server:~$ sudo zpool import -o readonly=on backup
cannot import 'backup': unsupported version or feature
unsupported feature(s): com.delphix:spacemap_histogram com.delphix:extensible_dataset
Décision : La lecture seule n’aide pas. Vous avez besoin d’un système qui supporte ces fonctionnalités, ou d’upgrader le ZFS de ce système.
Tâche 3 : Vérifier quelles fonctionnalités votre ZFS local supporte
cr0x@server:~$ zpool get -H -o property,value all | grep feature@
feature@async_destroy enabled
feature@empty_bpobj active
feature@lz4_compress active
feature@spacemap_histogram -
feature@extensible_dataset -
feature@embedded_data -
feature@bookmarks enabled
Sens de la sortie : Les fonctionnalités affichant - sont inconnues/non supportées par cette implémentation.
Décision : Si le pool requiert spacemap_histogram et que vous affichez -, l’import ne fonctionnera jamais ici.
Arrêtez et choisissez : mettez à niveau ZFS ici, ou déplacez les disques vers un hôte qui le supporte déjà.
Tâche 4 : Identifier la version locale d’OpenZFS (Linux)
cr0x@server:~$ zfs version
zfs-2.1.5-1
zfs-kmod-2.1.5-1
Décision : Vous pouvez maintenant comparer cette version à celle qui a importé le pool pour la dernière fois. Si le pool a été importé sur 2.2+,
supposez un décalage de fonctionnalités jusqu’à preuve du contraire.
Tâche 5 : Voir quel hôte a importé le pool en dernier (aide à trouver la machine « plus récente »)
cr0x@server:~$ zdb -C backup | head -n 25
MOS Configuration:
version: 5000
name: 'backup'
state: 0
txg: 925331
pool_guid: 998877665544332211
hostid: 0x3f2a9c10
hostname: 'stor-ops-07'
vdev_tree:
type: 'root'
id: 0
guid: 1234567890123456789
Sens de la sortie : Le pool enregistre le hostname/hostid qui a écrit dessus en dernier.
Décision : Allez trouver stor-ops-07 (ou son remplaçant). C’est votre meilleur pari pour un environnement d’import compatible.
Tâche 6 : Sur l’hôte « plus récent », lister les états des fonctionnalités pour le pool
cr0x@server:~$ sudo zpool get -H -o property,value all backup | grep feature@
feature@async_destroy enabled
feature@empty_bpobj active
feature@lz4_compress active
feature@spacemap_histogram active
feature@extensible_dataset active
feature@embedded_data active
feature@bookmarks enabled
Sens de la sortie : Ces fonctionnalités d’origine Delphix sont maintenant actives, donc le pool en dépend réellement.
Décision : La rétrogradation n’est pas réaliste. Votre voie est soit d’upgrader l’ancien système, soit de migrer les données vers un nouveau pool compatible.
Tâche 7 : Confirmer si un pool a un profil de compatibilité (si pris en charge)
cr0x@server:~$ sudo zpool get -H compatibility backup
compatibility off
Décision : Si vous avez des cibles OS mixtes, « off » sent mauvais. Pour les nouveaux pools vous devriez définir un profil de compatibilité aligné avec
le système le plus ancien sur lequel vous devez importer.
Tâche 8 : Créer un nouveau pool « portable » avec des fonctionnalités contraintes (exemple)
cr0x@server:~$ sudo zpool create -o ashift=12 -o compatibility=openzfs-2.1 portable mirror /dev/disk/by-id/wwn-0x5000c500a1b2c3d4 /dev/disk/by-id/wwn-0x5000c500a1b2c3d5
cannot set property for 'portable': invalid property 'compatibility'
Sens de la sortie : Vos outils actuels ne supportent pas la propriété (OpenZFS plus ancien, ou build vendeur).
Décision : N’improvisez pas. Si vous ne pouvez pas utiliser un profil de compatibilité, vous devez faire respecter la portabilité par la politique :
évitez zpool upgrade, évitez d’activer des fonctionnalités risquées, et validez les listes de fonctionnalités avant migration.
Tâche 9 : Afficher le statut du pool et confirmer que vous ne traitez pas aussi des vdevs manquants
cr0x@server:~$ sudo zpool status -v backup
pool: backup
state: ONLINE
status: Some supported features are not enabled on the pool.
action: The pool can be upgraded using 'zpool upgrade'. Once this is done,
the pool may no longer be accessible by software that does not support
the features. See zpool-features(7) for details.
config:
NAME STATE READ WRITE CKSUM
backup ONLINE 0 0 0
raidz2-0 ONLINE 0 0 0
/dev/disk/by-id/wwn-0x5000c50011111111 ONLINE 0 0 0
/dev/disk/by-id/wwn-0x5000c50022222222 ONLINE 0 0 0
/dev/disk/by-id/wwn-0x5000c50033333333 ONLINE 0 0 0
/dev/disk/by-id/wwn-0x5000c50044444444 ONLINE 0 0 0
Décision : Résistez à la tentation d’exécuter zpool upgrade parce que c’est suggéré.
Ce message est ZFS qui vous propose poliment un piège de portabilité.
Tâche 10 : Auditer les propriétés de dataset qui tendent à activer des fonctionnalités non portables
cr0x@server:~$ sudo zfs get -r -o name,property,value -s local encryption,keystatus,special_small_blocks,xattr,recordsize backup
NAME PROPERTY VALUE
backup encryption off
backup keystatus -
backup special_small_blocks 0
backup xattr sa
backup recordsize 128K
backup/vm encryption aes-256-gcm
backup/vm keystatus available
backup/vm special_small_blocks 16K
backup/vm xattr sa
backup/vm recordsize 16K
Sens de la sortie : Vous avez des datasets chiffrés et des comportements d’allocation spéciaux. Ce sont des déclencheurs courants d’activation de fonctionnalités.
Décision : Si le site récepteur/DR ne peut pas supporter le chiffrement ou les fonctionnalités de vdev spécialisées, vous avez besoin d’un plan de migration qui les évite
(nouvelle organisation de datasets, ou upgrade du récepteur).
Tâche 11 : Déterminer si votre flux de réplication exigera des fonctionnalités plus récentes (dry run)
cr0x@server:~$ sudo zfs send -nP backup/vm@daily-2025-12-25
size 26.4G
incremental backup/vm@daily-2025-12-24 backup/vm@daily-2025-12-25
Décision : Un dry run confirme que le flux existe et donne la taille. Ensuite, décidez si vous devez utiliser le send raw pour le chiffrement
(ce qui implique un support de fonctionnalités sur le récepteur) ou si vous pouvez répliquer en clair (ce qui change votre modèle de menace).
Tâche 12 : Utiliser une cible de receive contrôlée et tester l’import sur le système « plus ancien »
cr0x@server:~$ sudo zfs send -R backup/vm@daily-2025-12-25 | ssh dr-old 'sudo zfs receive -uF drpool/test-vm'
receiving full stream of backup/vm@daily-2025-12-25 into drpool/test-vm@daily-2025-12-25
received 26.4G stream in 00:12:41 (35.4M/sec)
Sens de la sortie : Le receive a réussi, et le dataset n’est pas monté (-u), ce qui est bon pour une validation contrôlée.
Décision : Testez maintenant si drpool peut être exporté/importé sur ce système plus ancien sans erreurs de fonctionnalités.
Si c’est le cas, vous avez une voie de portabilité compatible : migrer par réplication, pas en déplaçant des disques.
Tâche 13 : Vérifier la dérive d’activation des fonctionnalités dans le temps (attraper « quelqu’un l’a activé »)
cr0x@server:~$ sudo zpool get -H -o property,value all backup | awk -F'\t' '/feature@/ && $2=="active"{print $1}' | sort | head
feature@allocation_classes
feature@embedded_data
feature@extensible_dataset
feature@spacemap_histogram
Décision : Intégrez ceci dans la surveillance ou un rapport quotidien. Si la liste change, traitez‑la comme une dérive de schéma dans une base de données :
enquêtez sur qui/quoi a changé le comportement, et si les hypothèses de portabilité tiennent toujours.
Tâche 14 : Confirmer les fonctionnalités supportées par l’hôte « plus ancien » avant de promettre quoi que ce soit
cr0x@server:~$ zpool get -H -o property,value all | grep feature@ | head
feature@async_destroy enabled
feature@empty_bpobj active
feature@lz4_compress active
feature@spacemap_histogram -
feature@extensible_dataset -
feature@embedded_data -
Décision : Si vous voyez - pour des fonctionnalités actives sur le pool que vous devez déplacer, arrêtez.
Soit vous mettez à niveau cet hôte, soit vous acceptez qu’il ne soit pas une cible d’import valide.
Tâche 15 : Exporter proprement avant de déplacer le matériel (éviter la confusion « en cours d’utilisation »)
cr0x@server:~$ sudo zpool export backup
cr0x@server:~$ zpool import | grep -A2 'pool: backup'
pool: backup
id: 998877665544332211
state: ONLINE
Sens de la sortie : Un export propre détache le pool afin que le prochain import soit une action délibérée, pas une prise de contrôle confuse.
Décision : Faites de « exporter avant de déplacer » une exigence de contrôle de changement. Cela réduit l’ambiguïté en récupération et facilite ensuite le diagnostic.
Tâche 16 : Si vous devez importer un pool qui était « en cours d’utilisation », utilisez prudemment les flags d’import sûrs
cr0x@server:~$ sudo zpool import -f backup
cannot import 'backup': unsupported version or feature
Décision : -f peut outrepasser les vérifications « en cours d’utilisation ». Il ne peut pas outrepasser les « fonctionnalités non prises en charge ».
Si quelqu’un suggère « retentez -f », vous avez la permission de clore la réunion.
Trois mini-récits d’entreprise depuis le terrain
Mini-récit 1 : L’incident causé par une mauvaise hypothèse
Une entreprise de taille moyenne avait deux serveurs de stockage : un en production, un en labo qui servait aussi de « DR si on s’arrange ».
L’équipe traitait leur pool ZFS comme une infrastructure portable : même modèle de châssis, même HBA, même câblage, donc déplacer les disques devrait fonctionner.
Ils l’avaient fait une fois, des mois plus tôt. Ça « avait marché », donc c’est devenu une procédure.
Lors d’un week-end de maintenance, l’hôte de production a été remplacé par une image OS plus récente. Quelqu’un a remarqué un avertissement anodin :
« Some supported features are not enabled on the pool. » Ils ont lancé zpool upgrade pour régler ça.
Le pool est resté en ligne. Rien n’a explosé. Tout le monde est rentré chez soi en se sentant responsable.
Deux semaines plus tard, la production a eu une panne de carte mère. L’équipe a roulé les disques dans l’hôte de labo pour restaurer les services.
L’import a échoué avec « unsupported feature(s). » Le ZFS du labo était plus ancien ; il ne comprenait pas les fonctionnalités activées.
Le plan n’était pas mauvais parce que ZFS est pointilleux. Le plan était mauvais parce qu’il reposait sur une hypothèse non documentée : « les pools ZFS sont portables entre nos hôtes. »
La correction a été péniblement peu glorieuse : ils ont mis à niveau le ZFS du labo pour correspondre à la production (après validation du support des modules noyau),
ont importé le pool, puis planifié une vraie reconstruction DR où la réplication, pas le déplacement de disques, serait la méthode de récupération.
Le meilleur : le postmortem a montré que le zpool upgrade initial n’était pas nécessaire pour une fonctionnalité métier.
C’était une action cosmétique qui s’est transformée en multiplicateur d’incidents.
Mini-récit 2 : L’optimisation qui s’est retournée contre eux
Un groupe d’ingénierie des données gérait un cluster d’analytics sur ZFS. Ils adoraient les tweaks de performance comme certains aiment de nouveaux couteaux de cuisine.
Un ingénieur a activé quelques propriétés pour améliorer les métadonnées et les petits I/O : xattr=sa, records plus petits pour des datasets type VM,
et plus tard un vdev spécial pour les métadonnées et petits blocs. Les benchmarks étaient excellents. Les graphiques de latence p99 ont enfin arrêté de les gêner.
Puis ils ont décidé de répliquer le pool vers un système DR plus petit et moins coûteux. Le serveur DR utilisait une distribution différente et accusait du retard sur la version OpenZFS.
La réplication initiale a marché pour les datasets simples. Dès qu’ils ont inclus les datasets « optimisés », le côté receive a commencé à échouer de manière étrange.
Même lorsque la réplication réussissait, le test d’import côté DR échouait : des fonctionnalités liées aux classes d’allocation et au comportement de vdev spécial posaient problème.
Ce qui s’est retourné contre eux n’était pas l’optimisation en soi — c’était l’hypothèse organisationnelle que le DR avait les mêmes capacités que la production.
L’ingénieur avait amélioré la production en activant des fonctionnalités qui avaient en fait élevé le dialecte ZFS minimum nécessaire pour interpréter le pool.
Le DR n’était pas conçu pour ce dialecte.
Leur correction à long terme a été d’arrêter de traiter le DR comme une réflexion après coup et de standardiser le support des fonctionnalités ZFS entre les niveaux.
À court terme, ils ont créé un pool contraint en compatibilité sur le DR et ont changé le périmètre de réplication : n’envoyer que les datasets compatibles avec le profil DR,
et garder les datasets « sophistiqués » sur un pool séparé avec un plan DR incluant la mise à niveau de la cible. L’optimisation qui a mal tourné est devenue une leçon d’architecture :
les fonctionnalités de performance sont aussi des décisions de portabilité.
Mini-récit 3 : La pratique ennuyeuse mais correcte qui a sauvé la mise
Une entreprise SaaS avait une politique qui agaçait tout le monde : les pools de stockage devaient être étiquetés avec un « environnement d’import minimum ».
Avant toute mise à niveau ZFS ou changement de fonctionnalité du pool, l’ingénieur d’astreinte devait exécuter un audit rapide de compatibilité et coller la sortie dans la demande de changement.
Cela ressemblait à du théâtre bureaucratique. Jusqu’au jour où ça ne l’était plus.
Lors d’un rafraîchissement urgent de matériel, un ingénieur a remarqué que les nouveaux hôtes étaient sur une release OpenZFS plus récente et voulait « tout upgrader pendant qu’on y est ».
Le template de changement exigeait de lister les flags de fonctionnalités qui seraient activés et de comparer avec l’hôte de repli le plus ancien.
L’audit a montré que l’upgrade activerait des fonctionnalités non supportées par le système de repli.
Ils ont fait le choix impopulaire : ne pas lancer zpool upgrade pendant le rafraîchissement. Les services ont migré normalement.
Deux jours plus tard, une régression d’un pilote réseau sur les nouveaux hôtes a forcé un rollback temporaire vers l’environnement ancien.
Parce que les pools n’avaient pas été upgradés, le rollback a été une danse standard d’export/import, pas une prise d’otage par flags de fonctionnalités.
L’incident n’est jamais devenu une panne visible par les clients, et personne n’a fait la fête. C’est le but.
La pratique était ennuyeuse, un peu pénible, et exactement ce à quoi ressemble la fiabilité dans de vraies entreprises.
Erreurs courantes (symptôme → cause → correction)
1) Symptôme : « cannot import ‘POOL’: unsupported version or feature »
Cause racine : Le pool a des fonctionnalités actives que l’hôte actuel ne supporte pas.
Correction : Importer sur un hôte avec un OpenZFS plus récent/compatible qui supporte ces fonctionnalités ; puis migrer via zfs send/receive vers un pool compatible, ou upgrader le ZFS de l’ancien hôte.
2) Symptôme : la liste « unsupported feature(s): … » contient des entrées com.delphix:*
Cause racine : Le système d’import est trop ancien (ou a une build ZFS sans ces fonctionnalités), fréquent sur des appliances anciennes ou des distros conservatrices.
Correction : Standardisez une baseline OpenZFS minimale entre les systèmes qui doivent partager des pools, ou arrêtez de déplacer les disques et passez à une migration basée sur la réplication.
3) Symptôme : vous pouvez importer en production mais pas en DR
Cause racine : Le DR est en retard sur les fonctionnalités ZFS ; un changement de propriété de dataset a activé des fonctionnalités en production.
Correction : Soit upgrader le DR pour correspondre aux fonctionnalités de production, soit redessiner la réplication pour atterrir sur un pool contraint en compatibilité créé pour les capacités du DR.
4) Symptôme : quelqu’un dit « lancez zpool upgrade, c’est recommandé »
Cause racine : Confusion entre « recommandé » et « requis ». ZFS vous indique que de nouvelles fonctionnalités existent, pas que vous en avez besoin.
Correction : Faites de zpool upgrade un changement contrôlé avec une évaluation explicite d’impact de compatibilité et un plan de rollback.
5) Symptôme : après activation du chiffrement, les hôtes plus anciens ne peuvent pas importer ou recevoir
Cause racine : Le chiffrement repose sur des flags de fonctionnalités et introduit aussi des différences de gestion des clés ; la réplication peut demander le send raw et des fonctionnalités compatibles.
Correction : Validez le support des fonctionnalités de chiffrement sur tous les points d’import/receive avant d’activer. Si vous devez supporter des points plus anciens, chiffrez à un autre niveau ou upgradez les endpoints.
6) Symptôme : le pool s’importe, mais les outils se comportent étrangement selon les systèmes
Cause racine : Versions userland/module noyau mélangées, ou support partiel des fonctionnalités/backports.
Correction : Alignez les versions userland et kernel module ZFS ; traitez ZFS comme une unité, pas comme un menu de paquets.
7) Symptôme : « zpool import » montre le pool mais l’état est UNAVAIL avec « unsupported feature(s) » et aussi des périphériques manquants
Cause racine : Deux problèmes à la fois : visibilité vdev incomplète plus décalage de fonctionnalités. Les gens courent après le mauvais problème en premier.
Correction : Confirmez d’abord la visibilité des disques (chemins by-id), puis gérez le support des fonctionnalités. Si les fonctionnalités sont non supportées, aucun câblage ne résoudra le problème.
8) Symptôme : la réplication réussit, mais le test d’import du pool reçu échoue ailleurs
Cause racine : Vous avez prouvé le send/receive entre deux systèmes, pas la portabilité vers le troisième système. Le pool reçu peut aussi avoir activé des fonctionnalités.
Correction : Ajoutez une étape de test d’import sur la plateforme la plus ancienne requise comme porte dans le processus de migration.
Listes de contrôle / plan étape par étape
Checklist A : Avant de migrer un pool en déplaçant des disques
-
Identifiez le système le plus ancien qui doit importer le pool.
Si vous ne pouvez pas le nommer, présumez qu’il est plus ancien que ce que vous souhaitez. -
Sur le système source, inventorie des fonctionnalités actives.
Capturezzpool get all | grep feature@et joignez cette sortie à l’enregistrement de changement. -
Sur le système destination, inventorie les fonctionnalités supportées.
Tout-pour une fonctionnalité active sur le pool signifie « pas d’import ». -
Faites un export contrôlé.
Exportez avant de déplacer le matériel pour éviter des états « en cours d’utilisation » sales et une propriété ambiguë. -
Ayez un « hôte d’import connu bon » prêt.
Un environnement de secours avec un OpenZFS récent peut vous sauver quand la destination est trop vieille.
Checklist B : Lors de la création d’un pool destiné à être portable
- Définissez une baseline de portabilité. Exemple : « doit s’importer sur OpenZFS 2.1 sous Linux et FreeBSD » (ce que votre flotte exécute réellement).
- Utilisez des profils de compatibilité si votre plateforme les supporte. Sinon, documentez « ne pas upgrader les fonctionnalités » et faites respecter par le processus.
- Séparez les fonctionnalités expérimentales dans des pools distincts. Isolez le rayon d’action comme pour des migrations de schéma bêta.
- Standardisez les versions ZFS entre environnements. Production et DR ne devraient pas exécuter des sets de fonctionnalités majeurs différents sauf si vous aimez le risque.
- Automatisez la détection de dérive des fonctionnalités. Si les fonctionnalités actives changent, alertez et enquêtez.
Checklist C : Plan de migration qui évite les pièges de portabilité par flags (recommandé)
-
Créez un nouveau pool cible qui correspond à votre baseline requise.
Utilisez des contraintes de compatibilité si disponibles ; sinon, utilisez un hôte avec le ZFS baseline pour créer le pool et ne l’upgradez jamais. -
Répliquez avec
zfs send/receiveet validez.
Envoyez les datasets par étapes ; testez les montages et le comportement des applications. -
Testez l’import sur le système le plus ancien requis.
Exportez/importez le nouveau pool sur ce système comme une vraie porte, pas une expérience de pensée. -
Coupez et laissez l’ancien pool en lecture seule pendant une courte fenêtre.
Cela vous donne un rollback plus sûr que « renverser toute la migration ». -
Ce n’est qu’après cela que vous envisagez d’activer de nouvelles fonctionnalités.
Traitez l’activation comme un changement d’API qui casse la compatibilité.
Checklist D : Que faire quand vous êtes déjà bloqué
- N’essayez pas sans cesse des flags d’import au hasard. Les fonctionnalités non prises en charge ne céderont pas à la persistance.
- Trouvez un hôte compatible (ou un environnement de démarrage) qui supporte les fonctionnalités requises. Importez là‑bas.
- Remettez le métier en ligne en utilisant l’hôte compatible si nécessaire. Stabilisez d’abord ; migrez ensuite.
- Planifiez la migration vers un pool portable via la réplication. C’est la « rétrogradation » que vous pouvez réellement effectuer.
- Après la récupération, ajoutez des garde‑fous. Surveillance de la dérive des fonctionnalités et upgrades contrôlés pour éviter les répétitions.
FAQ
1) Les flags de fonctionnalités ZFS sont-ils la même chose que la « version du pool » ?
Non. Les versions de pool étaient un numéro unique de compatibilité. Les flags de fonctionnalités sont des capacités individuelles qui peuvent être activées/actives indépendamment.
Les problèmes de portabilité existent toujours ; ils sont simplement plus granulaires maintenant.
2) Si je ne lance jamais zpool upgrade, suis‑je à l’abri ?
Plus sûr, pas invulnérable. Certaines fonctionnalités peuvent devenir actives via des opérations normales ou des changements de propriété (chiffrement, allocation spéciale, etc.).
« Ne pas upgrader » est nécessaire dans certains environnements, mais ce n’est pas suffisant sans audit.
3) Puis‑je désactiver un flag après qu’il soit devenu actif ?
Généralement non. La plupart des fonctionnalités sont effectivement irréversibles sur un pool en ligne. Le chemin pratique est de migrer les données vers un nouveau pool créé avec l’ensemble de fonctionnalités souhaité.
4) L’import en lecture seule contourne-t‑il les fonctionnalités non prises en charge ?
Non. Si le système d’import ne peut pas interpréter les structures sur disque en toute sécurité, ZFS refusera même un import en lecture seule.
5) Quelle est la différence entre « enabled » et « active » dans les listes de fonctionnalités ?
Enabled signifie que le pool est autorisé à utiliser la fonctionnalité ; active signifie que le pool l’a effectivement utilisée et en dépend maintenant.
Active est la contrainte de portabilité la plus importante, mais enabled peut aussi importer selon la fonctionnalité et l’implémentation.
6) Puis‑je répliquer d’un pool avec de nouvelles fonctionnalités vers un système plus ancien ?
Parfois. La compatibilité de zfs send/receive dépend des fonctionnalités de dataset présentes dans le flux et de ce que le récepteur supporte.
Le chiffrement et certaines métadonnées peuvent forcer le récepteur à supporter des flags plus récents.
7) Pourquoi l’erreur d’import mentionne‑t‑elle des fonctionnalités com.delphix:* ?
Ces noms proviennent des travaux initiaux sur les flags dans l’écosystème ZFS. Le nom ne signifie pas que vous utilisez des produits Delphix.
Cela signifie que votre ZFS d’import ne comprend pas des fonctionnalités que votre pool a utilisées.
8) Quelle est la meilleure règle opérationnelle pour une flotte mixte ?
Choisissez un ensemble de fonctionnalités OpenZFS de référence et traitez‑le comme un contrat d’API. Construisez les pools selon cette baseline et n’activez pas de fonctionnalités qui la dépassent
sauf si vous les isolez intentionnellement.
9) Déplacer des disques entre Linux et FreeBSD est‑il sûr si les deux disent « OpenZFS » ?
Ça peut l’être, mais uniquement si les sets de fonctionnalités correspondent. « OpenZFS » est un nom de famille, pas une garantie d’identique support des fonctionnalités.
Comparez toujours les fonctionnalités supportées, pas seulement le branding de l’OS.
10) Que dois‑je stocker dans les enregistrements de changement pour la portabilité ZFS ?
Au minimum : zfs version, la liste des fonctionnalités du pool (zpool get all | grep feature@), et la liste des fonctionnalités supportées par le système de destination.
Si vous ne pouvez pas démontrer la compatibilité en texte, vous n’avez pas de compatibilité.
Conclusion : prochaines étapes à réaliser cette semaine
Les flags de fonctionnalités ne sont pas un défaut de ZFS. Ce sont un contrat. Soit vous gérez ce contrat, soit vous le violez accidentellement et ZFS refuse de coopérer.
Le refus est le système de fichiers qui vous rend service — juste au pire moment possible.
- Inventoriez les versions ZFS de votre flotte. Notez ce qui est exécuté où, y compris les boîtes DR et labo qui deviennent soudain « production ».
- Choisissez une baseline de portabilité. Le système le plus ancien sur lequel vous devez vraiment importer fixe le plafond pour les fonctionnalités.
- Mettez en place une étape d’audit des fonctionnalités avant les upgrades ou migrations. Capturez les fonctionnalités du pool et comparez-les aux fonctionnalités supportées de la cible.
- Arrêtez de déplacer les pools comme méthode par défaut de migration. Préférez la réplication vers un pool créé avec des contraintes de compatibilité explicites.
- Surveillez la dérive des fonctionnalités. Si l’ensemble actif change, traitez‑le comme un changement casse‑compatibilité et enquêtez immédiatement.
Si vous ne faites rien d’autre : arrêtez d’exécuter zpool upgrade parce qu’un message d’état l’a suggéré. Mettez à niveau délibérément, avec une cible de compatibilité,
ou acceptez que vous brûlez le pont derrière vous. ZFS s’en souviendra. Votre rotation d’astreinte aussi.