Baptiste Foucher
le 

Donnez des ailes à votre Gitlab CI

3 minutes de lecture

train.jpeg

Depuis bientôt 1 an, nous utilisons Gitlab CI à l'agence et nous en sommes pleinement satisfaits.

Cependant avec l'arrivée de nouveaux projets et l'accumulation de tests fonctionnels (Behat/ Selenium), nous avons subi des tests de plus en plus longs au point de nous sentir ralentis dans le développement.

Nous vous partageons donc quelques petites optimisations pour réduire grandement la durée de vos builds !

Partager le cache composer entre vos jobs

Avec Docker nos containers ne gardent aucune trace des précédentes exécutions si bien qu'à chaque nouvelle série de tests, il télécharge toutes les dépendances sur les dépôts distants ce qui prend rapidement 1 à 2 min suivant l'ampleur du projet.

L'idée est de monter un répertoire de l’hôte pour chaque container afin d'y stocker tout le cache de composer et ainsi réduire considérablement la durée d'installation et le trafic réseau.

Il nous suffit de modifier le fichier de config de gitlab-runner :

1    # /etc/gitlab-runner/config.toml
2    [[runners]]
3     [...]
4      environment = ["COMPOSER_CACHE_DIR=/cache-ci/composer"]
5      executor = "docker"
6      [runners.docker]
7       [...]
8        volumes = ["/cache", "/cache-ci:/cache-ci:rw"]

J'ai fait le choix ici de créer un répertoire /cache-ci sur l'hote que je monte au même emplacement dans les runners. J'ajoute ensuite la variable COMPOSER_CACHE_DIR=/cache-ci/composer qui sera injectée dans chaque job ; puis composer utilisera ainsi par défaut ce répertoire comme cache.

Idem pour npm et yarn

Même opération pour npm et yarn :

1    # /etc/gitlab-runner/config.toml
2    [[runners]]
3     [...]
4      environment = ["NPM_CONFIG_CACHE=/cache-ci/npm", "YARN_CACHE_FOLDER=/cache-ci/yarn"]
5      executor = "docker"
6      [runners.docker]
7       [...]
8        volumes = ["/cache", "/cache-ci:/cache-ci:rw"]

Utiliser la ram pour soulager les disques durs

Malgré un raid5 de disques SSD, nous avons rencontré un problème d'engorgement d'écriture sur les disques ralentissant grandement la rapidité de nos tests.

En contrepartie la ram de notre serveur était sous exploitée. N'ayant pas besoin de persister les données Docker car la durée de vie de nos containers n'est que de quelques minutes, nous avons décidé de stocker tous les containers et images Docker directement dans la ram.

Nous avons commencé par créer un répertoire /docker-data puis nous l'avons monté dans la ram avec tmpfs.

1    # /etc/fstab
2    tmpfs /var/lib/docker tmpfs defaults,size=150000M 0 0

Ensuite il suffit d'activer ce point de montage :

1    $ mount -a

Maintenant indiquons à Docker d'utiliser ce nouveau point de stockage par défaut :

1    #  /etc/default/docker
2    export DOCKER_TMPDIR="/docker-data"

Et redémarrez docker pour prendre en compte ces changements.

Attention cependant si vous utilisez d'autres services avec Docker il vous faudra créer un second socket Docker avec une autre config pour éviter de perdre toutes vos données en cas de plantage ou redémarrage de la machine.

Avant disk-before.jpeg cpu-before.jpeg

Après disk-after.jpeg cpu-after.jpeg


Avec ces petites optimisations nous avons réduit par 2 ou 3 la durée de nos tests tout en nous permettant d'en lancer 3 à 4 fois plus en même temps !

N'hésitez pas à nous faire vos retours et / ou à nous poser vos questions sous cet article. On sera ravis de pouvoir vous aider !