Pumbaで強制的にDockerコンテナ間のパケットをロスさせる

1年前の今頃、指定したDockerコンテナ間のパケットをロスさせるみたいなことをやっていた。

というのも、自分の学部4年での研究において分散システムのネットワーク分断の対策手法みたいなものを提案していた。そのアルゴリズムを簡易的に実装して、実際にネットワーク分断を発生させてスプリットブレインを起こそう。それを使って評価しよう。みたいなことをやった。

その時に巡り合ったのが今回紹介するPumbaである。

Pumbaとは

Pumbaはいわゆるカオスエンジニアリングツールの一種で、Dockerのコンテナ単位で手軽に様々な操作を行うことができる。

例えば任意のコンテナをkillしたりコンテナ間の通信のパケットをn%ロスさせたりすることができる。これを使うことで障害が起きた際にシステムがどのように動くのかを手元で観測するのが容易になる。

使い方

想定環境

  • MacBook Pro (16インチ, 2019)
  • macOS Big Sur 11.2.3

インストール

$ brew install pumba

任意コンテナ間のパケットをロス

ここでは、試しにalpineのDockerコンテナを2つ建ててその間のパケットをロスさせて観測してみようと思う。

1. Dockerネットワークを建てる

$ docker network create pumba_test_network

2. コンテナを建てる

ここではdebian:latestなイメージを用いているが、tcコマンドが使えるイメージなら何でもいい。

$ docker run --name container_1 --network pumba_test_network -itd debian:latest /bin/sh

$ docker run --name container_2 --network pumba_test_network -itd debian:latest /bin/sh

3. ローカルIP調べてpingを通す

container_1に入ってローカルIPを調べた後、container_2へpingを通す。

$ docker exec -it container_1 /bin/sh

====== container_1内 ======
$ ip addr
1: lo: <LOOPBACK,UP,LOWER_UP> mtu 65536 qdisc noqueue state UNKNOWN group default qlen 1000
    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
2: tunl0@NONE: <NOARP> mtu 1480 qdisc noop state DOWN group default qlen 1000
    link/ipip 0.0.0.0 brd 0.0.0.0
3: ip6tnl0@NONE: <NOARP> mtu 1452 qdisc noop state DOWN group default qlen 1000
    link/tunnel6 :: brd ::
92: eth0@if93: <BROADCAST,MULTICAST,UP,LOWER_UP> mtu 1500 qdisc noqueue state UP group default
    link/ether 02:42:ac:12:00:02 brd ff:ff:ff:ff:ff:ff link-netnsid 0
    inet 172.18.0.2/16 brd 172.18.255.255 scope global eth0
       valid_lft forever preferred_lft forever


$ ping container_2

4. pumbaのコマンド叩く

別でterminal開いてホストOS上でpumbaのコマンドを叩く。このコマンドで300秒間 container_2から172.18.0.2/32(container_1)へのパケットを100%ロスさせる事ができる。

$ pumba netem --duration 300s -target 172.18.0.2/32 loss -p 100 container_2

この状態でcontainer_1が投げているpingの様子を見ると多分止まってるはず。pumbaのコマンドを⌘+Cとかで止めるとpingが再度投げられ始める。

5. おまけ

先程はコンテナ2台で行ったが、複数台と複数台でパケットロスさせたりもできる。

下のコマンドは20台のコンテナを半分に分けてパケットロスさせたときの例。(実際に自分が実験で使ったやつ)

$ pumba netem --duration 330s -target 172.16.124.11/32 -target 172.16.124.12/32 -target 172.16.124.13/32 -target 172.16.124.14/32 -target 172.16.124.15/32 -target 172.16.124.16/32 -target 172.16.124.17/32 -target 172.16.124.18/32 -target 172.16.124.19/32 -target 172.16.124.20/32 loss -p 100 node1 node2 node3 node4 node5 node6 node7 node8 node9 node10

流石にここまで長いとコンテナ数が増減したときに手書きしたくなくなるので自分はコマンドを生成するスクリプト書いてた。

終わりに

今回は、B4のときに使ったPumbaについての記事をタイトルだけ書いて放置していたので1年眠らせて書いた。自分はパケットロスぐらいしか使うことがなかったが、ネットワーク遅延とかいろいろ面白そうな機能があるのでぜひいつか機会があったら触ってみたい。

コメントを残す

メールアドレスが公開されることはありません。 が付いている欄は必須項目です

CAPTCHA