Conteneuriser son application Laravel avec Docker

Publié le 23 mai 2024 par William Suppo
Couverture de l'article Conteneuriser son application Laravel avec Docker

Voici notre premier article au sujet de la conteneurisation avec Docker de notre application où nous allons découvrir la création d'une image système à travers le Dockerfile.

Écriture du Dockerfile

Tout d'abord, veuillez à disposer de Docker sur votre système.

Si vous êtes un utilisateur Linux, nous vous proposons ce tutoriel d'installation de Laravel Justu

Une fois Docker installé, nous allons écrire un Dockerfile, c'est un document contenant une suite de directives qui permet à Docker d’injecter, dans une image, les services dont a besoin notre application pour fonctionner. Il faut s'imaginer notre image résultante comme celle d'un système à part entière dans lequel on aurait installé un serveur web (Apache, Nginx, Caddy) ainsi que php et les extensions nécessaires.

Un Dockerfile s’appuie très souvent sur une image déjà construite, nous allons baser le nôtre sur l’image officielle de php qui embarque le serveur web Apache.

À savoir qu'il existe des versions de l'image dédiées à d'autres usages comme la ligne de commande

Rentrons dans le vif du sujet et écrivons notre première directive qui indique notre héritage à l'image php :

1FROM php:8.3-apache

À ce stade nous disposons que de PHP et Apache, mais probablement que notre application dépend de librairies et d'extensions PHP particulières. Voici comment installer quelques-unes des dépendances les plus communes :

1# Install system dependencies
2RUN apt-get update && apt-get install -y \
3 git \
4 curl \
5 libpng-dev \
6 libjpeg-dev \
7 libfreetype6-dev \
8 libonig-dev \
9 libxml2-dev \
10 libpq-dev \
11 libzip-dev \
12 libcurl4-openssl-dev \
13 zip \
14 unzip \
15 default-mysql-client
16 
17# Install PHP extensions
18RUN docker-php-ext-configure gd --with-freetype --with-jpeg \
19 && docker-php-ext-install pdo pdo_mysql mbstring exif pcntl bcmath gd zip curl intl

Afin que le serveur web Apache fonctionne correctement, nous allons devoir créer un fichier de config adapté que l'on nommera vhost.conf :

1<VirtualHost *:80>
2 DocumentRoot /app/public
3 
4 <Directory "/app">
5 AllowOverride all
6 Require all granted
7 </Directory>
8 
9 ErrorLog ${APACHE_LOG_DIR}/error.log
10 CustomLog ${APACHE_LOG_DIR}/access.log combined
11</VirtualHost>

Maintenant que nous avons notre fichier de config, il est nécessaire d'indiquer à Docker de le copier en lieu et place de la config par défaut :

1# Copy vhost config
2COPY vhost.conf /etc/apache2/sites-available/000-default.conf

Ensuite, pour permettre une bonne interprétation des URL, il est nécessaire d'activer le mode rewrite d'Apache :

1# Enable Apache mods
2RUN a2enmod rewrite

Continuons avec l'installation de composer afin de pouvoir gérer les paquets dont dépend notre application :

1# Get latest Composer
2RUN php -r "readfile('http://getcomposer.org/installer');" | php -- --install-dir=/usr/bin/ --filename=composer

Enfin, afin d’éviter les problèmes de permissions avec les fichiers auto-générés par l'application, comme les fichiers de cache et de logs, nous allons créer un utilisateur dédié qui aura le même id que celui que l'on utilise sur notre hôte, id que l'on va rendre configurable via l’argument WWW_USER :

1ARG WWW_USER=1000
2 
3# Create user
4RUN groupadd --force -g $WWW_USER webapp
5RUN useradd -ms /bin/bash --no-user-group -g $WWW_USER -u $WWW_USER webapp
6 
7USER ${WWW_USER}

Et voilà, nous avons terminé nos instructions, voici le Dockerfile complet :

1FROM php:8.3-apache
2 
3ARG WWW_USER=1000
4 
5# Set working directory
6WORKDIR /app
7 
8# Install system dependencies
9RUN apt-get update && apt-get install -y \
10 git \
11 curl \
12 libpng-dev \
13 libjpeg-dev \
14 libfreetype6-dev \
15 libonig-dev \
16 libxml2-dev \
17 libpq-dev \
18 libzip-dev \
19 libcurl4-openssl-dev \
20 zip \
21 unzip \
22 default-mysql-client
23 
24# Install PHP extensions
25RUN docker-php-ext-configure gd --with-freetype --with-jpeg \
26 && docker-php-ext-install pdo pdo_mysql mbstring exif pcntl bcmath gd zip curl intl
27 
28# Copy vhost config
29COPY vhost.conf /etc/apache2/sites-available/000-default.conf
30 
31# Enable Apache mods
32RUN a2enmod rewrite
33 
34# Get latest Composer
35RUN php -r "readfile('http://getcomposer.org/installer');" | php -- --install-dir=/usr/bin/ --filename=composer
36 
37# Create user
38RUN groupadd --force -g $WWW_USER webapp
39RUN useradd -ms /bin/bash --no-user-group -g $WWW_USER -u $WWW_USER webapp
40 
41# Clean cache
42RUN apt-get -y autoremove \
43 && apt-get clean \
44 && rm -rf /var/lib/apt/lists/* /tmp/* /var/tmp/*
45 
46USER ${WWW_USER}

Lancer un conteneur Docker depuis notre image

Pour la suite, on admet que les fichiers Dockerfile et vhost.conf sont à la racine de votre projet Laravel. Nous allons commencer par construire notre image depuis le Dockerfile en lui apposant un tag, le tout via la commande :

1docker build -t app:1.0 .

Revenons sur un détail qui peut être important, si l'id de votre utilisateur sur l'hôte n'est pas 1000, il va être nécessaire de le préciser lors de la construction de l'image, donc utilisez plutôt la commande suivante en adaptant la valeur de WWW_USER :

1docker build --build-arg WWW_USER=1001 -t app:1.0 .

Maintenant, il nous reste à lancer un conteneur depuis notre image afin de pouvoir accéder à notre application. Pour cela, on va monter dans le conteneur le code source de notre app via l'option -v $(pwd):/app et lier le port 8080 de notre hôte au port 80 du conteneur, port par lequel Apache répond aux requêtes, via l'option -p 8080:80 :

1docker run --name app -v $(pwd):/app -p 8080:80 -d app:1.0

Enfin, si on souhaite arrêter et supprimer notre conteneur, voici la commande :

1docker stop app
2docker rm app

Nous voilà à la fin de ce premier tutoriel sur la conteneurisation de notre application qui se destine plus à un usage en local que pour un usage en prod. Il serait opportun de réduire la taille de notre image en y ajoutant uniquement ce qui est nécessaire.

William Suppo avatar
William Suppo
Je mange du PHP au p'tit dej', et vous ?

A lire

Autres articles de la même catégorie