Maîtriser les conteneurs Dev dans VS Code
Créez des environnements de développement cohérents, portables et reproductibles à l'aide des conteneurs de développement.
Les développeurs se heurtent souvent au dilemme « fonctionne sur ma machine » en raison de désaccords de dépendances, de versions d’outils ou de différences d’OS.
Dev Containers dans Visual Studio Code (VS Code) résolvent cela de manière élégante — en vous permettant de développer dans un environnement conteneurisé configuré spécifiquement pour votre projet.
Le développement logiciel moderne exige des environnements cohérents et reproductibles qui fonctionnent sur toutes les machines et systèmes d’exploitation. Que vous travailliez sur un projet de science des données en Python, une application web en Node.js ou un microservice en Go, assurer que chaque membre de l’équipe a un environnement de développement identique peut être un défi.
Ce guide complet vous explique ce sont les Dev Containers, pourquoi ils sont précieux et comment les configurer dans VS Code pour des flux de travail de développement portables et fluides. Vous apprendrez tout, des configurations de base aux configurations avancées avec Docker Compose et aux bonnes pratiques pour la collaboration d’équipe.
🧩 Qu’est-ce que les Dev Containers ?
Les Dev Containers sont une fonction fournie par l’extension VS Code Remote - Containers (maintenant partie de VS Code Remote Development).
Ils vous permettent d’ouvrir votre projet dans un conteneur Docker préconfiguré avec toutes vos dépendances, langages et outils.
Pensez-y comme :
“Un environnement de développement entièrement configuré, défini comme du code.”
Au lieu d’installer Python, Node.js, des bases de données et divers outils directement sur votre machine, vous les définissez dans des fichiers de configuration. Lorsque vous ouvrez le projet dans VS Code, il démarre automatiquement un conteneur avec tout ce qui est préinstallé et configuré exactement comme spécifié.
Une configuration de Dev Container typique inclut :
- Un Dockerfile ou une référence à une image de base (définissant le système d’exploitation du conteneur, les langages et les outils)
- Un fichier
devcontainer.json
(configurant les paramètres de l’espace de travail, les extensions VS Code, le transfert de ports, les variables d’environnement et les commandes de démarrage) - Un docker-compose.yml optionnel si votre projet dépend de plusieurs services (comme des bases de données, Redis, des files d’attente de messages, etc.)
⚙️ Pourquoi utiliser les Dev Containers ?
Voici ce qui les rend puissants :
-
Reproductibilité : Chaque développeur et chaque système CI utilise exactement le même environnement. Plus de problèmes comme « ça fonctionne sur ma machine mais pas sur la vôtre ». Ce qui fonctionne sur votre ordinateur fonctionnera exactement de la même manière sur l’ordinateur de votre collègue, qu’il s’agisse d’un Windows, d’un Mac ou d’un ordinateur Linux.
-
Isolation : Aucun besoin de polluer votre machine locale avec des dépendances conflictuelles. Travailler sur plusieurs projets nécessitant différentes versions de Python, Node.js ou d’autres outils sans conflits de version ou sans jongler avec des environnements virtuels.
-
Portabilité : Fonctionne sur tout OS qui prend en charge Docker. Votre environnement de développement voyage avec votre code. Clonez un dépôt, ouvrez-le dans VS Code, et vous êtes prêt à coder en quelques minutes — indépendamment de votre système d’exploitation.
-
Consistance d’équipe : Une configuration partagée à travers toute votre équipe. Les nouveaux membres de l’équipe peuvent être opérationnels en quelques minutes au lieu de passer des heures (ou des jours) à configurer leur environnement de développement avec les bons outils et versions.
-
Automatisation : Installe automatiquement les extensions VS Code, les dépendances linguistiques et les outils lors de l’ouverture du projet. Les commandes post-creation peuvent exécuter des migrations de base de données, insérer des données ou effectuer d’autres tâches de configuration sans intervention manuelle.
-
Sécurité : Isoler les dépendances potentiellement risquées dans des conteneurs. Si vous avez besoin de tester avec une ancienne version vulnérable d’une bibliothèque, elle reste contenue et n’affecte pas votre système hôte.
Exemple concret : Imaginez rejoindre une équipe travaillant sur un projet de microservices qui utilise Python 3.11, PostgreSQL 15, Redis et Elasticsearch. Sans Dev Containers, vous passeriez des heures à installer et configurer chaque composant. Avec Dev Containers, vous ouvrez le projet dans VS Code, laissez-le construire le conteneur, et vous êtes en train d’écrire du code en 5 à 10 minutes.
🧱 Configuration d’un Dev Container dans VS Code
Allons-y étape par étape.
1. Installer les outils requis
Avant de commencer, assurez-vous que les éléments suivants sont installés :
-
Docker Desktop (ou un runtime conteneur équivalent comme Podman)
- Pour Windows/Mac : Téléchargez et installez Docker Desktop
- Pour Linux : Installez Docker Engine et assurez-vous que votre utilisateur fait partie du groupe docker
-
VS Code (version la plus récente recommandée)
-
L’extension Dev Containers (par Microsoft)
- Ouvrez VS Code
- Allez dans Extensions (
Ctrl+Shift+X
ouCmd+Shift+X
sur macOS) - Recherchez “Dev Containers”
- Installez l’extension avec l’ID :
ms-vscode-remote.remote-containers
Vérifiez votre configuration :
# Vérifiez que Docker est en cours d'exécution
docker --version
docker ps
# Devrait afficher la version Docker et les conteneurs en cours d'exécution (s'il y en a)
2. Initialiser le Dev Container
Ouvrez le dossier de votre projet dans VS Code
et ouvrez le Palette de commandes (Ctrl+Shift+P
ou Cmd+Shift+P
sur macOS), puis tapez et sélectionnez :
Dev Containers: Ajouter des fichiers de configuration Dev Container...
VS Code affichera une liste de modèles d’environnement prédéfinis. Choisissez celui qui correspond à votre projet :
- Node.js — Projets JavaScript/TypeScript
- Python — Sciences des données, applications web, scripts
- Go — Applications et services Go
- .NET — Applications C#/F#
- Java — Projets Spring Boot, Maven, Gradle
- Docker-in-Docker — Lorsque vous avez besoin de Docker à l’intérieur de votre conteneur
- Et bien plus encore…
Vous pouvez également sélectionner des fonctionnalités supplémentaires comme :
- Outils courants (git, curl, wget)
- Clients de base de données
- Outils CLI cloud (AWS, Azure, GCP)
Ce générateur crée un dossier .devcontainer
avec :
devcontainer.json
— Fichier de configuration principalDockerfile
— Définition d’image personnalisée (ou une référence à une image de base prédéfinie)
3. Personnaliser devcontainer.json
Le fichier devcontainer.json
est le lieu où tout se passe. Voici un exemple bien documenté pour un projet Node.js :
{
// Nom d'affichage du conteneur dans VS Code
"name": "Conteneur de développement Node.js",
// Configuration de construction - peut utiliser Dockerfile ou une image prédéfinie
"build": {
"dockerfile": "Dockerfile",
"context": ".."
},
// Alternative : utiliser une image prédéfinie au lieu d'un Dockerfile
// "image": "mcr.microsoft.com/devcontainers/javascript-node:18",
// Configuration de l'espace de travail
"customizations": {
"vscode": {
// Paramètres VS Code applicables dans le conteneur
"settings": {
"terminal.integrated.defaultProfile.linux": "bash",
"editor.formatOnSave": true,
"editor.defaultFormatter": "esbenp.prettier-vscode"
},
// Extensions à installer automatiquement
"extensions": [
"dbaeumer.vscode-eslint",
"esbenp.prettier-vscode",
"eamodio.gitlens",
"ms-azuretools.vscode-docker"
]
}
},
// Transfert de ports - rendre les ports du conteneur accessibles sur l'hôte
"forwardPorts": [3000, 5432],
"portsAttributes": {
"3000": {
"label": "Application",
"onAutoForward": "notify"
}
},
// Commandes à exécuter à différentes étapes
"postCreateCommand": "npm install", // Après la création du conteneur
"postStartCommand": "npm run dev", // Après le démarrage du conteneur
// Variables d'environnement
"containerEnv": {
"NODE_ENV": "développement",
"PORT": "3000"
},
// Exécuter le conteneur en tant qu'utilisateur non root (recommandé pour la sécurité)
"remoteUser": "node",
// Monter des volumes supplémentaires
"mounts": [
"source=${localEnv:HOME}/.ssh,target=/home/node/.ssh,readonly,type=bind"
]
}
Explication des options de configuration clés :
name
— Nom d’affichage affiché dans la barre d’état de VS Codebuild
/image
— Utiliser un Dockerfile ou une image prédéfiniecustomizations.vscode.extensions
— Extensions VS Code à installer automatiquementforwardPorts
— Ports à exposer depuis le conteneur vers l’hôtepostCreateCommand
— S’exécute une fois que le conteneur est créé (ex. :npm install
,pip install -r requirements.txt
)postStartCommand
— S’exécute chaque fois que le conteneur démarrecontainerEnv
— Variables d’environnement disponibles dans le conteneurremoteUser
— Compte utilisateur à utiliser à l’intérieur du conteneurmounts
— Fichiers/dossiers supplémentaires à monter (comme les clés SSH)
💡 Conseils pro :
- Utilisez
postCreateCommand
pour les opérations lentes (npm install, pip install) - Utilisez
postStartCommand
pour les tâches de démarrage rapides (migrations de base de données) - Spécifiez toujours les extensions nécessaires à votre projet — cela garantit un outillage cohérent
- Utilisez des variables d’environnement pour la configuration qui diffère entre les développeurs
4. Construire et ouvrir dans le conteneur
Une fois votre configuration prête, il est temps de lancer votre environnement de développement :
Ouvrez la Palette de commandes (Ctrl+Shift+P
/ Cmd+Shift+P
) et exécutez :
Dev Containers: Reouvrir dans le conteneur
Ce qui se passe ensuite :
-
Construction de l’image — VS Code construit l’image Docker basée sur votre Dockerfile ou tire une image prédéfinie. Cela peut prendre quelques minutes la première fois.
-
Création du conteneur — Docker crée un nouveau conteneur à partir de l’image construite.
-
Montage des volumes — Votre dossier de projet est monté dans le conteneur, rendant votre code accessible à l’intérieur.
-
Installation des extensions — Toutes les extensions VS Code spécifiées sont installées automatiquement dans le conteneur.
-
Commandes post-creation — Votre
postCreateCommand
s’exécute (ex. :npm install
,pip install -r requirements.txt
). -
Prêt ! — VS Code se reconnecte au conteneur, et vous êtes maintenant en développement à l’intérieur.
Vérifiez que vous êtes dans le conteneur :
Vous pouvez confirmer que vous travaillez à l’intérieur du conteneur en ouvrant un terminal et en exécutant :
# Vérifiez le système d'exploitation
uname -a
# Sortie : Linux ... (noyau du conteneur)
# Vérifiez le nom d'hôte (généralement l'ID du conteneur)
hostname
# Sortie : abc123def456
# Vérifiez les processus en cours d'exécution
ps aux
# Vous verrez les processus du conteneur, pas ceux de votre système hôte
Remarquez que la barre d’état de VS Code (en bas à gauche) affiche maintenant : Dev Container : [Nom de votre conteneur]
Commandes du cycle de vie du conteneur :
- Reconstruire le conteneur —
Dev Containers: Reconstruire le conteneur
(lorsque vous modifiez le Dockerfile) - Reconstruire sans cache —
Dev Containers: Reconstruire le conteneur sans cache
(pour une construction fraîche) - Reouvrir localement —
Dev Containers: Reouvrir le dossier localement
(quitter le conteneur, travailler sur l’hôte)
5. Ajouter des services supplémentaires (optionnel)
Les applications réelles dépendent souvent de bases de données, de couches de mise en cache, de files d’attente ou d’autres services. Vous pouvez utiliser Docker Compose pour orchestrer plusieurs conteneurs.
Exemple : Application full-stack avec Node.js, PostgreSQL et Redis
Créez un docker-compose.yml
dans votre dossier .devcontainer
:
version: "3.8"
services:
# Conteneur de développement principal
app:
build:
context: ..
dockerfile: .devcontainer/Dockerfile
volumes:
# Montage du dossier de projet
- ..:/workspace:cached
# Utilisez un volume nommé pour node_modules (meilleure performance)
- node_modules:/workspace/node_modules
# Gardez le conteneur en cours d'exécution
command: sleep infinity
# Accès réseau aux autres services
depends_on:
- db
- redis
environment:
DATABASE_URL: postgresql://dev:secret@db:5432/appdb
REDIS_URL: redis://redis:6379
# Base de données PostgreSQL
db:
image: postgres:15-alpine
restart: unless-stopped
volumes:
- postgres-data:/var/lib/postgresql/data
environment:
POSTGRES_USER: dev
POSTGRES_PASSWORD: secret
POSTGRES_DB: appdb
ports:
- "5432:5432"
# Cache Redis
redis:
image: redis:7-alpine
restart: unless-stopped
volumes:
- redis-data:/data
ports:
- "6379:6379"
volumes:
postgres-data:
redis-data:
node_modules:
Puis, mettez à jour votre devcontainer.json
pour utiliser Docker Compose :
{
"name": "Environnement de développement full-stack",
// Utilisez docker-compose au lieu d'un conteneur unique
"dockerComposeFile": "docker-compose.yml",
// Quel service utiliser comme conteneur de développement
"service": "app",
// Chemin vers le dossier de l'espace de travail à l'intérieur du conteneur
"workspaceFolder": "/workspace",
"customizations": {
"vscode": {
"extensions": [
"dbaeumer.vscode-eslint",
"esbenp.prettier-vscode",
"ms-azuretools.vscode-docker",
"ckolkman.vscode-postgres" // Client PostgreSQL
]
}
},
"forwardPorts": [3000, 5432, 6379],
"postCreateCommand": "npm install && npm run db:migrate",
"remoteUser": "node"
}
Ce que cette configuration fournit :
app
— Votre conteneur de développement avec Node.jsdb
— Base de données PostgreSQL, accessible àdb:5432
depuis votre applicationredis
— Cache Redis, accessible àredis:6379
- Volumes nommés — Persister les données de la base de données entre les redémarrages du conteneur
- Transfert de ports — Accédez à tous les services depuis votre machine hôte
Se connecter aux services depuis votre code :
// Dans votre application Node.js
const { Pool } = require('pg');
const redis = require('redis');
// Connexion à PostgreSQL
const pool = new Pool({
connectionString: process.env.DATABASE_URL
// Résout à : postgresql://dev:secret@db:5432/appdb
});
// Connexion à Redis
const redisClient = redis.createClient({
url: process.env.REDIS_URL
// Résout à : redis://redis:6379
});
Accéder aux services depuis votre machine hôte :
- App :
http://localhost:3000
- PostgreSQL :
localhost:5432
(en utilisant tout client PostgreSQL) - Redis :
localhost:6379
(en utilisantredis-cli
ou des outils graphiques)
Maintenant, lorsqu’on ouvre le projet dans VS Code, tous les services démarrent automatiquement !
🧠 Conseils avancés et bonnes pratiques
Utiliser des images préconstruites
Gagnez un temps de construction significatif en commençant par les images officielles de devcontainer de Microsoft :
{
"image": "mcr.microsoft.com/devcontainers/python:3.11",
"features": {
"ghcr.io/devcontainers/features/git:1": {},
"ghcr.io/devcontainers/features/github-cli:1": {}
}
}
Features sont des scripts d’installation réutilisables pour des outils courants (Git, GitHub CLI, Node, AWS CLI, etc.).
Bonnes pratiques de gestion de version
Commitez toujours votre dossier .devcontainer
:
git add .devcontainer/
git commit -m "Ajouter la configuration Dev Container"
git push
Cela garantit :
- ✅ Les nouveaux membres de l’équipe obtiennent automatiquement l’environnement
- ✅ Les changements d’environnement sont suivis et révisables
- ✅ Tout le monde développe dans la même configuration
Conseil pro : Ajoutez une section README expliquant la configuration du conteneur de développement :
## Configuration de développement
Ce projet utilise les Dev Containers de VS Code. Pour commencer :
1. Installez Docker Desktop et VS Code
2. Installez l'extension "Dev Containers"
3. Clonez ce dépôt
4. Ouvrez-le dans VS Code
5. Cliquez sur "Reouvrir dans le conteneur" lorsqu'on vous le demande
Débogage dans les conteneurs
Le débogage fonctionne sans problème. Configurez votre launch.json
comme d’habitude :
{
"version": "0.2.0",
"configurations": [
{
"name": "Lancer Node.js",
"type": "node",
"request": "launch",
"program": "${workspaceFolder}/index.js",
"skipFiles": ["<node_internals>/**"]
}
]
}
Définissez des points d’arrêt et déboguez normalement — VS Code gère automatiquement la connexion au conteneur.
Parité avec la CI/CD
Utilisez la même image de conteneur dans votre pipeline CI/CD :
# Exemple GitHub Actions
name: CI
on: [push, pull_request]
jobs:
test:
runs-on: ubuntu-latest
container:
image: mcr.microsoft.com/devcontainers/javascript-node:18
steps:
- uses: actions/checkout@v3
- run: npm install
- run: npm test
Cela garantit une parité dev/prod — si les tests passent localement, ils passeront en CI.
Optimisation des performances
Pour les utilisateurs macOS/Windows — utilisez des volumes nommés pour les dépendances :
{
"mounts": [
"source=myproject-node_modules,target=${containerWorkspaceFolder}/node_modules,type=volume"
]
}
Cela améliore significativement les performances d’E/S pour node_modules
, venv
, etc.
Développement multi-étapes
Créez différentes configurations pour différents rôles d’équipe :
.devcontainer/
├── devcontainer.json # Défaut (full-stack)
├── frontend/
│ └── devcontainer.json # Frontend uniquement (plus léger)
└── backend/
└── devcontainer.json # Backend uniquement (avec DB)
Les membres de l’équipe peuvent choisir leur environnement lorsqu’ils ouvrent le projet.
Travailler avec les clés SSH et Git
Montez vos clés SSH pour les opérations Git :
{
"mounts": [
"source=${localEnv:HOME}${localEnv:USERPROFILE}/.ssh,target=/home/node/.ssh,readonly,type=bind"
],
"postCreateCommand": "ssh-add ~/.ssh/id_ed25519 || true"
}
Fichiers d’environnement personnalisés
Chargez la configuration spécifique à l’environnement :
{
"runArgs": ["--env-file", ".devcontainer/.env"]
}
.devcontainer/.env
:
API_KEY=dev_key_here
DEBUG=true
LOG_LEVEL=debug
🔧 Résolution des problèmes courants
Le conteneur ne démarre pas
Erreur : Impossible de se connecter au démon Docker
Solution :
- Assurez-vous que Docker Desktop est en cours d’exécution
- Sur Linux, vérifiez :
sudo systemctl status docker
- Vérifiez que Docker est dans votre PATH :
docker --version
Performance lente sur macOS/Windows
Problème : Les opérations de fichiers sont lentes
Solutions :
-
Utilisez des volumes nommés pour
node_modules
,venv
, etc. -
Activez le partage de fichiers dans les paramètres de Docker Desktop
-
Considérez l’utilisation des options de montage
cached
oudelegated
:"workspaceMount": "source=${localWorkspaceFolder},target=/workspace,type=bind,consistency=cached"
Extensions non installées
Problème : Les extensions spécifiées dans devcontainer.json
ne s’installent pas
Solutions :
- Reconstruisez le conteneur :
Dev Containers: Reconstruire le conteneur
- Vérifiez que les identifiants d’extensions sont corrects
- Assurez-vous que les extensions prennent en charge les conteneurs distants (la plupart le font)
Port déjà utilisé
Erreur : Le port 3000 est déjà alloué
Solutions :
- Arrêtez les conteneurs en conflit :
docker ps
etdocker stop <conteneur>
- Changez le mappage des ports dans
forwardPorts
- Utilisez des ports dynamiques : VS Code attribuera automatiquement des ports disponibles
Les modifications du Dockerfile ne sont pas appliquées
Problème : Dockerfile modifié mais les changements ne s’affichent pas
Solution : Reconstruisez sans cache :
Dev Containers: Reconstruire le conteneur sans cache
Le conteneur s’arrête immédiatement
Problème : Le conteneur démarre puis s’arrête
Solution : Ajoutez une commande pour le maintenir en cours d’exécution dans docker-compose.yml
:
command: sleep infinity
Ou dans devcontainer.json
:
{
"overrideCommand": true
}
✅ Conclusion
Les Dev Containers dans VS Code apportent cohérence, simplicité et automatisation à votre flux de travail de développement. Ils transforment des configurations complexes et fragiles en environnements définis par le code qui fonctionnent, indépendamment de votre machine ou de votre système d’exploitation.
Points clés :
- 🎯 Éliminer les problèmes « fonctionne sur ma machine » — Tout le monde utilise des environnements identiques
- 🚀 Onboarding plus rapide — Les nouveaux membres de l’équipe sont productifs en quelques minutes, pas en jours
- 🔒 Meilleure sécurité — Isoler les dépendances de votre système hôte
- 📦 Portabilité — Votre environnement voyage avec votre code
- 🤝 Consistance d’équipe — Plus de conflits de versions de dépendances
- 🔄 Parité CI/CD — Utilisez la même image en développement et en intégration continue
Que vous travailliez sur un simple script Python ou une architecture complexe de microservices avec plusieurs bases de données, les Dev Containers offrent une base solide pour le développement moderne.
Si vous travaillez sur des projets multilingues, contribuez à des dépôts open source, onboarding fréquent de nouveaux développeurs ou souhaitez simplement des environnements de développement propres et reproductibles — les Dev Containers sont un outil indispensable dans votre stack.
Commencez petit : essayez les Dev Containers sur votre prochain projet. Une fois que vous aurez expérimenté les avantages, vous vous demanderez comment vous avez pu développer sans eux.
📚 Ressources utiles et articles liés
Documentation officielle :
- Documentation Microsoft Dev Containers
- Dev Container Images Repository — Images pré-construites pour divers langages et frameworks
- Dev Container Features — Extraits de configuration réutilisables pour les conteneurs de développement
Articles liés sur ce site :
- VSCode Cheatsheet — Raccourcis et commandes essentiels de VS Code
- Docker Cheatsheet — Référence des commandes Docker
- Docker Compose Cheatsheet — Orchestration de conteneurs multiples
- Python Cheatsheet — Référence du langage Python
- Installer Node.js — Guide d’installation de Node.js
- Go Cheatsheet — Référence du langage Go
- Popularité des langages de programmation et frameworks — Tendances technologiques et classements