DUICUO

ローカル クラスターは OpenELB を使用してロード バランサーを実装します。

テストを容易にするため、Ingress コントローラーに LoadBalaner タイプのサービスを構成する準備をしました。これはローカルのプライベート環境なので、このサービスタイプをサポートするロードバランサーをデプロイする必要があります。現在、コミュニティで最も人気のあるプロジェクトは MetalLB です。これは CNCF サンドボックスプロジェクトでもあります。2017 年末に開始され、4 年間の開発を経てコミュニティで広く採用されています。しかし、私がテストしたところ、MetalLB は常に不安定で、変更を有効にするためにコントローラーの再起動が必要になることがよくありました。そこで、中国の QingCloud が最近オープンソース化した別のロードバランサーである OpenELB に注目しました。

OpenELB(旧称PorterLB)は、ベアメタル、エッジ、プライベート環境向けに設計されたロードバランサプラグインです。Kubernetes、K3s、KubeSphereのロードバランサプラグインとして使用し、クラスタ外部にLoadBalancerタイプのサービスを公開できます。現在、CNCFサンドボックスプロジェクトとして公開されており、そのコア機能には以下が含まれます。

  • BGPとレイヤー2モードに基づく負荷分散
  • ルータベースのECMP負荷分散
  • IPアドレスプール管理
  • CRD を使用した BGP 設定

MetaLBと比較して

新進気鋭のOpenELBは、Kubernetesネイティブな実装を採用しており、CRDを介して直接設定・管理できます。以下は、OpenELBとMetaLBの簡単な比較です。

クラウドネイティブアーキテクチャ

OpenELBでは、CRDを使用してアドレス管理とBGP設定の両方を設定できます。Kubectlに慣れているユーザーにとって、OpenELBは非常に使いやすいです。MetalLBでは、設定はConfigMapを介して行われ、その状態を監視するには監視システムまたはログを確認する必要があります。

柔軟な住所管理

OpenELBは、EIPと呼ばれるカスタムリソースオブジェクトを通じてアドレスを管理します。EIPは、アドレス割り当てステータスを保存するためのStatusと呼ばれるサブリソースを定義し、アドレス割り当て時にレプリカ間の競合を防ぎます。

gobgpを使用してルートを公開する

独自のBGPプロトコルを実装するMetalLBとは異なり、OpenELBは標準のgobgpを使用してルートをアドバタイズします。これには以下の利点があります。

  • 開発コストが低く、gobgp コミュニティによってサポートされています。
  • GoBGP を使用すると機能を強化できます。
  • BgpConf/BgpPeer CRD を介して gobgp を動的に構成することにより、ユーザーは OpenELB を再起動せずに最新の構成情報を動的にロードできます。
  • gobgpをライブラリとして使用する場合、コミュニティはprotobufベースのAPIを提供しています。OpenELBもBgpConf/BgpPeer CRDを実装する際にこのAPIを参照し、互換性を維持しています。
  • OpenELB は、包括的なステータス情報を提供する BGP ネイバー構成を表示するステータス機能も提供します。

シンプルなアーキテクチャ、低リソース消費

OpenELBは現在、デプロイメントのデプロイのみを必要とし、複数のレプリカを通じて高可用性を実現しています。一部のレプリカに障害が発生しても、確立された通常の接続には影響しません。

BGPモードでは、デプロイメントの各レプリカはルータとの接続を確立し、等コストルートを発行します。そのため、通常は2つのレプリカをデプロイするだけで済みます。レイヤー2モードでは、Kubernetesが提供するリーダー選出メカニズムを通じて、異なるレプリカがリーダーを選出し、ARP/NDPリクエストに応答します。

インストール

Kubernetes クラスターでは、OpenELB は一度だけインストールすれば済みます。インストール後、クラスターに `openelb-manager` デプロイメントがインストールされ、1 つの `openelb-manager` ポッドが含まれます。`openelb-manager` ポッドは、Kubernetes クラスター全体に OpenELB の機能を実装します。インストール後、`openelb-manager` デプロイメントを拡張して、複数の OpenELB レプリカ(`openelb-manager` ポッド)を複数のクラスターノードに分散し、高可用性を確保できます。詳細については、「複数の OpenELB レプリカの設定」をご覧ください。

OpenELB のインストールと使用は非常に簡単です。次のコマンドを使用して 1 回のクリックでインストールできます。

 # k8s.gcr.io イメージを取得できない場合、その中のイメージ置き換える必要があることに注意してください。☸  kubectl apply -f https://raw.githubusercontent.com/openelb/openelb/master/deploy/openelb.yaml

上記のリソースマニフェストは、「openelb-manager」という名前のデプロイメントリソースオブジェクトをデプロイします。「openelb-manager」Podは、Kubernetesクラスター全体にOpenELB機能を実装します。高可用性を確保するため、このコントローラーは2つのレプリカに拡張できます。初期インストールでは、アドミッションWebhook用のHTTPS証明書も構成されます。インストール後、Podのステータスが正常かどうかを確認してください。

 ☸ ➜ kubectl ポッドを取得- n openelb-system
