LEARN · DEBUGGING GUIDE

Diagnosing Broken Networking in Docker Containers

Network issues in Docker can be infuriating and non-obvious. Here’s how to systematically debug when containers can’t talk across networks.

IntermediateDocker4 min read

What this usually means

Broken Docker container networking usually indicates misconfigured network bridges, missing or conflicting iptables rules, corrupted Docker networks, or host-level firewall changes. Sometimes caused by race conditions in network setup, orphaned containers holding onto network namespaces, or running Docker with limited capabilities. It’s rarely a problem with your application code—it’s almost always the container runtime or host network stack.

( 01 )Fast diagnosis

The first ten minutes — establish facts before touching code.

  • 1Run 'docker network ls' and 'docker network inspect <network>' to confirm network existence and configuration.
  • 2Start a busybox container attached to the suspect network and run 'ping', 'nslookup', and 'curl' to test connectivity.
  • 3Run 'docker exec <cid> ip addr' and 'ip route' to check container IP assignment and routing table.
  • 4Check 'iptables -L -n -v' (or 'nft list ruleset') on the host for missing or conflicting NAT/MASQUERADE rules.
  • 5Review 'dmesg | tail' for kernel/networking errors on the host.
  • 6If packets are just vanishing, run 'tcpdump -i <bridge> tcp port 80' while reproducing the failure.
( 02 )Where to look

The specific files, logs, configs, and dashboards that usually own this bug.

  • search/var/lib/docker/network/files/local-kv.db (for corrupt network state)
  • search/etc/docker/daemon.json (for user-defined bridge and DNS configs)
  • search'docker inspect <container>' output (look for 'NetworkSettings' and 'HostConfig')
  • searchHost's 'iptables' or 'nftables' config
  • searchOutput of 'systemctl status docker' and 'journalctl -u docker'
  • search/etc/resolv.conf inside the container
( 03 )Common root causes

Practical causes, not theory. These are the things you will actually find.

  • warningBroken or missing Docker network bridge (br-xxxx) on the host
  • warningHost firewall rules (ufw, firewalld, custom iptables) blocking container traffic
  • warningNetwork namespace leaks from orphaned or zombie containers
  • warningDocker daemon started with '--iptables=false' by mistake
  • warningManual changes to bridge interfaces or deletion of network devices outside Docker
  • warningDNS misconfiguration: custom resolver, missing /etc/resolv.conf, or mis-set --dns option
  • warningIPv6 enabled/disabled on host but not matching container config
( 04 )Fix patterns

Concrete fix directions. Pick the one that matches your root cause.

  • buildRestart Docker: 'systemctl restart docker' (sometimes fixes corrupted network state)
  • buildRecreate the bridge: 'docker network rm <network>' then 'docker network create ...'
  • buildFlush and re-apply firewall rules: 'iptables -F && iptables -t nat -F'
  • buildExplicitly set '--iptables=true' and '--ip-forward=true' in Docker daemon config
  • buildReboot to clean up zombie network namespaces if manual cleanup is too risky
  • buildSpecify correct DNS config: 'docker run --dns 8.8.8.8 ...' if resolv.conf is broken
( 05 )How to verify

A fix you cannot prove is a guess. Close the loop.

  • verifiedAfter fixes, run 'docker exec <cid> ping <ip>' and confirm traffic flows as expected.
  • verifiedConfirm external connectivity: 'curl https://www.google.com' inside container.
  • verifiedRedeploy multiple containers and test service discovery via container DNS.
  • verifiedWatch 'tcpdump' output on the bridge to confirm expected SYN/ACK packets.
  • verifiedValidate that 'docker network inspect' shows healthy network state and correct container attachment.
( 06 )Mistakes to avoid

Things that make this bug worse or harder to find.

  • warningDeleting Docker bridge devices manually with 'ip link del' (breaks everything until daemon restart)
  • warningMixing manual iptables rules with Docker-managed chains without understanding NAT/DOCKER chains
  • warningForgetting to check host firewall (ufw, firewalld) when containers can't reach outside
  • warningAssuming 'host.docker.internal' works everywhere—Linux requires special setup
  • warningIgnoring orphaned containers or network aliases left after failed orchestrator deploys
