Sviluppo web
Docker Compose per lo sviluppo: servizi, volumi e healthcheck
Un `compose.yaml` per database e applicazione: healthcheck, volumi che restano, override di team e il comando che cancella i dati senza chiedere.
In sintesi
- Il `compose.yaml` resta nel repository: due servizi, un volume nominato e un healthcheck coprono database e applicazione, con Docker Compose v5.6.1.
- `depends_on` con `condition: service_healthy` aspetta che Postgres risponda; senza condizione aspetta solo l'avvio del container.
- `docker compose down` conserva i volumi, `down -v` li cancella senza conferma: è il comando da non lanciare per abitudine.
Risposta breve: scrivi un compose.yaml con i servizi che il progetto richiede, avvia docker compose up -d e segui l'output con docker compose logs -f. Il file resta nel repository e vale per tutto il team.
Un compose.yaml che parte
services:
db:
image: postgres:17-alpine
environment:
POSTGRES_PASSWORD: dev
ports:
- "5432:5432"
volumes:
- db-data:/var/lib/postgresql/data
healthcheck:
test: ["CMD-SHELL", "pg_isready -U postgres"]
interval: 5s
retries: 10
app:
build: .
ports:
- "3000:3000"
environment:
DATABASE_URL: postgres://postgres:dev@db:5432/postgres
depends_on:
db:
condition: service_healthy
volumes:
db-data:
Due servizi bastano nella maggior parte dei progetti: database e applicazione. Il volume nominato db-data conserva i dati tra un riavvio e l'altro, e depends_on con condition: service_healthy aspetta che Postgres risponda, non solo che il container parta.
I comandi che si usano ogni giorno
docker compose up -d
docker compose ps
docker compose logs -f app
docker compose exec db psql -U postgres -c '\dt'
docker compose down
ps mostra stato e porte, logs -f segue un servizio, exec entra in un container già avviato. down ferma e rimuove i container, ma lascia i volumi: i dati restano.
Dati locali: quando cancellarli davvero
docker compose down -v
docker compose exec db psql -U postgres -c 'select count(*) from users;'
down -v elimina anche i volumi. È il comando giusto per ripartire da un database vuoto e quello sbagliato da lanciare per abitudine: non chiede conferma e non ha undo. Controlla prima con docker volume ls.
Override per il team
Un compose.override.yaml viene unito in automatico al file base: mount del codice, porte esposte, comando di watch. Tieni l'override fuori dal repository se contiene percorsi personali.
Limite dichiarato
Su Windows i bind mount passano da WSL2 e costano: un node_modules montato dall'host rallenta l'avvio in modo evidente. La documentazione Docker suggerisce un volume nominato o una cache di build per le dipendenze, non il bind mount.
Dove continuare
Nel catalogo trovi il system monitor, la card con metrica di avanzamento e i blocchi di dashboard. Per il resto leggi la struttura di un monorepo Next.js, gli indici PostgreSQL utili e il confronto Next.js o Vite.
Domande frequenti
Docker Compose è ancora gratuito?
Sì. Il plugin Docker Compose è parte di Docker Desktop e della CLI Docker, con licenza Apache 2.0: nessuna parte del file compose richiede un piano a pagamento.
Qual è la differenza tra compose.yaml e docker-compose.yml?
Nessuna funzionale: compose.yaml è il nome raccomandato dalla documentazione, docker-compose.yml resta supportato per compatibilità. Scegline uno e non tenere entrambi.
Perché l'app parte prima che il database sia pronto?
Perché depends_on da solo aspetta solo il container avviato, non il servizio disponibile. Aggiungi condition: service_healthy e un healthcheck con pg_isready, oppure gestisci il retry nel codice.
Come faccio a vedere i dati del database?
Con docker compose exec db psql -U postgres, che apre una sessione dentro il container già avviato. In alternativa esponi la porta 5432 e collega un client dal sistema host.
Posso usare Docker Compose in produzione?
Puoi, ma non è il caso d'uso per cui è pensato: manca il controllo su più nodi, il rolling update e il failover. Per lo sviluppo locale è lo strumento giusto; per la produzione serve un orchestratore.