Chapter 12 of 16 · Visual guide

Networking: user-defined bridge and Docker DNS

Create your own network and Docker gives you service discovery: containers find each other by name.

key idea / Docker itselfcontainer / good pathhost / watch outproblem / blockedneutral

The embedded DNS server

Every container on a user-defined network is pointed at 127.0.0.11.

The embedded DNS serverContainers on a user-defined network use the daemon DNS at 127.0.0.11. It answers names of containers on the same networks and forwards everything else to the host resolver.webresolv.confwho is X?Docker DNS127.0.0.11Container or alias?api → 172.18.0.3External name?github.com → upstream DNSyesno

Why names beat IPs

Names survive recreationThe same name resolves to a new IP after the container is recreated.Beforewebping apiDocker DNSapi = 172.18.0.2api172.18.0.2After docker stop api && docker run --name api ...webping apiDocker DNSapi = 172.18.0.3api (new)172.18.0.3No config change in web: it keeps asking for "api".
The name is stable. The IP behind it is allowed to change.

Aliases and round-robin

One name, several containersTwo containers share the network alias db. A lookup for db returns both addresses.webconnects to dbDocker DNSdb → .2 and .3db-1--network-alias db · .2db-2--network-alias db · .3
A shared --network-alias gives round-robin DNS: simple load spreading, no extra proxy.

What resolves, and what does not

LookupResolves on a user-defined network?
container name (--name api)yes
--network-alias dbyes, many containers can share one
Compose service nameyes, Compose adds it as an alias
a container on a different networkno, no shared network
anything on the default bridgeno DNS there
the image name (nginx:1.27)never: it is not a host name

Try it yourself

  1. Step 1 · Create a network and two named containers
    $ docker network create app
    $ docker run -d --name api --rm --network app alpine:3.20 sleep 300
    $ docker run -d --name web --rm --network app alpine:3.20 sleep 300
  2. Step 2 · Read the DNS server

    On a user-defined network the container’s resolver is 127.0.0.11.

    $ docker exec web cat /etc/resolv.conf
    nameserver 127.0.0.11
  3. Step 3 · Ping the name
    $ docker exec web ping -c 1 api
    PING api (172.18.0.2): 56 data bytes
    64 bytes from 172.18.0.2: seq=0 ttl=64
  4. Step 4 · Recreate api and ping the name again

    The IP can change. The name still resolves.

    $ docker stop api
    $ docker run -d --name api --rm --network app alpine:3.20 sleep 300
    $ docker exec web ping -c 1 api
    PING api (172.18.0.3): 56 data bytes
    $ docker stop api web
    $ docker network rm app

Recap

Quick check

Why does ping api keep working after you recreate the api container with a new IP?
Show answer

The name is looked up again through Docker DNS, which now returns the new address. Nothing in the caller stored the old IP.