From f810b078ec94ce74943e3a9fe22a077a08a8b85c Mon Sep 17 00:00:00 2001 From: Manuel Buil Date: Wed, 19 Jan 2022 14:02:19 +0100 Subject: [PATCH] Update network docs Signed-off-by: Manuel Buil --- .../en/faq/networking/cni-providers/_index.md | 47 +++++++++++------- static/img/rancher/cilium-logo.png | Bin 0 -> 13971 bytes 2 files changed, 30 insertions(+), 17 deletions(-) create mode 100644 static/img/rancher/cilium-logo.png diff --git a/content/rancher/v2.6/en/faq/networking/cni-providers/_index.md b/content/rancher/v2.6/en/faq/networking/cni-providers/_index.md index 498e63ad5f1..97bcadd763f 100644 --- a/content/rancher/v2.6/en/faq/networking/cni-providers/_index.md +++ b/content/rancher/v2.6/en/faq/networking/cni-providers/_index.md @@ -16,7 +16,7 @@ For more information visit [CNI GitHub project](https://github.com/containernetw ### What Network Models are Used in CNI? -CNI network providers implement their network fabric using either an encapsulated network model such as Virtual Extensible Lan ([VXLAN](https://github.com/coreos/flannel/blob/master/Documentation/backends.md#vxlan)) or an unencapsulated network model such as Border Gateway Protocol ([BGP](https://en.wikipedia.org/wiki/Border_Gateway_Protocol)). +CNI network providers implement their network fabric using either an encapsulated network model such as Virtual Extensible Lan ([VXLAN](https://github.com/flannel-io/flannel/blob/master/Documentation/backends.md#vxlan)) or an unencapsulated network model such as Border Gateway Protocol ([BGP](https://en.wikipedia.org/wiki/Border_Gateway_Protocol)). #### What is an Encapsulated Network? @@ -26,7 +26,7 @@ In simple terms, this network model generates a kind of network bridge extended This network model is used when an extended L2 bridge is preferred. This network model is sensitive to L3 network latencies of the Kubernetes workers. If datacenters are in distinct geolocations, be sure to have low latencies between them to avoid eventual network segmentation. -CNI network providers using this network model include Flannel, Canal, and Weave. +CNI network providers using this network model include Flannel, Canal, Weave or Cilium. Calico by default is not using this model but it could be configured. ![Encapsulated Network]({{}}/img/rancher/encapsulated-network.png) @@ -38,13 +38,13 @@ In simple terms, this network model generates a kind of network router extended This network model is used when a routed L3 network is preferred. This mode dynamically updates routes at the OS level for Kubernetes workers. It's less sensitive to latency. -CNI network providers using this network model include Calico and Romana. +CNI network providers using this network model include Calico. Cilium can also be configured with this model although it is not the default mode. ![Unencapsulated Network]({{}}/img/rancher/unencapsulated-network.png) ### What CNI Providers are Provided by Rancher? -Out-of-the-box, Rancher provides the following CNI network providers for Kubernetes clusters: Canal, Flannel, Calico and Weave. You can choose your CNI network provider when you create new Kubernetes clusters from Rancher. +Out-of-the-box, Rancher provides the following CNI network providers for RKE Kubernetes clusters: Canal, Flannel and Weave. For RKE2 Kubernetes clusters: Canal, Calico and Cilium. You can choose your CNI network provider when you create new Kubernetes clusters from Rancher. #### Canal @@ -64,23 +64,25 @@ For more information, see the [Canal GitHub Page.](https://github.com/projectcal ![Flannel Logo]({{}}/img/rancher/flannel-logo.png) -Flannel is a simple and easy way to configure L3 network fabric designed for Kubernetes. Flannel runs a single binary agent named flanneld on each host, which is responsible for allocating a subnet lease to each host out of a larger, preconfigured address space. Flannel uses either the Kubernetes API or etcd directly to store the network configuration, the allocated subnets, and any auxiliary data (such as the host's public IP). Packets are forwarded using one of several backend mechanisms, with the default encapsulation being [VXLAN](https://github.com/coreos/flannel/blob/master/Documentation/backends.md#vxlan). +Flannel is a simple and easy way to configure L3 network fabric designed for Kubernetes. Flannel runs a single binary agent named flanneld on each host, which is responsible for allocating a subnet lease to each host out of a larger, preconfigured address space. Flannel uses either the Kubernetes API or etcd directly to store the network configuration, the allocated subnets, and any auxiliary data (such as the host's public IP). Packets are forwarded using one of several backend mechanisms, with the default encapsulation being [VXLAN](https://github.com/flannel-io/flannel/blob/master/Documentation/backends.md#vxlan). -Encapsulated traffic is unencrypted by default. Therefore, flannel provides an experimental backend for encryption, [IPSec](https://github.com/coreos/flannel/blob/master/Documentation/backends.md#ipsec), which makes use of [strongSwan](https://www.strongswan.org/) to establish encrypted IPSec tunnels between Kubernetes workers. +Encapsulated traffic is unencrypted by default. Flannel provides two solutions for encryption: +* [IPSec](https://github.com/flannel-io/flannel/blob/master/Documentation/backends.md#ipsec), which makes use of [strongSwan](https://www.strongswan.org/) to establish encrypted IPSec tunnels between Kubernetes workers. It is considered experimental +* [Wireguard](https://github.com/flannel-io/flannel/blob/master/Documentation/backends.md#wireguard), which is a more performing alternative to strongswan Kubernetes workers should open UDP port `8472` (VXLAN) and TCP port `9099` (healthcheck). See [the port requirements for user clusters]({{}}/rancher/v2.6/en/cluster-provisioning/node-requirements/#networking-requirements) for more details. ![Flannel Diagram]({{}}/img/rancher/flannel-diagram.png) -For more information, see the [Flannel GitHub Page](https://github.com/coreos/flannel). +For more information, see the [Flannel GitHub Page](https://github.com/flannel-io/flannel). #### Calico ![Calico Logo]({{}}/img/rancher/calico-logo.png) -Calico enables networking and network policy in Kubernetes clusters across the cloud. Calico uses a pure, unencapsulated IP network fabric and policy engine to provide networking for your Kubernetes workloads. Workloads are able to communicate over both cloud infrastructure and on-prem using BGP. +Calico enables networking and network policy in Kubernetes clusters across the cloud. By default, Calico uses a pure, unencapsulated IP network fabric and policy engine to provide networking for your Kubernetes workloads. Workloads are able to communicate over both cloud infrastructure and on-prem using BGP. -Calico also provides a stateless IP-in-IP encapsulation mode that can be used, if necessary. Calico also offers policy isolation, allowing you to secure and govern your Kubernetes workloads using advanced ingress and egress policies. +Calico also provides a stateless IP-in-IP or VXLAN encapsulation mode that can be used, if necessary. Calico also offers policy isolation, allowing you to secure and govern your Kubernetes workloads using advanced ingress and egress policies. Kubernetes workers should open TCP port `179` (BGP). See [the port requirements for user clusters]({{}}/rancher/v2.6/en/cluster-provisioning/node-requirements/#networking-requirements) for more details. @@ -110,10 +112,11 @@ The following table summarizes the different features available for each CNI net | Provider | Network Model | Route Distribution | Network Policies | Mesh | External Datastore | Encryption | Ingress/Egress Policies | | ---- | ---- | ---- | ---- | ---- | ---- | ---- | ---- | -| Canal | Encapsulated (VXLAN) | No | Yes | No | K8S API | No | Yes | -| Flannel | Encapsulated (VXLAN) | No | No | No | K8S API | No | No | -| Calico | Encapsulated (VXLAN,IPIP) OR Unencapsulated | Yes | Yes | Yes | Etcd and K8S API | No | Yes | +| Canal | Encapsulated (VXLAN) | No | Yes | No | K8S API | Yes | Yes | +| Flannel | Encapsulated (VXLAN) | No | No | No | K8S API | Yes | No | +| Calico | Encapsulated (VXLAN,IPIP) OR Unencapsulated | Yes | Yes | Yes | Etcd and K8S API | Yes | Yes | | Weave | Encapsulated | Yes | Yes | Yes | No | Yes | Yes | +| Cilium | Encapsulated (VXLAN) | Yes | Yes | Yes | Etcd and K8S API | Yes | Yes | - Network Model: Encapsulated or unencapsulated. For more information, see [What Network Models are Used in CNI?](#what-network-models-are-used-in-cni) @@ -129,16 +132,26 @@ The following table summarizes the different features available for each CNI net - Ingress/Egress Policies: This feature allows you to manage routing control for both Kubernetes and non-Kubernetes communications. + +### Cilium + +![Cilium Logo]({{}}/img/rancher/cilium-logo.png) + +Cilium enables networking and network policies (L3, L4 and L7) in Kubernetes. Cilium by default uses eBPF technologies to route packets inside the node and vxlan to send packets to other nodes, unencapsulated techniques can also be configured. + +Cilium recommends kernel versions greater than 5.2 to be able to leverage the full potential of eBPF. Kubernetes workers should open TCP port `8472` for VXLAN and TCP port `4140` for health checks. Besides ICMP 8/0 must be enabled for health checks too. Fro more information check [Cilium System Requirements](https://docs.cilium.io/en/latest/operations/system_requirements/#firewall-requirements) + #### CNI Community Popularity -The following table summarizes different GitHub metrics to give you an idea of each project's popularity and activity. This data was collected in January 2020. +The following table summarizes different GitHub metrics to give you an idea of each project's popularity and activity. This data was collected in January 2022. | Provider | Project | Stars | Forks | Contributors | | ---- | ---- | ---- | ---- | ---- | -| Canal | https://github.com/projectcalico/canal | 614 | 89 | 19 | -| flannel | https://github.com/coreos/flannel | 4977 | 1.4k | 140 | -| Calico | https://github.com/projectcalico/calico | 1534 | 429 | 135 | -| Weave | https://github.com/weaveworks/weave/ | 5737 | 559 | 73 | +| Canal | https://github.com/projectcalico/canal | 679 | 100 | 21 | +| flannel | https://github.com/flannel-io/flannel | 7k | 2.5k | 185 | +| Calico | https://github.com/projectcalico/calico | 3.1k | 741 | 224 | +| Weave | https://github.com/weaveworks/weave/ | 6.2k | 635 | 84 | +| Cilium | https://github.com/cilium/cilium | 10.6k | 1.3k | 352 |
diff --git a/static/img/rancher/cilium-logo.png b/static/img/rancher/cilium-logo.png new file mode 100644 index 0000000000000000000000000000000000000000..681a0b3c530e7049adda19da7249ff9f9de74075 GIT binary patch literal 13971 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 literal 0 HcmV?d00001