Networking
🏠The everyday picture
Phones on an office's internal exchange can call each other by extension name; only the reception line connects to the outside world.
📘What it really is
-
Containers on the same user-defined network can reach each other by name: the API connects to the database at
postgresql://...@db:5432/crm, wheredbis the database container's name. -
Publishing ports (
-p) makes a container reachable from outside the network: -p 3001:3001publishes on all the host's addresses, which can bypass UFW (Module 66, Lesson 5);-
-p 127.0.0.1:3001:3001publishes only to the host itself, safe behind Nginx. -
Publish only what must be reached from outside: usually just the reverse proxy (Nginx or Caddy) on 80 and 443. The database needs no published port at all in production; the API reaches it on the internal network.
-
Commands:
docker network create crm-net,docker run --network crm-net --name db ...,docker network ls. - With Docker Compose (next lesson), a network is created automatically for each project.
🖱️Try it
Create a network crm-net. Run the database container on it with the name db (no published port), and your API container on
it with DATABASE_URL pointing at db, publishing the API on 127.0.0.1:3001 only. Check the API works at
http://localhost:3001/health, and that the database isn't reachable from your host on 5432.
✅Quick check
How does the API container find the database container on the same network?
Show the answer
By the database container's name, used as the host name.
Why publish the API as 127.0.0.1:3001:3001 instead of 3001:3001?
Show the answer
So it's only reachable from the host (and Nginx), not from the internet, and can't bypass the firewall.