( 07 )War story

Containers Couldn’t Reach Postgres on Custom Bridge

DevOps EngineerDocker 20.10 on Ubuntu 22.04; custom bridge network; iptables backend; ufw enabled

Timeline

  1. 09:15Deployed new backend and Postgres containers on 'my_net' network.
  2. 09:18Backend error logs: ECONNREFUSED when connecting to Postgres at 172.22.0.2:5432.
  3. 09:20'docker exec backend ping postgres' fails; 'Destination Host Unreachable' message.
  4. 09:25Verified both containers are on correct network via 'docker network inspect'.
  5. 09:28tcpdump on br-xxxx shows no traffic when pinging.
  6. 09:31Checked 'iptables -L -n -v' and found ufw default policy was DROP on FORWARD chain.
  7. 09:35Ran 'ufw route allow in on br-xxxx out on br-xxxx' and connectivity immediately restored.

I spun up a new microservice stack for QA using Docker Compose and a custom bridge. My backend container couldn't connect to Postgres, logging 'ECONNREFUSED'.

I inspected both containers and confirmed correct network attachment, but pings between them failed. Tcpdump on the bridge showed no attempted traffic.

Only after inspecting the host's iptables, I realized ufw was set to DROP traffic on the FORWARD chain by default, blocking all inter-container packets. Once I allowed traffic on the bridge, everything worked.

Root cause

Host firewall (ufw) was set to DROP on FORWARD by default, blocking Docker bridge traffic.

The fix

Added a ufw rule: 'ufw route allow in on br-xxxx out on br-xxxx'.

The lesson

Always check host firewalls—Docker relies on host FORWARD chain; ufw and firewalld can silently break networking.

( 08 )How Docker Container Networking Actually Works

Docker creates network namespaces and connects them via Linux bridge interfaces (br-xxxx). Default bridge and user-defined bridges use NAT to reach external networks.

Communication depends on iptables or nftables rules inserted by Docker. Host firewall rules outside these chains can block traffic, and custom bridges rely on the host's FORWARD policy being ACCEPT or at least permitting bridge-to-bridge traffic.

( 09 )Debugging Orphaned Networks and Namespace Leaks

Occasionally, containers fail to clean up, leaving stale network namespaces. These can block creation of new bridges or cause address conflicts.

List dangling namespaces with 'lsns -t net' and forcibly remove them only if no container is using the ns reference. Avoid rebooting unless truly stuck.

( 10 )Handling DNS Failures Inside Containers

Docker injects /etc/resolv.conf into containers by default. If the host uses systemd-resolved's stub (127.0.0.53), containers may get an unreachable resolver.

Override with '--dns' on run or set 'dns' in /etc/docker/daemon.json to point at a real upstream resolver.

( 11 )Mixing Docker with Host Security Tools

Tools like ufw and firewalld manipulate iptables in ways that can override Docker's chains. When the FORWARD policy becomes DROP, container-to-container traffic dies.

Always adjust firewall rules to explicitly allow inter-bridge traffic, or use the '--iptables=false' option with great caution and only if you're managing all rules yourself.

Frequently asked questions

Why does 'host.docker.internal' not work on Linux containers?

It's only set up automatically on Docker for Mac and Windows. On Linux, you need to manually add a host gateway or use '--add-host host.docker.internal:host-gateway' on recent Docker versions.

Can Docker networking break after a system upgrade?

Yes—changes to kernel, iptables/nftables, or firewall defaults can break Docker's bridges. Always revalidate connectivity after major upgrades.

How do I check which containers are using a particular network?

Run 'docker network inspect <network>' and check the 'Containers' section for all container IDs connected to that network.

How do I debug packet loss between containers?

Run 'tcpdump -i <bridge> host <container-ip>' on the host and repeat the connection attempt. If you see SYN but no SYN-ACK, routing or firewall is often the culprit.

What's the quickest way to confirm network setup in a new container?

Run 'docker run --rm -it --network <network> busybox sh' and use 'ping', 'nslookup', and 'curl' inside for live, low-level checks.