Assign static IP to Docker container

Solution 1:

Easy with Docker version 1.10.1, build 9e83765.

First you need to create your own docker network (mynet123)

docker network create --subnet=172.18.0.0/16 mynet123

then, simply run the image (I'll take ubuntu as example)

docker run --net mynet123 --ip 172.18.0.22 -it ubuntu bash

then in ubuntu shell

ip addr

Additionally you could use

  • --hostname to specify a hostname
  • --add-host to add more entries to /etc/hosts

Docs (and why you need to create a network) at https://docs.docker.com/engine/reference/commandline/network_create/

Solution 2:

For docker-compose you can use following docker-compose.yml

version: '2'
services:
  nginx:
    image: nginx
    container_name: nginx-container
    networks:
      static-network:
        ipv4_address: 172.20.128.2
networks:
  static-network:
    ipam:
      config:
        - subnet: 172.20.0.0/16
          #docker-compose v3+ do not use ip_range
          ip_range: 172.28.5.0/24

from host you can test using:

docker-compose up -d
curl 172.20.128.2

Modern docker-compose does not change ip address that frequently.

To find ips of all containers in your docker-compose in a single line use:

for s in `docker-compose ps -q`; do echo ip of `docker inspect -f "{{.Name}}" $s` is `docker inspect -f '{{range .NetworkSettings.Networks}}{{.IPAddress}}{{end}}' $s`; done

If you want to automate, you can use something like this example gist

Solution 3:

Not a direct answer but it could help.

I run most of my dockerized services tied to own static ips using the next approach:

  1. I create ip aliases for all services on docker host
  2. Then I run each service redirecting ports from this ip into container so each service have own static ip which could be used by external users and other containers.

Sample:

docker run --name dns --restart=always -d -p 172.16.177.20:53:53/udp dns
docker run --name registry --restart=always -d -p 172.16.177.12:80:5000 registry
docker run --name cache --restart=always -d -p 172.16.177.13:80:3142 -v /data/cache:/var/cache/apt-cacher-ng cache
docker run --name mirror --restart=always -d -p 172.16.177.19:80:80 -v /data/mirror:/usr/share/nginx/html:ro mirror
...

Solution 4:

I stumbled upon this problem during attempt to dockerise Avahi which needs to be aware of its public IP to function properly. Assigning static IP to the container is tricky due to lack of support for static IP assignment in Docker.

This article describes technique how to assign static IP to the container on Debian:

  1. Docker service should be started with DOCKER_OPTS="--bridge=br0 --ip-masq=false --iptables=false". I assume that br0 bridge is already configured.

  2. Container should be started with --cap-add=NET_ADMIN --net=bridge

  3. Inside container pre-up ip addr flush dev eth0 in /etc/network/interfaces can be used to dismiss IP address assigned by Docker as in following example:


auto lo
iface lo inet loopback

auto eth0
iface eth0 inet static
    pre-up ip addr flush dev eth0
    address 192.168.0.249
    netmask 255.255.255.0
    gateway 192.168.0.1
  1. Container's entry script should begin with /etc/init.d/networking start. Also entry script needs to edit or populate /etc/hosts file in order to remove references to Docker-assigned IP.