Docker – gitlab-runner conteneurisé et dind

J’ai choisi de mettre en place l’intégration continue avec un gitlab-runner conteneurisé et Docker in docker (Dind) pour lancer les commandes docker.

L’avantage du gitlab-runner conteneurisé est de ne pas se soucier de l’installation sur le système hôte qui effectue la construction. Gitlab-runner est un processus client qui communique avec le serveur gitlab afin de récupérer les constructions à faire.

Docker in docker permet de démarrer un démon docker (docker engine) vierge auquel va se connecter le docker CLI (ou docker-compose) pour lancer les conteneurs. Les 2 grosses flèches dans le schémas suivant signifient « lance un processus »

Gitlab-runner en service

Le démon gitlab-runner est lancé en service docker via docker-compose. Dans un repertoire disons runner créer le fichier docker-compose.yml suivant:

version: "3.7"
services:
    docker:
        image: 'gitlab/gitlab-runner:alpine'
        restart: always
        volumes:
            - '/srv/gitlab-runner/config:/etc/gitlab-runner'
            - '/var/run/docker.sock:/var/run/docker.sock'

Le premier volume permet de rendre persistant la configuration tandis que le second permet de se connecter au démon docker de l’hôte. Ainsi le gitlab-runner va pouvoir lancer des conteneurs frères via docker CLI.

Lancer le service par

docker-compose up -d

Il faut ensuite connecter le runner avec gitlab. Pour cela la documentation du gitlab-runner conteneurisé propose de lancer un autre conteneur temporaire qui partage le même répertoire de config persistant sur l’hôte. A par de montrer que les conteneurs peuvent partager un même repertoire, je trouve que cela complique la compréhension. Il est plus simple de se connecter au conteneur que l’on vient de lancer et d’y effectuer la tâche d’administration consistant à enregistrer un nouveau runner.

le démon gitlab-runner peut gérer plusieurs runner.

Determiner le nom du conteneur en faisant un

docker ps

La sortie doit contenir une ligne de la forme

746a1ebc7908 gitlab/gitlab-runner:alpine "/usr/bin/dumb-init …" 3 days ago Up 3 days runner_docker_1

Disposant de cette information, on peut lancer un shell dans le conteneur par

docker exec -it runner_docker_1 bash

On dispose alors d’un shell en tant que root. On doit y entrer la commande:

gitlab-runner register -n --url \n

https://gitlab.bressure.net \n

--registration-token xxxxxxx-yyyyyyy \n

--executor docker \n

--description 'docker runner' \n

--docker-image 'docker:18.09.06' \n

--docker-privileged

et renseigner les informations obligatoires suivantes

  • serveur gitlab: https://gitlab.bressure.net
  • token de connexion: voir dans l’admin du serveur gitlab pour obtenir un token pour un runner partagé
  • type de d’executor: docker
  • image par defaut: docker:18.09.06
  • utiliser le mode privilégié

Construction docker-compose

L’application est un blog worpdress composée d’un service wordpress et d’un service mysql. Pour mémoire voici son fichier docker-compose.yml

version: '3.3'

services:
   db:
     image: mysql:5.7
     volumes:
       - db_data:/var/lib/mysql
     restart: always
     environment:
       MYSQL_ROOT_PASSWORD: somewordpress
       MYSQL_DATABASE: wordpress
       MYSQL_USER: wordpress
       MYSQL_PASSWORD: wordpress

   wordpress:
     depends_on:
       - db
     image: wordpress:latest
     volumes:
       - www_data:/var/www/html
     ports:
       - "8180:80"
     restart: always
     environment:
       WORDPRESS_DB_HOST: db:3306
       WORDPRESS_DB_USER: wordpress
       WORDPRESS_DB_PASSWORD: wordpress
       WORDPRESS_DB_NAME: wordpress
volumes:
    db_data: {}
    www_data: {}

Comme il n’y a pas d’utilisation d’image docker personnalisées, la construction se limite la phase de test pour vérifier que l’application démarre. On utilise donc l’image docker/compose pour lancer principalement la commande docker-compose up

Voici le fichier CI de gitlab pour le projet blog

 image:
    name: docker/compose:1.24.0
    entrypoint: [""]



 before_script:
   - docker info
   - docker-compose version

 

 run_blog:
   stage: test
   tags:
     - docker
   variables:
    # For non-Kubernetes executors, we use tcp://docker:2375/
    DOCKER_HOST: tcp://docker:2375/
    # When using dind, it's wise to use the overlayfs driver for
    # improved performance.
    DOCKER_DRIVER: overlay2

   services:
     - docker:dind     
   script:
     - echo "run blog for testing"
     - docker-compose up -d
     - docker-compose ps

                         
    

Performances

Ce premier essai avec Dind révèle une première caractéristique. Chaque lancement d’une construction semble utiliser un nouveau conteneur docker. En tout cas il n’y a aucune persistance des images téléchargées. Ainsi à chaque exécution déclenchée par une modification de source (ici le fichier docker-compose.yml) les images de wordpress et mysql sont téléchargées. Avec ma connexion cela prend 5 minutes à chaque fois !

L’utilisation d’un proxy par le démon docker (dockerd) pourra être une solution que je mettrai en œuvre dans le prochain billet qui sera aussi l’occasion de faire du déploiement automatisé en environnement de préprod.

 

Laisser un commentaire

Votre adresse de messagerie ne sera pas publiée. Les champs obligatoires sont indiqués avec *

Ce site utilise Akismet pour réduire les indésirables. En savoir plus sur comment les données de vos commentaires sont utilisées.