Network
网络命名空间。linux kernel 提供的网络虚拟化的功能。创建多个隔离的网络空间。每个空间内 firewall, ether card, router table,协议栈 都是独立的,就像单独主机。
Namespace是Linux提供的一种对于系统全局资源的隔离机制;从进程的视角来看,同一个namespace中的进程看到的是该namespace自己独立的一份全局资源,
【实验】动手实现一下下面
# 创建namespace
ip netns add ns1
ip netns add ns2
ip netns exec ns1 ip a
创建一条 veth pair 连接:
ip link add veth-ns1 type veth peer name veth-ns2
可以发现此时多了两个网络接口:
两个接口 interface 的名字分别为: veth-ns1 veth-ns2
把他们分配给两个 namespace:
ip link set veth-ns1 netns ns1
ip link set veth-ns2 netns ns2
插上了:
ns2 也一样。
下面给他俩分配 ip address:
ip netns exec ns1 ip a add 192.168.1.1/24 dev veth-ns1
ip netns exec ns1 ip a add 192.168.1.2/24 dev veth-ns2
让网卡UP:
ip netns exec ns1 ip link set dev veth-ns1 up
ip netns exec ns2 ip link set dev veth-ns2 up
可以 ping 通了:
ns2 也一样。
CNM 容器网络模型。一种规范。沙盒sadbox + 终端endpoint + 网络network
sadbox -> namespace
endpoint -> veth interface 网卡
网桥和 router 的区别: 网桥用于同构网络,同网段通信;router用于异构网络,不同网段通信。
如上图。注意,C身上的两个终端(网卡)是不能通信的,除非有内部路由器。
上图第一个是 “单机桥接网络”。
你可以自己给 docker 添加 network. docker run 时还可以连:
-network network Connect a container to a network
DRIVER 驱动就是代码实现。
bridge network 是由 Bridge driver 驱动创建的,并创建一个默认网桥 docker0。
现实生活中真实的网桥长这样:
docker network inspect bridge
几个重要字段:
{
"Name": "bridge",
"Driver": "bridge",
"IPAM": {
"Config": [
{
"Subnet": "172.17.0.0/16",
"Gateway": "172.17.0.1"
}
]
},
"Containers": {
"79a86.............":{
"Name": "container0",
"IPv4Address": "172.17.0.2/16"
},
"d61ee3.............":{
"Name": "container0",
"IPv4Address": "172.17.0.2/16"
}
},
"Options": {
"com.docker.network.bridge.name": "docker0"
}
}
该网络中有两个container, 用的 docker0 做的网桥。
bridge network 是由 Bridge driver 创建的,并创建一个默认网桥 docker0。 container 与网桥间通过 veth pair 连接, 网桥与外网间通过 NAT 网络地址转换技术 连接。
我们还可以把容器们布置成这种结构:
用 inspect
可以看到如下信息, 就不截图了。
container | IP Addr |
---|---|
bb1-interface1 | 172.17.0.2/16 |
bb2-interface1 | 172.17.0.3/16 |
bb2-interface2 | 172.18.0.2/16 |
bb3-interface1 | 172.18.0.3/16 |
一个 network namespace 就代表一个独立的主机,一个容器就对应一个 namespace,所以一个容器就代表了网络中的一个独立主机。
CNM 是规范,Libnetwork 是规范的实现。Driver 是 Libnetwork 中不同网络模式的实现。