Aller au contenu principal

Kubernetes - Démarrage rapide

Prérequis pour suivre ce tutoriel

Afin de profiter des fonctionnalités de gestion de cluster Kubernetes depuis la plateforme NumSpot, les prérequis sont:

  • Un compte utilisateur NumSpot détenant le rôle Kubernetes Admin.
  • Ce compte devant être rattaché à un espace NumSpot.

Pré-requis

Les interactions avec l'API HTTP de NumSpot nécessitent d'être authentifié par un jeton d'accès (Access Token) dans une région et un espace donné. Il est donc nécessaire de préparer un environnement d'exécution en conséquence. Cet environnement sera utilisé par les commandes fournies dans ce document.

Préparation de l'environnement d'exécution
export REGION="eu-west-2"
export SPACE_ID="8e9cbfeb-573d-4f77-97c2-b7301f38bd2f"
export ACCESS_TOKEN="myaccesstoken"

De plus, certaines des commandes fournies à titre d'exemple dans ce document utilisent l'application jq. Il est donc nécessaire que cet outil soit disponible dans l'environnement d'exécution.

Créer mon premier cluster

Pour commencer, nous allons créer un cluster Kubernetes en utilisant l'API HTTP de NumSpot depuis la région standard (eu-west-2), ceci afin de limiter les coûts engendrés par les ressources déployées.

Notre premier cluster contiendra un groupe de nœuds (Nodepool) se composant de deux nodes de type verysmall (disposant de caractéristiques spécifiques).

Pour plus de facilité, nous choisirons la dernière version disponible de l'offre Kubernetes de NumSpot. Celle-ci peut être récupérée en se référant à la documentation sur les versions disponibles.

Enfin, nous utiliserons le CIDR 10.1.0.0/16 pour adresser nos machines virtuelles. Il est possible de choisir un CIDR sous la forme 10.X.0.0/16, pour plus de détails se référer à l'article sur le choix du CIDR.

Exemple de requête: Création d'un cluster Kubernetes
curl -X POST https://api.$REGION.numspot.com/kubernetes/spaces/$SPACE_ID/clusters \
--header "Authorization: Bearer $ACCESS_TOKEN" \
--header 'Content-Type: application/json' \
--data '{
"name": "my-first-cluster",
"cidr": "10.1.0.0/16",
"version": "1.29.5",
"nodeProfile": "verysmall",
"nodeCount": 3
}' \
| export OPERATION_ID=$(jq -r .id) && export CLUSTER_ID=$(jq -r .clusterid)
remarque

Dans la commande précédente, nous avons utilisé la commande jq pour récupérer:

  • OPERATION_ID : identifiant de l'operation retournée par la requête de création de cluster, qui nous servira lorsqu'on voudra suivre l'exécution de la création du cluster
  • CLUSTER_ID : identifiant du cluster en cours de création, qui nous servira pour opérer différentes actions une fois le cluster créé

La requête retournée donne les informations de l'operation lancée, à savoir la création d'un cluster.

Exemple de réponse: Création d'un cluster Kubernetes
{
"id": "4784f323-e98d-4d48-bf07-8fc6378a2a07",
"operationType": "CreateCluster",
"status": "PENDING",
"target": "https://..../kubernetes/spaces/8e9cbfeb-573d-4f77-97c2-b7301f38bd2f/clusters/3fa85f64-5717-4562-b3fc-2c963f66afa6",
"selfLink": "https://..../spaces/8e9cbfeb-573d-4f77-97c2-b7301f38bd2f/operations/4784f323-e98d-4d48-bf07-8fc6378a2a07",
"targetName": "my-first-cluster",
"clusterid": "3fa85f64-5717-4562-b3fc-2c963f66afa6",
...
}

Tracer l'operation de création du cluster en cours

