Tests d'intégration Go avec Docker : guide complet
\n\nLes tests d'intégration sont une étape critique du développement, en particulier dans le monde des microservices et des systèmes distribués. Go (Golang) combiné à Docker fournit des outils puissants et élégants pour créer des tests d'intégration fiables. Dans cet article, nous allons voir comment configurer l'environnement, écrire des tests pour interagir avec des bases de données et des services externes, en utilisant Docker, testcontainers-go et la bibliothèque standard testing.
1. Pourquoi Docker pour les tests d'intégration ?
\n\nLes tests unitaires traditionnels isolent la logique, mais ne vérifient pas l'interaction avec les dépendances réelles : bases de données, files d'attente, API. Docker résout ce problème en permettant :
\n- \n
- Isoler l'environnement : Chaque test lance un conteneur propre, éliminant les conflits d'état. \n
- Reproductibilité : Même environnement sur la machine locale et dans le CI/CD. \n
- Déploiement rapide : Les conteneurs se lancent en quelques secondes. \n
- Nettoyage facile : Après le test, le conteneur est détruit. \n
Nous utiliserons la bibliothèque testcontainers-go — elle fournit une API de haut niveau pour gérer le cycle de vie des conteneurs directement depuis le code des tests.
2. Configuration du projet et installation des dépendances
\n\nCréons un simple serveur HTTP en Go qui enregistre des données dans PostgreSQL. Ensuite, nous écrirons un test d'intégration vérifiant le point d'accès.
\n\nStructure du projet :
\nmyapp/\n├── main.go\n├── go.mod\n├── go.sum\n├── handlers/\n│ └── user.go\n└── integration_test.go\n\nÉtape 1 : Initialisons le module et installons testcontainers :
\ngo mod init myapp\ngo get github.com/testcontainers/testcontainers-go\ngo get github.com/testcontainers/testcontainers-go/modules/postgres\ngo get github.com/lib/pq\ngo get github.com/stretchr/testify/assert\n\nÉtape 2 : Écrivons un gestionnaire simple dans handlers/user.go :
package handlers\n\nimport (\n "database/sql"\n "encoding/json"\n "net/http"\n)\n\ntype User struct {\n Name string `json:"name"`\n Age int `json:"age"`\n}\n\nfunc CreateUser(db *sql.DB) http.HandlerFunc {\n return func(w http.ResponseWriter, r *http.Request) {\n var user User\n if err := json.NewDecoder(r.Body).Decode(&user); err != nil {\n http.Error(w, err.Error(), http.StatusBadRequest)\n return\n }\n _, err := db.Exec("INSERT INTO users (name, age) VALUES ($1, $2)", user.Name, user.Age)\n if err != nil {\n http.Error(w, err.Error(), http.StatusInternalServerError)\n return\n }\n w.WriteHeader(http.StatusCreated)\n json.NewEncoder(w).Encode(user)\n }\n}\n\n3. Écrire un test d'intégration avec Docker
\n\nVoici la partie la plus intéressante — un test qui démarre PostgreSQL dans Docker, crée la table, lance notre serveur et vérifie son fonctionnement.
\n\nFichier integration_test.go :
package myapp\n\nimport (\n "bytes"\n "context"\n "encoding/json"\n "net/http"\n "net/http/httptest"\n "testing"\n\n "myapp/handlers"\n\n "github.com/lib/pq"\n "github.com/stretchr/testify/assert"\n "github.com/testcontainers/testcontainers-go"\n "github.com/testcontainers/testcontainers-go/modules/postgres"\n "github.com/testcontainers/testcontainers-go/wait"\n)\n\nfunc TestCreateUserIntegration(t *testing.T) {\n ctx := context.Background()\n\n // 1. Démarrer le conteneur PostgreSQL\n pgContainer, err := postgres.RunContainer(ctx,\n testcontainers.WithImage("postgres:15-alpine"),\n postgres.WithDatabase("testdb"),\n postgres.WithUsername("test"),\n postgres.