标题来自 XCOM2 的成就之一 WHO NEEDS TYGAN
, 要求在最后一关使用初级科技通关, 简直恶趣味..
总之成功用 runc 调用 CNI 建立了 calico 网络, 流程是这样的:
- 安装 runc, calico, etcd, 创建 calico ippool:
- apiVersion: projectcalico.org/v3
kind: IPPool
metadata:
name: $POOL_NAME
spec:
natOutgoing: true
cidr: $POOL_CIDR
-
安装 calico CNI:
- curl -OL https://github.com/projectcalico/cni-plugin/releases/download/v3.4.4/calico-amd64
- curl -OL https://github.com/projectcalico/cni-plugin/releases/download/v3.4.4/calico-ipam-amd64
- mv ./calico-amd64 /opt/cni/bin/calico
- mv ./calico-ipam-amd64 /opt/cni/bin/calico-ipam
- chmod +x /opt/cni/bin/calico /opt/cni/bin/calico-ipam
-
准备 CNI 配置到 /etc/cni/net.d/
{
"name": "calico-cni",
"cniVersion": "0.3.1",
"type": "calico",
"etcd_endpoints": "http://127.0.0.1:2379",
"log_level": "info",
"ipam": {
"type": "calico-ipam",
"ipv4_pools": ["$POOL_NAME"]
}
}
当然要改成自己的 pool name.
-
然后 runc 走起来
- mkdir rootfs
- docker export $(docker create busybox) | tar -C rootfs -xvf -
- runc spec
-
骚的来了, 在 config.json 里加入 hook 调用 CNI:
"hooks": {
"prestart": [
{
"env": ["PATH=/opt/cni/bin/:/usr/local/sbin:/usr/local/bin:/usr/sbin:/usr/bin:/sbin:/bin:/usr/games:/usr/local/games:/snap/bin", "CNI_PATH=/opt/cni/bin"],
"path": "/root/cni-master/scripts/exec-plugins.sh",
"args": [
"/root/cni-master/scripts/exec-plugins.sh",
"add",
"zzc",
"/run/netns/zzc"
]
}
]
}
对了要先安装 cnitool, 我是直接下载 github.com/containernetworking/cni; 然后也要手动创建 netns zzc
(智障川)
- runc run zzc, 可以看到容器是成功集成到 calico SDN.
正好借这贴说下 docker 和 Kubernetes 的创建流程.
docker 的流程是:
- start container 的第一步, 调用 containerd 之前, 先把 CNM 流程走了, 请求 IP, 创建内部 endpoint 对象
- 然后 containerd NewContainer 时候在 OCI spec 里塞上 prestart hook, 类似
libnetwork-setkey $CONT_ID $CONTROL_ID
- 然后在 runc 启动容器前运行这个 hook, 会通过 controller id 绑定的一个 unix socket 给 dockerd 发请求, 然后 dockerd 会给容器创建好的 netns 设置上申请好的 IP 和 veth
Kubernetes:
- CRI 先创建好 pause 容器(呕
- 直接调用 CNI 申请 IP + 绑定到 pause 容器 netns 一步完成
- 然后 OCI spec 里指定 network namespace path 完事儿
可以看到两个的做法作风是完全不同的