Container Networking
Container Networking
Networking enables containers to communicate with each other and the outside world. This chapter covers Docker's networking model, network drivers, and how to connect containers effectively.
Docker Networking Basics
By default, Docker creates an isolated network environment for each container. Containers can:
- Communicate with the host machine
- Access the internet (outbound)
- Be connected to other containers through networks
# View existing networks
docker network ls
# Default networks
NETWORK ID NAME DRIVER SCOPE
abc123 bridge bridge local
def456 host host local
ghi789 none null localNetwork Drivers
Docker supports several network drivers for different use cases:
Bridge Network (Default)
The default network driver. Containers on the same bridge network can communicate via IP addresses.
# Create a bridge network
docker network create mynetwork
# Run containers on the network
docker run -d --name web --network mynetwork nginx
docker run -d --name api --network mynetwork node:20-alpine
# Containers can reach each other by name
docker exec web ping apiBridge Network Diagram
┌─────────────────────────────────────────────────────────┐
│ Host Machine │
│ ┌─────────────────────────────────────────────────┐ │
│ │ Docker Bridge Network │ │
│ │ (172.17.0.0/16) │ │
│ │ │ │
│ │ ┌──────────┐ ┌──────────┐ ┌──────────┐ │ │
│ │ │ web │ │ api │ │ db │ │ │
│ │ │172.17.0.2│ │172.17.0.3│ │172.17.0.4│ │ │
│ │ └──────────┘ └──────────┘ └──────────┘ │ │
│ │ │ │
│ └─────────────────────────────────────────────────┘ │
│ │ │
│ NAT/Port Mapping │
│ │ │
│ ┌────┴────┐ │
│ │ eth0 │ │
└────────────────────┴─────────┴───────────────────────────┘
│
InternetHost Network
Containers share the host's network stack directly. No network isolation.
# Run with host network
docker run -d --network host nginx
# Container ports are directly on host
# No need for -p port mapping
curl localhost:80Warning
Host networking removes network isolation. The container has full access to all host network interfaces. Use only when necessary for performance or special network requirements.
None Network
Completely isolated—no network access.
# Run with no network
docker run -d --network none alpine sleep infinity
# Container has only loopback interface
docker exec <container> ip addr
# Only shows 'lo' interfaceOverlay Network
For multi-host networking with Docker Swarm or Kubernetes:
# Create overlay network (requires Swarm mode)
docker network create --driver overlay my-overlay
# Used for distributed applications across hostsMacvlan Network
Assign a MAC address to containers, making them appear as physical devices:
# Create macvlan network
docker network create -d macvlan \
--subnet=192.168.1.0/24 \
--gateway=192.168.1.1 \
-o parent=eth0 \
macnetCreating and Managing Networks
Creating Networks
# Create with default settings
docker network create mynetwork
# Create with specific subnet
docker network create \
--driver bridge \
--subnet 172.20.0.0/16 \
--gateway 172.20.0.1 \
mynetwork
# Create with IP range
docker network create \
--subnet 192.168.0.0/24 \
--ip-range 192.168.0.128/25 \
--gateway 192.168.0.1 \
mynetworkInspecting Networks
# View network details
docker network inspect mynetwork
# See connected containers
docker network inspect mynetwork --format '{{range .Containers}}{{.Name}} {{end}}'
# View network configuration
docker network inspect bridge --format '{{.IPAM.Config}}'Connecting and Disconnecting
# Connect a running container to a network
docker network connect mynetwork mycontainer
# Connect with specific IP
docker network connect --ip 172.20.0.100 mynetwork mycontainer
# Disconnect from a network
docker network disconnect mynetwork mycontainerRemoving Networks
# Remove a network
docker network rm mynetwork
# Remove all unused networks
docker network pruneNote
You cannot remove a network that has connected containers. Disconnect or stop the containers first.
Container DNS
Docker provides automatic DNS resolution for containers on user-defined networks.
Automatic Service Discovery
# Create a network
docker network create app-network
# Start containers
docker run -d --name database --network app-network postgres:16
docker run -d --name backend --network app-network myapi
# Containers can reach each other by name
docker exec backend ping database
docker exec backend curl http://database:5432DNS Resolution
# Inside the 'backend' container:
$ ping database
PING database (172.20.0.2): 56 data bytes
64 bytes from 172.20.0.2: seq=0 ttl=64 time=0.089 ms
$ cat /etc/resolv.conf
nameserver 127.0.0.11
options ndots:0Network Aliases
Give containers additional DNS names:
# Create container with alias
docker run -d \
--name postgres \
--network app-network \
--network-alias db \
--network-alias database \
postgres:16
# Both names resolve to the same container
docker exec backend ping db
docker exec backend ping database
docker exec backend ping postgresCustom DNS Settings
# Use custom DNS servers
docker run -d \
--dns 8.8.8.8 \
--dns 8.8.4.4 \
--dns-search example.com \
myapp
# Set hostname
docker run -d --hostname myserver.local myappPort Publishing
Expose container ports to the host machine:
Basic Port Mapping
# Map container port 80 to host port 8080
docker run -d -p 8080:80 nginx
# Map to specific interface
docker run -d -p 127.0.0.1:8080:80 nginx
# Map multiple ports
docker run -d -p 80:80 -p 443:443 nginx
# Random host port
docker run -d -p 80 nginx
docker port <container> # Shows assigned portPort Protocols
# TCP (default)
docker run -d -p 8080:80/tcp nginx
# UDP
docker run -d -p 53:53/udp dns-server
# Both TCP and UDP
docker run -d -p 53:53/tcp -p 53:53/udp dns-serverViewing Port Mappings
# Show port mappings for a container
docker port mycontainer
# Show all containers with ports
docker ps --format "table {{.Names}}\t{{.Ports}}"Port Mapping Output
$ docker ps
CONTAINER ID IMAGE PORTS NAMES
abc123 nginx 0.0.0.0:80->80/tcp, 0.0.0.0:443->443/tcp web
def456 redis 6379/tcp cacheContainer Communication Patterns
Containers on the Same Network
# Create network
docker network create backend
# Start database
docker run -d \
--name postgres \
--network backend \
-e POSTGRES_PASSWORD=secret \
postgres:16
# Start app that connects to database
docker run -d \
--name api \
--network backend \
-e DATABASE_URL=postgres://postgres:secret@postgres:5432/app \
myapiContainers on Multiple Networks
# Create networks
docker network create frontend
docker network create backend
# API server on both networks
docker run -d \
--name api \
--network frontend \
myapi
docker network connect backend api
# Web server on frontend only
docker run -d --name web --network frontend nginx
# Database on backend only
docker run -d --name db --network backend postgres:16
# API can reach both web and db
# Web cannot reach db directlyNetwork Segmentation
┌─────────────────────────────────────┐
│ Frontend Network │
│ ┌──────────┐ ┌──────────┐ │
│ │ web │◄────►│ api │ │
│ │ (nginx) │ │ (node) │ │
│ └──────────┘ └────┬─────┘ │
└─────────────────────────┼──────────┘
│
┌─────────────────────────┼──────────┐
│ Backend Network│ │
│ ┌────┴─────┐ │
│ │ api │ │
│ │ (node) │ │
│ └────┬─────┘ │
│ │ │
│ ┌────┴─────┐ │
│ │ db │ │
│ │(postgres)│ │
│ └──────────┘ │
└─────────────────────────────────────┘IPv6 Support
Enable IPv6 for containers:
# Create dual-stack network
docker network create \
--ipv6 \
--subnet 172.28.0.0/16 \
--subnet 2001:db8::/64 \
mynetwork-v6
# Run container with IPv6
docker run -d --network mynetwork-v6 nginxTroubleshooting Networking
Debug Connectivity
# Check container's network settings
docker inspect --format='{{json .NetworkSettings.Networks}}' mycontainer
# See all network interfaces in container
docker exec mycontainer ip addr
# Check routing table
docker exec mycontainer ip route
# Test DNS resolution
docker exec mycontainer nslookup other-container
# Test connectivity
docker exec mycontainer ping other-container
docker exec mycontainer curl http://other-container:8080Common Network Tools
# Install network tools in Alpine
docker exec mycontainer apk add --no-cache curl bind-tools iputils
# Install in Debian/Ubuntu
docker exec mycontainer apt-get update && apt-get install -y curl dnsutils iputils-pingDebug Network Container
Use a debug container with all networking tools:
# Run a debug container on the same network
docker run -it --rm \
--network mynetwork \
nicolaka/netshoot \
/bin/bash
# Now you have: curl, dig, nslookup, ping, tcpdump, etc.Note
The nicolaka/netshoot image is a network troubleshooting container with all
common tools pre-installed. It's invaluable for debugging network issues.
Check IPtables Rules
# View Docker's iptables rules (on host)
sudo iptables -L -n -v
sudo iptables -t nat -L -n -v
# See Docker's network namespaces
sudo ls /var/run/docker/netns/Network Security
Isolate Sensitive Containers
# Create internal network (no external access)
docker network create --internal secure-network
# Containers can communicate internally but not reach internet
docker run -d --network secure-network sensitive-appLimit Container Communication
# Disable inter-container communication on default bridge
docker network create --opt com.docker.network.bridge.enable_icc=false isolated
# Containers must explicitly be linked to communicateUse Specific IP Bindings
# BAD: Binds to all interfaces (exposed externally)
docker run -p 8080:80 nginx
# GOOD: Bind to localhost only
docker run -p 127.0.0.1:8080:80 nginx
# GOOD: Bind to specific interface
docker run -p 10.0.0.5:8080:80 nginxWarning
By default, -p 8080:80 binds to 0.0.0.0, exposing the port on all network
interfaces including public ones. Always specify the interface for sensitive
services.
Network Performance
Use Host Network for Performance
# Host network eliminates NAT overhead
docker run --network host high-perf-app
# Useful for:
# - Network-intensive applications
# - Applications requiring many ports
# - Performance-critical scenariosOptimize MTU
# Create network with custom MTU
docker network create --opt "com.docker.network.driver.mtu=1450" mynetwork
# Useful in cloud environments with encapsulation overheadQuick Reference
| Command | Purpose |
|---|---|
docker network ls | List networks |
docker network create | Create a network |
docker network rm | Remove a network |
docker network inspect | View network details |
docker network connect | Connect container to network |
docker network disconnect | Disconnect from network |
docker network prune | Remove unused networks |
Network Driver Summary
| Driver | Use Case | Isolation | Performance |
|---|---|---|---|
bridge | Default, single host | Good | Good |
host | Maximum performance | None | Best |
none | Complete isolation | Complete | N/A |
overlay | Multi-host (Swarm) | Good | Moderate |
macvlan | Physical network integration | Varies | Good |
In the next chapter, we'll explore how to manage data persistence with volumes and bind mounts.