Skip to content
← Tous les articles
· Delta1 Labs KeyrightAuto-hébergementExploitationMises à niveau

Mettre à niveau une instance Keyright auto-hébergée en toute sécurité : migrations, zéro interruption, rollback

Mettre à niveau Keyright auto-hébergé est sans drame, car l'application est sans état et exécute ses propres migrations de schéma au démarrage — aucun SQL à la main. Mais vous voulez tout de même une procédure sûre : sauvegardez Postgres d'abord, testez hors production, épinglez le tag d'image et mettez à niveau un nœud à la fois derrière votre répartiteur de charge. Voici la séquence, y compris pourquoi le rollback consiste à restaurer la sauvegarde de la base, pas à rétrograder contre une base déjà migrée.

Mettre à niveau une brique d’infrastructure de licences, cela sonne comme le genre de maintenance qu’on programme pour 2 h du matin en retenant son souffle. Keyright auto-hébergé est délibérément ennuyeux ici, et c’est tout l’intérêt. L’application est un conteneur sans état qui possède son propre schéma de base de données et le migre au démarrage ; une mise à niveau se résume donc le plus souvent à « récupérer une image plus récente et redémarrer ». Mais « le plus souvent » n’est pas « toujours », et un serveur de licences se trouve sur le chemin d’activation de vos clients ; vous voulez donc tout de même une procédure sûre, pas seulement rapide. Cet article est cette procédure — comment les mises à niveau fonctionnent réellement, la séquence sûre, comment la faire sans interruption sur plusieurs nœuds, et la seule chose à propos du rollback qui piège tout le monde.

À retenir : Les mises à niveau sont sans drame parce que l’application est sans état et applique ses migrations EF Core automatiquement au démarrage — aucun SQL à la main. La séquence sûre reste : sauvegardez Postgres d’abord, testez hors production, épinglez le tag d’image et mettez à niveau un nœud à la fois. Le rollback consiste à restaurer la sauvegarde de la base et redéployer l’ancien tag — les migrations vont vers l’avant, donc vous ne rétrogradez pas contre une base déjà migrée.

Comment fonctionne réellement une mise à niveau

Keyright a exactement deux pièces mobiles : une application sans état et votre base de données. Cette séparation est ce qui rend les mises à niveau simples.

L’application est l’image ghcr.io/delta1-labs/keyright — un service ASP.NET Core sur le port 8080, sans base de données à l’intérieur. Chaque version de l’application porte ses propres migrations de schéma compilées dans l’image. Au démarrage, elle se connecte au PostgreSQL vers lequel vous la pointez via KEYRIGHT_DB et exécute db.Database.Migrate() — le premier démarrage crée chaque table et amorce le locataire par défaut, et une mise à niveau n’applique que les migrations nouvelles. Vous n’exécutez jamais de SQL à la main et vous n’importez jamais de schéma. Une nouvelle version qui a besoin d’un changement de schéma apporte ce changement avec elle et l’applique dès qu’elle démarre.

Comme les migrations s’exécutent au démarrage, la base doit être joignable quand le nouveau conteneur démarre. L’endpoint de readiness rend cela sûr à automatiser : GET /health/ready vérifie la connectivité à la base et renvoie 503 jusqu’à ce que Postgres soit joignable et le schéma à jour, tandis que GET /health est un 200 de liveness statique. Branchez votre répartiteur de charge et votre orchestrateur sur /health/ready et un nœud ne recevra tout simplement pas de trafic tant qu’il n’a pas migré et n’est pas réellement prêt à servir. Si un nœud ne peut pas atteindre la base au démarrage, il sort et redémarre au lieu de monter à moitié cassé — une panne que vous voyez immédiatement, pas une qui laisse filtrer de mauvaises réponses.

La séquence sûre

Même si la mécanique tient en une étape, faites ces quatre-là dans l’ordre.

