はじめまして。VMware の伊藤です。Tanzu 製品のプラットフォームアーキテクトとして働いており、開発と運用双方の経験があります。この記事では TKG のロードバランサーとして利用できる NSX-ALB の構成サンプルと設定の解説を実施します。
K8s でアプリを運用するということは、アプリを外に公開するということです。これを実施するには一般的にサービスのタイプ LoadBalancer を利用するか、Ingress を利用しますが、いずれにしても k8s と連携して動作するロードバランサーが必要です。この k8s のロードバランサーは、metallb に代表される k8s 内で動作するものと、今回紹介する NSX-ALB に代表される k8s 外で動作するものがあります。小規模での運用であれば前者で構いませんが、中規模以上であったり複雑なネットワーク構成を利用する必要があれば後者を利用する必要があります。
AWS などのパブリッククラウドはこの外部で動作するロードバランサーを自社サービスとして提供していますが、オンプレミスで TKG を利用する場合であれば自分たちで構築する必要があります。この記事では TKG がサポートする NSX-ALB を使って、k8s 用のロードバランサー構成を構築する参考情報を扱います。
記事のおおまかな構成としては以下となります。
- vSphere 版 NSX-ALB の概要
- vSphere 版 NSX-ALB のルーティング概要
- TKG 1 ネットワーク構成 <- 重要設定の解説
- TKG 2 ネットワーク構成
- TKG 3 ネットワーク構成(NSX-ALB で k8s vip ) <- 推奨構成
- TKG 3 ネットワーク構成(kube-vip で k8s vip)
概要を確認した上で目的の構成の解説を読むのがよいと思いますが、どの構成を採用するかは構築するかは要件に依存します。たとえば「1 ネットワーク構成」は作成するのが簡単なので開発環境などに良いかもしれません。ただ、管理系もデータ系も1つのネットワークに混ぜているので、もし本番環境で利用したら攻撃を受けやすく、障害にも弱い構成となってしまいます。一方「3 ネットワーク構成(静的ルートなし/あり)」は DMZ なども考慮したうえでトラフィックも分離されている綺麗な構成ですが、きちんとしたネットワークの設計が必要であり設定も複雑となるので「1 ネットワーク構成」ほどの手軽さはありません。
こういった点もふまえて、とりあえず各構成がどういった意図のもとに設計されているかをひととおり読んで、要件にあうものを選んで頂くのがよいかと思います。また、当然ですが上記にないオリジナルな構成を作ることも良いでしょう。なお、1 ネットワーク構成は他の構成で省いた解説を書いているので、詳しくない場合は一読ください。
上記の全てのネットワーク構成で「TKG マネージメントクラスタの構築、ワークロードクラスタの構築、nginx Pod の展開、nginx をサービスの Type LoadBalancer で公開、公開した nginx にブラウザでアクセスできること」を確認してあります。
この記事の内容は公式ドキュメントでは以下のページが該当します。
NSX-ALB 概要
この記事の主眼は構成なので細かな解説はしませんが、NSX-ALB の概要を知っていないとこの記事の内容が理解しづらいと思いますので簡単に紹介します。
端的にいってしまうと、NSX-ALB は仮想マシンベースで提供される集中管理型の分散ロードバランサーです。ハードウェアアプライアンスとして提供されるロードバランサーと異なり、スペックが十分な仮想化環境の上であればどこでも手軽に利用できて、台数の増加やマシンスペックの向上というかたちで柔軟なパフォーマンス調整ができます。また、ロードバランサー1台1台を設定するのではなく、コントローラーによる集中管理型ですので複数のサイトに多数配置するといったシナリオでも構築/運用/監視を負担少なく実現できます。従来ながらのロードバランサーとして利用することももちろん可能ですが、APIによる制御などにも対応しているので、今回のように TKG と連携させるといった他ソリューションとの協調動作も得意です。
NSX-ALB はおおまかに以下の図にある3つのコンポーネントから構成されています。図の Avi は NSX-ALB の旧名称です。
- NSX-ALB Controller: 全体を制御するコントローラー。いわゆるコントロールプレーン
- NSX-ALB Service Engine (SE) : ロードバランサーとしてデータを転送するエンジン。いわゆるデータプレーン
- AKO (Avi Kubernetes Operator) : TKG 上で動作する NSX-ALB と連携するためのコンポーネント
コンポーネントとしては色々ありますが、ユーザーとしてやることは2つだけで「NSX-ALB Controller を展開して、ネットワーク設定をする」ことと「TKG を展開する際に、NSX-ALB と連携する登録をする」だけです。これをすると、NSX-ALB SE や AKO は必要に応じて勝手に NSX-ALB Controller や TKG が払い出しをしています。
NSX-ALB のルーティング概要
NSX-ALB の展開方法や基本設定などは以下の記事を参照ください。
NSX-ALB はロードバランサーですので、ネットワーク機器としての設定が多くなります。たとえば、TKG から「このネットワークにロードバランサーのサービスを展開して、それを私(このネットワークのこの IP)に届けてください」といった指令が来た際に、そのネットワークやどうパケットを届ければよいかが NSX-ALB に登録されていなければサービスを展開することができません。
これらの設定をする際に特に注意を払って設定してもらいたいのは以下の3つです。
- NSX-ALB が認識する vSphere のネットワークと、ネットワークの IP
- vSphere のネットワークでロードバランサーを動作させるときに使える IP レンジの登録
- 直結していないネットワークにどうパケットを届けるか
そして設定の結論としては、以下の3つになります。
- 使いたいネットワークのサブネットと IP Pool (or DHCP)を設定する
- データ通信用のデフォルトゲートウェイを設定する
- マネージメント通信用のデフォルトゲートウェイを設定する
これらを以下の図の構成で説明します。
まず、図の中央にある NSX-ALB SE に着目してください。これは 4 つのネットワークに直接接続していますが、192.168.100.0 のネットワークには接続していません。
vSphere 上に展開された NSX-ALB が接続するネットワークは vSphere のネットワークになります。ただし、全てのネットワークに接続されるのではなく、NSX-ALB に設定されており、なおかつ利用されるものだけです。
たとえば上記の図ですと、
- 192.168.0.0/24: ロードバランサーのサービスを展開
- 192.168.1.0/24: 192/168.100.0/24 宛のパケットの転送に利用
- 192.168.2.0/24: ロードバランサーの転送先
- 192.168.3.0/24: 管理系の通信のポートに指定 (NSX-ALB Controller とのやりとり)
となります。192.168.4.0/24 のネットワークが vSphere 上に存在していたとしても、それが NSX-ALB が必要としていなければ VM として接続されていません。なお、VM に NIC が持たれるのは必要とされるタイミングなのでご注意ください。たとえば、192.168.0.0/24 のネットワークへの接続は、はじめてロードバランサーのサービスを展開した場合かもしれません。
また、ネットワークを利用する各ネットワークにインターフェースで接続するだけでなく、そのインターフェースに IP アドレスを割り当てる必要があります。この IP とロードバランサーで利用する IP になにを使うかという設定はあらかじめ指定した IP Pool を利用するか、DHCP 任せにすることができます。この記事では全て IP Pool を使っています。
NSX-ALB SE はロードバランサーのサービス宛のトラフィックを、それを必要とするマシンに転送する必要があります。たとえば上記の図であれば、k8s のサービス LoadBalancer で具体的には「192.168.0.0/24 に展開された 192.168.0.X のロードバランサーサービス」に届けられたトラフィックを、k8s のノードで具体的には「192.168.2.0/24 上にある 192.168.2.Y-Z のアドレスを持つ仮想マシン(複数)」のポッドに届ける必要があります。
このとき、NSX-ALB は「192.168.2.0/24 宛にトラフィック転送するには、どのインターフェースから誰にたいして転送すればよいか」を知っていなければいけません。この役割を果たすのがルーターやL3スイッチなどにも使われているルーティングテーブルです。これは NSX-ALB に接続するネットワークの登録をしたり、手動でどこにどう転送すればよいかを登録することで作成されます。
直接接続ネットワークは勝手に転送される設定がされていますが、注意が必要なのは「ロードバランサーからクライアントへの帰りの通信」です。アプリにアクセスするクライアントはインターネットの様々な場所からアクセスされます。つまり、様々な IP を持つクライアントにたいして返信パケットを転送する必要があるので、データ通信のデフォルトゲートウェイの設定が必要です。通常はアプリのロードバランサーサービスを展開するインターフェースのゲートウェイを指定します。
あまり多くはありませんが、上記図の 192.168.100.0/24 のような直接接続されない特定ネットワークへの通信をデフォルトゲートウェイ以外の Next Hop から場合は、より細かいルート指定で手動もしくはBGPで経路情報を作成しないといけない点に注意してください。これはルーターなどの「プレフィックス(サブネット)をより詳細に指定した経路情報を優先する」というルールと同じ原理で動きます。
以下にデフォルトゲートウェイの登録を図示します。先に説明したロードバランサーで使うデータ通信用のものだけでなく、マネージメント系通信のゲートウェイも登録が必要です。両方に別のインターフェースを指定することが一般的ですが、これから紹介する「1ネットワーク構成」のように両者に同一インターフェースを指定することも可能です。
NSX-ALB Controller での直接接続ネットワークの設定は「Infrastracture -> Network」と進むことで実施できます。認識するネットワークは接続情報は vCenter から直接取り込みますが、各ネットワークがどのようなサブネット(IP)かは自動認識できない場合は手動で登録してください。IP Pool の設定もここで実施します。
ルーティングの設定は「Infrastracture ->Routing」で実施します。
ここでは 192.168.52.0/22 (直接接続されていない場合)にたいして、192.168.48.1 (L3スイッチのSVI)に転送して、あとの転送はL3スイッチに任せています。Prefix に「0.0.0.0/0」を指定すると、デフォルトゲートウェイの設定になります。
図の下側にあるのは Infrastracture -> Cloud で設定できるルーティングの細かな設定です。必要に応じてチェックしますが、通常はチェック不要です。
以上で NSX-ALB の概要説明を終了し、ここからは具体的な TKG が使う NSX-ALB のネットワーク構成にはいります。各構成の説明のまえに、この記事で利用している足回りの vSphere と物理ネットワークのトポロジ図を記載しておきます。
NSX-ALB および TKG が利用可能なのは、以下の3つの Distributed Port です。
- dp-mgmt-32: 192.168.32.0/20
- dp-data-48: 192.168.48.0/22
- dp-data-52: 192.168.52.0/22
これらは L3 物理スイッチから ESXi ホストに Trunk VLAN として届けられ、ネットワーク間はルーティングができるように物理スイッチが設定されています。
1ネットワーク構成
この構成は1つのネットワークに管理系、外に公開するロードバランサーサービス、K8s ネットワークを全て押し込めたものです。先に説明したようにネットワーク構成が単純なので難しいことを考えずに構築できるというメリットがありますが、事故がおきやすい構成(たとえばユーザ操作で vCenter との重複 IP を発生させられる)となります。
重要ではない小規模な vSphere 環境上で、重要でない TKG をサクッと作りたいという場合にのみこの構成を採用してください。PoC や開発者自身が開発環境を構築/運用する場合などは、この構成がよいかもしれません。
この構成は以下のドキュメントで TKG と NSX-ALB の構築の最初から最後まで扱っています。
以下に構成図を記載します。
ロードバランサーのサービス(IP)は NSX-ALB SE に展開され、利用するネットワークは1つだけなので上記の赤枠の位置にアプリのロードバランサーサービスもk8s本体のロードバランサーサービスも展開されます。
具体的なNSX-ALB のネットワーク設定としては以下となります。
図の上で、NSX-ALB が認識する vSphere のネットワークの dp-mgmt-32 のみが設定されています。サブネット登録だけでなく、ロードバランサーで利用する IP Pool の設定もしてください。ここで設定した Pool の中からロードバランサーが利用する IP が払い出されます。
次にルーティング設定です。
今回のデータ転送先は直接接続ネットワークの「dp-mgmt-32」上の k8s 本体とアプリになりますので、ルーティングテーブルにエントリを追加しなくても最初から NSX-ALB は認識しています。つまり、「NSX-ALB SE -> k8s」はルーティングの設定は不要です。ただ、アプリからの帰りの通信は「k8s -> NSX-ALB -> クライアント」という流れで届けられますが、このクライアントのアドレスにどのようにパケットを届ければよいかを NSX-ALB SE は知りませんので、「0.0.0.0/0 宛の通信は 192.168.32.1」へ転送すると設定しています。クライアントの場所によってはルーティングの設定を書かなくても動きますが、余計なトラブルを防ぐために「ロードバランサーのインターフェースにデータ用のデフォルトゲートウェイを設定する」とルール付けするのが良いかと思います。
次に TKG を展開する際のマネージメントクラスタのスペック設定です。
着目してほしいのは Control Plane Endpoint Provider という項目で、ようするに「k8s クラスタの代表 IP をどのように設定しますか」という設定です。
図にも書いていますが、選択肢は2つあり NSX-ALB に代表 IP をもたせるか、k8s 上に直接代表 IP を持たせるかです。TKG 1.4 ではNSX-ALB 任せがデフォルトとなり、こちらのほうが IP 管理もしやすいので NSX-ALB を利用します。右側の欄で具体的な IP を指定することもできますが、これも自分で管理したくないので空欄にして NSX-ALB 任せにしています。
次の NSX-ALB の設定が非常に重要です。
図の左上のTKG構築時の NSX-ALB のネットワーク設定では
- Workload VIP Network Name : アプリで使うロードバランサーを展開する NSX-ALB SE のポート(ネットワーク)
- Management VIP Network Name : K8s 本体で使うロードバランサーを展開する NSX-ALB SE のポート
を指定します。
それぞれ、このネットワークの設計通りに唯一のネットワークである「dp-mgmt-32」を設定しています。
図の左下では k8s が使うネットワークの指定をしますが、これも設計通り「dp-mgmt-32」を指定しています。その隣にある「cluster service cidr」と「cluster pod cidr」は k8s 上に構築されるオーバーレイ方式の仮想ネットワークのアドレス帯指定です。組織のなかでこのアドレスを利用していなければ、そのままで問題ありません。dp-mgmt-32 の物理ネットワークのサブネットアドレスを指定すると、重複 IP で構築に失敗します。
vSphere 上で NSX-ALB が使うネットワークを確認すると、dp-mgmt-32 のみが登録されていることがわかります。Avi Internal は名前のとおり内部的なネットワークなので無視してください。
2ネットワーク構成
vCenter や NSX-ALB といった管理系の VM は末端にある k8s に比べると障害時の影響範囲が広いため、ネットワーク設計のベストプラクティスでは「管理系通信とデータ系通信のネットワークは分ける」のが一般的です。この2ネットワークの構成はそのベストプラクティスを踏襲した設計になっています。
ただし、DMZなどを考慮していない構成なので、社内サービスなどの第三者から攻撃される可能性が少ない場合でご利用ください。この構成を外部公開アプリケーションで採用すると、外部公開アプリと内部に隠すべき k8s 基盤が同一ネットワーク上に存在するため、ネットワークセキュリティ周りの設定が複雑化します。ネットワークや vSphere といったインフラ基盤的な視点では 2 ネットワーク構成を作るのも 3 ネットワーク構成を作るのも労力的に大差はありません。使えるネットワーク資源が豊富であれば 3 ネットワーク構成を採用してもよいかもしれません。
以下に構成図を記載します。
このネットワークは管理系は dp-mgmt-32 に寄せて、トラフィックが多いデータ系は dp-data-48 に寄せています。k8s のクラスタのノードは上で動いているアプリ全ての通信を送信/受信しているので、管理系ネットワークに置くのは適していません。
NSX-ALB のネットワーク構成を確認します。
ロードバランサーで利用する dp-data-48 のサブネットと IP Pool の設定がされています。管理系の dp-mgmt-32 はロードバランサーのデータ転送には利用されませんが、管理系の通信に必要なのでサブネットと IP Pool が設定されています。
ルーティングの設定は1ネットワーク構成のときと同様にデフォルトゲートウェイの設定のみしています。NSX-ALB と k8s の間のための設定ではなく、アドレスが不明なクライアントへの帰りパケットの転送のための設定です。
次にTKG 構築時のネットワーク設定は以下となります。
ロードバランサーのネットワークはアプリも k8s 本体もともに NSX-ALB SE の dp-data-48 ネットワークのインターフェースを利用するので、それが指定されています。k8s を展開するネットワークも dp-data-48 が指定されています。
vSphere 上で NSX-ALB SE が使うネットワークを確認すると、dp-data-48 と dp-mgmt-32 が登録されていることがわかります。
3ネットワーク構成(NSX-ALB で k8s vip)
この構成は通信を管理系、内部データ系(k8s)、外部データ系(ロードバランサーでアプリを外に公開)に分離した構成となります。外にアプリケーションを公開するのであれば、それはインターネットに公開されるということです。一般的にどのネットワークにアクセスできるかはファイアウォールなどで調整しますが、個別 IP 単位で調整すると手間がかかるため、ネットワークレベルで調整します。その際に「外に公開するネットワークに k8s の基盤自体が含まれている」という状況は望ましくないので、この外側と内側のデータネットワークを分けた構成が望ましいです。
以下に構成図を記載します。
先に説明したように、この構成はデータ系通信を外部向けの「dp-data-48」と内部向けの「dp-data-52」に分けています。着目してもらいたいのは、ネットワークを分けるだけでなく NSX-ALB SE 上のロードバランサーを展開するネットワークも「アプリはロードバランサーサービスを外側に公開」「k8s 本体はロードバランサーサービスを内側に公開」としている点です。今までのように k8s のロードバランサーをアプリと同じネットワークに展開すると、「k8s ノードには外部から直接アクセスできないが、k8s 本体のロードバランサー経由ではアクセスできる」という状態になり、当然望ましくありません。そのため、NSX-ALB SE を dp-data-48 だけでなく、dp-data-52 にも足を出すように構成しています。
この構成の NSX-ALB のネットワーク構成を記載します。
NSX-ALB が接続する全てのネットワークのサブネットと IP Pool が登録されています。ここでサブネットと IP Pool の設定さえしておけば、NSX-ALB SE は必要になったタイミングで vSphere のネットワークに動的(仮想マシン再起動などは発生しない)に NIC を追加して接続します。
ルーティングの設定はアプリ用のロードバランサーサービスを展開するインターフェースを使うデフォルトゲートウェイの設定のみしています。これは NSX-ALB と k8s の間のための設定ではなく、アドレスが不明なクライアントへの帰りパケットの転送のための設定です。
次にTKG 構築時のネットワーク設定は以下となります。
NSX-ALB の設定で
- Workload VIP Network Name がアプリのロードバランサーを展開する「dp-data-48」
- Management VIP Network Name が k8s 本体のロードバランサーを展開する「dp-data-52」
となっています。
k8s を展開するネットワークは「dp-data-52」となります。
この構成を構築すると、NSX-ALB SE は管理系の dp-mgmt-32 と、外側通信の dp-data-48、内側通信の dp-data-52 の全てのネットワークに接続します。
実際に k8s クラスタを構築し、nginx(アプリ)をサービス Type LoadBalancer で公開すると、NSX-ALB は k8s のロードバランサーを dp-data-52 に展開し、アプリのロードバランサーを dp-data-48 に展開します。
左側の Name から一番上のエントリがアプリの nginx で、振られているアドレスから dp-data-48 に属することがわかります。下の2つは k8s クラスタで、そのアドレスから dp-data-52 に属することがわかります。つまり、アプリあての通信は DMZ でロードバランスされ、k8s 本体あての通信は外からアクセスできないプライベートネットワークでロードバランスされます。
3ネットワーク構成(kube-vip で k8s vip)
この構成は kube-vip を利用するサンプルとして記載します。TKG 1.3 では利用されることが多かった構成ですが、TKG 1.4 では先に紹介した NSX-ALB を k8s のロードバランサーとして利用できるようになったため、新規構築はそちらを推奨します。
以下に構成図を記載します。
この構成では NSX-ALB のロードバランサーをアプリにしか利用しないため、dp-data-48 には接続しているものの、ロードバランサーを展開しない dp-data-52 には接続していません。クライアントから dp-data-48 上のロードバランサーがアプリ宛の通信を受け取ると、ロードバランサーはそれを宛先 k8s ノードに変更して、図の中央にある L3 スイッチを経由して dp-data-52 上の k8s ノードに届けます。
この構成の NSX-ALB ネットワーク設定は以下となります。
着目してほしいのは dp-data-52 のネットワーク設定がされていない(Noneになっている)ということです。もし仮に NSX-ALB が「dp-data-52 には 192.168.52.0/22 が繋がっている」ということを知っていれば、192.168.52.0/22 宛の通信を実施するのに Next Hop を経由するルーティングよりも「dp-data-52 にネットワーク接続(portを追加)する」という直接接続によるルーティングを優先します。
ここでは直接ネットワークの一覧に 192.168.52.0/22 のセグメントがないため、NSX-ALB はそこにどのようにデータを転送すればよいかわかりません。そのため、今回は NSX-ALB でスタティックルーティングで「192.168.52.0/22 宛の通信は 192.168.48.1 に転送する」と必要がありますが、これは今まで設定してきた帰り通信用のデフォルトゲートウェイの設定「0.0.0.0/0 宛の通信は 192.168.48.1 に転送する」に含まれているため、あえて個別に設定する必要はありません。
次に TKG の設定に入ります。今回は k8s の代表 IP を NSX-ALB ではなく、kube-vip にする設定をしています。
kube-vip は代表IPを固定で設定する必要があり、この設定をするとこの IP は k8s のマスターノードのいずれかが物理IPに加えて持つかたちで利用されます。
次に TKG の NSX-ALB 等の設定です。
今までと同じくWorkload VIP Network Name に加えて、Management VIP Network Name を設定していますが、後者は使われないので便宜上設定しているだけです。
この構成で k8s 上の nginx アプリを サービス Type LoadBalancer で公開すると、代表 IP は以下の状態になります。
まず、k8s の代表 IP 192.168.52.100 は NSX-ALB ではなく k8s のマスターノードが持っていることがわかります。そして、NSX-ALB はアプリの代表 IP 192.168.49.0 のみを持っていることがわかります。
以上で本記事を終了します。ご拝読ありがとうございました。