Gostaria de configurar os contêineres do Docker para parecerem um sistema real, atribuindo-lhes endereços IP estáticos em minha rede.
Atualmente tenho uma configuração de ponte de rede (br0) no host. Eu DOCKER_OPTS="-b=br0"
configurei no /etc/default/docker
arquivo. Consigo atribuir endereços estáticos a cada um dos contêineres por meio de seus /etc/network/interface
arquivos.
O problema é que o Docker continuará atribuindo endereços IP por conta própria. (Como faço para parar isso?) Ainda mais preocupante é que agora ele usará o esquema IP da rede em ponte. O que causará problemas de rede, pois pode atribuir endereços que já estão em uso na rede.
Problemas:
Suspensão/pausa da rede
O endereço de resposta durante o ping do contêiner pode mudar.
Error messages such as this are seen in the logs of the host:
kernel: [31912.876161] br0: port 3(vethb228701) entered disabled state
kernel: [31913.441517] device veth122d9f8 left promiscuous mode
kernel: [22491.609856] audit: type=1400 audit(1434148604.621:124): apparmor="DENIED" operation="getattr" info="Failed name lookup - disconnected path" error=-13 profile="/usr/sbin/ntpd" name="var/lib/docker/aufs/diff/eb00895db3d297979df741cd560ccbea2ab4d572264bd703fc6cbc7ea2acb5c4/usr/lib" pid=30955 comm="ntpd" requested_mask="r" denied_mask="r" fsuid=0 ouid=0
O Docker também atribui ao contêiner um endereço na mesma sub-rede da minha rede. No começo pensei que fosse simplesmente adicionar uma linha ao /etc/hosts
arquivo do contêiner. O que acontece, mas mesmo depois de removê-lo, os problemas ainda são vistos.
Exemplo:
root@myhostname:/# cat /etc/hosts
X.X.192.3 myhostname.mydomain.com myhostname
127.0.0.1 localhost
::1 localhost ip6-localhost ip6-loopback
fe00::0 ip6-localnet
ff00::0 ip6-mcastprefix
ff02::1 ip6-allnodes
ff02::2 ip6-allrouters
root@myhostname:/# ifconfig
eth0 Link encap:Ethernet HWaddr 02:42:09:1a:c0:03
inet addr:X.X.X.X Bcast:X.X.X.X Mask:255.255.252.0
inet6 addr: fe80::42:9ff:fe1a:c003/64 Scope:Link
UP BROADCAST RUNNING MTU:1500 Metric:1
RX packets:231 errors:0 dropped:26 overruns:0 frame:0
TX packets:46 errors:0 dropped:0 overruns:0 carrier:0
collisions:0 txqueuelen:0
RX bytes:23719 (23.7 KB) TX bytes:3960 (3.9 KB)
lo Link encap:Local Loopback
inet addr:127.0.0.1 Mask:255.0.0.0
inet6 addr: ::1/128 Scope:Host
UP LOOPBACK RUNNING MTU:65536 Metric:1
RX packets:0 errors:0 dropped:0 overruns:0 frame:0
TX packets:0 errors:0 dropped:0 overruns:0 carrier:0
collisions:0 txqueuelen:0
RX bytes:0 (0.0 B) TX bytes:0 (0.0 B)
Se nenhum nome de host for atribuído por meio da linha de comando (-h) para iniciar o contêiner, ele usará o nome de host atribuído aleatoriamente
Ambiente:
Host:
OS: Ubuntu 14.04.2
Arch: PPC64LE
Kernel: 3.16.0-30
docker version
:
Client version: 1.4.1-dev
Client API version: 1.17
Go version (client): gccgo (GCC) 5.0.0 20150118 (experimental)
Git commit (client): 7294f26
OS/Arch (client): linux/ppc64le
Server version: 1.4.1-dev
Server API version: 1.17
Go version (server): gccgo (GCC) 5.0.0 20150118 (experimental)
Git commit (server): 7294f26
Hardware:
IBM Power 8, 8247-22L
CPUs: 192
Memory: 512GB
Containers:
OS: Ubuntu 14.04.2
Arch: PPC64LE
Kernel: 3.16.0-30
Rede:
brctl show
bridge name bridge id STP enabled interfaces
br0 8000.6cae8b6aaf64 no eth0
br0 Link encap:Ethernet HWaddr 6c:ae:8b:6a:af:64
inet addr:X.X.X.X Bcast: X.X.X.X Mask:255.255.252.0
inet6 addr: fe80::6eae:8bff:fe6a:af64/64 Scope:Link
UP BROADCAST RUNNING MULTICAST MTU:1500 Metric:1
RX packets:6750867 errors:0 dropped:80 overruns:0 frame:0
TX packets:1586308 errors:0 dropped:0 overruns:0 carrier:0
collisions:0 txqueuelen:0
RX bytes:1049658934 (1.0 GB) TX bytes:6936734104 (6.9 GB)
eth0 Link encap:Ethernet HWaddr 6c:ae:8b:6a:af:64
UP BROADCAST RUNNING MULTICAST MTU:1500 Metric:1
RX packets:7155242 errors:0 dropped:7598 overruns:0 frame:0
TX packets:6347549 errors:0 dropped:0 overruns:0 carrier:0
collisions:0 txqueuelen:1000
RX bytes:1212526214 (1.2 GB) TX bytes:7339350703 (7.3 GB)
Interrupt:249
lo Link encap:Local Loopback
inet addr:127.0.0.1 Mask:255.0.0.0
inet6 addr: ::1/128 Scope:Host
UP LOOPBACK RUNNING MTU:65536 Metric:1
RX packets:238 errors:0 dropped:0 overruns:0 frame:0
TX packets:238 errors:0 dropped:0 overruns:0 carrier:0
collisions:0 txqueuelen:0
RX bytes:22564 (22.5 KB) TX bytes:22564 (22.5 KB)
Responder1
Eu também tentei resolver esse problema há algum tempo. Não consegui encontrar uma maneira de alterar o comportamento do docker em relação às atribuições de IP sem desabilitar toda a funcionalidade de rede ( --net=none
). Portanto, atribuí uma sub-rede até então não utilizada à interface do docker bridge e deixei o docker fazer a atribuição. Também escrevi um daemon que escuta determinados eventos da API do docker e, em seguida, envia atualizações dinâmicas para nosso servidor DNS, para que não precise me preocupar com os IPs e possa endereçar os contêineres pelo nome.
Aqui está o repositório do github para o daemon DNS. https://github.com/cschritt/docker-dns-daemon Em breve, enviarei minhas últimas alterações e algumas refatorações.
Responder2
Infelizmente, parece que não há como impedir que o Docker atribua endereços IP a contêineres no modo bridge. Como solução alternativa, adicionei pre-up ip addr flush dev eth0
para /etc/network/interface
descartar o endereço IP do Docker comodescrito aqui. Aqui está um exemplo de como isso pode ser feito:
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
A ressalva dessa abordagem ocorre com vários contêineres, quando o Docker injeta seus próprios endereços IP incorretos/substituídos nos /etc/hosts
arquivos dos contêineres. A única maneira que encontrei de corrigir isso é instalar inotify-tools
o pacote e executar o seguinte script para reverter /etc/hosts
ao seu estado predefinido assim que o Docker o alterar:
#!/bin/sh
while /usr/bin/inotifywait -e close /etc/hosts; do
cp -v /etc/hosts.orig /etc/hosts
done
O script acima requer que você adicione /etc/hosts.orig
um arquivo válido ao contêiner.
Responder3
Começando com Docker 1.10, previsto para ser lançado nos próximos dias, você pode especificar explicitamente um endereço IP estático ao iniciar seu contêiner, com as opções --ip=
e --ip6=
, para especificar endereços IPv4 e IPv6, respectivamente. Eles podem ser usados docker run
e docker network connect
persistirem enquanto o contêiner existir.