1. Sauvegardez PostgreSQL d’abord. C’est tout le filet de sécurité, car la voie propre pour revenir d’une mauvaise mise à niveau est une restauration de la base (voir plus bas). Prenez un pg_dump ou un snapshot managé juste avant de mettre à niveau, et confirmez que vous avez toujours votre KEYRIGHT_KEK et votre KEYRIGHT_SIGNING_KEY dans leur coffre à secrets séparé — la discipline complète est dans sauvegarder et restaurer une instance Keyright auto-hébergée. Une mise à niveau sans sauvegarde fraîche est une porte à sens unique.

2. Testez hors production. Restaurez une copie de la production dans une base de staging, pointez une instance de staging dessus sur le nouveau tag d’image, et laissez-la migrer. C’est là qu’une migration de schéma soit s’applique proprement contre des données de forme réelle, soit vous dit quelque chose que vous voulez savoir avant qu’elle ne touche la production. Faites un test de fumée de l’instance de staging (plus bas) et ne promouvez le tag qu’ensuite.

3. Déployez-la. Récupérez le nouveau tag épinglé et redémarrez. Sous Docker Compose :

docker compose pull
docker compose up -d

Compose recrée le conteneur depuis la nouvelle image ; il migre au démarrage et revient avec les mêmes KEYRIGHT_DB, KEYRIGHT_KEK et auto-licence. Sous Kubernetes avec le chart Helm, montez le tag d’image :

helm upgrade keyright delta1/keyright --reuse-values \
  --set image.tag=2.2.3

4. Vérifiez. Confirmez que la nouvelle version est active et toujours licenciée (voir la section de vérification plus bas).

Le guide d’exploitation propose cette même séquence sous forme de check-list concise à coller dans un runbook.

Mise à niveau progressive sans interruption

Si vous exécutez déjà deux ou trois nœuds pour la haute disponibilité, une mise à niveau cesse d’être une interruption. L’application est sans état et rétrocompatible au sein d’une ligne mineure, vous pouvez donc mettre à niveau une réplique à la fois pendant que le répartiteur continue de servir depuis les autres.

Le schéma est : sortez un nœud du pool, relancez-le sur le nouveau tag, attendez que GET /health/ready passe, puis passez au suivant. Comme il n’y a pas d’affinité de session — n’importe quel nœud peut répondre à n’importe quelle requête — rien n’est abandonné quand un nœud quitte le pool, et la concurrence reste sûre parce que les sièges et les crédits utilisent un check-and-deduct sérialisable dans Postgres, quel que soit le nœud qui traite la requête.

Sous Kubernetes, ce n’est qu’un RollingUpdate avec la sonde de readiness pointée sur /health/ready :

# values.yaml
replicaCount: 3
strategy:
  type: RollingUpdate
  rollingUpdate:
    maxUnavailable: 1   # une réplique à la fois
    maxSurge: 1
helm upgrade keyright delta1/keyright -f values.yaml --set image.tag=2.2.3

Kubernetes remplace un pod à la fois, chaque nouveau pod exécute ses migrations et ne rejoint le Service qu’une fois /health/ready au vert, et les anciens pods continuent de servir jusqu’à ce que leur remplaçant soit prêt. Vous pouvez le suivre avec kubectl rollout status deploy/keyright et mettre en pause ou annuler le déploiement du Deployment en cours de route si un nouveau pod ne devient jamais prêt — notez toutefois qu’annuler le déploiement ramène les pods, pas la base de données, ce qui compte pour l’histoire du rollback plus bas.

Un déploiement mono-nœud n’obtient pas cela gratuitement : docker compose up -d a une brève fenêtre de redémarrage pendant que l’unique conteneur se recrée et migre. Pour un serveur de licences c’est généralement acceptable, car les clients mettent en cache un lease signé et valident hors ligne entre les activations, donc un court redémarrage est absorbé par leur grâce — mais si vous voulez une maintenance réellement sans interruption, c’est l’argument pour exécuter deux nœuds.

Épinglez vos tags d’image

