LoginSignup
1
1

Dockerネットワーク間でPINGを通す

Posted at

はじめに

一般のご家庭向けです

逸般の誤家庭の方は、物理マシンでお試しください
※ YouTubeへのリンクです。音量に注意してください

この記事は

「Dockerのネットワークを使って、ネットワークの勉強をしたい」

そんな時、素早くDockerネットワークを構築できるとよい

素早くDockerネットワークを構築するための docker-compose.ymlと、その周辺フォルダー環境を書き残した記事です

コピペに次ぐコピペで、とりあえずAネットの端末からBネットの端末へPINGが通るようになります

フォルダ構成

適当な場所に適当なフォルダを作ったら
その下にdocker-compose.ymlを置く

さらに clietn1, client2, router フォルダをつくる

各フォルダの中には mnt フォルダと Dockerfile をつくる
mntフォルダにはentrypoint.shを入れる

以上!

│  docker-compose.yml
│
├─client1
│  │  Dockerfile
│  │
│  └─mnt
│          entrypoint.sh
│
├─client2
│  │  Dockerfile
│  │
│  └─mnt
│          entrypoint.sh
│
├─router
│  │  Dockerfile
│  │
│  └─mnt

Dockerfile

3つあるDockerfileの中身は共通です
Ubuntuをベースに、ネットワーク関連のパッケージをインストールしておきます

FROM ubuntu:latest

RUN apt update
RUN apt install -y vim iputils-ping iproute2 net-tools traceroute

※もっと軽量なイメージを使えばいいと思いましたが、今後実機を使うことを想定すると、無難なUbuntuがいいかなーと思いUbuntu採しました

docker-compose.yml

長ったらしく書いてますが、単に client1 が client2 に対してPING打つためだけの環境です

登場人物 IPアドレス 役割
client1 172.23.1.10 PING送る人
client1 172.23.2.10 PING受ける人
router 172.23.1.250, 172.23.2.250 2つのネットワークに所属してPING中継する人
version: '3.9'

services:
  client1:
    build: ./client1
    container_name: client1
    hostname: client1
    tty: true
    stdin_open: true
    privileged: true
    volumes:
      - ./client1/mnt:/mnt
    networks:
      delay-net1:      
        ipv4_address: 172.23.1.10
    command: bash -c "bash /mnt/entrypoint.sh && /bin/bash"

  client2:
    build: ./client2
    container_name: client2
    hostname: client2
    tty: true
    stdin_open: true
    privileged: true
    volumes:
      - ./client2/mnt:/mnt
    networks:
      delay-net2:      
        ipv4_address: 172.23.2.10
    command: bash -c "bash /mnt/entrypoint.sh && /bin/bash"

  router:
    build: ./router
    container_name: router
    hostname: router
    tty: true
    stdin_open: true
    volumes:
      - ./router/mnt:/mnt
    networks:
      delay-net1:
        ipv4_address: 172.23.1.250
      delay-net2:      
        ipv4_address: 172.23.2.250
    sysctls:
      - net.ipv4.ip_forward=1
      
networks:
  delay-net1:
    ipam:
      driver: default
      config:
        - subnet: 172.23.1.0/24
  delay-net2:
    ipam:
      driver: default
      config:
        - subnet: 172.23.2.0/24

いくつかのポイント説明

ボリュームをマウント

/mntフォルダを介して、ホストマシンでつくったシェルスクリプトなどを共有します

    volumes:
      - ./client1/mnt:/mnt

mntフォルダにentrypoint.shを入れておきます

ルーティング

ルーターは各クライアントのデフォルトゲートウェイとなります
デフォルトゲートウェイとなるためには、静的ルーティングを変更する必要があります(既定ではインターネットに向かってパケットを送信してしまう)

静的ルーティングを変更するには管理者権限が要るので、privileged: trueとしています

また、Ubuntuは既定でポートフォワードをしてくれますが、無効にした場合の挙動もみてみたいので、あえてポートフォワードの設定を明示しています
今回はポートフォワードしてもらってPING中継するので、下記設定です

    sysctls:
      - net.ipv4.ip_forward=1

コンテナに入って作業するために

下記の3行は、コンテナがすぐに終了しなようにするための措置です
意味はよくわかりません
コマンドでエントリポイントのシェルスクリプトを実行したあとに、&&でつないでbashを再度実行してます

    tty: true
    stdin_open: true
    command: bash -c "bash /mnt/entrypoint.sh && /bin/bash"

entrypoint.sh

エントリポイントで静的ルーティングを設定します
client1,2でそれぞれゲートウェイが異なるので、2つのシェルスクリプトを掲載しますが、差異は微々たるものです

  • client1
    • 172.23.2.0/24に向かうパケットは172.23.1.250(ルータ)を目指して送出
#!/bin/bash

# 静的ルーティング
ip route add 172.23.2.0/24 via 172.23.1.250
  • client2
    • 172.23.1.0/24に向かうパケットは172.23.2.250(ルータ)を目指して送出
#!/bin/bash

# 静的ルーティング
ip route add 172.23.1.0/24 via 172.23.2.250

いざ実行

docker-compose.ymlが置いてあるフォルダで下記コマンドを実行
docker compose up --build -d

クライアント1号機のコンテナに入って作業する
docker compose exec client1 bash

クライアント2号機に向けてtraceroutepingをした結果

client1  | traceroute to 172.23.2.10 (172.23.2.10), 30 hops max, 60 byte packets
client1  |  1  172.23.1.250  3.333 ms  0.153 ms  0.114 ms
client1  |  2  172.23.2.10  0.486 ms  0.168 ms  0.100 ms

client1  | PING 172.23.2.10 (172.23.2.10) 56(84) bytes of data.
client1  | 64 bytes from 172.23.2.10: icmp_seq=1 ttl=63 time=1.90 ms
client1  | 64 bytes from 172.23.2.10: icmp_seq=2 ttl=63 time=0.100 ms
client1  | 64 bytes from 172.23.2.10: icmp_seq=3 ttl=63 time=0.116 ms
client1  | 64 bytes from 172.23.2.10: icmp_seq=4 ttl=63 time=0.092 ms
client1  |
client1  | --- 172.23.2.10 ping statistics ---
client1  | 4 packets transmitted, 4 received, 0% packet loss, time 3118ms
client1  | rtt min/avg/max/mdev = 0.092/0.552/1.903/0.779 ms

ちゃんとルータ(172.23.1.250)を通っていることがわかる

おわりに

Dockerを使って手軽にPING疎通テストできる環境をつくった
しかもすべてスクリプトにお任せしているので、構築・破壊が容易
1年後でも、ここからコードをコピペすれば再現できる

今回つくったdocker-compose.ymlをベースにして
次回からはルータに機能を付与していきたい

パケットをわざと遅らせてみたり・・・(その布石がymlファイルの中にも書いてある)

付録 Docker Composeコマンド集

未来の自分のための備忘録

# Dockerfileを変更したときは --build 付ける
docker compose up -d
docker compose up --build -d

# Dockerfileを変更して、かつ再起動したいときは
docker compose down -v && docker compose up --build -d

# ログを見る
docker compose logs -f

# 今日はもう作業しないよ、ってとき
docker compose down -v

# 案外使わない再起動
docker compose restart

糸冬了!!

1
1
0

Register as a new user and use Qiita more conveniently

  1. You get articles that match your needs
  2. You can efficiently read back useful information
  3. You can use dark theme
What you can do with signing up
1
1