Edited at
RethinkDBDay 20

IDCFクラウドのDebian JessieでMulti-Host Docker Networking - Part 3: OverlayネットワークとDocker SwarmとDocker ComposeでRethinkDBをスケールさせる

More than 3 years have passed since last update.

 前回までに作成したOverlayネットワークのDocker SwarmクラスタへDocker Composeを使いRethinkDBをデプロイしてみます。 RethinkDBのブログは読んでいて楽しいので気に入っています。ES6 Generatorのサポートも早くモダンなデータベースです。


このシリーズ


参考

 以下のサイトを参考にしました。


仮想マシン

 前回と同じ仮想マシンを使います。

Dockerホストのhostname
Dockerホストのeth0
Docker Swarm

minion-1
10.3.0.101
Swarm Manager/Agent

minion-2
10.3.0.102
Swarm Agent

minion-3
10.3.0.103
Swarm Agent


RethinkDB

 RethinkDBはオフィシャルのイメージを使います。


プロジェクト

 rethinkの名前でディレクトリを作成してdocker-compose.ymlを配置します。このディレクトリ名はプロジェクト名としてコンテナの名前やOverlayネットワーク名として使われます。

$ tree .

.
└── rethink
└── docker-compose.yml


docker-compose.yml

 DockerでサクッとRethinkDBのクラスタを試すを参考にしてdocker-compose.ymlを作成します。


docker-compose.yml

seed:

image: rethinkdb:2
ports:
- "8088:8080"
command: rethinkdb -n seed --bind all

worker:
image: rethinkdb:2
environment:
- "affinity:container!=rethink_worker_*"
command: rethinkdb --bind all -j rethink_seed_1:29015

proxy:
image: rethinkdb:2
ports:
- "8080:8080"
environment:
- constraint:node==minion-3
command: rethinkdb proxy --bind all -j rethink_seed_1:29015


 Docker ComposeはReleasesサイトから最新バージョンをワンライナーでインストールします。

$ curl -L https://github.com/docker/compose/releases/download/1.5.2/docker-compose-`uname -s`-`uname -m` > /usr/local/bin/docker-compose && chmod +x /usr/local/bin/docker-compose


linksを使わない

 Networking in ComposeLinksにあるようにlibnetworkが導入されlinksはdeprecatedとなりました。docker-compose.ymlから削除しています。

 これまでDocker Composeはlinksを指定するとコンテナの/etc/hostsに自動的にエントリーされ名前解決ができました。libnetworkに対応してDocker Composeでは--x-networkingフラグをつけてupするとプロジェクト名(ディレクトリ名)のネットワークが自動的にdocker network createされます。{ネットワーク名}_{サービス名}_Nのホスト名がコンテナの/etc/hostsに登録され名前解決ができるようになりました。

 ただしlibnetworkがまだエイリアスに対応していなかったり、/etc/hostsへの登録にはいくつか問題がありissuesが上がっています。

 参考の例linksはサービス名で記述できましたが、{ネットワーク名}_{サービス名}_Nのように固定にする必要があります。

worker:

image: rethinkdb:2
links:
- seed:seed
command: rethinkdb --bind all -j seed:29015
proxy:
image: rethinkdb:2
ports:
- 8080:8080
links:
- worker:worker
command: rethinkdb proxy --bind all -j worker:29015


Affinity filter

 workerサービスはAffinity filterを使いanti-affinityフィルターを作ります。rethink_worker_*のコンテナが起動していない別のノードを選びます。

worker:

image: rethinkdb:2
environment:
- "affinity:container!=rethink_worker_*"
command: rethinkdb --bind all -j rethink_seed_1:29015


Constraint filter

 proxyサービスはConstraint Filterを指定してminion-3のノードを特定して起動します。IDCFクラウドの設定でパブリックIPアドレスとminion-3をスタティックNATしています。

proxy:

image: rethinkdb:2
ports:
- "8080:8080"
environment:
- constraint:node==minion-3
command: rethinkdb proxy --bind all -j rethink_seed_1:29015


Docker SwarmとOverlayネットワーク

DOCKER_HOST環境変数にSwarm Managerを設定してからupするとSwarmクラスタにデプロイします。

$ export DOCKER_HOST=tcp://10.3.0.101:3333

$ pwd
/root/rethink
$ docker-compose \
--x-networking \
--x-network-driver=overlay \
up -d

Dockerイメージがないノードではdocker pullするので少し時間がかかります。docker-compose psで確認するとサービスのコンテナが1つずつ起動しました。

$ docker-compose ps

Name Command State Ports
-----------------------------------------------------------------------------------------------------
rethink_proxy_1 rethinkdb proxy --bind Up 28015/tcp, 29015/tcp, 1
all ... 0.3.0.103:8080->8080/tc
p
rethink_seed_1 rethinkdb -n seed Up 28015/tcp, 29015/tcp, 1
--bind all 0.3.0.101:8088->8080/tc
p
rethink_worker_1 rethinkdb --bind all -j Up 28015/tcp, 29015/tcp,
re ... 8080/tcp

 --x-networkingフラグを指定するとプロジェクト名でDockerネットワークを作成します。rethinkネットワークが作成されました。

