Calico
Calico 是一项开放式源代码社区项目,可为容器和虚拟机提供联网功能。{:shortdesc}
Calico 基于开放式系统互连 (OSI) 模型的第三层(也称为第 3 层或网络层)构建。Calico 使用边界网关协议 (BGP) 来构建帮助实现代理程序节点间通信的路由表。通过使用该协议,Calico 网络可以实现更高的性能和更好网络隔离。
Calico 实施 Kubernetes 容器网络接口 (CNI) 作为插件,并为 Kubernetes 提供代理程序,以便为容器和 pod 提供联网功能。
Calico 创建第 3 层平面网络,并向每个 pod 分配完全可路由的 IP 地址。它将大型网络 CIDR 分割为较小的 IP 地址块,并将其中一个或多个较小的块分配到集群中的节点。分割是在 IBM Cloud Private 安装期间使用 CIDR 表示法的 config.yaml 中的 network_cidr 参数完成的。
缺省情况下,Calico 会在集群所有节点之间创建 BGP mesh,并将容器网络的路径广播至所有工作程序节点。每个节点均配置为充当子网的第 3 层网关。该子网分配到工作程序节点,并提供到主机上托管的 pod 子网的连接。所有节点都参与 BGP mesh,以将该工作程序节点的所有本地路径都广播道所有其他节点。集群外部的 BGP 同级可参与,但集群大小会影响这些外部同级接收到的 BGP 广播的数量。当集群扩展超过一定规模后,可能需要路由反射器。
有关更多信息,请参阅 Configuring BGP Peers。
路由 pod 流量时,Calico 使用诸如节点本地路由表和 iptable 等系统功能。所有 pod 流量都会先遍历 iptable 规则,然后再路由至其目标。
Calico 使用 etcd 键/值库来维持其状态。缺省情况下,在 IBM Cloud Private 中,Calico 使用与 Kubernetes 相同的 etcd 键/值库来存储策略和网络配置状态。
Calico 可配置为允许 pod 彼此通信,无论是否使用 IP-in-IP 隧道均可。IP-in-IP 为所有包添加了额外的头作为封装的一部分,但允许容器在其覆盖网络上通过几乎任何非重叠底层网络来进行通信。
在某些环境中,底层子网地址空间因受到约束而无权添加其他 IP 池。这种情况与某些公共云相似,而 Calico 正适用于此。但在无需覆盖网络的环境中,必须禁用 IP-in-IP 隧道以除去包封装开销并允许任何物理路由基础结构执行包检查,以便对其进行审计并保证合规性。在此类情况下,可通过向 BGP mesh 添加底层网络路由器来使底层网络发现其他 pod 子网。有关节点位于不同网络分段上时 Calico 网络的更多信息,请参阅跨不同网络分段的 Calico 网络。
Calico 组件
Calico 具有以下组件:
- calico/node agent]
- calico/cni
- calico/kube-controller
为确保节点满足 Calico 系统需求,请复查准备节点中的信息。

calico/node agent
此实体包含三个组件 - felix、bird 和 confd。
felix的主要职责是对于主机的 IPtables 和路径进行编程以提供您所需的来往该主机上的 pod 的连接。bird是面向 Linux® 的开放式源代码 BGP 代理程序,用于在主机之间交换路由信息。由felix编程的路径将由bird进行选取,以便在集群主机之间进行分发。confd会监视etcd数据存储器中对 BGP 配置进行的更改,例如,IPAM 信息、AS 编号等。它还可更改bird配置文件,并触发bird以在每台主机上重新装入这些文件。calico/node agent 可创建 veth 对,以将 pod 网络名称空间与主机的缺省网络名称空间相连。
calico/cni
CNI 插件通过为节点中托管的 pod 配置 IP 地址来提供 IP 地址管理 (IPAM) 功能。
calico/kube-controller
calico/kube-controller 可监视 Kubernetes NetworkPolicy 对象,并使 Calico 数据存储器与 Kubernetes 对象保持同步。每个节点上运行的 calico/node 使用 Calico etcd 数据存储器中的信息来对本地 iptable 进行编程。
calicoctl
calicoctl 是命令行工具,可用于管理 Calico 网络和安全策略以及其他 Calico 配置。它通过与 etcd 直接通信来处理数据存储器。它可提供多种资源管理命令,并可用于对 Calico 网络问题进行故障诊断。要设置 Calico CLI,请参阅安装 Calico CLI (calicoctl)。
跨不同网络分段的 Calico 网络
当节点位于不同网络分段上时,在底层和基础结构网络中通过路由器来连接这些节点。不同子网上的两个节点之间的流量会遍历作为两个子网的网关的路由器。如果路由器未发现 pod 子网,那么将无法在主机之间转发包。

