Docker + Pipeworkをつかってコンテナに固定ipを割り当てる
モチベーション
Dockerのインターフェースに固定ipを振りたい
背景
現状,Dockerでコンテナを起動するとそれぞれのコンテナにeth0が追加される.その際に振られるipはDockerが勝手に割り振ってしまうためにコンテナに固定ipでアクセスしたいときは不便である.自分でbtctlをつかってブリッジや仮想インターフェースを作っても良いが,Pipeworkというツールを使うと簡単にDockerに固定をipを振れるようなので使ってみる.
環境
- OS:Ubuntu 14.04
Pipeworkのインストール
Dockerがインストールされ,コンテナが既にあるubuntuマシンにて以下を実行
$ sudo -s
$ git clone https://github.com/jpetazzo/pipework.git
$ apt-get install -y bridge-utils
$ apt-get install -y arping
コンテナにNICを追加する
コンテナIDを調べ,NICを追加したいコンテナを起動し,NICを追加する.
$ docker ps -a
$ docker start 9bc312779a79
$ ./pipework br1 9bc312779a79 192.168.10.5/24 (コンテナに振りたいip)
この時br1という名前のブリッジが自動的に生成されるが,br1のipは自分で振る必要がある.
$ ip addr add 192.168.10.254/24 dev br1
$ ip addr show br1
22: br1: <BROADCAST,MULTICAST,UP,LOWER_UP> mtu 1500 qdisc noqueue state UP group default
link/ether 3e:1c:29:d7:b7:04 brd ff:ff:ff:ff:ff:ff
inet 192.168.10.254/24 scope global br1
valid_lft forever preferred_lft forever
inet6 fe80::e828:a5ff:fe57:2f79/64 scope link
valid_lft forever preferred_lft forever
これでホストから192.168.10.5に対してpingが通るようになった.
Docker + Pipeworkの挙動メモ
これまでに生成されたインタフェースを見ると,
$ ip addr show
1: lo: <LOOPBACK,UP,LOWER_UP> mtu 65536 qdisc noqueue state UNKNOWN group default
link/loopback 00:00:00:00:00:00 brd 00:00:00:00:00:00
inet 127.0.0.1/8 scope host lo
valid_lft forever preferred_lft forever
inet6 ::1/128 scope host
valid_lft forever preferred_lft forever
2: eth0: <BROADCAST,MULTICAST,UP,LOWER_UP> mtu 9001 qdisc pfifo_fast state UP group default qlen 1000
link/ether 06:09:72:64:53:b4 brd ff:ff:ff:ff:ff:ff
inet 172.31.15.159/20 brd 172.31.15.255 scope global eth0
valid_lft forever preferred_lft forever
inet6 fe80::409:72ff:fe64:53b4/64 scope link
valid_lft forever preferred_lft forever
3: docker0: <BROADCAST,MULTICAST,UP,LOWER_UP> mtu 9001 qdisc noqueue state UP group default
link/ether 56:84:7a:fe:97:99 brd ff:ff:ff:ff:ff:ff
inet 172.17.42.1/16 scope global docker0
valid_lft forever preferred_lft forever
inet6 fe80::5484:7aff:fefe:9799/64 scope link
valid_lft forever preferred_lft forever
22: br1: <BROADCAST,MULTICAST,UP,LOWER_UP> mtu 1500 qdisc noqueue state UP group default
link/ether 3e:1c:29:d7:b7:04 brd ff:ff:ff:ff:ff:ff
inet 192.168.10.254/24 scope global br1
valid_lft forever preferred_lft forever
inet6 fe80::e828:a5ff:fe57:2f79/64 scope link
valid_lft forever preferred_lft forever
30: vethc78d: <BROADCAST,UP,LOWER_UP> mtu 9001 qdisc pfifo_fast master docker0 state UP group default qlen 1000
link/ether 02:53:af:6d:e5:91 brd ff:ff:ff:ff:ff:ff
inet6 fe80::53:afff:fe6d:e591/64 scope link
valid_lft forever preferred_lft forever
32: veth1pl7845: <BROADCAST,MULTICAST,UP,LOWER_UP> mtu 1500 qdisc pfifo_fast master br1 state UP group default qlen 1000
link/ether fa:22:e8:ae:a9:15 brd ff:ff:ff:ff:ff:ff
inet6 fe80::f822:e8ff:feae:a915/64 scope link
valid_lft forever preferred_lft forever
vethXXXというのがDockerが自動で作成したブリッジdocker0に紐付いている仮想NICで, veth1plXXXというのがPipeworkが作成したブリッジに紐付いている仮想NIC(これがコンテナ内に生成されたNIC eth1と対になっているNIC)
$ brctl show
bridge name bridge id STP enabled interfaces
br1 8000.3e1c29d7b704 no veth1pl7845
docker0 8000.56847afe9799 no vethc78d
コンテナ内に入ってアドレスを調べるとちゃんと,Pipeworkで指定したアドレスがeth1に振られている.
$ ip addr show
1: lo: <LOOPBACK,UP,LOWER_UP> mtu 9001 qdisc noqueue state UNKNOWN group default
link/loopback 00:00:00:00:00:00 brd 00:00:00:00:00:00
inet 127.0.0.1/8 scope host lo
valid_lft forever preferred_lft forever
inet6 ::1/128 scope host
valid_lft forever preferred_lft forever
39: eth0: <BROADCAST,UP,LOWER_UP> mtu 9001 qdisc pfifo_fast state UP group default qlen 1000
link/ether 4a:f7:d8:18:24:c4 brd ff:ff:ff:ff:ff:ff
inet 172.17.0.14/16 scope global eth0
valid_lft forever preferred_lft forever
inet6 fe80::48f7:d8ff:fe18:24c4/64 scope link
valid_lft forever preferred_lft forever
41: eth1: <BROADCAST,MULTICAST,UP,LOWER_UP> mtu 1500 qdisc pfifo_fast state UP group default qlen 1000
link/ether ee:3c:8b:39:3f:c1 brd ff:ff:ff:ff:ff:ff
inet 192.168.10.5/24 scope global eth1
valid_lft forever preferred_lft forever
inet6 fe80::ec3c:8bff:fe39:3fc1/64 scope link
valid_lft forever preferred_lft forever
そして,コンテナを停止すると自動的に仮想NICは削除される.
$ ip addr show
1: lo: <LOOPBACK,UP,LOWER_UP> mtu 65536 qdisc noqueue state UNKNOWN group default
link/loopback 00:00:00:00:00:00 brd 00:00:00:00:00:00
inet 127.0.0.1/8 scope host lo
valid_lft forever preferred_lft forever
inet6 ::1/128 scope host
valid_lft forever preferred_lft forever
2: eth0: <BROADCAST,MULTICAST,UP,LOWER_UP> mtu 9001 qdisc pfifo_fast state UP group default qlen 1000
link/ether 06:09:72:64:53:b4 brd ff:ff:ff:ff:ff:ff
inet 172.31.15.159/20 brd 172.31.15.255 scope global eth0
valid_lft forever preferred_lft forever
inet6 fe80::409:72ff:fe64:53b4/64 scope link
valid_lft forever preferred_lft forever
3: docker0: <NO-CARRIER,BROADCAST,MULTICAST,UP> mtu 9001 qdisc noqueue state DOWN group defaul
$ brctl show
bridge name bridge id STP enabled interfaces
br1 8000.000000000000 no
docker0 8000.56847afe9799 no
Dockerでサーバを運用する際にうっかりコンテナを停止してしまった時はNICが消えるので注意.このへんの処理は自動化しといたほうがいいかな.