使用 Calico CNI 打通 Kubernetes 集群网络

一些废话

k8s 的 cni 其中一个重要的功能是将 Pod 的网络栈接管后使用某种协议封包从而在 node 之间传输。比如:

  • flanal:基于 udp 的私有协议
  • cilium:vxlan
  • calico:IPIP

在通过路由和转发将数据包发送至目标地址所在的 Node 节点上,让 Node 节点上运行的网络组件解包后将原始网络数据通过 CNI 接口传递给 Pod 容器。

这样一来,要完成传统网络与 k8s 的 SDN 网络互联互通,需要解决封包格式与路由条目这两个问题。

好在我们的 calico 这个网络组件诞生就是为了和传统网络协议所兼容。通过简单的配置,可以使 calico 对虚拟网络的数据不封包,直接三层转发。即 calico 的 BGP 模式。

calico 在每个 Node 节点上运行 BGP 协议以和集群其他节点交换路由表,使每个 Node 节点都变成了一台 BGP 路由器。从而使得 k8s 的虚拟网络,在原有的网络上直接三层转发。

同时,我们还可以在内网的 DNS 服务器上为集群的域名配置解析委派,将 cluster.local 域转发至集群 coreDNS 进行解析,即可完成集群域名互通。

实操

(一)中,我们使用 cilium 替换了 kubeadm 预装的 kube-proxy 组件。但我们这里要用 calico ,就需要把 kube-proxy 请回来。

在生成默认配置后,我们需要向 kubeadm.init.yaml 文件追加以下内容:

---
apiVersion: kubeproxy.config.k8s.io/v1alpha1
kind: KubeProxyConfiguration
mode: ipvs
ipvs:
  strictARP: true

kubeadm 会在初始化集群时传将上面的配置传给 kube-proxykube-proxy 默认会使用 iptables 规则做 DNAT 来实现 service,效率略低,因此我们改用了 ipvs 模式,也就是经典 lvs。同时,我们这里设置 ipvsARP 模式为 strict,方便后期使用 metal-lb 的 2 层模式。

启动第一个 controlplane 节点 中,将 --skip-phases=addon/kube-proxy 参数去掉,即:

kubeadm init \
    --config kubeadm.init.yaml \
    --upload-certs 

calico3.15 开始学坏了,你往集群里直接安装的不是 calico ,而是一个叫做 tigeraOperator 的控制器。这个控制器会通过 Installation.operator.tigera.io 这个 CRD 里设置的安装参数来帮你安装 calico。不过,比起之前 calico 放弃 helm 安装,这个 tigeraOperator 是支持 helm 的,并且支持使用 helm values 设置 Installation 这个 CRD。

helm repo add projectcalico https://projectcalico.docs.tigera.io/charts

helm install calico projectcalico/tigera-operator \
    --version v3.22.1 \
    --set installation.registry=192.168.1.10:8082' \
    --set tigeraOperator.registry=null \
    --set calicoctl.image='calico/ctl'

还记得 192.168.1.10:8082 么,这是我们在(一)中搭建的私库。由于 tigeraOperator 写死了要在镜像名里带上仓库地址,installation.registry 留空会导致直接使用 docker.io 仓库——这样每个 node 都需要直接连接公网仓库下载一次镜像,过于浪费带宽了。我们还是提前把镜像下载好 push 进咱们自己的仓库里吧。

设置

虽说 calico 使用 BGP 协议与路由器或者三层交换机协商路由表,但其实用的是 iBGP 协议,和运营商、IDC 之间的 eBGP 还是有区别的。

BGP 呢首先就要有 AS 号,这个号和 IP 地址一样是需要统一分配和购买的。好在 64512 - 65534 这一段是专门分配用来做私有编号的,就像 IP 里面的私有地一样。这里我们就用 64512

kind: BGPConfiguration
apiVersion: crd.projectcalico.org/v1
metadata:
  generation: 1
  name: default
spec:
  asNumber: 64512
  logSeverityScreen: Info
  nodeToNodeMeshEnabled: false
  serviceClusterIPs:
    - cidr: 10.43.0.0/16
---
kind: BGPPeer
apiVersion: crd.projectcalico.org/v1
metadata:
  generation: 1
  name: router-or-l3sw
spec:
  asNumber: 64512
  peerIP: 192.168.1.1

这里我们预设了 192.168.1.1 这个 ip 是你的路由器或者三层交换机——不管是啥,你需要在这个设备上开启 BGP 协议,使用同样的 AS 号码 64512来开启 iBGP,同时设置集群所有 nodeIPpeer,并设置 Route Reflector。之后导入上文的 calicoCRD 配置,就可以去路由器上观察 BGP 状态和路由表了。

使用

  • Pod 容器 IP 和 Service 服务 clusterip 集群 IP 均可直接访问,注意需要添加端口访问。
  • Pod 容器 IP 直接使用服务本身监听的端口访问。Service 服务 clusterip 集群 IP 使用服务映射端口访问。
  • Pod 容器 IP 每次重启、部署、更新均会发生变更。Service 服务 clusterip 集群 IP 不会。
  • 集群服务可以通过域名访问。格式是【服务名】.【命名空间】.svc.cluster.local:【服务端口】。
最后编辑于
©著作权归作者所有,转载或内容合作请联系作者
【社区内容提示】社区部分内容疑似由AI辅助生成,浏览时请结合常识与多方信息审慎甄别。
平台声明:文章内容(如有图片或视频亦包括在内)由作者上传并发布,文章内容仅代表作者本人观点,简书系信息发布平台,仅提供信息存储服务。

相关阅读更多精彩内容

友情链接更多精彩内容