有两种方法可用于处理这种情况:
-
可将 Calico 配置为针对节点上托管的每个子网在每个节点上创建 IP-in-IP 隧道端点。源自 pod 并且正在离开节点的任何包都将以 IP-in-IP 头进行封装,并且节点 IP 地址将用作为源。借助这种方式,基础结构路由器将无法看到 pod IP 地址。
由于在每个端点都需要执行额外的包处理以对包进行封装和解封,因此 IP-in-IP 隧道会带来额外的网络吞吐量和延迟。在裸机上,由于可将某些网络操作卸载至网络接口卡,因此开销不明显。但在虚拟机上,开销显著,并且还会受到系统管理器所配置和使用的 CPU 核心数和网络 I/O 技术的影响。如果使用的最大传输单元 (MTU) 大小较小,那么同样可能造成显著的额外包封装开销,因为这样会造成包分段。必须尽可能启用巨型帧。
-
第二个选项是使基础结构路由器发现 pod 网络。可通过在路由器上启用 BGP 并在集群中添加节点作为 BGP 同级来完成此操作。这些步骤允许路由器和主机在彼此之间交换路由信息。在此场景中,集群大小可发挥与在 BGP mesh 中相同的作用。在路由器上启用 BGP 后,集群中的每个节点都是路由器的同级。
适用于使用 Calico 容器网络的 IBM Cloud Private 配置选项
config.yaml:
network_type: calico
network_cidr: 10.1.0.0/16
calico_ipip_mode: Always
calico_tunnel_mtu: 1430
calico_ip_autodetection_method: can-reach={{ groups['master'][0] }}
-
network_type:选择calico以部署 Calico 作为容器网络(缺省值为calico) -
network_cidr:network_cidr:选择足够大的专用 IP 子网,该专用 IP 子网将供计划在集群上托管的所有工作负载使用。此 IP 范围不得与现有主机网络或service_cluster_ip_range冲突。根据添加到 IBM Cloud Private 的组件数目和安装的组件与功能部件数目,各版本之间的 IP 数目不尽相同。可通过列出所有已安装的 pod 来获取当前 IP 总数。如果有
N个工作程序节点并且目标为P个 pod,那么安全的 IP 范围是( N x P ) + N。此范围可容许N-1个节点不可用。缺省值为10.1.0.0/16,该值足以托管大型集群。 -
calico_ipip_mode:该选项可用于启用 IP-in-IP 隧道。必须在需要覆盖网络的环境中启用该选项,例如,在包含根据主机 IP 执行严格的源 IP 检查的出口包(例如,OpenStack)的环境中。如果基础结构路由器无法配置为允许交换 BGP 路由,那么同样需要启用该选项。当该参数设置为
Always时,需要允许ip protocol 4经过所有节点之间的基础结构防火墙(例如,OpenStack 中的安全组)。 -
calico_tunnel_mtu:此参数会在隧道设备和 pod 接口上设置相应的 MTU。利用此参数,即可根据基础结构网络的路径 MTU (PMTU) 来调整 MTU,以避免出现包分段。并且,在某些情况下,基础结构防火墙并未编程为允许传播 ICMP PMTU 错误消息。由此导致 L3 会话无法掌握 PMTU,从而可能导致包和连接丢失。缺省值为 1430,该值适用于大部分场景和 IaaS 网络,如 OpenStack Neutron VxLAN 网络。该值必须比接口 MTU 或 PMTU 少至少 20 个字节才能容纳 IP-in-IP 头。
-
calico_ip_autodetection_method:此参数用于选择节点上的接口以及用于跨节点间的 pod 对 pod 数据通信。有三种方法可用于帮助选择 pod 的数据路径。-
first-found该方法使用节点上最先找到的有效接口上的第一个有效 IP 地址。
-
interface=<interface name list>该参数接受一列以逗号分隔的正则表达式名称作为值。它使用指定接口上找到的第一个 IP 地址。
示例:
calico_ip_autodetection_method: interface=eth0 calico_ip_autodetection_method: interface=eth.* calico_ip_autodetection_method: interface=eth.*,ens.*注: 网络接口名称不得包含以下字符串:
docker.*、cbr.*、dummy.*、virbr.*、lxcbr.*、veth.*、lo、cali.*、tunl.*或flannel.*。 -
can-reach=<remote IP address or host name>can-reach方法是用节点的本地路由表。它还使用用于与指定目标地址进行通信的接口来确定 pod 网络接口。该参数接受远程 IP 地址或域名作为值。Calico 无法识别某些 IP。确保接口的 IP 不在以下范围内:
10.0.2.15/24:此 IP 范围是缺省的 vagrant/virtualbox NAT 接口地址范围。192.168.122.*:此 IP 范围是缺省的 libvirt VM 接口地址范围。
-
有关使用 Calico 的 IBM Cloud Private 部署拓扑的信息,请参阅 IBM Cloud Private 部署拓扑。
Prometheus/Grafana 中的 Calico 监视
缺省情况下,管理节点上运行的 Prometheus 组件会针对度量值擦除 IBM Cloud Private 中运行的 Calico 节点代理程序。IBM Cloud Private 包含 Grafana 仪表板,用于显示从图形表示中的 Calico 检索到的集群网络度量值。
此外,可使用从 Felix 分类的这些度量值来设置警报。