参考訳：network コマンドの動作

Work with network commands
http://docs.docker.com/engine/userguide/networking/work-with-networks/

----
# network コマンドの動作

このページでは、network サブコマンドの例を紹介します。コマンドは Docker ネットワークと、ネットワーク内のコンテナを相互に使えるようにします。コマンドは Docker エンジン CLI を使って利用できます。コマンドは次のようなものです。


* `docker network create`
* `docker network connect`
* `docker network ls`
* `docker network rm`
* `docker network disconnect`
* `docker network inspect`

必須ではありませんが、このセクションで例に取り組む前に [Docker ネットワークの理解](http://qiita.com/zembutsu/items/1da05cb6a60e1c5acc25)についてを読んでおくことは良い考えです。例では `bridge` ネットワークを扱いますので、すぐに試すことができます。それよりも `overlay` ネットワークについて知りたい場合は、こちらより[マルチ・ホスト・ネットワーク導入ガイド](http://qiita.com/zembutsu/items/36032ee78e82278b3c6a)をお読みください。

## ネットワークの作成

Docker エンジンをインストールすると、Docker エンジンは自動的に `bridge` ネットワークを作成します。このネットワークは `docker0` ブリッジに対応するものであり、エンジンが伝統的に頼っているものです。このネットワークについて説明を付け加えるとすると、自分自身で `bridge` や `overlay` ネットワークを作成できます。

```
$ docker network create simple-network
de792b8258895cf5dc3b43835e9d61a9803500b991654dacb1f4f0546b1c88f8
$ docker network inspect simple-network
[
    {
        "Name": "simple-network",
        "Id": "de792b8258895cf5dc3b43835e9d61a9803500b991654dacb1f4f0546b1c88f8",
        "Scope": "local",
        "Driver": "bridge",
        "IPAM": {
            "Driver": "default",
            "Config": [
                {}
            ]
        },
        "Containers": {},
        "Options": {}
    }
]
```

`bridge` ネットワークが望ましくなければ、事前調整をすることで `overlay` ネットワークを使うこともできます。調整とは次のようなものです：

* キーバリュー・ストアに対するアクセス。エンジンがサポートするキーバリュー・ストアは、Consul、Etcd、Zookeeper（分散ストア）です。
* ホストのクラスタが、キーバリュー・ストアに接続する。
* Swarm の各ホスト上で動作するエンジン `daemon` に、適切な設定を行う。

`docker デーモン` が `overlaye` ネットワークをサポートするオプションは、次の通りです：

* `--cluster-store`
* `--cluster-store-opt`
* `--cluster-advertise`

これらを使う代わりに、Docker Swarm をインストールしてクラスタを管理するのも良い考えです。実装にあたって、Swarm は高度なディスカバリとサーバ管理を提供します。

ネットワークを作成するとき、デフォルトではエンジンはサブネットが重複しないネットワークを作成します。このデフォルト設定は `--subnet` オプションを直接指定することにより上書き可能です。`bridge` ネットワーク上では、単一のサブネットのみ作成可能です。`overlay` ネットワークは複数のサブネットをサポートします。

`--subnetwork` オプションに加えて、他にも `--gateway` `--ip-range` `--aux-address` オプションを指定可能です。

```
$ docker network create -d overlay
  --subnet=192.168.0.0/16 --subnet=192.170.0.0/16
  --gateway=192.168.0.100 --gateway=192.170.0.100
  --ip-range=192.168.1.0/24
  --aux-address a=192.168.1.5 --aux-address b=192.168.1.6
  --aux-address a=192.170.1.5 --aux-address b=192.170.1.6
  my-multihost-network
```

サブネットが重複しないように気をつけてください。もし重複する場合、ネットワークの作成に失敗し、エンジンはエラーを返します。

## コンテナへの接続 (attach)

コンテナに対して、動的に１つまたは複数のネットワークを接続できます。これらのネットワークは、バックエンドのネットワークが同じでも違っていても構いません。接続すると、コンテナは他のコンテナに対して IP アドレスか名前で通信できます。

`overlay` ネットワークかカスタム・プラグインでは、マルチホスト接続をサポートしていますが、異なったホストから起動した場合もまた、この方法により通信可能となります。

２つのコンテナを作成する例：

```
$ docker run -itd --name=container1 busybox
18c062ef45ac0c026ee48a83afa39d25635ee5f02b58de4abc8f467bcaa28731

$ docker run -itd --name=container2 busybox
498eaaaf328e1018042c04b2de04036fc04719a6e39a097a4f4866043a2c2152
```

それから、分離するための `bridge` ネットワークを作成し、テストしてみましょう。

```
$ docker network create -d bridge isolated_nw
f836c8deb6282ee614eade9d2f42d590e603d0b1efa0d99bd88b88c503e6ba7a
```

`container2` にネットワークを接続し、`inspect` でネットワークが接続されているか確認します：

```
$ docker network connect isolated_nw container2
$ docker network inspect isolated_nw
[[
    {
        "Name": "isolated_nw",
        "Id": "f836c8deb6282ee614eade9d2f42d590e603d0b1efa0d99bd88b88c503e6ba7a",
        "Scope": "local",
        "Driver": "bridge",
        "IPAM": {
            "Driver": "default",
            "Config": [
                {}
            ]
        },
        "Containers": {
            "498eaaaf328e1018042c04b2de04036fc04719a6e39a097a4f4866043a2c2152": {
                "EndpointID": "0e24479cfaafb029104999b4e120858a07b19b1b6d956ae56811033e45d68ad9",
                "MacAddress": "02:42:ac:15:00:02",
                "IPv4Address": "172.21.0.2/16",
                "IPv6Address": ""
            }
        },
        "Options": {}
    }
]
```

エンジンが自動的に `container2` に IP アドレスを割り当てていることがわかります。ネットワーク作成時に `--subnetwork` を指定すると、ネットワークは割り当てられたアドレスを使います。次は３つめのコンテナを起動します。`docker run` コマンドで `--net` オプションを使うことにより、どのネットワークに接続するか指定して起動します：

```
$ docker run --net=isolated_nw -itd --name=container3 busybox
c282ca437ee7e926a7303a64fc04109740208d2c20e442366139322211a6481c
```

それから、`container3` が使用しているネットワーク・リソースを調べます。

```
$ docker inspect --format='{{json .NetworkSettings.Networks}}'  container3
{"isolated_nw":{"EndpointID":"e5d077f9712a69c6929fdd890df5e7c1c649771a50df5b422f7e68f0ae61e847","Gateway":"172.21.0.1","IPAddress":"172.21.0.3","IPPrefixLen":16,"IPv6Gateway":"","GlobalIPv6Address":"","GlobalIPv6PrefixLen":0,"MacAddress":"02:42:ac:15:00:03"}}
```

このコマンドを `container2` でも繰り返します。Python をインストールしていれば、次のように表示されます。

```
$ docker inspect --format='{{json .NetworkSettings.Networks}}'  container2 | python -m json.tool
{
    "bridge": {
        "EndpointID": "281b5ead415cf48a6a84fd1a6504342c76e9091fe09b4fdbcc4a01c30b0d3c5b",
        "Gateway": "172.17.0.1",
        "GlobalIPv6Address": "",
        "GlobalIPv6PrefixLen": 0,
        "IPAddress": "172.17.0.3",
        "IPPrefixLen": 16,
        "IPv6Gateway": "",
        "MacAddress": "02:42:ac:11:00:03"
    },
    "isolated_nw": {
        "EndpointID": "0e24479cfaafb029104999b4e120858a07b19b1b6d956ae56811033e45d68ad9",
        "Gateway": "172.21.0.1",
        "GlobalIPv6Address": "",
        "GlobalIPv6PrefixLen": 0,
        "IPAddress": "172.21.0.2",
        "IPPrefixLen": 16,
        "IPv6Gateway": "",
        "MacAddress": "02:42:ac:15:00:02"
    }
}
```

`container2` は２つのネットワークに属しているのが分かります。１つはコンテナを起動する時の、デフォルトで参加した `bridge` ネットワーク。もう１つは後から接続した `isolated_nw` です。

図：

`container3` の場合は、`docker run` 実行時に `isolated_nw` に接続するように指定したので、コンテナは `bridge` に繋がりません。

`docker attach` コマンドを使って実行中の `container2` に接続詞、ネットワーク・スタックを確認します：

```
$ docker attach container2
```

コンテナのネットワーク・スタックに２つのイーサネット・インターフェースが見えるでしょう。１つはデフォルトの bridge ネットワークで、もう１つは `isolated_nw` ネットワークです。

```
/ # ifconfig
eth0      Link encap:Ethernet  HWaddr 02:42:AC:11:00:03  
          inet addr:172.17.0.3  Bcast:0.0.0.0  Mask:255.255.0.0
          inet6 addr: fe80::42:acff:fe11:3/64 Scope:Link
          UP BROADCAST RUNNING MULTICAST  MTU:9001  Metric:1
          RX packets:8 errors:0 dropped:0 overruns:0 frame:0
          TX packets:8 errors:0 dropped:0 overruns:0 carrier:0
          collisions:0 txqueuelen:0
          RX bytes:648 (648.0 B)  TX bytes:648 (648.0 B)

eth1      Link encap:Ethernet  HWaddr 02:42:AC:15:00:02  
          inet addr:172.21.0.2  Bcast:0.0.0.0  Mask:255.255.0.0
          inet6 addr: fe80::42:acff:fe15:2/64 Scope:Link
          UP BROADCAST RUNNING MULTICAST  MTU:1500  Metric:1
          RX packets:8 errors:0 dropped:0 overruns:0 frame:0
          TX packets:8 errors:0 dropped:0 overruns:0 carrier:0
          collisions:0 txqueuelen:0
          RX bytes:648 (648.0 B)  TX bytes:648 (648.0 B)

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)
```

コンテナの `etc/hosts` ファイルを表示します：

```
/ # cat /etc/hosts
172.17.0.3	498eaaaf328e
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
172.21.0.3	container3
172.21.0.3	container3.isolated_nw
```

`isotated_nw` はユーザによって定義されたものです。Docker ネットワーク機能は適切な名前解決ができるよう `/etc/hosts` を更新します。`container2` の内部では、`container3` に対して名前で ping できるでしょう。

```
/ # ping -w 4 container3
PING container3 (172.21.0.3): 56 data bytes
64 bytes from 172.21.0.3: seq=0 ttl=64 time=0.070 ms
64 bytes from 172.21.0.3: seq=1 ttl=64 time=0.080 ms
64 bytes from 172.21.0.3: seq=2 ttl=64 time=0.080 ms
64 bytes from 172.21.0.3: seq=3 ttl=64 time=0.097 ms

--- container3 ping statistics ---
4 packets transmitted, 4 packets received, 0% packet loss
round-trip min/avg/max = 0.070/0.081/0.097 ms
```

デフォルトのブリッジ・ネットワークの場合は、このようになりません。`container2` と `container1` は、どちらもデフォルトのブリッジ・ネットワークに接続しています。Docker はこのブリッジ・ネットワークに対してディスカバリ・サービス（訳者注：ホスト名に応じて、自動で名前解決する機能）を提供しません。そのため、`/etc/hosts` ファイルに記述しない限り、`container1` という名前で ping しても失敗します。

```
/ # ping -w 4 container1
ping: bad address 'container1'
```

`container1` の IP アドレスを使う場合は、ping は成功します：

```
/ # ping -w 4 172.17.0.2
PING 172.17.0.2 (172.17.0.2): 56 data bytes
64 bytes from 172.17.0.2: seq=0 ttl=64 time=0.095 ms
64 bytes from 172.17.0.2: seq=1 ttl=64 time=0.075 ms
64 bytes from 172.17.0.2: seq=2 ttl=64 time=0.072 ms
64 bytes from 172.17.0.2: seq=3 ttl=64 time=0.101 ms

--- 172.17.0.2 ping statistics ---
4 packets transmitted, 4 packets received, 0% packet loss
round-trip min/avg/max = 0.072/0.085/0.101 ms
```

もし `container1` と `container2` を接続したい場合は、`docker run --link` コマンドを使うことにより、２つのコンテナ間は IP アドレス同様、名前でもやりとり可能になります。

`container2` をデタッチして離れるには、`CtRL-p CTRL-q` を実行します。

この例 における`container2` は、`container1` と `container3`の 両ネットワークに接続しています。しかし `container3` と `container1` は同じネットワークではないため、通信できません。試しに、`container3` から `container1` に IP アドレスで ping してみます。

```
$ docker attach container3
/ # ping 172.17.0.2
PING 172.17.0.2 (172.17.0.2): 56 data bytes
^C
--- 172.17.0.2 ping statistics ---
10 packets transmitted, 0 packets received, 100% packet loss
```

コンテナをネットワークに接続するには、コンテナが実行中の必要があります。もしコンテナを停止すると、所属するネットワークの状態を確認しようとしても、表示されません。`docker network inspect` コマンドは、コンテナ実行中のみ表示するものです。

## コンテナの切断 (disconnect)

コンテナをネットワークから切断するのに `docker network disconnect` コマンドを使います。

```
$ docker network disconnect isolated_nw container2

docker inspect --format='{{json .NetworkSettings.Networks}}'  container2 | python -m json.tool
{
    "bridge": {
        "EndpointID": "9e4575f7f61c0f9d69317b7a4b92eefc133347836dd83ef65deffa16b9985dc0",
        "Gateway": "172.17.0.1",
        "GlobalIPv6Address": "",
        "GlobalIPv6PrefixLen": 0,
        "IPAddress": "172.17.0.3",
        "IPPrefixLen": 16,
        "IPv6Gateway": "",
        "MacAddress": "02:42:ac:11:00:03"
    }
}


$ docker network inspect isolated_nw
[[
    {
        "Name": "isolated_nw",
        "Id": "f836c8deb6282ee614eade9d2f42d590e603d0b1efa0d99bd88b88c503e6ba7a",
        "Scope": "local",
        "Driver": "bridge",
        "IPAM": {
            "Driver": "default",
            "Config": [
                {}
            ]
        },
        "Containers": {
            "c282ca437ee7e926a7303a64fc04109740208d2c20e442366139322211a6481c": {
                "EndpointID": "e5d077f9712a69c6929fdd890df5e7c1c649771a50df5b422f7e68f0ae61e847",
                "MacAddress": "02:42:ac:15:00:03",
                "IPv4Address": "172.21.0.3/16",
                "IPv6Address": ""
            }
        },
        "Options": {}
    }
]
```

コンテナをネットワークから切断すると、接続していたネットワーク上の他のコンテナとは通信できません。この例の `container2` は、`isolated_nw` 上の `container3` と通信できなくなっています。

```
$ docker attach container2

/ # ifconfig
eth0      Link encap:Ethernet  HWaddr 02:42:AC:11:00:03  
          inet addr:172.17.0.3  Bcast:0.0.0.0  Mask:255.255.0.0
          inet6 addr: fe80::42:acff:fe11:3/64 Scope:Link
          UP BROADCAST RUNNING MULTICAST  MTU:9001  Metric:1
          RX packets:8 errors:0 dropped:0 overruns:0 frame:0
          TX packets:8 errors:0 dropped:0 overruns:0 carrier:0
          collisions:0 txqueuelen:0
          RX bytes:648 (648.0 B)  TX bytes:648 (648.0 B)

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)

/ # ping container3
PING container3 (172.20.0.1): 56 data bytes
^C
--- container3 ping statistics ---
2 packets transmitted, 0 packets received, 100% packet loss
```

`container2` は、まだブリッジ・ネットワークに対する完全な接続性を持っています。

```
/ # ping container1
PING container1 (172.17.0.2): 56 data bytes
64 bytes from 172.17.0.2: seq=0 ttl=64 time=0.119 ms
64 bytes from 172.17.0.2: seq=1 ttl=64 time=0.174 ms
^C
--- container1 ping statistics ---
2 packets transmitted, 2 packets received, 0% packet loss
round-trip min/avg/max = 0.119/0.146/0.174 ms
/ #
```

## ネットワークの削除 (remove)

ネットワーク上のすべてのコンテナが停止または切断すると、ネットワークを削除(remove)できます。

```
$ docker network disconnect isolated_nw container3
```

```
docker network inspect isolated_nw
[
    {
        "Name": "isolated_nw",
        "Id": "f836c8deb6282ee614eade9d2f42d590e603d0b1efa0d99bd88b88c503e6ba7a",
        "Scope": "local",
        "Driver": "bridge",
        "IPAM": {
            "Driver": "default",
            "Config": [
                {}
            ]
        },
        "Containers": {},
        "Options": {}
    }
]

$ docker network rm isolated_nw
```

全てのネットワーク一覧から `isolated_nw` が削除されたのを確認します。

```
$ docker network ls
NETWORK ID          NAME                DRIVER
72314fa53006        host                host                
f7ab26d71dbd        bridge              bridge              
0f32e83e61ac        none                null  
```