Ce challenge ne vous donne aucune commande ni aucun manifeste : il vous donne une application, un budget, cinq pannes à provoquer, et vous demande les preuves. Il s'adresse à qui a suivi les leçons Container Registry, premier cluster, pools, Ingress et stockage du volet, et veut savoir s'il saurait les enchaîner sans la page sous les yeux. Vous en repartirez avec une application livrée depuis votre registre, exposée par un seul répartiteur, dont les données et le service ont survécu à ce que vous leur avez fait subir, et un projet revenu à zéro. Le corrigé est replié en bas de page : ne l'ouvrez qu'après avoir livré, ou après une heure de blocage réel.
Ce que vous allez faire
Section intitulée « Ce que vous allez faire »- Publier une image dans un registre privé et la faire tirer par le cluster.
- Exposer deux composants derrière un seul Load Balancer, et le compter.
- Provoquer une montée en charge, une panne de nœud et la perte d'un pod.
- Démonter dans l'ordre qui ne laisse ni répartiteur ni volume facturé.
Le besoin
Section intitulée « Le besoin »L'outil interne de l'équipe passe en conteneurs : un composant web sans
état, servi à plusieurs exemplaires, et un composant data qui écrit sur un
disque et doit retrouver ses fichiers après n'importe quel redémarrage. Les
deux doivent être joignables depuis Internet sous un même nom, sur deux chemins
différents, et l'équipe refuse de payer un répartiteur par composant : le
dernier essai en avait fait naître trois, dont deux que personne n'avait
demandés.
Le trafic est irrégulier. La direction accepte de payer des nœuds
supplémentaires pendant les pics, pas après. Et l'incident de référence
reste la perte d'un nœud un vendredi soir : cette fois, le service doit y
survivre sans intervention, et les données de data doivent être là le
lundi.
Rien n'a besoin de survivre à la session, et surtout pas un Load Balancer que vos manifestes ne nomment jamais.
Les contraintes
Section intitulée « Les contraintes »Chaque contrainte a une preuve associée, et c'est la preuve qui compte, pas la
déclaration. Sur ce volet, la preuve la plus trompeuse est un docker pull
qui réussit grâce au cache, ou un kubectl delete qui rend la main sans que
le volume ait disparu.
| # | Contrainte | Preuve attendue |
|---|---|---|
| 1 | L'image de web est construite par vous et publiée dans un registre privé de la même région que le cluster | la liste du registre avec l'image et sa visibilité, et le refus de tirage depuis un poste non authentifié, cache vidé |
| 2 | Le cluster tire cette image sans secret de tirage | le pod en Running, et l'absence de tout imagePullSecret dans les manifestes |
| 3 | Un seul pool, avec l'autoscaling activé entre un minimum et un maximum que vous justifiez, et l'autoréparation activée | la fiche du pool avec ses trois réglages |
| 4 | web et data sont joignables depuis Internet sur deux chemins d'un même nom, et il n'existe qu'un seul Load Balancer dans le projet | les deux réponses, un contrôle négatif sur un chemin non routé, et la liste des Load Balancers du projet, longue d'une ligne |
| 5 | Une montée en charge provoque l'arrivée d'au moins un nœud, puis le pool redescend | le message du planificateur, la taille du pool avant, pendant, après, et le temps mesuré |
| 6 | Le service survit au remplacement d'un nœud qui porte un exemplaire de web | des requêtes qui continuent d'aboutir pendant l'opération, et la taille du pool inchangée après |
| 7 | Les données de data survivent à la suppression de son pod | un fichier écrit avant, relu après, et le temps de réattache |
| 8 | Le coût horaire reste sous 0,07 € au repos et sous 0,11 € au pic | votre calcul avant création, poste par poste, puis la consommation lue après |
| 9 | Le démontage ne laisse ni Load Balancer, ni volume Block, ni image derrière lui | la liste des Load Balancers, des volumes Block et des namespaces de registre, toutes vides |
Une dixième exigence se règle par une phrase : expliquez pourquoi le cluster n'a pas eu besoin de secret de tirage, et à partir de quel changement il en faudrait un.
Ce que vous devez livrer
Section intitulée « Ce que vous devez livrer »Un dossier de six éléments, lisibles par quelqu'un qui n'a pas assisté à la construction. Le format est libre, le contenu ne l'est pas.
- L'architecture, en un schéma ou un tableau : registre, cluster, pool et ses bornes, les deux composants, le contrôleur d'entrée, le volume, et pour chaque choix la raison.
- Les manifestes et le fichier de construction de l'image, tels que vous les avez appliqués.
- Les neuf preuves du tableau des contraintes, sous forme de sorties de commandes recopiées et datées.
- Les trois incidents racontés : la montée en charge, le remplacement du nœud, la perte du pod, avec ce que vous avez observé et mesuré.
- Le coût : votre calcul avant création à partir des prix relevés par la CLI, puis la consommation lue après.
- Trois réponses écrites : pourquoi aucun secret de tirage n'a été
nécessaire ; pourquoi la taille demandée pour le volume et la taille
provisionnée diffèrent ; pourquoi les
Servicepartent avant le cluster.
Comment vous auto-évaluer
Section intitulée « Comment vous auto-évaluer »La grille se lit ligne par ligne, et une ligne à zéro sur les contraintes 4, 7 ou 9 rend le reste secondaire : un répartiteur de trop, des données perdues ou un volume facturé après le démontage ne sont pas « presque » réussis.
| Critère | Ce qui vaut les points | Points |
|---|---|---|
| Contraintes 1 à 9 prouvées | chaque preuve est une sortie de commande, datée, reliée à la contrainte | 9 × 1,5 |
| Les trois incidents | observés, mesurés, et reliés à ce que la leçon annonçait | 3 |
| Les trois réponses | chacune s'appuie sur un fait d'une leçon, pas sur une intuition | 3 |
| Sobriété | aucune ressource créée qui ne serve une contrainte, budget tenu | 0,5 |
Seuil : 14 sur 20. En dessous, rejouez le challenge une semaine plus tard, sans relire le corrigé entre-temps. Au-dessus, vous êtes prêt pour la montée de version sous trafic, qui clôt le volet.
La solution, repliée
Section intitulée « La solution, repliée »N'ouvrez ce bloc qu'après avoir livré, ou après une heure de blocage réel. Il ne contient aucune commande ni aucun manifeste nouveau : chaque geste renvoie à la leçon qui l'a validée en lab, avec l'ancre exacte.
Le plan de construction, les pièges et l'ordre de destruction
Le registre d'abord, dans la région du cluster. Un namespace se crée en
moins d'une seconde, une image poussée est en inherit et suit la visibilité
du namespace ; hors de la même région, chaque tirage coûte 0,033 € par Go. La
preuve du refus de tirage exige de vider le cache d'abord, sinon un
docker pull en cache ne prouve aucun droit
(créer un namespace et y pousser une image,
où placer le registre par rapport au cluster,
qui peut tirer votre image).
Le cluster se crée en une commande, pool compris, et DEV1-S y est refusé
faute de mémoire : DEV1-M est le plus petit type retenu par les leçons, à
0,020196 € par heure. Un pool créé ainsi sort avec l'autoscaling et
l'autoréparation à false : les deux se demandent, et min-size comme
max-size n'ont d'effet qu'une fois l'autoscaling activé
(créer un cluster en une commande,
pourquoi certains types de nœuds sont refusés,
créer un pool autoscalé).
Aucun secret de tirage dans le même projet : l'authentification se fait au
niveau du nœud, hors des objets Kubernetes, et le secret redevient nécessaire
dès que le registre vit dans un autre projet, où le tirage échoue en
insufficient_scope. C'est la première réponse écrite
(un cluster a-t-il besoin d'un secret de tirage).
Un seul répartiteur, donc un contrôleur d'entrée et deux ClusterIP. Un
Service de type LoadBalancer fait naître un lb-s à 0,023 € par heure,
absent de vos manifestes ; un contrôleur Ingress en crée un seul quel que soit
le nombre de routes, ce que la leçon a compté : zéro, puis un, puis un encore
avec deux routes. Prouvez le routage avec un contenu unique par destination et
un contrôle négatif sur un chemin non routé
(Ingress ou Service LoadBalancer,
combien de Load Balancers chaque approche fait naître,
le mesurer avec son contrôle négatif).
Le volume de data reste Pending tant qu'aucun pod ne le consomme, et
rien n'est facturé avant : c'est WaitForFirstConsumer, pas une panne. La
classe par défaut suffit ; évitez sa jumelle -retain, dont le volume survit
au PVC. Demandez 5G et non 5Gi, sans quoi 5,37 Go décimaux sont
provisionnés, ce qui est la seconde réponse écrite. Les données survivent au
pod, réattache mesurée à 4 secondes, et le volume suit le pod d'un nœud à
l'autre dans la même zone
(quelle classe de stockage choisir,
pourquoi mon PVC reste-t-il Pending,
les données survivent-elles au pod).
La montée en charge se lit dans le planificateur, dont le dénominateur de
0/N nodes are available augmente à chaque nœud livré ; l'autoscaler a mis
175 secondes à fournir les nœuds manquants lors du lab. À max-size, rien ne
signale de panne : seuls des pods Pending et un pool à sa taille maximale.
La descente n'est pas immédiate, ce qui compte pour la contrainte 5
(ce que dit le planificateur,
quand l'autoscaler atteint son maximum,
faire redescendre le pool).
La perte d'un nœud se joue avec le remplacement, pas la suppression :
node replace rend le pool à sa taille en 125 secondes, node delete réduit
le pool d'un et ne remplace jamais. Le drain exige d'ignorer les DaemonSets,
et la disponibilité pendant l'opération se mesure avec des requêtes continues
(supprimer un nœud ou le remplacer,
le service survit-il au drain d'un nœud).
Le budget : deux DEV1-M au repos et quatre au pic, à 0,020196 € par
heure chacun, plus un lb-s à 0,023 €, soit environ 0,063 € par heure au
repos et 0,104 € au pic, plus le registre à 0,027 € par Go et par mois.
Le même cluster oublié un mois coûte environ 61 €
(combien coûte un cluster Kapsule).
L'ordre de destruction est la troisième réponse écrite. Les Service et
le contrôleur d'entrée partent avant le cluster, sinon le répartiteur reste
orphelin et facturé ; on les sélectionne sur leur type, jamais sur le
namespace, sous peine de supprimer coredns. Le PVC part ensuite, et sa
suppression se vérifie avec la liste des volumes Block, jamais avec le seul
kubectl delete. Le cluster, puis le namespace du registre, ferment la
session
(nettoyer, pools,
le contrôle qui rend la preuve valable).
À retenir
Section intitulée « À retenir »- Un registre dans la région du cluster, une image en
inherit, et un refus de tirage prouvé cache vidé. - Aucun secret de tirage dans le même projet : l'authentification est au niveau du nœud, et le secret redevient nécessaire dès l'autre projet.
DEV1-Sest refusé par Kapsule ;DEV1-Mà 0,020196 € par heure est le plus petit type retenu, et rien n'est automatique sans le demander.- Un contrôleur d'entrée fait naître un seul Load Balancer, un
Servicede typeLoadBalancerun par service, à 0,023 € par heure chacun. - Un PVC reste
Pendingsans consommateur,5Giprovisionne 5,37 Go, et les données survivent au pod avec une réattache de 4 secondes. node replacegarde la taille du pool,node deletela réduit ; l'autoscaler a mis 175 secondes à livrer ses nœuds.- Les
Servicepartent avant le cluster, et le volume se vérifie avec la liste Block : sinon répartiteur et volume survivent, facturés.
Pour aller plus loin
Section intitulée « Pour aller plus loin »- Bases de données managées : la carte du volet : le composant
datade ce challenge finit par mériter une base managée, et la carte dit laquelle. - PostgreSQL en réseau privé : sauvegarder, perdre, restaurer : la brique que ce cluster consommera, et son plan de reprise.
Ressources externes
Section intitulée « Ressources externes »- Documentation Kubernetes Kapsule : pools, autoscaling, versions et cycle de vie.
- Documentation Container Registry : namespaces, visibilité et tarification.
- Dépôt
scaleway/scaleway-csi: les classes de stockage et leur comportement, à la source.