Optimiser tes Dockerfile et la taille de tes images
Une image Docker trop grosse, c'est :
- des builds lents,
- des déploiements lents,
- des temps de démarrage parfois pénibles,
- plus de surface d'attaque côté sécurité.
Bonne nouvelle : avec quelques réflexes, tu peux déjà faire beaucoup mieux que les Dockerfile générés à l'arrache.
Choisir une bonne image de base
Premier levier : le FROM.
FROM node:22-alpine
Comparé à un node:22 classique (basé sur Debian), l'image Alpine est beaucoup plus légère.
Mais attention :
- Alpine utilise
muslet nonglibc→ certaines libs natives peuvent être plus chiantes à compiler, - pour des applis très complexes, tu peux préférer une
-slim(Debian allégée).
Règle simple :
- tente d'abord
*-alpineou*-slim, - si tu bloques sur des dépendances natives, reviens sur une image de base plus complète.
Multistage builds : builder d'un côté, runner de l'autre
Patron classique :
FROM node:22-alpine AS build
WORKDIR /app
COPY package*.json ./
RUN npm ci
COPY . .
RUN npm run build
FROM node:22-alpine AS runtime
WORKDIR /app
COPY --from=build /app/dist ./dist
COPY package*.json ./
RUN npm ci --omit=dev
CMD ["node", "dist/main.js"]
Idée :
- la phase
buildcontient tout ce qu'il faut pour compiler (devDependencies, outils, etc.), - la phase
runtimene reçoit que le code compilé + les deps nécessaires à l'exécution.
Résultat : image plus petite, et en général plus sécurisée.
Éviter les caches et fichiers inutiles
Quelques réflexes :
- Ajoute un
.dockerignore:
node_modules
.git
.cache
dist
Dockerfile*
docker-compose*.yml
- Nettoie les caches des gestionnaires de paquets si tu dois installer des dépendances :
RUN apk add --no-cache build-base python3
Sur Debian/Ubuntu :
RUN apt-get update \
&& apt-get install -y --no-install-recommends build-essential python3 \
&& rm -rf /var/lib/apt/lists/*
Minimiser le nombre de layers
Chaque RUN, COPY, ADD crée un layer. Ce n'est pas dramatique en soi, mais tu peux regrouper des commandes qui vont ensemble :
RUN apt-get update \
&& apt-get install -y --no-install-recommends build-essential python3 \
&& rm -rf /var/lib/apt/lists/*
Plutôt que :
RUN apt-get update
RUN apt-get install -y build-essential python3
RUN rm -rf /var/lib/apt/lists/*
Vérifier la taille et le contenu
Commande simple pour voir la taille de tes images :
docker image ls | sort -k 7 -h
Pour inspecter une image :
docker history mon-image:1.0.0
docker inspect mon-image:1.0.0
Tu peux aussi lancer une image en shell et regarder ce qu'il y a dedans :
docker run -it --rm mon-image:1.0.0 sh
Exemple : API Node.js optimisée
FROM node:22-alpine AS build
WORKDIR /app
COPY package*.json ./
RUN npm ci
COPY . .
RUN npm run build
FROM node:22-alpine AS runtime
WORKDIR /app
ENV NODE_ENV=production
COPY --from=build /app/dist ./dist
COPY package*.json ./
RUN npm ci --omit=dev
EXPOSE 3000
CMD ["node", "dist/main.js"]
Ce Dockerfile est déjà correct pour beaucoup de projets internes.
Ce qui reste à voir
Dans le dernier article de la série Docker, on parlera de :
- registry privé,
- stratégie de tags (prod/staging/feature),
- sécurité minimale (utilisateur non root, secrets),
- comment préparer sereinement le terrain pour un futur déploiement sur Kubernetes.