$ docker network ls

NETWORK ID NAME DRIVER
3f8bacd30250 rethink overlay
f10c0f7978af dn overlay
b68b118036d2 bridge bridge
636664a4f746 docker_gwbridge bridge
6e0cf0387184 none null
bc09b464b0c5 host host

Swarm Managerを指定してdocker psで確認するとNAMES列のコンテナ名は{Dockerホスト名}/{ネットワーク名}_{サービス名}_Nのように付けられています。

$ docker ps

CONTAINER ID IMAGE COMMAND CREATED STATUS PORTS NAMES
b9f13b49004a rethinkdb:2 "rethinkdb proxy --bi" 4 seconds ago Up 2 seconds 28015/tcp, 10.3.0.103:8080->8080/tcp, 29015/tcp minion-3/rethink_proxy_1
581d02852c24 rethinkdb:2 "rethinkdb --bind all" 5 seconds ago Up 4 seconds 8080/tcp, 28015/tcp, 29015/tcp minion-2/rethink_worker_1
4ae146ed7671 rethinkdb:2 "rethinkdb -n seed --" 6 seconds ago Up 5 seconds 28015/tcp, 29015/tcp, 10.3.0.101:8088->8080/tcp minion-1/rethink_seed_1}}}

 --x-network-driver=overlayフラグはコンテナのeth0にOverlayネットワークを作成します。

$ docker exec minion-3/rethink_proxy_1 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
134: eth0: <BROADCAST,MULTICAST,UP,LOWER_UP> mtu 1450 qdisc noqueue state UP group default
link/ether 02:42:0a:00:00:04 brd ff:ff:ff:ff:ff:ff
inet 10.0.0.4/24 scope global eth0
valid_lft forever preferred_lft forever
inet6 fe80::42:aff:fe00:4/64 scope link
valid_lft forever preferred_lft forever
136: eth1: <BROADCAST,MULTICAST,UP,LOWER_UP> mtu 1500 qdisc noqueue state UP group default
link/ether 02:42:ac:12:00:03 brd ff:ff:ff:ff:ff:ff
inet 172.18.0.3/16 scope global eth1
valid_lft forever preferred_lft forever
inet6 fe80::42:acff:fe12:3/64 scope link
valid_lft forever preferred_lft forever

 /etc/hostsにもOverlayネットワークに参加してホスト名が登録されているので、Dockerホストをまたいだ名前解決ができます。

$ docker exec minion-3/rethink_proxy_1 cat /etc/hosts

10.0.0.4 f704478aaadf
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
10.0.0.2 rethink_seed_1
10.0.0.2 rethink_seed_1.rethink
10.0.0.3 rethink_worker_1
10.0.0.3 rethink_worker_1.rethink
10.0.0.5 rethink_worker_2
10.0.0.5 rethink_worker_2.rethink
10.0.0.6 rethink_worker_3
10.0.0.6 rethink_worker_3.rethink


scale

 upしている状態でworkerサービスのコンテナを3台にscaleします。

$ docker-compose \

--x-networking \
--x-network-driver=overlay \
scale worker=3
Creating and starting 2 ... done
Creating and starting 3 ... done

 anti-affinityのフィルターを指定するとworkerサービスのコンテナはなるべく同じDockerホスト上で起動しないようスケジュールされます。worker=3としてSwarmクラスタのノード数と合わせたので1つずつコンテナが起動しました。

$ docker ps

CONTAINER ID IMAGE COMMAND CREATED STATUS PORTS NAMES
d6a1e40685f9 rethinkdb:2 "rethinkdb --bind all" 8 seconds ago Up 7 seconds 8080/tcp, 28015/tcp, 29015/tcp minion-3/rethink_worker_3
4eb7c2959112 rethinkdb:2 "rethinkdb --bind all" 8 seconds ago Up 7 seconds 8080/tcp, 28015/tcp, 29015/tcp minion-1/rethink_worker_2
b9f13b49004a rethinkdb:2 "rethinkdb proxy --bi" 2 minutes ago Up 2 minutes 28015/tcp, 10.3.0.103:8080->8080/tcp, 29015/tcp minion-3/rethink_proxy_1
581d02852c24 rethinkdb:2 "rethinkdb --bind all" 2 minutes ago Up 2 minutes 8080/tcp, 28015/tcp, 29015/tcp minion-2/rethink_worker_1
4ae146ed7671 rethinkdb:2 "rethinkdb -n seed --" 2 minutes ago Up 2 minutes 28015/tcp, 29015/tcp, 10.3.0.101:8088->8080/tcp minion-1/rethink_seed_1


トラブルシュート

 --x-networkingをつけないでscaleしたコンテナには/etc/hostsが入りません。scaleしたコンテナが同じDockerホストのコンテナも名前解決ができなくなり、少し嵌りました。

$ docker exec minion-3/rethink_worker_3 cat /etc/hosts

172.17.0.3 8df54f957347
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