N’utilisez pas latest flottant. Épinglez une version concrète — image.tag=2.2.3 sous Helm, un tag explicite dans votre fichier Compose — pour que ce que vous avez testé en staging soit, octet pour octet, ce qui part en production, et qu’un pod replanifié à 3 h du matin n’aille pas récupérer discrètement une image plus récente que vous n’avez jamais validée. Les déploiements reproductibles font la différence entre une mise à niveau que vous avez effectuée et une qui vous est arrivée. La référence de configuration couvre l’épinglage des tags avec le reste des valeurs Helm ; cette même discipline d’épinglage est ce qui rend reproductibles les transferts d’image air-gapped quand vous portez un tarball à travers l’isolement.

Rollback : restaurez la sauvegarde, ne rétrogradez pas

Voici la partie à intérioriser. Les migrations vont vers l’avant. Une nouvelle version peut avoir modifié le schéma au démarrage, et l’ancienne image ne sait pas s’exécuter contre ce schéma plus récent. Vous ne faites donc pas de rollback en pointant l’ancien tag d’image vers une base déjà migrée — c’est le seul geste qui transforme une situation récupérable en un bazar.

Le rollback pris en charge est :

  1. Restaurez la sauvegarde PostgreSQL prise à l’étape un, ramenant le schéma et les données à leur état exact antérieur à la mise à niveau.
  2. Redéployez le tag d’image précédent contre la base restaurée.

Comme l’ancienne image et la base restaurée (ancien schéma) correspondent, l’instance remonte directement. C’est précisément pourquoi la séquence sûre commence par une sauvegarde et un test hors production : vous voulez attraper une mauvaise mise à niveau en staging, et si jamais elle atteint la production, vous voulez un point de restauration propre plutôt qu’un schéma à éditer à la main. (Sous Kubernetes, helm rollback ou kubectl rollout undo ramènent les pods à l’ancien tag — utile si la nouvelle image ne démarre tout simplement pas — mais ils ne ramènent pas la base, donc associez-les à une restauration de la base si une migration s’est déjà exécutée.)

Vérifiez après la mise à niveau

Trois contrôles confirment une bonne mise à niveau :

  • GET /health rapporte la nouvelle version et renvoie 200 — la nouvelle image est active et migrée.
  • GET /admin/self-license rapporte toujours votre édition et une phase active — Keyright est fail-closed, donc une KEYRIGHT_SELF_LICENSE valide doit toujours être présente après la mise à niveau, sinon chaque requête client renvoie 402. La clé ne change pas au fil d’une mise à niveau ; ce contrôle confirme seulement qu’elle a été reportée et que l’instance sert, et n’est pas bloquée. (/admin/self-diagnostics donne la même chose en un seul appel : version, migrations en attente et phase de licence.)
  • Un GET /v1/validate de test contre une licence connue renvoie un lease valide — la preuve que la clé de signature produit toujours des leases que vos clients acceptent de bout en bout.

Si les trois passent, la mise à niveau est faite et vous êtes toujours sur le chemin d’activation.

Où cela s’inscrit

Les mises à niveau sont la quatrième pièce de l’exploitation de Keyright auto-hébergé en production, aux côtés de la haute disponibilité, de la sauvegarde et récupération et de l’exploitation air-gapped. Comme Keyright est un seul produit dans les deux modes de déploiement, la forme application-sans-état-plus-votre-base-de-données — et donc toute cette histoire de mise à niveau — est identique que vous exécutiez un nœud sur un portable ou trois derrière un répartiteur de charge. Keyright auto-hébergé est tarifé par déploiement entre Standard, Pro et Enterprise (tarifs) ; les mises à niveau progressives sans interruption réclament les deux ou trois nœuds que couvrent Pro et Enterprise, mais la mécanique de migration-au-démarrage et la discipline de sauvegarde-d’abord sont les mêmes à chaque palier.

Essayez Nebula.NET

Renforcez votre code .NET en quelques minutes — commencez avec l'édition gratuite.