Nous pouvons vérifier l'état de notre operation en exécutant une requête qui récupère les détails de l'operation à partir de son identifiant (stocké dans la variable d'environnement OPERATION_ID).

Exemple de requête: Récupérer les informations d'une operation
curl -X GET https://api.$REGION.numspot.com/kubernetes/spaces/$SPACE_ID/operations/$OPERATION_ID \
--header "Authorization: Bearer $ACCESS_TOKEN" \
--header 'Accept: application/json'
Exemple de réponse: Récupérer les informations d'une operation
{
"id": "4784f323-e98d-4d48-bf07-8fc6378a2a07",
"operationType": "CreateCluster",
"status": "PENDING",
"target": "https://..../kubernetes/spaces/8e9cbfeb-573d-4f77-97c2-b7301f38bd2f/clusters/3fa85f64-5717-4562-b3fc-2c963f66afa6",
"selfLink": "https://..../spaces/8e9cbfeb-573d-4f77-97c2-b7301f38bd2f/operations/4784f323-e98d-4d48-bf07-8fc6378a2a07",
"targetName": "my-first-cluster",
"clusterid": "3fa85f64-5717-4562-b3fc-2c963f66afa6",
...
}

On peut remarquer que l'operation contient une propriété operationType indiquant l'action de l'operation. Dans notre cas, son type est CreateCluster, indiquant que l'operation est une création de cluster Kubernetes.

La propriété status d'une operation indique l'état d'avancement de celle-ci. Les différentes valeurs possibles sont :

  • PENDING: l'operation est en attente d'être exécutée.
  • RUNNING: l'operation est en cours d’exécution.
  • INTERRUPTED: l'operation a été interrompue par des processus d'administration de NumSpot.
  • FAILED: l'operation a rencontré un problème technique durant l'exécution et a échouée.
  • DONE: l'operation est terminée avec succès.

Tant que l'operation n'est pas terminée (INTERRUPTED, FAILED ou DONE), continuez à la surveiller avec cette même requête. Si la propriété status devient DONE, félicitations : vous avez enfin votre premier cluster Kubernetes prêt à être utilisé.

Vérifier l'état du cluster Kubernetes

Une fois le cluster créé, il est important de vérifier qu'il soit dans un état exploitable.

Exemple de requête: Récupérer l'état du cluster et de ses workers
curl -X GET https://api.$REGION.numspot.com/kubernetes/spaces/$SPACE_ID/clusters/$CLUSTER_ID/state \
--header "Authorization: Bearer $ACCESS_TOKEN" \
--header 'Content-Type: application/json'
Exemple de réponse: Récupérer les informations d'un cluster Kubernetes
{
"name": "my-first-cluster",
"health": "OK",
"nodes": [
{
"name": "worker1",
"status": "OK",
"cpu": {
"used": "2000m",
"available": "92m"
},
"memory": {
"used": "102400Ki",
"available": "3633016Ki"
}
}
{
"name": "worker2",
"status": "OK",
"cpu": {
"used": "2000m",
"available": "147m"
},
"memory": {
"used": "102400Ki",
"available": "3633016Ki"
}
}
{
"name": "worker3",
"status": "OK",
"cpu": {
"used": "2000m",
"available": "114m"
},
"memory": {
"used": "102400Ki",
"available": "3633016Ki"
}
}
]
}

On retrouve dans le corps de la réponse la propriété nodes, donnant des informations sur chaque nœud utilisable par l'utilisateur. Un nœud, identifiable par son nom (name), est fonctionnel lorsque la propriété status est à OK. Dans notre cas, les 3 nœuds que nous avions demandés lors de la création sont bel et bien utilisables dans le cluster.

Accéder au cluster

Pour utiliser le cluster au travers de l'invite de commande kubectl, il est nécessaire de se munir des éléments suivants:

  • URL de l'API Kubernetes
  • fichier kubeconfig d'accès au cluster
  • IP du bastion SSH et sa clé privée autorisant l'accès au réseau du cluster

Récupérer l'URL de l'API Kubernetes et l'IP du bastion

L'URL de l'API Kubernetes ainsi que l'IP du bastion SSH sont exposées dans les informations du cluster.

Exemple de requête: Récupérer les informations du cluster
curl -X GET https://api.$REGION.numspot.com/kubernetes/spaces/$SPACE_ID/clusters/$CLUSTER_ID \
--header "Authorization: Bearer $ACCESS_TOKEN" \
--header 'Content-Type: application/json'

La propriété urls.[0].api contient l'URL de l'API Kubernetes. La propriété clientBastionPublicIP contient l'adresse IP du bastion SSH.

Exemple de réponse: Récupérer les informations d'un cluster
{
"id": "5953ed12-062e-4f16-a49f-7ca242f00c18",
"version": "1.29.5",
"clientBastionPublicIP": "80.247.12.251",
...
"urls": [
{
"api": "internal-lbm-910bd3953029-840420822.cloudgouv-eu-west-1.lbu.outscale.com"
}
]
}

Pour simplifier les exemples suivants, stockez ces deux informations respectivement dans les variables d'environnement kubernetesApiHost et clientBastionPublicIP.

Sauvegarder les informations pour les exemples suivants
export kubernetesApiHost="url-kubernetes-api"
export clientBastionPublicIP="ip-du-bastion"

Récupérer les fichiers

Dans cette étape, nous allons récupérer deux fichiers, la clé privée SSH (PrivateKey) autorisant l'accès au réseau du cluster, ainsi que le fichier kubeconfig contenant les informations d'authentification à l'API Kubernetes.

Nous allons d'abord récupérer la clé privée SSH du bastion.

Exemple de requête: Récupérer la clé privée SSH du bastion
curl -X GET https://api.$REGION.numspot.com/kubernetes/spaces/$SPACE_ID/clusters/$CLUSTER_ID/privatekey \
--header "Authorization: Bearer $ACCESS_TOKEN" \
--header 'Content-Type: application/octet-stream'

Le contenu devra être stocké dans un fichier que l'on nommera de manière arbitraire privatekey.rsa. Ce fichier nécessite des permissions particulières pouvants être attribuées avec la commande suivante:

chmod 0600 privatekey.rsa

Nous allons ensuite, avec le même processus, récupérer le fichier kubeconfig:

Exemple de requête: Récupérer le fichier kubeconfig du cluster
curl -X GET https://api.$REGION.numspot.com/kubernetes/spaces/$SPACE_ID/clusters/$CLUSTER_ID/kubeconfig \
--header "Authorization: Bearer $ACCESS_TOKEN" \
--header 'Content-Type: application/octet-stream'

Le contenu devra être stocké dans un fichier que l'on nommera de manière arbitraire kubeconfig.yaml.

Préparer le fichier kubeconfig

Dans le fichier kubeconfig.yaml, remplacer la propriété server par https://127.0.0.1:6443.

Connexion avec le bastion du cluster

Afin d'atteindre l'API du cluster, il est nécessaire d'avoir un accès au réseau des machines du cluster. Pour ce faire, nous allons initier une connexion vers le bastion SSH afin de rediriger les commandes kubectl vers le cluster.

Exemple de commande: Connexion vers le bastion SSH
ssh-keyscan $clientBastionPublicIP >> ~/.ssh/known_hosts
ssh -i privatekey.rsa -o IdentitiesOnly=yes -l client-tunnel -L 127.0.0.1:6443:$kubernetesApiHost:6443 -N $clientBastionPublicIP &

Tester la connection

Une fois la connexion établie, définir la variable d'environnement KUBECONFIG en utilisant le chemin de kubeconfig:

Exemple de commande: Définir le fichier kubeconfig à utiliser
export KUBECONFIG=$PWD/kubeconfig

Verifiez que le cluster est accessible avec kubectl en utilisant la commande suivante:

Exemple de commande: Récupérer les versions Kubernetes du client kubectl et du cluster
kubectl version

La réponse de la commande doit comprendre la version de l'API Kubernetes du cluster:

Exemple de réponse: Récupérer les versions de Kubernetes client et serveur
Client Version: v1.X.X
...
Server Version: v1.29.5

Créer un premier déploiement

Une fois la connexion avec le cluster fonctionnelle, nous allons pouvoir déployer notre première application.

Créez un fichier deployments.yaml avec le contenu suivant.

apiVersion: apps/v1
kind: Deployment
metadata:
name: nginx-deployment
labels:
app: nginx
spec:
selector:
matchLabels:
app: nginx
replicas: 3
template:
metadata:
labels:
app: nginx
spec:
containers:
- name: nginx
image: nginx:1.27.0
ports:
- containerPort: 80

Pour déployer cette ressource, il suffit d’exécuter:

Créer une ressource
kubectl create deployment -f deployments.yaml

La demande de création de déploiement a été validée et est en train d'être exécutée par Kubernetes.

Nous allons vérifier que le pod correspondant au déploiement est fonctionnel. Pour cela, il est nécessaire de connaître l'état du pod (readinessProbe et livenessProbe) depuis la ligne de commande suivante:

Retrouver la liste des pods filtrés par le label de déploiement
kubectl get pods -l app=nginx

Vérifions que le pod du déploiement est correctement déployé et fonctionnel en nous référant à la valeur présente sous la colonne READY. Si 1/1 est rapporté, le pod est fonctionnel. Si une autre valeur est rapportée, vérifiez la valeur de la colonne STATUS.

Liste des pods
NAME                                 READY   STATUS    RESTARTS   AGE
nginx-56d947767c-2948z 1/1 Running 0 2d11h

Voilà, votre première application est correctement déployée et prête à recevoir des requêtes.

Augmenter le nombre de worker du cluster

Conformément aux paramètres fournis lors de notre demande de création de cluster, le cluster contient actuellement 2 workers. Nous allons en ajouter 2 afin d'en avoir 4 au total.

Rappelons-nous que nous avons demandé des profils de workers verysmall.

Exemple de requête: Ajouter des workers dans un cluster
curl -X POST https://api.$REGION.numspot.com/kubernetes/spaces/$SPACE_ID/clusters/workers/add \
--header "Authorization: Bearer $ACCESS_TOKEN" \
--header 'Content-Type: application/json' \
--data '{
"nodeCount": 2,
"nodeProfile": "verysmall",
}'

La requête renvoit les informations de l'operation lancée.

Exemple de réponse: Ajouter des workers dans un cluster
{
"clusterId": "3fa85f64-5717-4562-b3fc-2c963f66afa6",
"id": "680d2446-dc82-4a98-8b6b-71f3f982acaa",
"operationType": "AddWorkers",
"status": "PENDING",
"targetLink": "https://..../spaces/8e9cbfeb-573d-4f77-97c2-b7301f38bd2f/clusters/3fa85f64-5717-4562-b3fc-2c963f66afa6",
"selfLink": "https://..../spaces/8e9cbfeb-573d-4f77-97c2-b7301f38bd2f/operations/680d2446-dc82-4a98-8b6b-71f3f982acaa",
...
}

Pour rappel, on peut suivre la bonne exécution de l'operation.

remarque

Pensez à mettre à jour la valeur de la variable d'environnement OPERATION_ID.

En effet, cette nouvelle operation a produit un nouvel identifiant différent de celui de l'operation de création du cluster.

Exemple de requête: Récupérer les informations d'une operation
curl -X GET /kubernetes/spaces/$SPACE_ID/operations/$OPERATION_ID \
--header "Authorization: Bearer $ACCESS_TOKEN" \
--header 'Accept: application/json'