名前準備完了ステータス再起動年齢
openelb-admission-create--1-cf857 0 / 1 完了0 58分
openelb-admission-patch--1-dhgrq 0 / 1 完了2 58分
openelb-manager-848495684-nppkr 1 / 1 実行中1 ( 35 分) 48 分
openelb-manager-848495684-svn7z 1 / 1 実行中1 ( 35 分) 48 分
☸ ➜ kubectl で検証Webhook構成を取得します
名前ウェブフック年齢
openelb-admission 1 62分
☸ ➜ kubectlmutatingwebhook 設定を取得します
名前ウェブフック年齢
openelb-admission 1 62分

さらに、関連する CRD ユーザー OpenELB 構成がいくつかインストールされます。

 ☸ ➜ kubectl get crd | grep kubesphere
bgpconfs .network .kubesphere .io 2022-04-10T08 : 01 : 18Z
bgppeers .network .kubesphere .io 2022-04-10T08 : 01 : 18Z
eips .network .kubesphere .io 2022-04-10T08 : 01 : 18Z

構成

次に、OpenELBをレイヤー2モードで使用する方法を説明します。まず、すべてのKubernetesクラスタノードが同じレイヤー2ネットワーク(同じルーター)上にあることを確認する必要があります。私のテスト環境には合計3つのノードがあり、ノード情報は以下の通りです。

 ☸ ➜ kubectl ノードを取得- o ワイド
名前ステータス役割年齢バージョン内部IP 外部IP OSイメージカーネルバージョンコンテナランタイム
master1 コントロールプレーン準備完了マスター15d v1 .22.8 192.168.0.111 < なし> CentOS Linux 7 ( Core ) 3.10.0 -1160.25.1.el7.x86_64 containerd :// 1.5.5
node1 準備完了< なし> 15d v1 .22.8 192.168.0.110 < なし> CentOS Linux 7 ( Core ) 3.10.0 -1160.25.1.el7.x86_64 containerd :// 1.5.5
node2 準備完了< なし> 15d v1 .22.8 192.168.0.109 < なし> CentOS Linux 7 ( Core ) 3.10.0 -1160.25.1.el7.x86_64 containerd :// 1.5.5

3 つのノードの IP アドレスは、192.168.0.109、192.168.0.110、192.168.0.111 です。

まず、kube-proxy に対して strictARP を有効にして、Kubernetes クラスター内のすべてのネットワーク インターフェースが他のネットワーク インターフェースからの ARP 要求に応答しなくなり、代わりに OpenELB が ARP 要求を処理できるようにする必要があります。

 ☸ ➜ kubectl edit configmap kube-proxy - n kube-system
……
IPVS :
strictARP :
……

次に、次のコマンドを実行して、kube-proxy コンポーネントを再起動します。

 ☸ ➜ kubectl ロールアウトdaemonset kube-proxy - n kube-system を再起動します

OpenELBがインストールされたノードに複数のネットワークインターフェースがある場合、OpenELBがレイヤー2モードで使用するネットワークインターフェースを指定する必要があります。ノードにネットワークインターフェースが1つしかない場合は、この手順を省略できます。OpenELBがインストールされたmaster1ノードに2つのネットワークインターフェース(eth0 192.168.0.2とens33 192.168.0.111)があり、eth0 192.168.0.2をOpenELBで使用すると仮定すると、master1ノードにネットワークインターフェースを指定するためのアノテーションを追加する必要があります。

 ☸ ➜ kubectl annotate nodes master1 layer2 .openelb ​​.kubesphere .io / v1alpha1 = "192.168.0.2"

次に、OpenELBのIPアドレスプールとして機能するEipオブジェクトを作成します。以下のようにリソースオブジェクトを作成します。

 api バージョン: ネットワーク.kubesphere.io / v1alpha2
種類: Eip
メタデータ
名前: eip-pool
仕様:
アドレス: 192.168.0.100 -192.168.0.108
プロトコル: レイヤー2
無効: false
インターフェース: ens33

ここでは、`address` 属性を使ってIPアドレスプールを指定します。OpenELBで使用される1つ以上のIPアドレスを入力できます(異なるEIPオブジェクトのIP範囲は重複できないことに注意してください)。値の形式は以下のとおりです。

  • IP アドレス (例: 192.168.0.100)。
  • IP アドレス/サブネット マスク (例: 192.168.0.0/24)。
  • IP アドレス 1 ~ IP アドレス 2、例: 192.168.0.91 ~ 192.168.0.100。

`protocol` 属性は、EIP オブジェクトが使用される OpenELB モードを指定します。Layer2 または BGP に設定でき、デフォルトは BGP です。ここでは Layer2 モードを使用するため、明示的に指定する必要があります。`interface` 属性は、OpenELB が ARP または NDP 要求をリッスンするネットワークインターフェースを指定します。このフィールドは、protocol が Layer2 に設定されている場合にのみ有効です。私の環境では、ens33 ネットワークインターフェースです。`disable` 属性は、EIP オブジェクトを無効にするかどうかを示します。

