Kubernetes Calico BGP Full Mesh模式 电脑版发表于:2022/11/20 16:34  >#Kubernetes Calico BGP Full Mesh模式 [TOC] ## Full Mesh模式简介 tn2>Full Mesh - 全互联模式,启用了 BGP 之后,Calico 的默认行为是在每个节点彼此对等的情况下创建完整的内部 BGP(iBGP)连接,这使 Calico 可以在任何 L2 网络(无论是公有云还是私有云)上运行,或者说(如果配了 IPIP)可以在任何不禁止 IPIP 流量的网络上作为 overlay 运行。对于 vxlan overlay,Calico 不使用 BGP。 Full-mesh 模式对于 100 个以内的工作节点或更少节点的中小规模部署非常有用,但是在较大的规模上,Full-mesh 模式效率会降低,较大规模情况下,Calico 官方建议使用 Route reflectors。 ## 启动Full Mesh模式 tn2>我们可以通过关闭IPIP模式和Vxlan模式来打开Full Mesh模式。 ```bash calicoctl --allow-version-mismatch get ipPool -o wide kubectl edit ippool default-ipv4-ippool calicoctl --allow-version-mismatch get ipPool -o wide ```  tn2>然后修改`calico.yaml`的`calico_backend `的参数为`bird`,以及设置`CALICO_IPV4POOL_IPIP `、`CALICO_IPV4POOL_VXLAN `、`CALICO_IPV6POOL_VXLAN `为`Never`。然后再进行apply。 ```bash kubectl apply -f calico.yaml # 通过下面的命令来进行测试。 calicoctl --allow-version-mismatch node status ```  tn2>参与BGP路由的每个AS都被分配一个唯一的自制系统编号(ASN),对BGP来说ASN是区分整个相互连接的网络的唯一标识。64512到65535之间的ASN编号保留给专用网络。 我们可以通过如下命令来查看Calico的ASN。 ```bash calicoctl --allow-version-mismatch get node -o wide ```  ## 路由学习 tn2>关于每个不同的节点中,所学习的路由是BGP学习到的还是非BGP学习到的,我们都可以到每个Calico Pod节点中进行查看。 ```bash # 查看Calico运行到一些Pod kubectl get pod -n kube-system -o wide | grep calico # 进入calico容器内部 kubectl exec -n kube-system -it calico-node-bc6hd /bin/bash # 使用birdcl工具查看相关路由 birdcl show ? ```  tn2>我们通过`show interfaces`来查看网络接口。  tn2>我们可以看到eth0是一个多接入的广播。 当然我们还可以通过`show route`的方式查看BGP学习到的路由(这里不一定看到所有的路由学习,因为不同的协议只能看到自己能够学习到的)。  tn2>如果我还想看具体的路由是由什么协议来维护的可以通过如下命令来查看(举个例子`192.168.36.64/26`) ```bash show route for 192.168.36.64 all ```  | 属性 | 描述 | | ------------ | ------------ | | Type | 协议类型 | | BGP.origin | 原始路由协议 | | BGP.as_path | 该属性记录了BGP传递过程中所经过的AS号,实际是一个AS号的列表。它的长短决定通信路径的决策。 | | BGP.next_hop | 下一跳 | | BGP.local_pref | 当BGP有多个路由选择到达目标时,该属性决定其中的优先级。 | ## node-to-node mesh tn2>关于`node-to-node mesh`的Peer类型的模式,它相当于节点对节点的方式的人人平等,其中的一台机器有添加新的路由所有的节点路由都需要学习。多了会造成每个路由随时随地都在学习消耗新年。 (官方建议100台机子一下使用) <br/> 它的路由IP也是节点的IP,就是直连的方式,所以如果该路由行不通了就没有其他方式,导致访问的路由方式不能保证高可用性。 (节点少没影响) ## 抓包 tn2>通过抓包,普获新pod运行的路由学习情况。 ```bash tcpdump -pne -i eth0 -w eth0_bgp_full_mesh.cap kubectl apply -f cni.yaml ```  tn2>由于BGP使用TCP传输协议端口号为179,所以我们在Wireshark中的过滤`tcp.port==179`就可以了。  tn2>这里只有Keepalive,如果像节点重启或者禁用ip池,它还会有UPDATE、OPEN新的ip的路由消息。 (这里就不做尝试,大家可以自行尝试一下加深理解) 关于禁用节点可根据添加如下命令参数来进行设置,设置后新pod将无法创建IP而报错。 ```bash kubectl edit ippool default-ipv4-ippool # spec.disabled: true ``` tn2>关于bgp的配置在`/etc/calico/confd/config/bird.cfg`文件中,如果我们有一些其他的需要添加更改的也可以在这个文件中做配置,接下来我们可以来解读一下。 ```bash kubectl exec -n kube-system calico-node-bc6hd cat "/etc/calico/confd/config/bird.cfg" ``` ```bash function apply_communities () { } # Generated by confd include "bird_aggr.cfg"; include "bird_ipam.cfg"; # 路由id名 router id 10.211.55.7; # 配置路由表和内核之间的同步。 protocol kernel { learn; # 从内核学习所有外来路由 persist; # 不要在bird关闭时删除路由 scan time 2; # 每2秒扫描内核路由表 import all; export filter calico_kernel_programming; # 默认为不导出 graceful restart; # 当重新加载BIRD配置时,开启优雅的重新启动以减少航路中的潜在网络震荡。对于全自动网格,由于多个节点同时更新其BGP配置,因此无法防止BGP震荡,因此GR无法保证在这种情况下正常工作。 merge paths on; # 允许导出多路径路由(ECMP) } # 监视界面上/下事件。 protocol device { debug { states }; scan time 2; # 每2秒扫描一次接口 } protocol direct { debug { states }; interface -"cali*", -"kube-ipvs*", "*"; #排除cali*和kube ipvs*,但包括所有其他内容。在IPVS模式下,kube代理创建一个kube-ipvs0接口。我们排除了kube-ipvs0,因为这个接口为每个正在使用的集群IP获取一个地址。当我们合法地想要导出集群IP时,我们使用静态路由。 } # 所有BGP客户端模版 template bgp bgp_template { debug { states }; description "Connection to BGP peer"; local as 64512; # AS 值 multihop; gateway recursive; # 默认设置。 import all; # 导入所有路线,因为我们不知道上游 # 拓扑是并且因此必须信任ToR/RR。 export filter calico_export_to_bgp_peers; # 只希望导出工作负载的路由。 add paths on; graceful restart; # 请查看内核模块对graceful的注解 connect delay time 2; connect retry time 5; error wait time 5,30; } # 上面基本上是路由反射器的 # 下面是node到node的mesh # ------------- Node-to-node mesh ------------- # 跳过自己 # For peer /host/k8s-125-master/ip_addr_v4 # Skipping ourselves (10.211.55.7) # 由于我这里有两个节点所以有两条peer信息 # For peer /host/k8s-125-node1/ip_addr_v4 protocol bgp Mesh_10_211_55_8 from bgp_template { neighbor 10.211.55.8 as 64512; source address 10.211.55.7; # The local address we use for the TCP connection passive on; # Mesh is unidirectional, peer will connect to us. } # For peer /host/k8s-125-node2/ip_addr_v4 protocol bgp Mesh_10_211_55_9 from bgp_template { neighbor 10.211.55.9 as 64512; source address 10.211.55.7; # The local address we use for the TCP connection passive on; # Mesh is unidirectional, peer will connect to us. } # ------------- Global peers ------------- # No global peers configured. # ------------- Node-specific peers ------------- # No node-specific peers configured. ```