EIP オブジェクトを作成した後、Status パラメータを使用して IP プールの特定のステータスを表示できます。

 ☸ ➜ kubectl でeip を取得
名前CIDR 使用量合計
eip プール192.168.0.100 -192.168.0.108 0 9
☸ ➜ kubectl でeip を取得し、 eip-pool - oyaml を実行します
api バージョン: ネットワーク.kubesphere.io / v1alpha2
種類: Eip
メタデータ
ファイナライザー:
- ファイナライザー.ipam .kubesphere .io / v1alpha1
名前: eip-pool
仕様:
アドレス: 192.168.0.100 -192.168.0.108
インターフェース: ens33
プロトコル: レイヤー2
状態
最初のIP : 192.168.0.100
最終IP : 192.168.0.108
プールサイズ: 9
準備完了: true
v4 :

ロード バランサーのアドレス プールが準備できたので、次に示すように、単純なサービスを作成し、ロード バランサーを通じて公開します。

 # openelb-nginx .yaml
apiバージョン: アプリ/ v1
種類: デプロイメント
メタデータ
名前: nginx
仕様:
セレクター:
マッチラベル
アプリ: nginx
テンプレート
メタデータ
ラベル:
アプリ: nginx
仕様:
コンテナ
- 名前: nginx
画像: nginx
ポート:
- コンテナポート: 80

シンプルな nginx サービスをデプロイする方法は次のとおりです。

 ☸ ➜ kubectl apply -f openelb -nginx .yaml
☸ ➜ kubectl でポッドを取得する
名前準備完了ステータス再起動年齢
nginx-7848d4b86f-zmm8l 1 / 1 実行中0 42秒

次に、次に示すように、LoadBalancer タイプのサービスを作成して、nginx サービスを公開します。

 # openelb-nginx-svc .yaml
apiバージョン: v1
種類: サービス
メタデータ
名前: nginx
注釈:
lb .kubesphere .io / v1alpha1 : openelb
プロトコル.openelb ​​.kubesphere .io / v1alpha1 : レイヤー2
eip .openelb .kubesphere .io / v1alpha2 : eip-pool
仕様:
セレクター:
アプリ: nginx
タイプ: ロードバランサー
ポート:
- 名前: http
ポート80
ターゲットポート: 80

ここで、サービスにいくつかの注釈を追加したことに注意してください。

  • lb.kubesphere.io/v1alpha1: openelb は、このサービスが OpenELB を使用することを指定するために使用されます。
  • protocol.openelb.kubesphere.io/v1alpha1: layer2 は、OpenELB が Layer2 モードで使用されていることを示します。
  • `eip.openelb.kubesphere.io/v1alpha2:eip-pool` アノテーションは、OpenELB が使用する EIP オブジェクトを指定します。このアノテーションが設定されていない場合、OpenELB はプロトコルに一致する最初の利用可能な EIP オブジェクトを自動的に使用します。あるいは、このアノテーションを削除し、`spec:loadBalancerIP` フィールドを追加して(例: `spec:loadBalancerIP: 192.168.0.108`)、特定の IP アドレスをサービスに割り当てることもできます。

同様に、上記のサービスを直接作成します。

 ☸ ➜ kubectl apply -f openelb -nginx-svc .yaml
サービス/ nginx が作成されました
☸ ➜ kubectl でnginx サービスを取得します
名前タイプクラスターIP 外部IP ポート( ) 年齢
nginx ロードバランサー10.100.126.91 192.168.0.101 80 : 31555 / TCP 4秒

作成後、サービスに EXTERNAL-IP が割り当てられていることがわかります。これを使用して、nginx サービスにアクセスできます。

 ☸ ➜ 192.168.0.101 をカールする
< !DOCTYPE html >
<html>
<ヘッド>
<title> nginx ようこそ! </title>
<スタイル>
html { カラースキーム: 明るい暗い; }
本文{ : 35em ; マージン: 0 auto ;
フォントファミリー: TahomaVerdanaArialsans-serif ; }
</スタイル>
</head>
<本文>
< h1 > nginx ようこそ! </ h1 >
< p > このページ表示されれ nginx ウェブサーバー正常にインストールされており
動作していますさらに設定必要です</p>
< p > オンラインドキュメントサポートについて
< a href = "http://nginx.org/" > nginx .org </ a >。< br />
商用サポート以下からご利用いただけます
< a href = "http://nginx.com/" > nginx.com </ a > </ p >
< p >< em > nginx をご利用いただきありがとうございます </ em ></ p >
</本文>
</html>

さらに、OpenElbはBGPモードとマルチルートクラスタシナリオもサポートしています。アップデート方法と使用方法の詳細については、公式ドキュメント(https://openelb.github.io/docs/)をご覧ください。

参考資料

  • https://openelb.github.io/docs/ をご覧ください。
  • https://kubesphere.io/zh/blogs/openelb-joins-cncf-sandbox-project/.
  • https://mp.weixin.qq.com/s/uFwYaPE7cVolLWxYHcgZdQ.