目次にジャンプ
documentation.suse.com / SUSE Edgeドキュメント

SUSE Edgeドキュメント

発行日: 2024年7月10日

SUSE Edgeドキュメント

『SUSE Edgeドキュメント』をお読みいただきありがとうございます。このドキュメントには、クイックスタートガイド、検証済みの設計、コンポーネントの使用に関するガイダンス、サードパーティ統合、エッジコンピューティングインフラストラクチャとワークロードを管理するためのベストプラクティスが記載されています。

1 SUSE Edgeとは

SUSE Edgeは、インフラストラクチャとクラウドネイティブなアプリケーションをエッジにデプロイするという独自の課題に対処することに特化した、緊密に統合されて包括的に検証されたエンドツーエンドのソリューションです。SUSE Edgeが重点を置いているのは、独創的でありながら高い柔軟性とスケーラビリティを持つセキュアなプラットフォームを提供し、初期デプロイメントイメージの構築からノードのプロビジョニングとオンボーディング、アプリケーションのデプロイメント、可観測性、ライフサイクル全体の運用にまで対応することです。このプラットフォームは、最良のオープンソースソフトウェアに基づいてゼロから構築されており、SUSEが持つ、30年にわたってセキュアで安定した定評あるSUSE Linuxプラットフォームを提供してきた歴史と、Rancherポートフォリオによって拡張性に優れ機能豊富なKubernetes管理を提供してきた経験の両方に合致するものです。SUSE Edgeは、これらの機能の上に構築されており、小売、医療、輸送、物流、通信、スマート製造、産業用IoTなど、さまざまな市場セグメントに対応できる機能を提供します。

2 設計理念

このソリューションは、顧客の要件や期待はさまざまであるため「万能」なエッジプラットフォームは存在しないという考え方に基づいて設計されています。エッジデプロイメントにより、実に困難な問題を解決し、継続的に進化させることが要求されます。たとえば、大規模なスケーラビリティ、ネットワークの可用性の制限、物理的なスペースの制約、新たなセキュリティの脅威と攻撃ベクトル、ハードウェアアーキテクチャとシステムリソースのバリエーション、レガシインフラストラクチャやレガシアプリケーションのデプロイとインタフェースの要件、耐用年数を延長している顧客ソリューションといった課題があります。こうした課題の多くは、従来の考え方(たとえば、データセンター内やパブリッククラウドへのインフラストラクチャやアプリケーションのデプロイメント)とは異なるため、はるかに細かく設計を検討し、一般的な前提の多くを再検討する必要があります。

たとえば、SUSEはミニマリズム、モジュール性、操作のしやすさに価値を見出しています。システムは複雑化するほど故障しやすくなるため、エッジ環境ではミニマリズムが重要です。数百、数十万カ所に及ぶとなると、複雑なシステムは複雑な故障が発生します。また、SUSEのソリューションはモジュール性を備えているため、ユーザの選択肢を増やしながら、デプロイしたプラットフォームが不必要に複雑になることを解消できます。さらに、ミニマリズムおよびモジュール性と、操作のしやすさとのバランスを取ることも必要です。人間はプロセスを何千回も繰り返すとミスを犯す可能性があるため、プラットフォーム側で潜在的なミスを確実に回復し、技術者が現場に出向かなくても済むようにすると同時に、一貫性と標準化を実現するよう努める必要もあります。

3 どのクイックスタートを使用すべきか

動作環境とライフサイクル要件はさまざまであるため、SUSEでは、SUSE Edgeを運用する市場セグメントやユースケースに大まかに一致する別個のデプロイメントパターンを多数サポートしています。また、これらの各デプロイメントパターンに対応するクイックスタートガイドを作成し、ユーザのニーズに基づいてSUSE Edgeプラットフォームに習熟できるようにしています。以下に、現在サポートされている3つのデプロイメントパターンを、各クイックスタートのページへのリンクと併せて説明します。

3.1 ダイレクトネットワークプロビジョニング

ダイレクトネットワークプロビジョニングでは、デプロイ先のハードウェアの詳細がわかっている場合に、アウトオブバンド管理インタフェースに直接アクセスして、プロビジョニングプロセス全体をオーケストレーションして自動化します。このシナリオで顧客が期待するソリューションとは、エッジサイトを一元的な場所から完全に自動化してプロビジョニングすることができ、ブートイメージの作成をはるかに上回る機能を備えていて、エッジロケーションでの手動操作を最小限に抑えられるソリューションです。つまり、ラックに搭載して電源をオンにし、必要なネットワークを物理ハードウェアに接続するだけで、自動化プロセスによってアウトオブバンド管理(Redfish APIなど)を介してマシンの電源が投入され、ユーザの介入なしにインフラストラクチャのプロビジョニング、オンボーディング、デプロイメントが処理されるソリューションです。これが機能するための鍵は、管理者がシステムを把握している、つまりどのハードウェアがどこにあるかを管理者が把握していることと、デプロイメントが中央で処理されることが想定されていることです。

このソリューションは最も堅牢です。管理者がハードウェアの管理インタフェースを直接操作して既知のハードウェアを扱うことに加え、ネットワークの利用可否に対する制約が少ないためです。機能面では、このソリューションは、Cluster APIとMetal3を広範に使用して、ベアメタルからオペレーティングシステム、Kubernetes、階層化アプリケーションまでを自動プロビジョニングし、デプロイメント後にSUSE Edgeの他の一般的なライフサイクル管理機能にリンクする機能を提供します。このソリューションのクイックスタートについては、第1章 「Metal3を使用したBMCの自動デプロイメントを参照してください。

3.2 「Phone Home」ネットワークプロビジョニング

場合によっては、中央管理クラスタでハードウェアを直接管理できない環境で運用することがあります(たとえば、リモートネットワークがファイアウォールの背後にある場合や、アウトオブバンド管理インタフェースがない場合などがあり、エッジでよく見られる「PC」タイプのハードウェアで一般的です)。このシナリオの場合のために、SUSEでは、ハードウェアのブートストラップ時にその配置先がわかっていなくても、クラスタとそのワークロードをリモートでプロビジョニングできるツールを提供しています。エッジコンピューティングについて考える場合、ほとんどの人はこう考えます。エッジコンピューティングとは、不明な部分がある数千あるいは数万台のシステムがエッジロケーションで起動し、安全にPhone Home通信を行い、そのシステムの身元を検証し、実行すべき処理についての指示を受信することです。ここで要件として期待されるのは、工場でマシンを事前イメージングしたり、USBなどでブートイメージをアタッチしたりする以外には、ユーザがほとんど介入しなくてもプロビジョニングとライフサイクル管理ができることです。この領域での主な課題は、こうしたデバイスの規模、一貫性、セキュリティ、ライフサイクルに対処することです。

このソリューションでは、非常に柔軟で一貫性のある方法でシステムをプロビジョニングおよびオンボーディングできます。システムの場所、タイプや仕様、初回電源投入日時などは問いません。SUSE Edgeでは、Edge Image Builderを使用してシステムを非常に柔軟にカスタマイズできます。また、ノードのオンボーディングとKubernetesのプロビジョニングにはRancherのElementalが提供する登録機能を活用するとともに、オペレーティングシステムへのパッチの適用にはSUSE Managerを活用します。このソリューションのクイックスタートについては、第2章 「Elementalを使用したリモートホストのオンボーディングを参照してください。

3.3 イメージベースのプロビジョニング

スタンドアロン環境、エアギャップ環境、またはネットワークが制限された環境で運用する必要があるお客様向けに、SUSE Edgeでは、必要なデプロイメントアーティファクトがすべて含まれる、完全にカスタマイズされたインストールメディアを生成できるソリューションを提供しています。これにより、シングルノードとマルチノード両方の高可用性Kubernetesクラスタを、必要なワークロードと追加の階層化コンポーネントを含めてエッジに設定できます。これはすべて、外部とのネットワーク接続や集中管理プラットフォームの介入なしに行うことができます。ユーザエクスペリエンスは、インストールメディアをターゲットシステムに提供するという点では「Phone Home」ソリューションによく似ていますが、このソリューションは「インプレースでブートストラップ」する点が異なります。このシナリオでは、生成されたクラスタをRancherに接続して継続的に管理する(つまり、大幅な再設定や再デプロイメントなしに、「非接続」動作モードから「接続」動作モードに移行する)ことも、分離した状態のまま動作を続行することもできます。どちらの場合も、一貫した同じメカニズムを適用してライフサイクル操作を自動化できることに注意してください。

さらに、このソリューションを使用すると、「ダイレクトネットワークプロビジョニング」モデルと「Phone Homeネットワークプロビジョニング」モデルの両方をサポートする集中型インフラストラクチャをホストできる管理クラスタを迅速に作成することもできます。この方法では、あらゆるタイプのエッジインフラストラクチャを最も迅速・簡単にプロビジョニングできます。このソリューションでは、SUSE Edge Image Builderの機能を多用して、完全にカスタマイズされた無人インストールメディアを作成します。クイックスタートについては、第3章 「Edge Image Builderを使用したスタンドアロンクラスタを参照してください。

4 SUSE Edgeで使用されるコンポーネント

SUSE Edgeは、SUSEの既存コンポーネント(LinuxチームとRancherチームが構築したコンポーネントを含む)と、SUSEがインフラストラクチャの要件と複雑さの両方に対処できるようにするためにEdgeチームが構築した追加機能とコンポーネントの両方で構成されています。コンポーネントのリスト、各コンポーネントの概要説明へのリンク、およびSUSE Edgeでの用途については、以下を参照してください。

パート I クイックスタート

クイックスタートはこちら

  • 1 Metal3を使用したBMCの自動デプロイメント
  • Metal3は、Kubernetesにベアメタルインフラストラクチャ管理機能を提供するCNCFプロジェクトです。

  • 2 Elementalを使用したリモートホストのオンボーディング
  • このセクションでは、SUSE Edgeの一部としての「Phone Homeネットワークプロビジョニング」ソリューションについて説明します。このソリューションは、Elementalを使用してノードのオンボーディングを支援します。Elementalは、Kubernetesを使用してリモートホスト登録と一元化された完全なクラウドネイティブOS管理を可能にするソフトウェアスタックです。SUSE Edgeスタックでは、Elementalの登録機能を使用して、リモートホストをRancherにオンボーディングできます。これにより、ホストを集中管理プラットフォームに統合し、そこからKubernetesクラスタ…

  • 3 Edge Image Builderを使用したスタンドアロンクラスタ
  • Edge Image Builder (EIB)は、完全なエアギャップシナリオでもマシンをブートストラップできるCustomized, Ready-to-Boot (CRB)ディスクイメージの生成プロセスを効率化するツールです。EIBを使用すると、SUSE Edgeの3つのデプロイメントフットプリントすべてで使用するデプロイメントイメージを作成できます。これは、EIBが十分に柔軟であり、最小限のカスタマイズ(例: ユーザの追加やタイムゾーンの設定)から、あらゆる設定を網羅したイメージ(例: 複雑なネットワーク設定を行い、マルチノードKubernetesクラスタをデプロイして、顧客ワークロードを…

1 Metal3を使用したBMCの自動デプロイメント

Metal3は、Kubernetesにベアメタルインフラストラクチャ管理機能を提供するCNCFプロジェクトです。

Metal3は、Redfishなどのアウトオブバンドプロトコルを介した管理をサポートするベアメタルサーバのライフサイクルを管理するためのKubernetesネイティブリソースを提供します。

また、Cluster API (CAPI)も十分にサポートされており、広く採用されているベンダニュートラルなAPIを使用して、複数のインフラストラクチャプロバイダにわたってインフラストラクチャリソースを管理できます。

1.1 この方法を使用する理由

この方法は、ターゲットハードウェアがアウトオブバンド管理をサポートしていて、完全に自動化されたインフラストラクチャ管理フローが望まれるシナリオで役立ちます。

管理クラスタは宣言型APIを提供するように設定されており、このAPIによってダウンストリームクラスタのベアメタルサーバのインベントリと状態を管理できます。これには、自動検査、クリーニング、プロビジョニング/プロビジョニング解除も含まれます。

1.2 アーキテクチャの概要

クイックスタートmetal3アーキテクチャ

1.3 前提条件

ダウンストリームクラスタのサーバハードウェアとネットワーキングに関連する固有の制約がいくつかあります。

  • 管理クラスタ

    • ターゲットサーバ管理/BMC APIへのネットワーク接続が必要

    • ターゲットサーバのコントロールプレーンネットワークへのネットワーク接続が必要

    • マルチノード管理クラスタの場合、追加の予約済みIPアドレスが必要

  • 制御対象ホスト

    • Redfish、iDRAC、またはiLOのインタフェースを介したアウトオブバンド管理のサポートが必要

    • 仮想メディアを使用したデプロイメントのサポートが必要(PXEは現在未サポート)

    • Metal3プロビジョニングAPIにアクセスするために管理クラスタへのネットワーク接続が必要

ツールがいくつか必要です。ツールは管理クラスタにインストールするか、管理クラスタにアクセス可能なホストにインストールできます。

SLE-Micro.x86_64-5.5.0-Default-GM.raw.xz OSイメージファイルは、SUSE Customer CenterまたはSUSEダウンロードページからダウンロードする必要があります。

1.3.1 管理クラスタのセットアップ

管理クラスタをインストールし、Metal3を使用する基本的な手順は次のとおりです。

  1. RKE2管理クラスタをインストールします。

  2. Rancherのインストール

  3. ストレージプロバイダをインストールします。

  4. Metal3の依存関係をインストールします。

  5. CAPIの依存関係をインストールします。

  6. ダウンストリームクラスタホスト用のSLEMicro OSイメージを構築します。

  7. BareMetalHost CRを登録し、ベアメタルのインベントリを定義します。

  8. CAPIリソースを定義して、ダウンストリームクラスタを作成します。

このガイドでは、既存のRKE2クラスタとRancher (cert-managerを含む)が、たとえばEdge Image Builder (第9章 「Edge Image Builder)を使用してインストールされていることを前提としています。

ヒント
ヒント

ここでの手順は、ATIP管理クラスタのドキュメント(第29章 「管理クラスタの設定)で説明されているように、完全に自動化することもできます。

1.3.2 Metal3の依存関係のインストール

cert-managerがまだRancherのインストールの一部としてインストールされていない場合は、cert-managerをインストールして実行する必要があります。

永続ストレージプロバイダをインストールする必要があります。Longhornを推奨しますが、開発/PoC環境ではローカルパスを使用することもできます。以下の手順は、StorageClassがデフォルトとしてマークされていることを前提としています。マークされていない場合は、Metal3チャートに追加の設定が必要です。

追加のIPが必要です。このIPはMetalLBによって管理され、Metal3管理サービスに一貫したエンドポイントを提供します。このIPは、コントロールプレーンサブネットに属していて、静的設定用に予約されている必要があります(どのDHCPプールにも属していてはなりません)。

ヒント
ヒント

管理クラスタがシングルノードである場合、MetalLBを介して管理されるフローティングIPを追加する必要はありません。「シングルノード設定」(1.6.1項 「シングルノード設定」)を参照してください。

  1. まず、MetalLBをインストールします。

    helm install \
      metallb oci://registry.suse.com/edge/metallb-chart \
      --namespace metallb-system \
      --create-namespace
  2. 続いて、次のように、予約済みIPを使用してIPAddressPoolL2Advertismentを定義し、STATIC_IRONIC_IPとして定義します。

    export STATIC_IRONIC_IP=<STATIC_IRONIC_IP>
    
    cat <<-EOF | kubectl apply -f -
    apiVersion: metallb.io/v1beta1
    kind: IPAddressPool
    metadata:
      name: ironic-ip-pool
      namespace: metallb-system
    spec:
      addresses:
      - ${STATIC_IRONIC_IP}/32
      serviceAllocation:
        priority: 100
        serviceSelectors:
        - matchExpressions:
          - {key: app.kubernetes.io/name, operator: In, values: [metal3-ironic]}
    EOF
    cat <<-EOF | kubectl apply -f -
    apiVersion: metallb.io/v1beta1
    kind: L2Advertisement
    metadata:
      name: ironic-ip-pool-l2-adv
      namespace: metallb-system
    spec:
      ipAddressPools:
      - ironic-ip-pool
    EOF
  3. これでMetal3をインストールできます。

    helm install \
      metal3 oci://registry.suse.com/edge/metal3-chart \
      --namespace metal3-system \
      --create-namespace \
      --set global.ironicIP="${STATIC_IRONIC_IP}"
  4. initContainerがこのデプロイメントで実行されるまでに2分ほどかかる場合があります。そのため、Podがすべて実行されていることを確認してから次に進んでください。

    kubectl get pods -n metal3-system
    NAME                                                    READY   STATUS    RESTARTS   AGE
    baremetal-operator-controller-manager-85756794b-fz98d   2/2     Running   0          15m
    metal3-metal3-ironic-677bc5c8cc-55shd                   4/4     Running   0          15m
    metal3-metal3-mariadb-7c7d6fdbd8-64c7l                  1/1     Running   0          15m
警告
警告

metal3-systemネームスペースのすべてのPodが実行されるまで、次の手順に進まないでください。

1.3.3 Cluster APIの依存関係のインストール

まず、Rancherに組み込みのCAPIコントローラを無効にする必要があります。

cat <<-EOF | kubectl apply -f -
apiVersion: management.cattle.io/v3
kind: Feature
metadata:
  name: embedded-cluster-api
spec:
  value: false
EOF

kubectl delete mutatingwebhookconfiguration.admissionregistration.k8s.io mutating-webhook-configuration
kubectl delete validatingwebhookconfigurations.admissionregistration.k8s.io validating-webhook-configuration
kubectl wait --for=delete namespace/cattle-provisioning-capi-system --timeout=300s

次に、SUSEイメージを使用するために、設定ファイルが必要です。

mkdir ~/.cluster-api
cat >  ~/.cluster-api/clusterctl.yaml <<EOF
images:
  all:
    repository: registry.suse.com/edge
EOF

clusterctl 1.6.xをインストールし、その後、次のようにコア、インフラストラクチャ、ブートストラップ、およびコントロールプレーンのプロバイダをインストールします。

clusterctl init --core "cluster-api:v1.6.2" --infrastructure "metal3:v1.6.0" --bootstrap "rke2:v0.2.6" --control-plane "rke2:v0.2.6"

しばらくすると、コントローラPodがcapi-systemcapm3-systemrke2-bootstrap-system、およびrke2-control-plane-systemの各ネームスペースで実行されているはずです。

1.3.4 ダウンストリームクラスタイメージの準備

Edge Image Builder (第9章 「Edge Image Builder)を使用して、ダウンストリームクラスタホスト上にプロビジョニングされる、変更されたSLEMicroベースイメージを準備します。

ほとんどの設定はEdge Image Builderを使用して行うことができますが、このガイドではダウンストリームクラスタをセットアップするために必要な最小限の設定について説明します。

1.3.4.1 イメージの設定

Edge Image Builderを実行する場合、そのホストからディレクトリがマウントされるため、ターゲットイメージの定義に使用する設定ファイルを保存するディレクトリ構造を作成する必要があります。

  • downstream-cluster-config.yamlはイメージ定義ファイルです。詳細については、第3章 「Edge Image Builderを使用したスタンドアロンクラスタを参照してください。

  • ダウンロードされたベースイメージはxzで圧縮されているので、unxzで展開し、base-imagesフォルダの下にコピー/移動する必要があります。

  • networkフォルダはオプションです。詳細については、1.3.5.1.1項 「静的ネットワーク設定用の追加スクリプト」を参照してください。

  • custom/scriptsディレクトリには、初回ブート時に実行されるスクリプトが含まれています。現在は、デプロイメント時にOSルートパーティションのサイズを変更するために、growfs.shスクリプトが必要です。

├── downstream-cluster-config.yaml
├── base-images/
│   └ SLE-Micro.x86_64-5.5.0-Default-GM.raw
├── network/
|   └ configure-network.sh
└── custom/
    └ scripts/
        └ growfs.sh
1.3.4.1.1 ダウンストリームクラスタイメージ定義ファイル

downstream-cluster-config.yamlファイルは、ダウンストリームクラスタイメージの主要な設定ファイルです。次に、Metal3を介したデプロイメントの最小例を示します。

apiVersion: 1.0
image:
  imageType: RAW
  arch: x86_64
  baseImage: SLE-Micro.x86_64-5.5.0-Default-GM.raw
  outputImageName: SLE-Micro-eib-output.raw
operatingSystem:
  kernelArgs:
    - ignition.platform.id=openstack
    - net.ifnames=1
  systemd:
    disable:
      - rebootmgr
  users:
    - username: root
      encryptedPassword: ${ROOT_PASSWORD}
      sshKeys:
      - ${USERKEY1}

${ROOT_PASSWORD}はルートユーザの暗号化パスワードで、テスト/デバッグに役立ちます。このパスワードは、openssl passwd -6 PASSWORDコマンドで生成できます。

運用環境では、${USERKEY1}を実際のSSHキーに置き換えて、usersブロックに追加できるSSHキーを使用することをお勧めします。

注記
注記

net.ifnames=1は、Predictable Network Interface Namingを有効にします。

これはmetal3チャートのデフォルト設定と一致しますが、この設定は、設定されたチャートのpredictableNicNamesの値と一致する必要があります。

また、ignition.platform.id=openstackは必須であり、この引数がないと、Metal3の自動化フローでIgnitionによるSLEMicroの設定が失敗することにも注意してください。

1.3.4.1.2 Growfsスクリプト

現在は、カスタムスクリプト(custom/scripts/growfs.sh)があります。これは、プロビジョニング後の初回ブート時にディスクサイズに合わせてファイルシステムを拡張するために必要です。growfs.shスクリプトには次の情報が含まれています。

#!/bin/bash
growfs() {
  mnt="$1"
  dev="$(findmnt --fstab --target ${mnt} --evaluate --real --output SOURCE --noheadings)"
  # /dev/sda3 -> /dev/sda, /dev/nvme0n1p3 -> /dev/nvme0n1
  parent_dev="/dev/$(lsblk --nodeps -rno PKNAME "${dev}")"
  # Last number in the device name: /dev/nvme0n1p42 -> 42
  partnum="$(echo "${dev}" | sed 's/^.*[^0-9]\([0-9]\+\)$/\1/')"
  ret=0
  growpart "$parent_dev" "$partnum" || ret=$?
  [ $ret -eq 0 ] || [ $ret -eq 1 ] || exit 1
  /usr/lib/systemd/systemd-growfs "$mnt"
}
growfs /
注記
注記

同じアプローチを使用して、プロビジョニングプロセス中に実行する独自のカスタムスクリプトを追加します。詳細については、第3章 「Edge Image Builderを使用したスタンドアロンクラスタを参照してください。

この回避策に関連するバグは、https://bugzilla.suse.com/show_bug.cgi?id=1217430です。

1.3.4.2 イメージの作成

これまでのセクションに従ってディレクトリ構造を準備したら、次のコマンドを実行してイメージを構築します。

podman run --rm --privileged -it -v $PWD:/eib \
 registry.suse.com/edge/edge-image-builder:1.0.2 \
 build --definition-file downstream-cluster-config.yaml

これにより、上記の定義に基づいて、SLE-Micro-eib-output.rawという名前の出力イメージファイルが作成されます。

その後、この出力イメージをWebサーバ経由で利用できるようにする必要があります。その際、Metal3チャートを使用して有効にしたメディアサーバコンテナ(注記)か、ローカルにアクセス可能な他のサーバのいずれかを使用します。以下の例では、このサーバをimagecache.local:8080として参照します。

1.3.5 BareMetalHostインベントリの追加

自動デプロイメント用にベアメタルサーバを登録するには、リソースを2つ作成する必要があります。BMCアクセス資格情報を保存するシークレットと、BMC接続とその他の詳細を定義するMetal3 BareMetalHostリソースです。

apiVersion: v1
kind: Secret
metadata:
  name: controlplane-0-credentials
type: Opaque
data:
  username: YWRtaW4=
  password: cGFzc3dvcmQ=
---
apiVersion: metal3.io/v1alpha1
kind: BareMetalHost
metadata:
  name: controlplane-0
  labels:
    cluster-role: control-plane
spec:
  online: true
  bootMACAddress: "00:f3:65:8a:a3:b0"
  bmc:
    address: redfish-virtualmedia://192.168.125.1:8000/redfish/v1/Systems/68bd0fb6-d124-4d17-a904-cdf33efe83ab
    disableCertificateVerification: true
    credentialsName: controlplane-0-credentials

次の点に注意してください。

  • シークレットのユーザ名/パスワードはbase64でエンコードされている必要があります。また、末尾に改行を含めないでください(たとえば、単なるechoではなく、echo ‑nを使用してください)。

  • cluster-roleラベルは、この時点で設定することも、後でクラスタの作成時に設定することもできます。以下の例では、control-planeまたはworkerを想定しています。

  • bootMACAddressは、ホストのコントロールプレーンNICに一致する有効なMACである必要があります。

  • bmcのアドレスはBMC管理APIへの接続です。次のアドレスがサポートされています。

    • redfish-virtualmedia://<IP ADDRESS>/redfish/v1/Systems/<SYSTEM ID>: Redfish仮想メディア(たとえば、SuperMicro)

    • idrac-virtualmedia://<IP ADDRESS>/redfish/v1/Systems/System.Embedded.1: Dell iDRAC

  • BareMetalHost APIの詳細については、アップストリームのAPIドキュメントを参照してください。

1.3.5.1 静的IPの設定

上記のBareMetalHostの例では、DHCPでコントロールプレーンネットワークの設定を提供することを想定していますが、静的IPなどの手動設定が必要なシナリオでは、以下に説明するように追加の設定を指定できます。

1.3.5.1.1 静的ネットワーク設定用の追加スクリプト

Edge Image Builderでゴールデンイメージを作成する際には、networkフォルダ内に次のconfigure-network.shファイルを作成します。

このファイルにより、初回ブート時に設定ドライブのデータを使用して、NM Configuratorツールを使ってホストネットワーキングを設定します。

#!/bin/bash

set -eux

# Attempt to statically configure a NIC in the case where we find a network_data.json
# In a configuration drive

CONFIG_DRIVE=$(blkid --label config-2 || true)
if [ -z "${CONFIG_DRIVE}" ]; then
  echo "No config-2 device found, skipping network configuration"
  exit 0
fi

mount -o ro $CONFIG_DRIVE /mnt

NETWORK_DATA_FILE="/mnt/openstack/latest/network_data.json"

if [ ! -f "${NETWORK_DATA_FILE}" ]; then
  umount /mnt
  echo "No network_data.json found, skipping network configuration"
  exit 0
fi

DESIRED_HOSTNAME=$(cat /mnt/openstack/latest/meta_data.json | tr ',{}' '\n' | grep '\"metal3-name\"' | sed 's/.*\"metal3-name\": \"\(.*\)\"/\1/')

mkdir -p /tmp/nmc/{desired,generated}
cp ${NETWORK_DATA_FILE} /tmp/nmc/desired/${DESIRED_HOSTNAME}.yaml
umount /mnt

./nmc generate --config-dir /tmp/nmc/desired --output-dir /tmp/nmc/generated
./nmc apply --config-dir /tmp/nmc/generated
1.3.5.1.2 ホストネットワーク設定の追加シークレット

NM Configurator (第10章 「Edgeネットワーキング)でサポートされているnmstate形式のデータを含む追加シークレットをホストごとに定義できます。

その後、このシークレットは、BareMetalHostリソースでpreprovisioningNetworkDataNameの指定フィールドを使用して参照されます。

apiVersion: v1
kind: Secret
metadata:
  name: controlplane-0-networkdata
type: Opaque
stringData:
  networkData: |
    interfaces:
    - name: enp1s0
      type: ethernet
      state: up
      mac-address: "00:f3:65:8a:a3:b0"
      ipv4:
        address:
        - ip:  192.168.125.200
          prefix-length: 24
        enabled: true
        dhcp: false
    dns-resolver:
      config:
        server:
        - 192.168.125.1
    routes:
      config:
      - destination: 0.0.0.0/0
        next-hop-address: 192.168.125.1
        next-hop-interface: enp1s0
---
apiVersion: metal3.io/v1alpha1
kind: BareMetalHost
metadata:
  name: controlplane-0
  labels:
    cluster-role: control-plane
spec:
  preprovisioningNetworkDataName: controlplane-0-networkdata
# Remaining content as in previous example
注記
注記

mac-addressは、nmstate APIではオプションですが、NM Configuratorを介した設定では必須であり、必ず指定する必要があります。

1.3.5.2 BareMetalHostの準備

上記の説明に従ってBareMetalHostリソースと関連するシークレットを作成すると、次のようにホスト準備ワークフローがトリガされます。

  • ターゲットホストのBMCに接続された仮想メディアによってramdiskイメージがブートされる

  • ramdiskがハードウェア詳細を検査し、ホストをプロビジョニング用に準備する(たとえば、ディスクから以前のデータを消去する)

  • このプロセスが完了すると、BareMetalHostのstatus.hardwareフィールドのハードウェア詳細が更新され、検証可能になる

このプロセスには数分かかる場合がありますが、完了すると、BareMetalHostの状態がavailableになります。

% kubectl get baremetalhost
NAME             STATE       CONSUMER   ONLINE   ERROR   AGE
controlplane-0   available              true             9m44s
worker-0         available              true             9m44s

1.3.6 ダウンストリームクラスタの作成

続いて、ダウンストリームクラスタを定義するCluster APIリソースと、BareMetalHostリソースをプロビジョニングしてからブートストラップを実行してRKE2クラスタを形成するマシンリソースを作成します。

1.3.7 コントロールプレーンのデプロイメント

コントロールプレーンをデプロイするために、以下のリソースを含む次のようなyamlマニフェストを定義します。

  • クラスタリソースでは、クラスタ名、ネットワーク、およびコントロールプレーン/インフラストラクチャプロバイダのタイプ(この場合はRKE2/Metal3)を定義します。

  • Metal3Clusterでは、コントロールプレーンのエンドポイント(シングルノードの場合はホストIP、マルチノードの場合はLoadBalancerエンドポイント。この例ではシングルノードを想定)を定義します。

  • RKE2ControlPlaneでは、RKE2のバージョンと、クラスタのブートストラップ時に必要な追加設定を定義します。

  • Metal3MachineTemplateではBareMetalHostリソースに適用するOSイメージを定義し、hostSelectorでは使用するBareMetalHostを定義します。

  • Metal3DataTemplateでは、BareMetalHostに渡す追加のメタデータを定義します(networkDataは現在のところEdgeソリューションではサポートされていないことに注意してください)。

シンプルにするために、この例では、BareMetalHostにIP 192.168.125.200が設定されたシングルノードのコントロールプレーンを想定しています。より高度なマルチノードの例については、ATIPのドキュメント(第31章 「完全に自動化されたダイレクトネットワークプロビジョニング)を参照してください。

apiVersion: cluster.x-k8s.io/v1beta1
kind: Cluster
metadata:
  name: sample-cluster
  namespace: default
spec:
  clusterNetwork:
    pods:
      cidrBlocks:
        - 192.168.0.0/18
    services:
      cidrBlocks:
        - 10.96.0.0/12
  controlPlaneRef:
    apiVersion: controlplane.cluster.x-k8s.io/v1alpha1
    kind: RKE2ControlPlane
    name: sample-cluster
  infrastructureRef:
    apiVersion: infrastructure.cluster.x-k8s.io/v1beta1
    kind: Metal3Cluster
    name: sample-cluster
---
apiVersion: infrastructure.cluster.x-k8s.io/v1beta1
kind: Metal3Cluster
metadata:
  name: sample-cluster
  namespace: default
spec:
  controlPlaneEndpoint:
    host: 192.168.125.200
    port: 6443
  noCloudProvider: true
---
apiVersion: controlplane.cluster.x-k8s.io/v1alpha1
kind: RKE2ControlPlane
metadata:
  name: sample-cluster
  namespace: default
spec:
  infrastructureRef:
    apiVersion: infrastructure.cluster.x-k8s.io/v1beta1
    kind: Metal3MachineTemplate
    name: sample-cluster-controlplane
  replicas: 1
  agentConfig:
    format: ignition
    kubelet:
      extraArgs:
        - provider-id=metal3://BAREMETALHOST_UUID
    additionalUserData:
      config: |
        variant: fcos
        version: 1.4.0
        systemd:
          units:
            - name: rke2-preinstall.service
              enabled: true
              contents: |
                [Unit]
                Description=rke2-preinstall
                Wants=network-online.target
                Before=rke2-install.service
                ConditionPathExists=!/run/cluster-api/bootstrap-success.complete
                [Service]
                Type=oneshot
                User=root
                ExecStartPre=/bin/sh -c "mount -L config-2 /mnt"
                ExecStart=/bin/sh -c "sed -i \"s/BAREMETALHOST_UUID/$(jq -r .uuid /mnt/openstack/latest/meta_data.json)/\" /etc/rancher/rke2/config.yaml"
                ExecStart=/bin/sh -c "echo \"node-name: $(jq -r .name /mnt/openstack/latest/meta_data.json)\" >> /etc/rancher/rke2/config.yaml"
                ExecStartPost=/bin/sh -c "umount /mnt"
                [Install]
                WantedBy=multi-user.target
    version: v1.28.9+rke2r1
---
apiVersion: infrastructure.cluster.x-k8s.io/v1beta1
kind: Metal3MachineTemplate
metadata:
  name: sample-cluster-controlplane
  namespace: default
spec:
  template:
    spec:
      dataTemplate:
        name: sample-cluster-controlplane-template
      hostSelector:
        matchLabels:
          cluster-role: control-plane
      image:
        checksum: http://imagecache.local:8080/SLE-Micro-eib-output.raw.sha256
        checksumType: sha256
        format: raw
        url: http://imagecache.local:8080/SLE-Micro-eib-output.raw
---
apiVersion: infrastructure.cluster.x-k8s.io/v1beta1
kind: Metal3DataTemplate
metadata:
  name: sample-cluster-controlplane-template
  namespace: default
spec:
  clusterName: sample-cluster
  metaData:
    objectNames:
      - key: name
        object: machine
      - key: local-hostname
        object: machine
      - key: local_hostname
        object: machine

上記の例をコピーし、自身の環境に合わせて調整したら、kubectlを使用して適用し、clusterctlでクラスタのステータスを監視できます。

% kubectl apply -f rke2-control-plane.yaml

# Wait for the cluster to be provisioned - status can be checked via clusterctl
% clusterctl describe cluster sample-cluster
NAME                                                    READY  SEVERITY  REASON  SINCE  MESSAGE
Cluster/sample-cluster                                  True                     22m
├─ClusterInfrastructure - Metal3Cluster/sample-cluster  True                     27m
├─ControlPlane - RKE2ControlPlane/sample-cluster        True                     22m
│ └─Machine/sample-cluster-chflc                        True                     23m

1.3.8 ワーカー/コンピュートのデプロイメント

コントロールプレーンと同様に、次のリソースを含むyamlマニフェストを定義します。

  • MachineDeploymentでは、レプリカ(ホスト)の数とブートストラップ/インフラストラクチャプロバイダ(この場合はRKE2/Metal3)を定義します。

  • RKE2ConfigTemplateでは、エージェントホストのブートストラップ用のRKE2のバージョンと初回ブート設定を記述します。

  • Metal3MachineTemplateではBareMetalHostリソースに適用するOSイメージを定義し、hostSelectorでは使用するBareMetalHostを定義します。

  • Metal3DataTemplateでは、BareMetalHostに渡す追加のメタデータを定義します(networkDataは現在のところEdgeソリューションではサポートされていないことに注意してください)。

apiVersion: cluster.x-k8s.io/v1beta1
kind: MachineDeployment
metadata:
  labels:
    cluster.x-k8s.io/cluster-name: sample-cluster
  name: sample-cluster
  namespace: default
spec:
  clusterName: sample-cluster
  replicas: 1
  selector:
    matchLabels:
      cluster.x-k8s.io/cluster-name: sample-cluster
  template:
    metadata:
      labels:
        cluster.x-k8s.io/cluster-name: sample-cluster
    spec:
      bootstrap:
        configRef:
          apiVersion: bootstrap.cluster.x-k8s.io/v1alpha1
          kind: RKE2ConfigTemplate
          name: sample-cluster-workers
      clusterName: sample-cluster
      infrastructureRef:
        apiVersion: infrastructure.cluster.x-k8s.io/v1beta1
        kind: Metal3MachineTemplate
        name: sample-cluster-workers
      nodeDrainTimeout: 0s
      version: v1.28.9+rke2r1
---
apiVersion: bootstrap.cluster.x-k8s.io/v1alpha1
kind: RKE2ConfigTemplate
metadata:
  name: sample-cluster-workers
  namespace: default
spec:
  template:
    spec:
      agentConfig:
        format: ignition
        version: v1.28.9+rke2r1
        kubelet:
          extraArgs:
            - provider-id=metal3://BAREMETALHOST_UUID
        additionalUserData:
          config: |
            variant: fcos
            version: 1.4.0
            systemd:
              units:
                - name: rke2-preinstall.service
                  enabled: true
                  contents: |
                    [Unit]
                    Description=rke2-preinstall
                    Wants=network-online.target
                    Before=rke2-install.service
                    ConditionPathExists=!/run/cluster-api/bootstrap-success.complete
                    [Service]
                    Type=oneshot
                    User=root
                    ExecStartPre=/bin/sh -c "mount -L config-2 /mnt"
                    ExecStart=/bin/sh -c "sed -i \"s/BAREMETALHOST_UUID/$(jq -r .uuid /mnt/openstack/latest/meta_data.json)/\" /etc/rancher/rke2/config.yaml"
                    ExecStart=/bin/sh -c "echo \"node-name: $(jq -r .name /mnt/openstack/latest/meta_data.json)\" >> /etc/rancher/rke2/config.yaml"
                    ExecStartPost=/bin/sh -c "umount /mnt"
                    [Install]
                    WantedBy=multi-user.target
---
apiVersion: infrastructure.cluster.x-k8s.io/v1beta1
kind: Metal3MachineTemplate
metadata:
  name: sample-cluster-workers
  namespace: default
spec:
  template:
    spec:
      dataTemplate:
        name: sample-cluster-workers-template
      hostSelector:
        matchLabels:
          cluster-role: worker
      image:
        checksum: http://imagecache.local:8080/SLE-Micro-eib-output.raw.sha256
        checksumType: sha256
        format: raw
        url: http://imagecache.local:8080/SLE-Micro-eib-output.raw
---
apiVersion: infrastructure.cluster.x-k8s.io/v1beta1
kind: Metal3DataTemplate
metadata:
  name: sample-cluster-workers-template
  namespace: default
spec:
  clusterName: sample-cluster
  metaData:
    objectNames:
      - key: name
        object: machine
      - key: local-hostname
        object: machine
      - key: local_hostname
        object: machine

上記の例をコピーし、自身の環境に合わせて調整したら、kubectlを使用して適用し、clusterctlでクラスタのステータスを監視できます。

% kubectl apply -f rke2-agent.yaml

# Wait some time for the compute/agent hosts to be provisioned
% clusterctl describe cluster sample-cluster
NAME                                                    READY  SEVERITY  REASON  SINCE  MESSAGE
Cluster/sample-cluster                                  True                     25m
├─ClusterInfrastructure - Metal3Cluster/sample-cluster  True                     30m
├─ControlPlane - RKE2ControlPlane/sample-cluster        True                     25m
│ └─Machine/sample-cluster-chflc                        True                     27m
└─Workers
  └─MachineDeployment/sample-cluster                    True                     22m
    └─Machine/sample-cluster-56df5b4499-zfljj           True                     23m

1.3.9 クラスタのプロビジョニング解除

ダウンストリームクラスタをプロビジョニング解除するには、上記の作成手順で適用したリソースを削除します。

% kubectl delete -f rke2-agent.yaml
% kubectl delete -f rke2-control-plane.yaml

これにより、BareMetalHostリソースのプロビジョニング解除がトリガされます。これには数分かかることがあり、その後リソースは再び利用可能な状態になります。

% kubectl get bmh
NAME             STATE            CONSUMER                            ONLINE   ERROR   AGE
controlplane-0   deprovisioning   sample-cluster-controlplane-vlrt6   false            10m
worker-0         deprovisioning   sample-cluster-workers-785x5        false            10m

...

% kubectl get bmh
NAME             STATE       CONSUMER   ONLINE   ERROR   AGE
controlplane-0   available              false            15m
worker-0         available              false            15m

1.4 既知の問題

  • 現在、アップストリームのIPアドレス管理コントローラはサポートされていません。このコントローラには、SLEMicroで選択されているネットワーク設定ツールと初回ブートツールチェーンとの互換性がまだないためです。

  • 関連して、 IPAMリソースと、Metal3DataTemplateのnetworkDataフィールドは現在のところサポートされていません。

  • redfish-virtualmediaを介したデプロイメントのみが現在サポートされています。

  • デプロイされたクラスタは現在、Rancherにインポートされません。

  • Rancherの組み込みCAPIコントローラが無効化されるため、上記の方法でMetal3用に設定した管理クラスタを、Elemental (第11章 「Elemental)などの他のクラスタプロビジョニング方法でも使用することはできません。

1.5 予定されている変更

  • Rancherへのデプロイされたクラスタのインポート。これは今後、Rancher Turtlesを介してインポートできるようになる予定です。

  • Rancher Turtlesとの連携。これにより、Rancherの組み込みCAPIを無効にする必要がなくなるため、管理クラスタを介して他のクラスタ方法も使用できるようになります。

  • networkDataフィールドを使用した、IPAMリソースと設定のサポートの有効化。

1.6 追加のリソース

ATIPのドキュメント(第26章 「SUSE Adaptive Telco Infrastructure Platform (ATIP))に、通信事業者のユースケースにおけるMetal3のより高度な使用例が記載されています。

1.6.1 シングルノード設定

管理クラスタがシングルノードであるテスト/PoC環境では、MetalLBを介して管理されるフローティングIPを追加する必要はありません。

このモードでは、管理クラスタAPIのエンドポイントが管理クラスタのIPになるため、DHCPを使用している場合はそのIPを予約するか、管理クラスタのIPが変更されないように静的に設定する必要があります(以下では<MANAGEMENT_CLUSTER_IP>と表記しています)。

このシナリオを有効にするために必要なmetal3チャートの値は次のとおりです。

global:
  ironicIP: <MANAGEMENT_CLUSTER_IP>
metal3-ironic:
  service:
    type: NodePort

1.6.2 仮想メディアISOをアタッチするためのTLSの無効化

一部のサーバベンダは、仮想メディアISOイメージをBMCにアタッチする際にSSL接続を検証しますが、Metal3のデプロイメント用に生成された証明書は自己署名されているため、問題が発生する可能性があります。この問題を回避するには、次のようなmetal3チャートの値を使用して、仮想メディアディスクをアタッチする場合にのみTLSを無効にすることができます。

global:
  enable_vmedia_tls: false

別の解決策は、CA証明書を使用してBMCを設定することです。この場合、kubectlを使用してクラスタから証明書を読み込むことができます。

kubectl get secret -n metal3-system ironic-vmedia-cert -o yaml

これにより、証明書をサーバのBMCコンソールで設定できますが、そのプロセスはベンダ固有です(すべてのベンダで可能というわけではなく、可能でない場合はenable_vmedia_tlsフラグが必要なことがあります)。

2 Elementalを使用したリモートホストのオンボーディング

このセクションでは、SUSE Edgeの一部としての「Phone Homeネットワークプロビジョニング」ソリューションについて説明します。このソリューションは、Elementalを使用してノードのオンボーディングを支援します。Elementalは、Kubernetesを使用してリモートホスト登録と一元化された完全なクラウドネイティブOS管理を可能にするソフトウェアスタックです。SUSE Edgeスタックでは、Elementalの登録機能を使用して、リモートホストをRancherにオンボーディングできます。これにより、ホストを集中管理プラットフォームに統合し、そこからKubernetesクラスタに加えて、階層化コンポーネント、アプリケーション、およびそのライフサイクルをすべて共通の場所からデプロイおよび管理できるようになります。

このアプローチが役立つシナリオとしては、制御するデバイスがアップストリームクラスタと同じネットワーク上にないか、アウトオブバンド管理コントローラが搭載されておらず、より直接的に制御できない場合や、さまざまな「不明」なシステムをエッジで多数ブートしており、それらを安全にオンボーディングして大規模に管理する必要がある場合が考えられます。これは、小売や産業用IoTなど、デバイスが設置されるネットワークをほとんど制御できない分野のユースケースによく見られるシナリオです。

2.1 アーキテクチャの概要

クイックスタートElementalアーキテクチャ

2.2 必要なリソース

このクイックスタートを実行するためのシステムと環境の最小要件を次に示します。

  • 集中管理クラスタ(RancherとElementalをホストするクラスタ)用のホスト:

    • 開発またはテスト用の場合、最小8GBのRAMと20GBのディスク容量 (運用環境での使用についてはこちら を参照)

  • プロビジョニングするターゲットノード、すなわちエッジデバイス(デモまたはテストの場合は仮想マシンを使用可能)

    • 最小4GBのRAM、2 CPUコア、20GBのディスク

  • 管理クラスタの解決可能なホスト名、またはsslip.ioなどのサービスで使用する静的IPアドレス

  • Edge Image Builderでインストールメディアを構築するためのホスト

    • SLES 15 SP5、openSUSE Leap 15.5、またはPodmanをサポートする他の互換オペレーティングシステムを実行していること

    • KubectlPodman、およびHelmがインストールされていること

  • ブート用のUSBフラッシュ ドライブ(物理ハードウェアを使用する場合)

注記
注記

ターゲットマシンにある既存のデータはこのプロセスの一環として上書きされます。ターゲットデプロイメントノードに接続されているUSBストレージデバイスやディスク上のデータは、必ずバックアップしてください。

このガイドは、アップストリームクラスタをホストするためにDigital Oceanドロップレットを使用し、ダウンストリームデバイスとしてIntel NUCを使用して作成されています。インストールメディアの構築には、SUSE Linux Enterprise Serverを使用しています。

2.3 Elementalの使用方法

Elementalをインストールして使用するための基本的な手順は次のとおりです。

2.3.1 ブートストラップクラスタの構築

まず、RancherとElementalをホストできるクラスタを作成します。このクラスタは、ダウンストリームノードが接続されているネットワークからルーティングできる必要があります。

2.3.1.1 Kubernetesクラスタの作成

ハイパースケーラ(Azure、AWS、Google Cloudなど)を使用している場合、クラスタを設定する最も簡単な方法は、ハイパースケーラのビルトインツールを使用することです。このガイドでは、簡潔にするために、これらの各オプションのプロセスについては詳述しません。

ベアメタルや別のホスティングサービスにインストールしようとしていて、Kubernetesディストリビューションそのものも用意する必要がある場合は、RKE2を使用することをお勧めします。

2.3.1.2 DNSの設定

続行する前に、クラスタへのアクセスを設定する必要があります。クラスタ自体のセットアップと同様に、DNSの設定方法は、クラスタがホストされている場所によって異なります。

ヒント
ヒント

DNSレコードの設定を扱わない場合(たとえば、これが一時的なテストサーバである場合)、代わりにsslip.ioなどのサービスを使用できます。このサービスを使用すると、<address>.sslip.ioを使用して任意のIPアドレスを解決できます。

2.3.2 Rancherのインストール

Rancherをインストールするには、作成したクラスタのKubernetes APIにアクセスする必要があります。これは、使用しているKubernetesのディストリビューションによって異なります。

RKE2の場合、kubeconfigファイルは/etc/rancher/rke2/rke2.yamlに書き込まれます。このファイルをローカルシステムに~/.kube/configとして保存します。このファイルを編集して、外部にルーティング可能な正しいIPアドレスまたはホスト名を含めなければならない場合があります。

Rancherのドキュメントに記載されているコマンドを使用して、Rancherを簡単にインストールできます。

  1. cert-managerをインストールします。

    • Linux
    • Windows
    helm repo add rancher-prime https://charts.rancher.com/server-charts/prime
    
    kubectl create namespace cattle-system
    
    kubectl apply -f https://github.com/cert-manager/cert-manager/releases/download/v1.13.3/cert-manager.crds.yaml
    helm repo add jetstack https://charts.jetstack.io
    
    helm repo update
    
    helm install cert-manager jetstack/cert-manager \
     --namespace cert-manager \
     --create-namespace
  2. 次に、Rancher自体をインストールします。

    • Linux
    • Windows
    helm install rancher rancher-prime/rancher \
      --namespace cattle-system \
      --set hostname=<DNS or sslip from above> \
      --set replicas=1 \
      --set bootstrapPassword=<PASSWORD_FOR_RANCHER_ADMIN>
注記
注記

これを運用システムにする予定の場合は、cert-managerを使用して、実際の証明書(Let's Encryptの証明書など)を設定してください。

設定したホスト名をブラウズし、使用したbootstrapPasswordでRancherにログインします。ガイドに従って簡単なセットアッププロセスを完了します。

2.3.3 Elementalのインストール

Rancherをインストールしたら、続いてElementalのオペレータと必要なCRDをインストールできます。Elemental用のHelmチャートはOCIアーティファクトとして公開されているため、インストールは他のチャートよりも若干シンプルです。Rancherのインストールに使用したものと同じシェルからインストールすることも、ブラウザでRancherのシェル内からインストールすることもできます。

helm install --create-namespace -n cattle-elemental-system \
 elemental-operator-crds \
 oci://registry.suse.com/rancher/elemental-operator-crds-chart \
 --version 1.4.4

helm install --create-namespace -n cattle-elemental-system \
 elemental-operator \
 oci://registry.suse.com/rancher/elemental-operator-chart \
 --version 1.4.4

2.3.3.1 (オプション) Elemental UI拡張機能のインストール

  1. Elemental UIを使用するには、Rancherインスタンスにログインし、左上の3点リーダーメニューをクリックします。

    Elemental拡張機能のインストール1
  2. このページの[Available (使用可能)]タブから、Elementalカードの[Install (インストール)]をクリックします。

    Elemental拡張機能のインストール2
  3. 拡張機能をインストールすることを確認します。

    Elemental拡張機能のインストール3
  4. インストール後、ページを再ロードするよう求められます。

    Elemental拡張機能のインストール4
  5. 再ロードすると、[OS Management (OS管理)]グローバルアプリからElemental拡張機能にアクセスできるようになります。

    Elemental拡張機能へのアクセス

2.3.3.2 Elementalの設定

シンプルにするために、変数$ELEMを、設定ディレクトリを配置する場所のフルパスに設定することをお勧めします。

export ELEM=$HOME/elemental
mkdir -p $ELEM

マシンがElementalに登録できるようにするために、fleet-defaultネームスペースにMachineRegistrationオブジェクトを作成する必要があります。

このオブジェクトの基本的なバージョンを作成してみましょう。

cat << EOF > $ELEM/registration.yaml
apiVersion: elemental.cattle.io/v1beta1
kind: MachineRegistration
metadata:
  name: ele-quickstart-nodes
  namespace: fleet-default
spec:
  machineName: "\${System Information/Manufacturer}-\${System Information/UUID}"
  machineInventoryLabels:
    manufacturer: "\${System Information/Manufacturer}"
    productName: "\${System Information/Product Name}"
EOF

kubectl apply -f $ELEM/registration.yaml
注記
注記

このcatコマンドでは、各$をバックスラッシュ(\)でエスケープしています。このため、バッシュではテンプレート化されていません。手動でコピーする場合は、バックスラッシュを削除してください。

オブジェクトが作成されたら、割り当てられるエンドポイントを見つけてメモを取ります。

REGISURL=$(kubectl get machineregistration ele-quickstart-nodes -n fleet-default -o jsonpath='{.status.registrationURL}')

または、UIからこの操作を実行することもできます。

UI拡張機能
  1. [OS Management extension (OS管理拡張機能)]から[Create Registration Endpoint (登録エンドポイントの作成) ]をクリックします。

    [Create Registration (登録の作成)]をクリックします。
  2. この設定に名前を付けます。

    名前の追加
    注記
    注記

    [Cloud Configuration (クラウドの設定)]フィールドは無視して構いません。ここのデータは、Edge Image Builderを使用した次の手順で上書きされるためです。

  3. 次に、下にスクロールして、マシンの登録時に作成されるリソースに付ける各ラベルに対して[Add Label (ラベルの追加)]をクリックします。これはマシンを区別するのに役立ちます。

    ラベルの追加
  4. 最後に、[Create (作成)]をクリックして、設定を保存します。

    [Create (作成)]をクリック
UI拡張機能

設定を作成した直後の場合は、[Registration URL (登録URL)]が一覧にされます。[Copy (コピー)]をクリックしてアドレスをコピーできます。

URLのコピー
ヒント
ヒント

クリックしてその画面から移動してしまった場合は、左側のメニューの[Registration Endpoints (登録エンドポイント)]をクリックし、先ほど作成したエンドポイント名をクリックできます。

このURLは次の手順で使用します。

2.3.4 インストールメディアの構築

Elementalの現在のバージョンには独自のインストールメディアを構築する方法が用意されていますが、SUSE Edge 3.0では代わりにEdge Image Builderでインストールメディアを構築します。したがって、生成されるシステムは、SLE Microをベースオペレーティングシステムとして構築されます。

ヒント
ヒント

Edge Image Builderの詳細については、導入ガイド(第3章 「Edge Image Builderを使用したスタンドアロンクラスタ)のほかに、コンポーネントのドキュメント(第9章 「Edge Image Builder)も参照してください。

PodmanがインストールされたLinuxシステムから、次のコマンドを実行します。

mkdir -p $ELEM/eib_quickstart/base-images
mkdir -p $ELEM/eib_quickstart/elemental
curl $REGISURL -o $ELEM/eib_quickstart/elemental/elemental_config.yaml
cat << EOF > $ELEM/eib_quickstart/eib-config.yaml
apiVersion: 1.0
image:
    imageType: iso
    arch: x86_64
    baseImage: SLE-Micro.x86_64-5.5.0-Default-SelfInstall-GM.install.iso
    outputImageName: elemental-image.iso
operatingSystem:
  users:
    - username: root
      encryptedPassword: \$6\$jHugJNNd3HElGsUZ\$eodjVe4te5ps44SVcWshdfWizrP.xAyd71CVEXazBJ/.v799/WRCBXxfYmunlBO2yp1hm/zb4r8EmnrrNCF.P/
EOF
注記
注記
  • エンコードされていないパスワードはeibです。

  • このcatコマンドでは、各$をバックスラッシュ(\)でエスケープしています。このため、バッシュではテンプレート化されていません。手動でコピーする場合は、バックスラッシュを削除してください。

podman run --privileged --rm -it -v $ELEM/eib_quickstart/:/eib \
 registry.suse.com/edge/edge-image-builder:1.0.2 \
 build --definition-file eib-config.yaml

物理デバイスをブートする場合は、イメージをUSBフラッシュ ドライブに書き込む必要があります。これは、次のコマンドで実行できます。

sudo dd if=/eib_quickstart/elemental-image.iso of=/dev/<PATH_TO_DISK_DEVICE> status=progress

2.3.5 ダウンストリームノードのブート

インストールメディアを作成したので、それを使用してダウンストリームノードをブートできます。

Elementalで制御するシステムごとに、インストールメディアを追加してデバイスをブートします。インストールが完了すると、デバイスは再起動して自身を登録します。

UI拡張機能を使用している場合は、[Inventory of Machines (マシンのインベントリ)]にノードが表示されます。

注記
注記

ログインプロンプトが表示されるまでインストールメディアを取り外さないでください。初回ブート時には、USBスティック上のファイルにアクセスしたままになります。

2.3.6 ダウンストリームクラスタの作成

Elementalを使用して新しいクラスタをプロビジョニングする際に作成する必要があるオブジェクトが2つあります。

  • Linux
  • UI拡張機能

最初のオブジェクトはMachineInventorySelectorTemplateです。このオブジェクトにより、クラスタとインベントリ内のマシン間のマッピングを指定できます。

  1. インベントリ内のマシンをラベルに一致させるセレクタを作成します。

    cat << EOF > $ELEM/selector.yaml
    apiVersion: elemental.cattle.io/v1beta1
    kind: MachineInventorySelectorTemplate
    metadata:
      name: location-123-selector
      namespace: fleet-default
    spec:
      template:
        spec:
          selector:
            matchLabels:
              locationID: '123'
    EOF
  2. リソースをクラスタに適用します。

    kubectl apply -f $ELEM/selector.yaml
  3. マシンの名前を取得し、一致するラベルを追加します。

    MACHINENAME=$(kubectl get MachineInventory -n fleet-default | awk 'NR>1 {print $1}')
    
    kubectl label MachineInventory -n fleet-default \
     $MACHINENAME locationID=123
  4. シンプルなシングルノードK3sクラスタリソースを作成し、クラスタに適用します。

    cat << EOF > $ELEM/cluster.yaml
    apiVersion: provisioning.cattle.io/v1
    kind: Cluster
    metadata:
      name: location-123
      namespace: fleet-default
    spec:
      kubernetesVersion: v1.28.9+k3s1
      rkeConfig:
        machinePools:
          - name: pool1
            quantity: 1
            etcdRole: true
            controlPlaneRole: true
            workerRole: true
            machineConfigRef:
              kind: MachineInventorySelectorTemplate
              name: location-123-selector
              apiVersion: elemental.cattle.io/v1beta1
    EOF
    
    kubectl apply -f $ELEM/cluster.yaml

これらのオブジェクトを作成したら、先ほどインストールした新しいノードを使用して新しいKubernetesクラスタがスピンアップするはずです。

ヒント
ヒント

システムを簡単にグループ化できるようにするには、環境内でその場所に固有であることがわかっている項目を検索する起動スクリプトを追加できます。

たとえば、各場所に固有のサブネットがあることがわかっている場合は、そのネットワークプレフィックスを検索して、対応するMachineInventoryにラベルを追加するスクリプトを記述できます。

これは通常、ご使用のシステムの設計に合わせたカスタムスクリプトになりますが、次のようになります。

INET=`ip addr show dev eth0 | grep "inet\ "`
elemental-register --label "network=$INET" \
 --label "network=$INET" /oem/registration

2.4 ノードのリセット

SUSE Rancher Elementalは、「ノードリセット」を実行する機能をサポートしています。ノードリセットは、Rancherからクラスタ全体が削除されたとき、クラスタからシングルノードが削除されたとき、またはマシンインベントリからノードが手動で削除されたときに任意でトリガできます。これは、孤立したリソースをリセットしてクリーンアップし、クリーンアップされたノードを自動的にマシンインベントリに戻して再利用可能にする場合に役立ちます。ノードリセットはデフォルトでは有効になっていないため、削除されたシステムはクリーンアップされず(つまり、データは削除されず、Kubernetesクラスタリソースはダウンストリームクラスタで動作し続けます)、データを消去してマシンをElemental経由でRancherに再登録するには手動操作が必要となります。

この機能をデフォルトで有効にするには、MachineRegistrationconfig.elemental.reset.enabled: trueを追加して明示的に有効にする必要があります。例:

config:
  elemental:
    registration:
      auth: tpm
    reset:
      enabled: true

その後、このMachineRegistrationに登録されているすべてのシステムが自動的にelemental.cattle.io/resettable:'true'のアノテーションを受け取って設定に反映します。既存のMachineInventoryにこのアノテーションがない場合や、すでにノードをデプロイ済みである場合などに、個々のノードで手動でこの操作を実行する場合は、MachineInventoryを変更し、resettable設定を追加します。例:

apiVersion: elemental.cattle.io/v1beta1
kind: MachineInventory
metadata:
  annotations:
    elemental.cattle.io/os.unmanaged: 'true'
    elemental.cattle.io/resettable: 'true'

SUSE Edge 3.0では、Elemental Operatorによってオペレーティングシステム上にマーカが配置され、これによってクリーンアッププロセスが自動的にトリガされます。クリーンアッププロセスは、すべてのKubernetesサービスを停止して永続データをすべて削除し、すべてのKubernetesサービスをアンインストールして、残っているKubernetes/Rancherディレクトリをクリーンアップし、元のElemental MachineRegistration設定を使用して強制的にRancherに再登録します。これは自動的に行われるため、手動での操作は必要ありません。呼び出されるスクリプトは/opt/edge/elemental_node_cleanup.shにあり、マーカが配置されるとすぐにsystemd.pathを介してトリガされるため、直ちに実行されます。

警告
警告

resettable機能を使用する場合、Rancherからノード/クラスタを削除する際の望ましい動作は、データを消去して再登録を強制することであると想定されています。この状況ではデータが確実に失われるため、この機能は、自動リセットを実行することがわかっている場合にのみ使用してください。

2.5 次の手順

このガイドの使用後に調べるべき推奨リソースを次に示します。

3 Edge Image Builderを使用したスタンドアロンクラスタ

Edge Image Builder (EIB)は、完全なエアギャップシナリオでもマシンをブートストラップできるCustomized, Ready-to-Boot (CRB)ディスクイメージの生成プロセスを効率化するツールです。EIBを使用すると、SUSE Edgeの3つのデプロイメントフットプリントすべてで使用するデプロイメントイメージを作成できます。これは、EIBが十分に柔軟であり、最小限のカスタマイズ(例: ユーザの追加やタイムゾーンの設定)から、あらゆる設定を網羅したイメージ(例: 複雑なネットワーク設定を行い、マルチノードKubernetesクラスタをデプロイして、顧客ワークロードをデプロイし、Rancher/ElementalとSUSE Managerを介して集中管理プラットフォームに登録するイメージ)までを提供できるためです。EIBはコンテナイメージ内で動作するため、プラットフォーム間できわめて容易に移植可能です、さらに、必要な依存関係をすべて備えた自己完結型であるため、EIBツールの操作に使用するシステムにインストール済みのパッケージに及ぼす影響が最小限に抑えられます。

詳細については、Edge Image Builderの紹介(第9章 「Edge Image Builder)を参照してください。

3.1 前提条件

  • SLES 15 SP5、openSUSE Leap 15.5、またはopenSUSE Tumbleweedを実行しているx86_64物理ホスト(または仮想マシン)

  • 利用可能なコンテナランタイム(Podmanなど)

  • 最新のSLE Micro 5.5 SelfInstall「GM2」ISOイメージのダウンロードコピー(こちらにあります)

注記
注記

互換性のあるコンテナランタイムが利用可能であれば、他のオペレーティングシステムでも機能する可能性はありますが、他のプラットフォームでは広範なテストは行われていません。このドキュメントではPodmanに焦点を当てていますが、Dockerでも同じ機能を実現できるはずです。

3.1.1 EIBイメージの取得

EIBのコンテナイメージは一般に公開されており、イメージ構築ホストで次のコマンドを実行することでSUSE Edgeレジストリからダウンロードできます。

podman pull registry.suse.com/edge/edge-image-builder:1.0.2

3.2 イメージ設定ディレクトリの作成

EIBはコンテナ内で動作するため、ホストから設定ディレク トリをマウントして、必要な設定を指定できるようにする必要があります。ビルドプロセス中に、EIBは必要な入力ファイルやサポートアーティファクトすべてにアクセスできます。このディレクトリは、特定の構造に従う必要があります。このディレクトリがホームディレクトリに存在し、「eib」という名前であると仮定して、ディレクトリを作成してみましょう。

export CONFIG_DIR=$HOME/eib
mkdir -p $CONFIG_DIR/base-images

前の手順では、SLE Micro 5.5の入力イメージをホストする「base-images」ディレクトリを作成しました。ダウンロードしたイメージをこの設定ディレクトリに確実にコピーしましょう。

cp /path/to/downloads/SLE-Micro.x86_64-5.5.0-Default-SelfInstall-GM2.install.iso $CONFIG_DIR/base-images/slemicro.iso
注記
注記

EIBの実行中に元のゴールデンイメージは変更「されません」。EIBの設定ディレクトリのルートに、目的の設定でカスタマイズされた新しいバージョンが作成されます。

この時点では、設定ディレクトリは次のようになっているはずです。

└── base-images/
    └── slemicro.iso

3.3 イメージ定義ファイルの作成

定義ファイルには、Edge Image Builderがサポートする設定可能なオプションの大部分が記述されています。オプションの完全な例については、こちらを参照してください。以下で説明する例よりも広範な例については、アップストリームのイメージ構築ガイドを参照することをお勧めします。まずは、OSイメージの非常に基本的な定義ファイルから始めましょう。

cat << EOF > $CONFIG_DIR/iso-definition.yaml
apiVersion: 1.0
image:
  imageType: iso
  arch: x86_64
  baseImage: slemicro.iso
  outputImageName: eib-image.iso
EOF

この定義では、x86_64ベースのシステム用の出力イメージを生成するように指定しています。さらに変更を加えるためのベースとして使用するイメージは、slemicro.isoという名前のisoイメージであり、$CONFIG_DIR/base-images/slemicro.isoにあることが想定されています。また、EIBがイメージの変更を完了すると、出力イメージはeib-image.isoという名前になり、デフォルトでは$CONFIG_DIRに存在することも記述されています。

これで、ディレクトリ構造は次のようになります。

├── iso-definition.yaml
└── base-images/
    └── slemicro.iso

以降のセクションでは、一般的な操作の例をいくつか紹介していきます。

3.3.1 OSユーザの設定

EIBを使用すると、パスワードやSSHキーなどのログイン情報を事前にユーザに設定できます(固定されたルートパスワードの設定も含む)。この例の一部として、ルートパスワードを修正します。最初の手順は、OpenSSLを使用して一方向暗号化パスワードを作成することです。

openssl passwd -6 SecurePassword

これは次のような出力になります。

$6$G392FCbxVgnLaFw1$Ujt00mdpJ3tDHxEg1snBU3GjujQf6f8kvopu7jiCBIhRbRvMmKUqwcmXAKggaSSKeUUOEtCP3ZUoZQY7zTXnC1

次に、定義ファイルにoperatingSystemというセクションを追加し、その中にusers配列を含めます。作成したファイルは次のようになります。

apiVersion: 1.0
image:
  imageType: iso
  arch: x86_64
  baseImage: slemicro.iso
  outputImageName: eib-image.iso
operatingSystem:
  users:
    - username: root
      encryptedPassword: $6$G392FCbxVgnLaFw1$Ujt00mdpJ3tDHxEg1snBU3GjujQf6f8kvopu7jiCBIhRbRvMmKUqwcmXAKggaSSKeUUOEtCP3ZUoZQY7zTXnC1
注記
注記

ユーザの追加、ホームディレクトリの作成、ユーザIDの設定、ssh-key認証の追加、グループ情報の変更も行うことができます。他の例については、アップストリームのイメージ構築ガイドを参照してください。

3.3.2 RPMパッケージの設定

EIBの主な特徴の1つは、イメージにソフトウェアパッケージを追加するメカニズムを備えていることです。このため、インストールが完了した時点で、システムはインストールされたパッケージをすぐに利用できます。EIBでは、ユーザは以下を行うことができます。

  • イメージ定義のリスト内の名前でパッケージを指定する

  • これらのパッケージを検索するネットワークリポジトリを指定する

  • 一覧にされたパッケージをSUSEの公式リポジトリで検索するためのSUSE Customer Center (SCC)資格情報を指定する

  • $CONFIG_DIR/rpmsディレクトリ経由で、ネットワークリポジトリに存在しないカスタムRPMをサイドロードする

  • 同じディレクトリ($CONFIG_DIR/rpms/gpg-keys)経由で、サードパーティ製パッケージの検証を有効にするためにGPGキーを指定する

これにより、EIBは、イメージの構築時にパッケージ解決プロセスを実行し、ゴールデンイメージを入力として受け取り、提供されているパッケージ(リストで指定されているか、ローカルで提供されているパッケージ)をすべてプルしてインストールしようと試みます。EIBは、依存関係を含むすべてのパッケージを出力イメージ内に存在するリポジトリにダウンロードし、そのパッケージを初回ブートプロセス中にインストールするようにシステムに指示します。イメージの構築中にこのプロセスを実行することで、初回ブート時にパッケージが目的のプラットフォーム(エッジのノードなど)が正常にインストールされることが保証されます。これは、操作時に追加パッケージをネットワーク経由でプルするのではなく、イメージに事前に書き込んでおきたい環境でも便利です。たとえば、エアギャップ環境や、ネットワークが制限された環境です。

これを示すシンプルな例として、サードパーティベンダがサポートするNVIDIAリポジトリにあるnvidia-container-toolkit RPMパッケージをインストールします。

  packages:
    packageList:
      - nvidia-container-toolkit
    additionalRepos:
      - url: https://nvidia.github.io/libnvidia-container/stable/rpm/x86_64

生成される定義ファイルは次のようになります。

apiVersion: 1.0
image:
  imageType: iso
  arch: x86_64
  baseImage: slemicro.iso
  outputImageName: eib-image.iso
operatingSystem:
  users:
    - username: root
      encryptedPassword: $6$G392FCbxVgnLaFw1$Ujt00mdpJ3tDHxEg1snBU3GjujQf6f8kvopu7jiCBIhRbRvMmKUqwcmXAKggaSSKeUUOEtCP3ZUoZQY7zTXnC1
  packages:
    packageList:
      - nvidia-container-toolkit
    additionalRepos:
      - url: https://nvidia.github.io/libnvidia-container/stable/rpm/x86_64

上記はシンプルな例ですが、完全を期するために、イメージ生成を実行する前にNVIDIAパッケージ署名キーをダウンロードしてください。

$ mkdir -p $CONFIG_DIR/rpms/gpg-keys
$ curl -fsSL https://nvidia.github.io/libnvidia-container/gpgkey > rpms/gpg-keys/nvidia.gpg
警告
警告

この方法でRPMを追加することは、サポートされているサードパーティコンポーネント、またはユーザが提供(および保守)するパッケージを追加することを目的としています。このメカニズムは、通常ではSLE Microでサポートされないパッケージを追加する目的では使用しないでください。このメカニズムを使用して、openSUSEのリポジトリから新しいリリースやサービスパックなどのコンポーネントを追加した場合(この操作はサポートされません)、最終的にサポート対象外の設定になるおそれがあります。特に、依存関係の解決によってオペレーティングシステムのコア部分が置き換えられる場合は、作成されたシステムが期待どおりに機能しているように見えても注意が必要です。確信が持てない場合は、SUSEの担当者に連絡してサポートを依頼し、目的の設定がサポート可能かどうかを判断してください。

注記
注記

追加の例を含む総合的なガイドについては、アップストリームのパッケージインストールガイドを参照してください。

3.3.3 Kubernetesクラスタとユーザワークロードの設定

EIBのもう1つの特徴は、EIBを使用すると、「インプレースでブートストラップ」する、つまり調整のためにどのような形態の集中管理インフラストラクチャも必要としない、シングルノードとマルチノード両方の高可用性Kubernetesクラスタのデプロイメントを自動化できることです。このアプローチは主にエアギャップデプロイメント、すなわちネットワークが制限された環境のためのものですが、ネットワークに制限なく完全にアクセスできる場合であっても、スタンドアロンクラスタを迅速にブートストラップする方法として役立ちます。

この方法を使用すると、カスタマイズされたオペレーティングシステムをデプロイできるだけでなく、Kubernetesの設定を指定したり、Helmチャートを介して追加の階層化コンポーネントを指定したり、指定したKubernetesマニフェストを介してユーザワークロードを指定したりすることもできます。ただしこの方法を使用する場合、その背景にある設計理念として、ユーザがエアギャップ化を望んでいるとデフォルトで想定します。したがって、イメージ定義で指定されているすべての項目を、ユーザが指定したワークロードを含めてイメージにプルします。その際に、EIBは、提供された定義で要求されている検出済みイメージをすべてローカルにコピーし、作成されたデプロイ済みシステムの組み込みのイメージレジストリで提供します。

次の例では、既存のイメージ定義を使用してKubernetesの設定を指定します(この例では、複数のシステムとその役割が一覧にされていないため、デフォルトでシングルノードを想定します)。この設定により、シングルノードのRKE2 KubernetesクラスタをプロビジョニングするようにEIBに指示します。ユーザが指定したワークロード(マニフェストを使用)と階層化コンポーネント(Helmを使用)の両方のデプロイメントの自動化を説明するために、SUSE EdgeのHelmチャートを使用してKubeVirtをインストールし、Kubernetesマニフェストを使用してNGINXをインストールします。既存のイメージ定義に追加する必要がある設定は次のとおりです。

kubernetes:
  version: v1.28.9+rke2r1
  manifests:
    urls:
      - https://k8s.io/examples/application/nginx-app.yaml
  helm:
    charts:
      - name: kubevirt-chart
        version: 0.2.4
        repositoryName: suse-edge
    repositories:
      - name: suse-edge
        url: oci://registry.suse.com/edge

作成された完全な定義ファイルは次のようになります。

apiVersion: 1.0
image:
  imageType: iso
  arch: x86_64
  baseImage: slemicro.iso
  outputImageName: eib-image.iso
operatingSystem:
  users:
    - username: root
      encryptedPassword: $6$G392FCbxVgnLaFw1$Ujt00mdpJ3tDHxEg1snBU3GjujQf6f8kvopu7jiCBIhRbRvMmKUqwcmXAKggaSSKeUUOEtCP3ZUoZQY7zTXnC1
  packages:
    packageList:
      - nvidia-container-toolkit
    additionalRepos:
      - url: https://nvidia.github.io/libnvidia-container/stable/rpm/x86_64
kubernetes:
  version: v1.28.9+rke2r1
  manifests:
    urls:
      - https://k8s.io/examples/application/nginx-app.yaml
  helm:
    charts:
      - name: kubevirt-chart
        version: 0.2.4
        repositoryName: suse-edge
    repositories:
      - name: suse-edge
        url: oci://registry.suse.com/edge
注記
注記

マルチノードデプロイメント、カスタムネットワーキング、Helmチャートのオプション/値など、オプションの他の例については、アップストリームドキュメントを参照してください。

3.3.4 ネットワークの設定

このクイックスタートの最後の例では、EIBで生成したイメージを使ってシステムをプロビジョニングした場合に作成されるネットワークを設定しましょう。ネットワーク設定を指定しない限り、ブート時に検出されたすべてのインタフェースでDHCPが使用されるのがデフォルトのモデルであることを理解することが重要です。ただし、これが常に望ましい設定であるとは限りません。これは特に、DHCPが利用できず静的な設定を指定する必要がある場合や、より複雑なネットワーキング構造(ボンド、LACP、VLANなど)を設定する必要がある場合、特定のパラメータ(ホスト名、DNSサーバ、ルートなど)を上書きする必要がある場合に該当します。

EIBでは、ノードごとの設定を指定することも(対象のシステムをMACアドレスで一意に識別します)、上書きによって各マシンに同一の設定を指定することもできます(システムのMACアドレスが不明な場合に便利です)。またEIDでは、Network Manager Configurator (nmc)というツールも追加で使用されます。Network Manager ConfiguratorはSUSE Edgeチームによって構築されたツールであり、nmstate.ioの宣言型ネットワークスキーマに基づいてカスタムネットワーキング設定を適用できるようにします。また、ブートしているノードをブート時に識別し、必要なネットワーク設定をサービス開始前に適用します。

ここでは、1つのインタフェースを持つシステムに静的ネットワーク設定を適用します。そのために、ネットワークの望ましい状態を、必要なnetworkディレクトリ内にある(目的のホスト名に基づく)ノード固有のファイルに記述します。

mkdir $CONFIG_DIR/network

cat << EOF > $CONFIG_DIR/network/host1.local.yaml
routes:
  config:
  - destination: 0.0.0.0/0
    metric: 100
    next-hop-address: 192.168.122.1
    next-hop-interface: eth0
    table-id: 254
  - destination: 192.168.122.0/24
    metric: 100
    next-hop-address:
    next-hop-interface: eth0
    table-id: 254
dns-resolver:
  config:
    server:
    - 192.168.122.1
    - 8.8.8.8
interfaces:
- name: eth0
  type: ethernet
  state: up
  mac-address: 34:8A:B1:4B:16:E7
  ipv4:
    address:
    - ip: 192.168.122.50
      prefix-length: 24
    dhcp: false
    enabled: true
  ipv6:
    enabled: false
EOF
警告
警告

上記の例は、テストを仮想マシン上で実行すると仮定して、デフォルトの192.168.122.0/242サブネット用に設定されています。ご使用の環境に合わせて、MACアドレスも忘れずに変更してください。同じイメージを使用して複数のノードをプロビジョニングできるため、 EIBで(nmcを介して)設定されたネットワーキングは、各ノードをMACアドレスで一意に識別できるかどうかに依存しており、その後、ブート中にnmcは正しいネットワーキング設定を各マシンに適用します。つまり、インストール先のシステムのMACアドレスを把握する必要があります。また、デフォルトの動作ではDHCPに依存しますが、configure-network.shフックを利用して、すべてのノードに共通の設定を適用することもできます。詳細については、ネットワーキングのガイド (第10章 「Edgeネットワーキング)を参照してください。

作成されるファイル構造は、次のようになります。

├── iso-definition.yaml
├── base-images/
│   └── slemicro.iso
└── network/
    └── host1.local.yaml

作成したネットワーク設定が解析され、必要なNetworkManager接続ファイルが自動的に生成されて、EIBが作成する新しいインストールイメージに挿入されます。これらのファイルはホストのプロビジョニング中に適用され、完全なネットワーク設定が生成されます。

注記
注記

上記の設定のより包括的な説明と、この機能の例については、エッジネットワーキングのコンポーネント(第10章 「Edgeネットワーキング)を参照してください。

3.4 イメージの構築

EIBで使用するゴールデンイメージとイメージ定義ができたので、イメージを構築してみましょう。これには、podmanを使用し、定義ファイルを指定して「build」コマンドでEIBコンテナを呼び出すだけです。

podman run --rm -it --privileged -v $CONFIG_DIR:/eib \
registry.suse.com/edge/edge-image-builder:1.0.2 \
build --definition-file iso-definition.yaml

コマンドの出力は次のようになります。

Setting up Podman API listener...
Generating image customization components...
Identifier ................... [SUCCESS]
Custom Files ................. [SKIPPED]
Time ......................... [SKIPPED]
Network ...................... [SUCCESS]
Groups ....................... [SKIPPED]
Users ........................ [SUCCESS]
Proxy ........................ [SKIPPED]
Resolving package dependencies...
Rpm .......................... [SUCCESS]
Systemd ...................... [SKIPPED]
Elemental .................... [SKIPPED]
Suma ......................... [SKIPPED]
Downloading file: dl-manifest-1.yaml 100%  (498/498 B, 5.9 MB/s)
Populating Embedded Artifact Registry... 100%  (3/3, 11 it/min)
Embedded Artifact Registry ... [SUCCESS]
Keymap ....................... [SUCCESS]
Configuring Kubernetes component...
The Kubernetes CNI is not explicitly set, defaulting to 'cilium'.
Downloading file: rke2_installer.sh
Downloading file: rke2-images-core.linux-amd64.tar.zst 100% (782/782 MB, 98 MB/s)
Downloading file: rke2-images-cilium.linux-amd64.tar.zst 100% (367/367 MB, 100 MB/s)
Downloading file: rke2.linux-amd64.tar.gz 100%  (34/34 MB, 101 MB/s)
Downloading file: sha256sum-amd64.txt 100%  (3.9/3.9 kB, 1.5 MB/s)
Downloading file: dl-manifest-1.yaml 100%  (498/498 B, 7.2 MB/s)
Kubernetes ................... [SUCCESS]
Certificates ................. [SKIPPED]
Building ISO image...
Kernel Params ................ [SKIPPED]
Image build complete!

構築されたISOイメージは$CONFIG_DIR/eib-image.isoに保存されます。

├── iso-definition.yaml
├── eib-image.iso
├── _build
│   └── cache/
│       └── ...
│   └── build-<timestamp>/
│       └── ...
├── base-images/
│   └── slemicro.iso
└── network/
    └── host1.local.yaml

ビルドごとに、$CONFIG_DIR/_build/内にタイムスタンプ付きのフォルダが作成されます。このフォルダには、ビルドのログ、ビルド中に使用されたアーティファクト、およびCRBイメージに追加されたすべてのスクリプトとアーティファクトを含むcombustionディレクトリとartefactsディレクトリが含まれます。

このディレクトリの内容は次のようになります。

├── build-<timestamp>/
│   │── combustion/
│   │   ├── 05-configure-network.sh
│   │   ├── 10-rpm-install.sh
│   │   ├── 12-keymap-setup.sh
│   │   ├── 13b-add-users.sh
│   │   ├── 20-k8s-install.sh
│   │   ├── 26-embedded-registry.sh
│   │   ├── 48-message.sh
│   │   ├── network/
│   │   │   ├── host1.local/
│   │   │   │   └── eth0.nmconnection
│   │   │   └── host_config.yaml
│   │   ├── nmc
│   │   └── script
│   │── artefacts/
│   │   │── registry/
│   │   │   ├── hauler
│   │   │   ├── nginx:1.14.2-registry.tar.zst
│   │   │   ├── rancher_kubectl:v1.28.7-registry.tar.zst
│   │   │   └── registry.suse.com_suse_sles_15.5_virt-operator:1.1.1-150500.8.12.1-registry.tar.zst
│   │   │── rpms/
│   │   │   └── rpm-repo
│   │   │       ├── addrepo0
│   │   │       │   └── x86_64
│   │   │       │       ├── nvidia-container-toolkit-1.15.0-1.x86_64.rpm
│   │   │       │       ├── ...
│   │   │       ├── repodata
│   │   │       │   ├── ...
│   │   │       └── zypper-success
│   │   └── kubernetes/
│   │       ├── rke2_installer.sh
│   │       ├── registries.yaml
│   │       ├── server.yaml
│   │       ├── images/
│   │       │   ├── rke2-images-cilium.linux-amd64.tar.zst
│   │       │   └── rke2-images-core.linux-amd64.tar.zst
│   │       ├── install/
│   │       │   ├── rke2.linux-amd64.tar.gz
│   │       │   └── sha256sum-amd64.txt
│   │       └── manifests/
│   │           ├── dl-manifest-1.yaml
│   │           └── kubevirt-chart.yaml
│   ├── createrepo.log
│   ├── eib-build.log
│   ├── embedded-registry.log
│   ├── helm
│   │   └── kubevirt-chart
│   │       └── kubevirt-0.2.4.tgz
│   ├── helm-pull.log
│   ├── helm-template.log
│   ├── iso-build.log
│   ├── iso-build.sh
│   ├── iso-extract
│   │   └── ...
│   ├── iso-extract.log
│   ├── iso-extract.sh
│   ├── modify-raw-image.sh
│   ├── network-config.log
│   ├── podman-image-build.log
│   ├── podman-system-service.log
│   ├── prepare-resolver-base-tarball-image.log
│   ├── prepare-resolver-base-tarball-image.sh
│   ├── raw-build.log
│   ├── raw-extract
│   │   └── ...
│   └── resolver-image-build
│       └──...
└── cache
    └── ...

ビルドが失敗した場合、情報が含まれる最初のログはeib-build.logです。そこから、失敗したコンポーネントに移動してデバッグを行います。

この時点で、以下を行う、すぐに使用できるイメージができているはずです。

  1. SLE Micro 5.5をデプロイする

  2. ルートパスワードを設定する

  3. nvidia-container-toolkitパッケージをインストールする

  4. コンテンツをローカルに提供する組み込みのコンテナレジストリを設定する

  5. シングルノードRKE2をインストールする

  6. 静的ネットワーキングを設定する

  7. KubeVirtをインストールする

  8. ユーザが指定したマニフェストをデプロイする

3.5 イメージ構築プロセスのデバッグ

イメージ構築プロセスが失敗する場合は、アップストリームのデバッグガイドを参照してください。

3.6 新しく構築されたイメージのテスト

新しく構築されたCRBイメージをテストする方法については、アップストリームのイメージテストガイドを参照してください。

パート II 使用するコンポーネント

Edgeのコンポーネントのリスト

  • 4 Rancher
  • https://ranchermanager.docs.rancher.comにあるRancherのアップストリームドキュメントを参照してください。

  • 5 Rancher Dashboard拡張機能
  • 拡張機能により、ユーザ、開発者、パートナー、および顧客はRancher UIを拡張および強化できます。SUSE Edge 3.0では、KubeVirtとAkriのダッシュボード拡張機能を提供しています。

  • 6 Fleet
  • Fleetは、ユーザがローカルクラスタをより細かく制御できるようにするとともに、GitOpsを通じて常時監視を行えるようにすることを目的に設計されたコンテナ管理およびデプロイメントエンジンです。Fleetはスケール能力に重点を置いているだけでなく、クラスタに何がインストールされているかを正確に監視するための高度な制御と可視性もユーザに提供します。

  • 7 SLE Micro
  • SLE Microの公式ドキュメントを参照してください

  • 8 Metal3
  • Metal3は、Kubernetesにベアメタルインフラストラクチャ管理機能を提供するCNCFプロジェクトです。

  • 9 Edge Image Builder
  • 公式リポジトリを参照してください。

  • 10 Edgeネットワーキング
  • このセクションでは、SUSE Edgeソリューションにおけるネットワーク設定へのアプローチについて説明します。宣言的な方法でSLE Micro上でNetworkManagerを設定する方法を示し、関連ツールの統合方法について説明します。

  • 11 Elemental
  • Elementalは、Kubernetesを使用した完全にクラウドネイティブな集中型のOS管理を可能にするソフトウェアスタックです。Elementalスタックは、Rancher自体またはエッジノード上に存在する多数のコンポーネントで構成されます。中核となるコンポーネントは次のとおりです。

  • 12 Akri
  • Akriは、リーフデバイスを検出してKubernetesネイティブリソースとして提供することを目的としたCNCF-Sandboxプロジェクトです。また、検出された各デバイスに対してPodやジョブをスケジュールすることもできます。デバイスはノードローカルでもネットワーク接続されていてもよく、さまざまなプロトコルを使用できます。

  • 13 K3s
  • K3sは、リソースに制約のあるリモートの無人の場所やIoTアプライアンス内の運用ワークロード向けに設計された、高可用性のKubernetes認定ディストリビューションです。

  • 14 RKE2
  • RKE2の公式ドキュメントを参照してください。

  • 15 Longhorn
  • Longhornは、Kubernetes向けに設計された、信頼性が高くユーザフレンドリな軽量の分散ブロックストレージシステムです。オープンソースプロジェクトとして、当初はRancher Labsによって開発されていましたが、現在はCNCFの下でインキュベートされています。

  • 16 NeuVector
  • NeuVectorはKubernetes向けのセキュリティソリューションであり、L7ネットワークセキュリティ、ランタイムセキュリティ、サプライチェーンセキュリティ、およびコンプライアンスチェックを1つの統合パッケージで提供します。

  • 17 MetalLB
  • MetalLBの公式ドキュメントを参照してください。

  • 18 Edge Virtualization
  • このセクションでは、Edge Virtualizationを使用してエッジノードで仮想マシンを実行する方法について説明します。Edge Virtualizationは包括的なソリューションではなく、機能も限られていることを指摘しておくことが重要です。Edge Virtualizationは、基本的な仮想マシン機能が要求される軽量な仮想化の要件を解決しようとするものです。より包括的な仮想化(およびハイパーコンバージドインフラストラクチャ)ソリューションは、Harvesterで提供されています。

4 Rancher

https://ranchermanager.docs.rancher.comにあるRancherのアップストリームドキュメントを参照してください。

Rancherは、オープンソースの強力なKubernetes管理プラットフォームであり、複数の環境にまたがるKubernetesクラスタのデプロイメント、運用、および監視を効率化します。オンプレミス、クラウド、エッジのいずれのクラスタを管理する場合でも、Rancherは、Kubernetesに関するあらゆるニーズに対応する、統合された中央プラットフォームを提供します。

4.1 Rancherの主な機能

  • マルチクラスタ管理: Rancherの直感的なインタフェースを使用して、パブリッククラウド、プライベートデータセンター、エッジロケーションのどこからでもKubernetesクラスタを管理できます。

  • セキュリティとコンプライアンス: Rancherでは、Kubernetes環境全体にセキュリティポリシー、ロールベースのアクセス制御(RBAC)、およびコンプライアンス標準が適用されます。

  • クラスタ操作のシンプル化: Rancherはクラスタのプロビジョニング、アップグレード、トラブルシューティングを自動化し、あらゆる規模のチームでKubernetesの操作をシンプル化します。

  • 中央型のアプリケーションカタログ: Rancherアプリケーションカタログは、多種多様なHelmチャートとKubernetes Operatorを提供し、コンテナ化アプリケーションのデプロイと管理を容易にします。

  • 継続的デリバリ: RancherはGitOpsと継続的インテグレーション/継続的デリバリパイプラインをサポートしており、自動化および効率化されたアプリケーションデリバリプロセスを実現します。

4.2 SUSE EdgeでのRancherの使用

Rancherは、SUSE Edgeスタックに複数のコア機能を提供します。

4.2.1 Kubernetesの集中管理

大量の分散クラスタが存在する一般的なエッジデプロイメントでは、Rancherは、これらのKubernetesクラスタを管理するための中央コントロールプレーンとして機能します。プロビジョニング、アップグレード、監視、およびトラブルシューティングのための統合インタフェースを提供し、操作をシンプル化し、一貫性を確保します。

4.2.2 クラスタデプロイメントのシンプル化

Rancherは、軽量なSLE Micro (SUSE Linux Enterprise Micro)オペレーティングシステム上でのKubernetesクラスタの作成を効率化し、Kubernetesの堅牢な機能を備えたエッジインフラストラクチャの展開を容易にします。

4.2.3 アプリケーションのデプロイメントと管理

統合されたRancherアプリケーションカタログは、SUSE Edgeクラスタ全体でのコンテナ化アプリケーションのデプロイと管理をシンプル化し、エッジワークロードのシームレスなデプロイメントを可能にします。

4.2.4 セキュリティとポリシーの適用

Rancherは、ポリシーベースのガバナンスツール、ロールベースのアクセス制御(RBAC)を備えているほか、外部の認証プロバイダと統合できます。これにより、SUSE Edgeのデプロイメントは、分散環境において重要なセキュリティとコンプライアンスを維持できます。

4.3 ベストプラクティス

4.3.1 GitOps

RancherにはビルトインコンポーネントとしてFleetが含まれており、Gitに保存されたコードでクラスタ設定やアプリケーションのデプロイメントを管理できます。

4.3.2 可観測性

Rancherには、PrometheusやGrafanaなどのビルトインのモニタリングおよびログツールが含まれており、クラスタのヘルスとパフォーマンスについて包括的な洞察を得ることができます。

4.4 Edge Image Builderを使用したインストール

SUSE Edgeは、SLE Micro OSのベースイメージをカスタマイズするために第9章 「Edge Image Builderを使用しています。EIBでプロビジョニングしたKubernetesクラスタ上にRancherをエアギャップインストールするには、21.6項 「Rancherのインストール」に従ってください。

4.5 追加リソース

5 Rancher Dashboard拡張機能

拡張機能により、ユーザ、開発者、パートナー、および顧客はRancher UIを拡張および強化できます。SUSE Edge 3.0では、KubeVirtとAkriのダッシュボード拡張機能を提供しています。

Rancher Dashboard拡張機能の一般情報については、Rancherのドキュメントを参照してください。

5.1 前提条件

拡張機能を有効にするには、Rancherにui-plugin operatorがインストールされている必要があります。Rancher Dashboard UIを使用している場合、左側のナビゲーションの[Configuration (設定)]セクションの[Extensions (拡張機能)]に移動します。ui-plugin operatorがインストールされていない場合、こちらで説明されているように、拡張機能のサポートを有効にするように求めるプロンプトが表示されます。

operatorは、次のようにHelmを使用してインストールすることもできます。

helm repo add rancher-charts https://charts.rancher.io/
helm upgrade --create-namespace -n cattle-ui-plugin-system \
  --install ui-plugin-operator rancher-charts/ui-plugin-operator
helm upgrade --create-namespace -n cattle-ui-plugin-system \
  --install ui-plugin-operator-crd rancher-charts/ui-plugin-operator-crd

または、専用のGitRepoリソースを作成してFleetを使用してインストールすることもできます。詳細については、Fleetのセクションとfleet-examplesリポジトリを参照してください。

5.2 インストール

ダッシュボード拡張機能を含むすべてのSUSE Edge 3.0コンポーネントは、OCIアーティファクトとして配布されます。Rancher Dashboard Apps/Marketplaceは、OCIベースのHelmリポジトリをまだサポートしていません。したがって、SUSE Edge拡張機能をインストールするには、HelmまたはFleetを使用できます。

5.2.1 Helmを使用したインストール

# KubeVirt extension
helm install kubevirt-dashboard-extension oci://registry.suse.com/edge/kubevirt-dashboard-extension-chart --version 1.0.0 --namespace cattle-ui-plugin-system

# Akri extension
helm install akri-dashboard-extension oci://registry.suse.com/edge/akri-dashboard-extension-chart --version 1.0.0 --namespace cattle-ui-plugin-system
注記
注記

拡張機能はcattle-ui-plugin-systemネームスペースにインストールする必要があります。

注記
注記

拡張機能がインストールされたら、Rancher Dashboard UIを再ロードする必要があります。

5.2.2 Fleetを使用したインストール

Fleetを使用してダッシュボード拡張機能をインストールするには、カスタムのfleet.yamlバンドル設定ファイルを使用して、Gitリポジトリを指すgitRepoリソースを定義する必要があります。

# KubeVirt extension fleet.yaml
defaultNamespace: cattle-ui-plugin-system
helm:
  releaseName: kubevirt-dashboard-extension
  chart: oci://registry.suse.com/edge/akri-dashboard-extension-chart
  version: "1.0.0"
# Akri extension fleet.yaml
defaultNamespace: cattle-ui-plugin-system
helm:
  releaseName: akri-dashboard-extension
  chart: oci://registry.suse.com/edge/akri-dashboard-extension-chart
  version: "1.0.0"
注記
注記

releaseNameプロパティは必須です。また、拡張機能をui-plugin-operatorで正しくインストールするには、拡張機能の名前に一致する必要があります。

cat <<- EOF | kubectl apply -f -
apiVersion: fleet.cattle.io/v1alpha1
metadata:
  name: edge-dashboard-extensions
  namespace: fleet-local
spec:
  repo: https://github.com/suse-edge/fleet-examples.git
  branch: main
  paths:
  - fleets/kubevirt-dashboard-extension/
  - fleets/akri-dashboard-extension/
EOF

詳細については、Fleetのセクションおよびfleet-examplesのリポジトリを参照してください。

拡張機能がインストールされると、その拡張機能が[Extensions (拡張機能)]セクションの[Installed (インストール済み)]タブに表示されます。拡張機能はApps/Marketplace経由でインストールされたものではないため、「Third-Party (サードパーティ)」というラベルが付きます。

インストール済みダッシュボード拡張機能

5.3 KubeVirtダッシュボード拡張機能

KubeVirt拡張機能は、Rancher Dashboard UIに基本的な仮想マシン管理機能を提供します。その機能については、エッジの仮想化を参照してください。

5.4 Akriダッシュボード拡張機能

Akriは、異種リーフデバイス(IPカメラやUSBデバイスなど)をKubernetesクラスタのリソースとして簡単に公開できると同時に、GPUやFPGAなどの組み込みハードウェアリソースの公開もサポートするKubernetesリソースインタフェースです。Akriは、このようなデバイスにアクセスできるノードを継続的に検出し、それらに基づいてワークロードをスケジュールします。

Akriダッシュボード拡張機能を使用すると、Rancher Dashboardユーザインタフェースを使用して、リーフデバイスを管理および監視し、デバイスが検出されたらワークロードを実行できます。

拡張機能については、Akriに関するセクションで詳しく説明されています。

6 Fleet

Fleetは、ユーザがローカルクラスタをより細かく制御できるようにするとともに、GitOpsを通じて常時監視を行えるようにすることを目的に設計されたコンテナ管理およびデプロイメントエンジンです。Fleetはスケール能力に重点を置いているだけでなく、クラスタに何がインストールされているかを正確に監視するための高度な制御と可視性もユーザに提供します。

Fleetは、生のKubernetes YAML、Helmチャート、Kustomize、またはこれら3つの組み合わせのGitからデプロイメントを管理できます。ソースにかかわらず、すべてのリソースは動的にHelmチャートに変換され、すべてのリソースをクラスタにデプロイするエンジンとしてHelmが使用されます。その結果、ユーザはクラスタの高度な制御、一貫性、監査能力を実現できます。

Fleetの仕組みについては、こちらのページを参照してください。

6.1 Helmを使用したFleetのインストール

FleetはRancherにビルトインされていますが、Helmを使用して、スタンドアロンアプリケーションとして任意のKubernetesクラスタにインストールすることもできます。

6.2 RancherでのFleetの使用

Rancherは、Fleetを使用してアプリケーションを管理対象クラスタ全体にデプロイします。Fleetを使用した継続的デリバリにより、大量のクラスタで実行されるアプリケーションを管理するために設計された、大規模なGitOpsが導入されます。

FleetはRancherと統合してその一部として機能します。Rancherで管理されるクラスタには、インストール/インポートプロセスの一部としてFleetエージェントが自動的にデプロイされるため、クラスタはすぐにFleetで管理できるようになります。

6.3 Rancher UIでのFleetへのアクセス

FleetはRancherにプリインストールされており、Rancher UIの[Continuous Delivery (継続的デリバリ)]オプションで管理されます。継続的デリバリに関する追加情報、およびFleetのトラブルシューティングに関する他のヒントについては、こちらを参照してください。

Fleetダッシュボード

[Continuous Delivery (継続的デリバリ)]セクションは次の項目で構成されます。

6.3.1 Dashboard (ダッシュボード)

すべてのワークスペースにわたるすべてのGitOpsリポジトリの概要ページ。リポジトリのあるワークスペースのみが表示されます。

6.3.2 Git repos (Gitリポジトリ)

選択したワークスペース内のGitOpsリポジトリのリスト。ページ上部のドロップダウンリストを使用してアクティブなワークスペースを選択します。

6.3.3 Clusters (クラスタ)

管理対象クラスタのリスト。デフォルトでは、Rancherで管理されているすべてのクラスタがfleet-defaultワークスペースに追加されます。fleet-localワークスペースにはローカル(管理)クラスタが含まれます。ここから、クラスタをPause (一時停止)またはForce Update (強制的に更新)したり、クラスタを別のワークスペースに移動したりすることができます。クラスタを編集すると、クラスタのグループ化に使用するラベルや注釈を更新できます。

6.3.4 Cluster groups (クラスタグループ)

このセクションでは、セレクタを使用してワークスペース内のクラスタのカスタムグループを作成できます。

6.3.5 Advanced (詳細)

[Advanced (詳細)]セクションでは、ワークスペースやその他の関連するFleetリソースを管理できます。

6.4 Rancher Dashboardを使用してRancherおよびFleetとともにKubeVirtをインストールする例

  1. fleet.yamlファイルを含むGitリポジトリを作成します。

    defaultNamespace: kubevirt
    helm:
      chart: "oci://registry.suse.com/edge/kubevirt-chart"
      version: "0.2.4"
      # kubevirt namespace is created by kubevirt as well, we need to take ownership of it
      takeOwnership: true
  2. Rancher Dashboardで、☰ > [Continuous Delivery (継続的デリバリ)] > [Git Repos (Gitリポジトリ)]に移動して、[Add Repository (リポジトリの追加)]をクリックします。

  3. リポジトリの作成ウィザードの指示に従ってGitリポジトリを作成します。[Name (名前)][Repository URL (リポジトリのURL)](前の手順で作成したGitリポジトリを参照)を指定し、適切なブランチまたはリビジョンを選択します。より複雑なリポジトリの場合は、[Paths (パス)]を指定して、1つのリポジトリで複数のディレクトリを使用します。

    Fleetリポジトリの作成1
  4. Next (次へ)]をクリックします。

  5. 次の手順では、ワークロードをデプロイする場所を定義できます。クラスタの選択では複数の基本オプションがあります。クラスタをまったく選択しないことも、すべてのクラスタを選択することも、特定の管理対象クラスタやクラスタグループ(定義されている場合)を直接選択することもできます。[Advanced (詳細)]オプションを使用すると、YAML経由でセレクタを直接編集できます。

    Fleetリポジトリの作成2
  6. Create (作成)]をクリックします。リポジトリが作成されます。今後、ワークロードはリポジトリ定義に一致するクラスタにインストールされ、同期が維持されます。

6.5 デバッグとトラブルシューティング

ナビゲーションの[Advanced (詳細)]セクションでは、下位レベルのFleetリソースの概要が表示されます。バンドルは、Gitからのリソースのオーケストレーションに使用される内部リソースです。Gitリポジトリがスキャンされると、バンドルが1つ以上生成されます。

特定のリポジトリに関連するバンドルを見つけるには、[Git Repos (Gitリポジトリ)]の[Detail (詳細)]ページに移動し、[Bundles (バンドル)]タブをクリックします。

Fleetリポジトリバンドル

クラスタごとに、作成されたBundleDeploymentリソースにバンドルが適用されます。BundleDeploymentの詳細を表示するには、[Git Repos (Gitリポジトリ)]の[Detail (詳細)]ページの右上にある [Graph (グラフ)]ボタンをクリックします。[Repo (リポジトリ) ]>[Bundles (バンドル)]>[BundleDeployments]のグラフがロードされます。グラフ内のBundleDeploymentをクリックすると詳細が表示され、[Id (ID)]をクリックするとBundleDeployment YAMLが表示されます。

Fleetリポジトリのグラフ

Fleetのトラブルシューティングのヒントに関する追加情報については、こちらを参照してください。

6.6 Fleetの例

Edgeチームは、Fleetを使用してEdgeプロジェクトをインストールする例を含むリポジトリを維持しています。

Fleetプロジェクトには、Gitリポジトリ構造のすべてのユースケースをカバーするfleet-examplesリポジトリが含まれています。

7 SLE Micro

SLE Microの公式ドキュメントを参照してください

SUSE Linux Enterprise Microは、エッジ向けの軽量でセキュアなオペレーティングシステムです。SUSE Linux Enterprise Microには、SUSE Linux Enterpriseのエンタープライズ向けに強化されたコンポーネントと、開発者が最新のイミュータブルオペレーティングシステムに求める機能が統合されています。その結果、クラス最高のコンプライアンスを備えた信頼性の高いインフラストラクチャプラットフォームが実現し、使いやすさも向上しています。

7.1 SUSE EdgeでのSLE Microの用途

SUSEでは、SLE Microをプラットフォームスタックのベースオペレーティングシステムとして使用します。これにより、構築基盤となる、安全で安定した最小限のベースが提供されます。

SLE Microでは、独自の方法でファイルシステム(Btrfs)スナップショットを使用しており、アップグレードで問題が発生した場合に簡単にロールバックできます。これにより、問題が発生した場合、物理的にアクセスしなくてもプラットフォーム全体をリモートで安全にアップグレードできます。

7.2 ベストプラクティス

7.2.1 インストールメディア

SUSE Edgeは、Edge Image Builder (第9章 「Edge Image Builder)を使用して、SLE Microのセルフインストールのインストールイメージを事前設定します。

7.2.2 ローカル管理

SLE Microには、Webアプリケーションでホストをローカルに管理できるCockpitが付属しています。

このサービスはデフォルトでは無効になっていますが、systemdサービスcockpit.socketを有効にすることで開始できます。

7.3 既知の問題

  • 現時点では、SLE Microで利用可能なデスクトップ環境はありませんが、コンテナ化されたソリューションが開発中です。

8 Metal3

Metal3は、Kubernetesにベアメタルインフラストラクチャ管理機能を提供するCNCFプロジェクトです。

Metal3は、Redfishなどのアウトオブバンドプロトコルを介した管理をサポートするベアメタルサーバのライフサイクルを管理するためのKubernetesネイティブリソースを提供します。

また、Cluster API (CAPI)も十分にサポートされており、広く採用されているベンダニュートラルなAPIを使用して、複数のインフラストラクチャプロバイダにわたってインフラストラクチャリソースを管理できます。

8.1 SUSE EdgeでのMetal3の用途

この方法は、ターゲットハードウェアがアウトオブバンド管理をサポートしていて、完全に自動化されたインフラストラクチャ管理フローが望まれるシナリオで役立ちます。

この方法では宣言型APIが提供されており、このAPIを使用することで、検査、クリーニング、プロビジョニング/プロビジョニング解除の自動化を含む、ベアメタルサーバのインベントリと状態の管理が可能になります。

8.2 既知の問題

  • アップストリームのIPアドレス管理コントローラは、SUSEが選択したネットワーク設定ツールとの互換性がまだないため、現在はサポートされていません。

  • 関連して、IPAMリソースとMetal3DataTemplateのnetworkDataフィールドはサポートされていません。

  • redfish-virtualmediaを介したデプロイメントのみが現在サポートされています。

9 Edge Image Builder

公式リポジトリを参照してください。

Edge Image Builder (EIB)は、マシンをブートストラップするためのCustomized, Ready-to-Boot (CRB)ディスクイメージの生成を効率化するツールです。これらのイメージにより、SUSEソフトウェアスタック全体を単一のイメージでエンドツーエンドにデプロイできます。

EIBはあらゆるプロビジョニングシナリオ向けのCRBイメージを作成できますが、EIBが非常に大きな価値を発揮するのは、ネットワークが制限されているか、完全に分離されているエアギャップデプロイメントにおいてです。

9.1 SUSE EdgeでのEdge Image Builderでの用途

SUSE Edgeでは、さまざまなシナリオ用にカスタマイズされたSLE Microイメージをシンプルかつ迅速に設定するためにEIBを使用します。これらのシナリオには、以下を使用する仮想マシンとベアメタル マシンのブートストラップが含まれます。

  • K3s/RKE2 Kubernetesの完全なエアギャップデプロイメント(シングルノードとマルチノード)

  • HelmチャートとKubernetesマニフェストの完全なエアギャップデプロイメント

  • Elemental APIを介したRancherへの登録

  • Metal3

  • カスタマイズされたネットワーキング(静的 IP、ホスト名、VLAN、ボンディングなど)

  • カスタマイズされたオペレーティングシステム設定(ユーザ、グループ、パスワード、SSHキー、プロキシ、NTP、カスタムSSL証明書など)

  • ホストレベルおよびサイドロードRPMパッケージのエアギャップインストール(依存関係の解決を含む)

  • OS管理のためのSUSE Managerへの登録

  • 組み込みコンテナイメージ

  • カーネルコマンドライン引数

  • ブート時に有効化/無効化されるsystemdユニット

  • 手動タスク用のカスタムスクリプトとファイル

9.2 はじめに

Edge Image Builderの使用とテストに関する包括的なドキュメントについては、こちらを参照してください。

また、Edge Image Builderのクイックスタートガイド(第3章 「Edge Image Builderを使用したスタンドアロンクラスタ)では、基本的なデプロイメントシナリオを説明しています。

9.3 既知の問題

  • EIBは、Helmチャートをテンプレート化してテンプレート内のすべてのイメージを解析することで、Helmチャートをエアギャップ化します。Helmチャートですべてのイメージをテンプレート内に保持せず、代わりにイメージをサイドロードする場合、EIBではそれらのイメージを自動的にエアギャップ化できません。これを解決するには、検出されないイメージを定義ファイルのembeddedArtifactRegistryセクションに手動で追加します。

10 Edgeネットワーキング

このセクションでは、SUSE Edgeソリューションにおけるネットワーク設定へのアプローチについて説明します。宣言的な方法でSLE Micro上でNetworkManagerを設定する方法を示し、関連ツールの統合方法について説明します。

10.1 NetworkManagerの概要

NetworkManagerは、プライマリネットワーク接続と他の接続インタフェースを管理するツールです。

NetworkManagerは、ネットワーク設定を、望ましい状態が含まれる接続ファイルとして保存します。これらの接続は、/etc/NetworkManager/system-connections/ディレクトリにファイルとして保存されます。

NetworkManagerの詳細については、アップストリームのSLE Microのドキュメントを参照してください。

10.2 nmstateの概要

nmstateは広く採用されているライブラリ(CLIツールが付属)であり、定義済みスキーマを使用したネットワーク設定用の宣言型APIを提供します。

nmstateの詳細については、アップストリームドキュメントを参照してください。

10.3 NetworkManager Configurator (nmc)の概要

SUSE Edgeで利用可能なネットワークのカスタマイズオプションは、NetworkManager Configurator (短縮名はnmc)と呼ばれるCLIツールを使用して実行します。このツールはnmstateライブラリによって提供される機能を利用しているため、静的IPアドレス、DNSサーバ、VLAN、ボンディング、ブリッジなどを完全に設定できます。このツールを使用して、事前定義された望ましい状態からネットワーク設定を生成し、その設定を多数のノードに自動的に適用できます。

NetworkManager Configurator (nmc)の詳細については、アップストリームリポジトリを参照してください。

10.4 SUSE EdgeでのNetworkManager Configuratorの用途

SUSE Edgeは、nmcを利用して次のようなさまざまなプロビジョニングモデルでネットワークをカスタマイズします。

10.5 Edge Image Builderを使用した設定

Edge Image Builder (EIB)は、1つのOSイメージで複数のホストを設定できるツールです。このセクションでは、宣言型アプローチを使用して、どのように目的のネットワーク状態を記述するかと、それらがどのように各NetworkManager接続に変換され、プロビジョニングプロセス中に適用されるかを示します。

10.5.1 前提条件

このガイドに従って操作を進める場合、以下がすでに用意されていることを想定しています。

  • SLES 15 SP5またはopenSUSE Leap 15.5を実行しているx86_64物理ホスト(または仮想マシン)

  • 利用可能なコンテナランタイム(Podmanなど)

  • SLE Micro 5.5のRAWイメージのコピー(こちらにあります)

10.5.2 Edge Image Builderのコンテナイメージの取得

EIBのコンテナイメージは一般に公開されており、次のコマンドを実行してSUSE Edgeレジストリからダウンロードできます。

podman pull registry.suse.com/edge/edge-image-builder:1.0.2

10.5.3 イメージ設定ディレクトリの作成

まず設定ディレクトリを作成しましょう。

export CONFIG_DIR=$HOME/eib
mkdir -p $CONFIG_DIR/base-images

ダウンロードしたゴールデンイメージのコピーを確実に設定ディレクトリに移動します。

mv /path/to/downloads/SLE-Micro.x86_64-5.5.0-Default-GM.raw $CONFIG_DIR/base-images/
注記
注記

EIBは、ゴールデンイメージの入力を変更することはありません。

この時点では、設定ディレクトリは次のようになっているはずです。

└── base-images/
    └── SLE-Micro.x86_64-5.5.0-Default-GM.raw

10.5.4 イメージ定義ファイルの作成

定義ファイルには、Edge Image Builderがサポートする設定オプションの大部分を記述します。

OSイメージの非常に基本的な定義ファイルから開始しましょう。

cat << EOF > $CONFIG_DIR/definition.yaml
apiVersion: 1.0
image:
  arch: x86_64
  imageType: raw
  baseImage: SLE-Micro.x86_64-5.5.0-Default-GM.raw
  outputImageName: modified-image.raw
operatingSystem:
  users:
    - username: root
      encryptedPassword: $6$jHugJNNd3HElGsUZ$eodjVe4te5ps44SVcWshdfWizrP.xAyd71CVEXazBJ/.v799/WRCBXxfYmunlBO2yp1hm/zb4r8EmnrrNCF.P/
EOF

imageセクションは必須で、入力イメージ、そのアーキテクチャとタイプ、および出力イメージの名前を指定します。operatingSystemセクションはオプションであり、プロビジョニングされたシステムにroot/eibのユーザ名/パスワードでログインできるようにするための設定を含めます。

注記
注記

openssl passwd -6 <password>を実行して、独自の暗号化パスワードを自由に使用してください。

この時点では、設定ディレクトリは次のようになっているはずです。

├── definition.yaml
└── base-images/
    └── SLE-Micro.x86_64-5.5.0-Default-GM.raw

10.5.5 ネットワーク設定の定義

先ほど作成したイメージ定義ファイルには、望ましいネットワーク設定が含まれていません。そこで、network/という特別なディレクトリの下にその設定を入力します。では、作成してみましょう。

mkdir -p $CONFIG_DIR/network

前述のように、NetworkManager Configurator (nmc)ツールでは、事前定義されたスキーマの形式での入力が必要です。さまざまなネットワーキングオプションの設定方法については、アップストリームのNMStateの例のドキュメントを参照してください。

このガイドでは、次の3つの異なるノードでネットワーキングを設定する方法について説明します。

  • 2つのEthernetインタフェースを使用するノード

  • ネットワークボンディングを使用するノード

  • ネットワークブリッジを使用するノード

警告
警告

特にKubernetesクラスタを設定する場合、まったく異なるネットワークセットアップを運用ビルドで使用することは推奨されません。ネットワーキング設定は通常、特定のクラスタ内のノード間、または少なくともロール間で同種にすることをお勧めします。このガイドにはさまざまな異なるオプションが含まれていますが、これは参考例として提供することのみを目的としています。

注記
注記

以下では、IPアドレス範囲192.168.122.1/24を使用するデフォルトのlibvirtネットワークを想定しています。ご自身の環境でこの範囲が異なる場合は、適宜調整してください。

node1.suse.comという名前の最初のノードに対して、望ましい状態を作成しましょう。

cat << EOF > $CONFIG_DIR/network/node1.suse.com.yaml
routes:
  config:
    - destination: 0.0.0.0/0
      metric: 100
      next-hop-address: 192.168.122.1
      next-hop-interface: eth0
      table-id: 254
    - destination: 192.168.122.0/24
      metric: 100
      next-hop-address:
      next-hop-interface: eth0
      table-id: 254
dns-resolver:
  config:
    server:
      - 192.168.122.1
      - 8.8.8.8
interfaces:
  - name: eth0
    type: ethernet
    state: up
    mac-address: 34:8A:B1:4B:16:E1
    ipv4:
      address:
        - ip: 192.168.122.50
          prefix-length: 24
      dhcp: false
      enabled: true
    ipv6:
      enabled: false
  - name: eth3
    type: ethernet
    state: down
    mac-address: 34:8A:B1:4B:16:E2
    ipv4:
      address:
        - ip: 192.168.122.55
          prefix-length: 24
      dhcp: false
      enabled: true
    ipv6:
      enabled: false
EOF

この例では、2つのEthernetインタフェース(eth0とeth3)、要求されたIPアドレス、ルーティング、およびDNS解決の望ましい状態を定義しています。

警告
警告

必ず、すべてのEthernetインタフェースのMACアドレスを記述してください。これらのMACアドレスは、プロビジョニングプロセス中にノードの識別子として使用され、どの設定を適用すべきかを判断するのに役立ちます。このようにして、1つのISOまたはRAWイメージを使用して複数のノードを設定できます。

次は、node2.suse.comという名前の2つ目のノードです。このノードではネットワークボンディングを使用します。

cat << EOF > $CONFIG_DIR/network/node2.suse.com.yaml
routes:
  config:
    - destination: 0.0.0.0/0
      metric: 100
      next-hop-address: 192.168.122.1
      next-hop-interface: bond99
      table-id: 254
    - destination: 192.168.122.0/24
      metric: 100
      next-hop-address:
      next-hop-interface: bond99
      table-id: 254
dns-resolver:
  config:
    server:
      - 192.168.122.1
      - 8.8.8.8
interfaces:
  - name: bond99
    type: bond
    state: up
    ipv4:
      address:
        - ip: 192.168.122.60
          prefix-length: 24
      enabled: true
    link-aggregation:
      mode: balance-rr
      options:
        miimon: '140'
      port:
        - eth0
        - eth1
  - name: eth0
    type: ethernet
    state: up
    mac-address: 34:8A:B1:4B:16:E3
    ipv4:
      enabled: false
    ipv6:
      enabled: false
  - name: eth1
    type: ethernet
    state: up
    mac-address: 34:8A:B1:4B:16:E4
    ipv4:
      enabled: false
    ipv6:
      enabled: false
EOF

この例では、IPアドレス指定を有効にしていない2つのEthernetインタフェース(eth0とeth1)の望ましい状態と、ラウンドロビンポリシーによるボンディング、およびネットワークトラフィックを転送するために使用する各アドレスを定義します。

最後に、3つ目となる、望ましい状態の最後のファイルを作成します。これはネットワークブリッジを利用し、node3.suse.comという名前です。

cat << EOF > $CONFIG_DIR/network/node3.suse.com.yaml
routes:
  config:
    - destination: 0.0.0.0/0
      metric: 100
      next-hop-address: 192.168.122.1
      next-hop-interface: linux-br0
      table-id: 254
    - destination: 192.168.122.0/24
      metric: 100
      next-hop-address:
      next-hop-interface: linux-br0
      table-id: 254
dns-resolver:
  config:
    server:
      - 192.168.122.1
      - 8.8.8.8
interfaces:
  - name: eth0
    type: ethernet
    state: up
    mac-address: 34:8A:B1:4B:16:E5
    ipv4:
      enabled: false
    ipv6:
      enabled: false
  - name: linux-br0
    type: linux-bridge
    state: up
    ipv4:
      address:
        - ip: 192.168.122.70
          prefix-length: 24
      dhcp: false
      enabled: true
    bridge:
      options:
        group-forward-mask: 0
        mac-ageing-time: 300
        multicast-snooping: true
        stp:
          enabled: true
          forward-delay: 15
          hello-time: 2
          max-age: 20
          priority: 32768
      port:
        - name: eth0
          stp-hairpin-mode: false
          stp-path-cost: 100
          stp-priority: 32
EOF

この時点では、設定ディレクトリは次のようになっているはずです。

├── definition.yaml
├── network/
│   │── node1.suse.com.yaml
│   │── node2.suse.com.yaml
│   └── node3.suse.com.yaml
└── base-images/
    └── SLE-Micro.x86_64-5.5.0-Default-GM.raw
注記
注記

network/ディレクトリにあるファイル名は意図的なものです。これらの名前は、プロビジョニングプロセス中に設定されるホスト名に対応しています。

10.5.6 OSイメージの構築

これで必要な設定はすべて完了したので、次のコマンドを実行するだけでイメージを構築できます。

podman run --rm -it -v $CONFIG_DIR:/eib registry.suse.com/edge/edge-image-builder:1.0.2 build --definition-file definition.yaml

出力は次のようになります。

Generating image customization components...
Identifier ................... [SUCCESS]
Custom Files ................. [SKIPPED]
Time ......................... [SKIPPED]
Network ...................... [SUCCESS]
Groups ....................... [SKIPPED]
Users ........................ [SUCCESS]
Proxy ........................ [SKIPPED]
Rpm .......................... [SKIPPED]
Systemd ...................... [SKIPPED]
Elemental .................... [SKIPPED]
Suma ......................... [SKIPPED]
Embedded Artifact Registry ... [SKIPPED]
Keymap ....................... [SUCCESS]
Kubernetes ................... [SKIPPED]
Certificates ................. [SKIPPED]
Building RAW image...
Kernel Params ................ [SKIPPED]
Image build complete!

上のスニペットからNetworkコンポーネントが正常に設定されていることがわかるので、エッジノードのプロビジョニングに進むことができます。

注記
注記

ログファイル(network-config.log)とそれぞれのNetworkManager接続ファイルは、イメージ実行のタイムスタンプ付きディレクトリの下にある、結果の_buildディレクトリで検査できます。

10.5.7 エッジノードのプロビジョニング

作成されたRAWイメージをコピーしてみましょう。

mkdir edge-nodes && cd edge-nodes
for i in {1..4}; do cp $CONFIG_DIR/modified-image.raw node$i.raw; done

構築されたイメージを4回コピーしましたが、3つのノードのネットワーク設定しか指定していません。これは、どの目的の設定にも一致しないノードをプロビジョニングするとどうなるかも紹介したいためです。

注記
注記

このガイドでは、ノードのプロビジョニングの例に仮想化を使用します。必要な拡張機能がBIOSで有効になっていることを確認してください(詳細については、こちらを参照してください)。

virt-installを使用し、コピーしたRAWディスクを使用して仮想マシンを作成します。各仮想マシンは10GBのRAMと6個のvCPUを使用します。

10.5.7.1 1つ目のノードのプロビジョニング

仮想マシンを作成しましょう。

virt-install --name node1 --ram 10000 --vcpus 6 --disk path=node1.raw,format=raw --osinfo detect=on,name=sle-unknown --graphics none --console pty,target_type=serial --network default,mac=34:8A:B1:4B:16:E1 --network default,mac=34:8A:B1:4B:16:E2 --virt-type kvm --import
注記
注記

上記で説明した望ましい状態のMACアドレスと同じMACアドレスを持つネットワークインタフェースを作成することが重要です。

操作が完了すると、次のような内容が表示されます。

Starting install...
Creating domain...

Running text console command: virsh --connect qemu:///system console node1
Connected to domain 'node1'
Escape character is ^] (Ctrl + ])


Welcome to SUSE Linux Enterprise Micro 5.5  (x86_64) - Kernel 5.14.21-150500.55.19-default (ttyS0).

SSH host key: SHA256:XN/R5Tw43reG+QsOw480LxCnhkc/1uqMdwlI6KUBY70 (RSA)
SSH host key: SHA256:/96yGrPGKlhn04f1rb9cXv/2WJt4TtrIN5yEcN66r3s (DSA)
SSH host key: SHA256:Dy/YjBQ7LwjZGaaVcMhTWZNSOstxXBsPsvgJTJq5t00 (ECDSA)
SSH host key: SHA256:TNGqY1LRddpxD/jn/8dkT/9YmVl9hiwulqmayP+wOWQ (ED25519)
eth0: 192.168.122.50
eth1:


Configured with the Edge Image Builder
Activate the web console with: systemctl enable --now cockpit.socket

node1 login:

これで、root:eibの資格情報ペアを使用してログインできます。ここで提示されているvirsh consoleよりもSSHでホストに接続したい場合は、SSHで接続することもできます。

ログインしたら、すべての設定が完了していることを確認しましょう。

ホスト名が適切に設定されていることを確認します。

node1:~ # hostnamectl
 Static hostname: node1.suse.com
 ...

ルーティングが適切に設定されていることを確認します。

node1:~ # ip r
default via 192.168.122.1 dev eth0 proto static metric 100
192.168.122.0/24 dev eth0 proto static scope link metric 100
192.168.122.0/24 dev eth0 proto kernel scope link src 192.168.122.50 metric 100

インターネット接続が利用できることを確認します。

node1:~ # ping google.com
PING google.com (142.250.72.78) 56(84) bytes of data.
64 bytes from den16s09-in-f14.1e100.net (142.250.72.78): icmp_seq=1 ttl=56 time=13.2 ms
64 bytes from den16s09-in-f14.1e100.net (142.250.72.78): icmp_seq=2 ttl=56 time=13.4 ms
^C
--- google.com ping statistics ---
2 packets transmitted, 2 received, 0% packet loss, time 1002ms
rtt min/avg/max/mdev = 13.248/13.304/13.361/0.056 ms

2つのEthernetインタフェースが設定されていて、そのうちの1つだけがアクティブであることを確認します。

node1:~ # ip a
1: lo: <LOOPBACK,UP,LOWER_UP> mtu 65536 qdisc noqueue state UNKNOWN group default qlen 1000
    link/loopback 00:00:00:00:00:00 brd 00:00:00:00:00:00
    inet 127.0.0.1/8 scope host lo
       valid_lft forever preferred_lft forever
    inet6 ::1/128 scope host
       valid_lft forever preferred_lft forever
2: eth0: <BROADCAST,MULTICAST,UP,LOWER_UP> mtu 1500 qdisc pfifo_fast state UP group default qlen 1000
    link/ether 34:8a:b1:4b:16:e1 brd ff:ff:ff:ff:ff:ff
    altname enp0s2
    altname ens2
    inet 192.168.122.50/24 brd 192.168.122.255 scope global noprefixroute eth0
       valid_lft forever preferred_lft forever
3: eth1: <BROADCAST,MULTICAST,UP,LOWER_UP> mtu 1500 qdisc pfifo_fast state UP group default qlen 1000
    link/ether 34:8a:b1:4b:16:e2 brd ff:ff:ff:ff:ff:ff
    altname enp0s3
    altname ens3

node1:~ # nmcli -f NAME,UUID,TYPE,DEVICE,FILENAME con show
NAME  UUID                                  TYPE      DEVICE  FILENAME
eth0  dfd202f5-562f-5f07-8f2a-a7717756fb70  ethernet  eth0    /etc/NetworkManager/system-connections/eth0.nmconnection
eth1  7e211aea-3d14-59cf-a4fa-be91dac5dbba  ethernet  --      /etc/NetworkManager/system-connections/eth1.nmconnection

2つ目のインタフェースが、目的のネットワーキング状態で指定されている定義済みのeth3ではなく、eth1になっていることがわかります。これは、NetworkManager Configurator (nmc)が、MACアドレス34:8a:b1:4b:16:e2を持つNICにOSによって別の名前が付けられていることを検出することができ、それに応じて設定を調整するためです。

プロビジョニングのCombustionのフェーズを検査して、この調整が実際に行われたことを確認します。

node1:~ # journalctl -u combustion | grep nmc
Apr 23 09:20:19 localhost.localdomain combustion[1360]: [2024-04-23T09:20:19Z INFO  nmc::apply_conf] Identified host: node1.suse.com
Apr 23 09:20:19 localhost.localdomain combustion[1360]: [2024-04-23T09:20:19Z INFO  nmc::apply_conf] Set hostname: node1.suse.com
Apr 23 09:20:19 localhost.localdomain combustion[1360]: [2024-04-23T09:20:19Z INFO  nmc::apply_conf] Processing interface 'eth0'...
Apr 23 09:20:19 localhost.localdomain combustion[1360]: [2024-04-23T09:20:19Z INFO  nmc::apply_conf] Processing interface 'eth3'...
Apr 23 09:20:19 localhost.localdomain combustion[1360]: [2024-04-23T09:20:19Z INFO  nmc::apply_conf] Using interface name 'eth1' instead of the preconfigured 'eth3'
Apr 23 09:20:19 localhost.localdomain combustion[1360]: [2024-04-23T09:20:19Z INFO  nmc] Successfully applied config

続いて残りのノードをプロビジョニングしますが、ここでは最終的な設定の違いのみを示します。これからプロビジョニングするすべてのノードに対して、上記のチェックのいずれか、またはすべてを自由に適用してください。

10.5.7.2 2つ目のノードのプロビジョニング

仮想マシンを作成しましょう。

virt-install --name node2 --ram 10000 --vcpus 6 --disk path=node2.raw,format=raw --osinfo detect=on,name=sle-unknown --graphics none --console pty,target_type=serial --network default,mac=34:8A:B1:4B:16:E3 --network default,mac=34:8A:B1:4B:16:E4 --virt-type kvm --import

仮想マシンが稼働したら、このノードがボンディングされたインタフェースを使用しているかどうかを確認できます。

node2:~ # ip a
1: lo: <LOOPBACK,UP,LOWER_UP> mtu 65536 qdisc noqueue state UNKNOWN group default qlen 1000
    link/loopback 00:00:00:00:00:00 brd 00:00:00:00:00:00
    inet 127.0.0.1/8 scope host lo
       valid_lft forever preferred_lft forever
    inet6 ::1/128 scope host
       valid_lft forever preferred_lft forever
2: eth0: <BROADCAST,MULTICAST,SLAVE,UP,LOWER_UP> mtu 1500 qdisc pfifo_fast master bond99 state UP group default qlen 1000
    link/ether 34:8a:b1:4b:16:e3 brd ff:ff:ff:ff:ff:ff
    altname enp0s2
    altname ens2
3: eth1: <BROADCAST,MULTICAST,SLAVE,UP,LOWER_UP> mtu 1500 qdisc pfifo_fast master bond99 state UP group default qlen 1000
    link/ether 34:8a:b1:4b:16:e3 brd ff:ff:ff:ff:ff:ff permaddr 34:8a:b1:4b:16:e4
    altname enp0s3
    altname ens3
4: bond99: <BROADCAST,MULTICAST,MASTER,UP,LOWER_UP> mtu 1500 qdisc noqueue state UP group default qlen 1000
    link/ether 34:8a:b1:4b:16:e3 brd ff:ff:ff:ff:ff:ff
    inet 192.168.122.60/24 brd 192.168.122.255 scope global noprefixroute bond99
       valid_lft forever preferred_lft forever

ルーティングでボンディングが使用されていることを確認します。

node2:~ # ip r
default via 192.168.122.1 dev bond99 proto static metric 100
192.168.122.0/24 dev bond99 proto static scope link metric 100
192.168.122.0/24 dev bond99 proto kernel scope link src 192.168.122.60 metric 300

静的な接続ファイルが適切に利用されていることを確認します。

node2:~ # nmcli -f NAME,UUID,TYPE,DEVICE,FILENAME con show
NAME    UUID                                  TYPE      DEVICE  FILENAME
bond99  4a920503-4862-5505-80fd-4738d07f44c6  bond      bond99  /etc/NetworkManager/system-connections/bond99.nmconnection
eth0    dfd202f5-562f-5f07-8f2a-a7717756fb70  ethernet  eth0    /etc/NetworkManager/system-connections/eth0.nmconnection
eth1    0523c0a1-5f5e-5603-bcf2-68155d5d322e  ethernet  eth1    /etc/NetworkManager/system-connections/eth1.nmconnection

10.5.7.3 3つ目のノードのプロビジョニング

仮想マシンを作成しましょう。

virt-install --name node3 --ram 10000 --vcpus 6 --disk path=node3.raw,format=raw --osinfo detect=on,name=sle-unknown --graphics none --console pty,target_type=serial --network default,mac=34:8A:B1:4B:16:E5 --virt-type kvm --import

仮想マシンが稼働したら、このノードがネットワークブリッジを使用していることを確認できます。

node3:~ # ip a
1: lo: <LOOPBACK,UP,LOWER_UP> mtu 65536 qdisc noqueue state UNKNOWN group default qlen 1000
    link/loopback 00:00:00:00:00:00 brd 00:00:00:00:00:00
    inet 127.0.0.1/8 scope host lo
       valid_lft forever preferred_lft forever
    inet6 ::1/128 scope host
       valid_lft forever preferred_lft forever
2: eth0: <BROADCAST,MULTICAST,UP,LOWER_UP> mtu 1500 qdisc pfifo_fast master linux-br0 state UP group default qlen 1000
    link/ether 34:8a:b1:4b:16:e5 brd ff:ff:ff:ff:ff:ff
    altname enp0s2
    altname ens2
3: linux-br0: <BROADCAST,MULTICAST,UP,LOWER_UP> mtu 1500 qdisc noqueue state UP group default qlen 1000
    link/ether 34:8a:b1:4b:16:e5 brd ff:ff:ff:ff:ff:ff
    inet 192.168.122.70/24 brd 192.168.122.255 scope global noprefixroute linux-br0
       valid_lft forever preferred_lft forever

ルーティングでブリッジが使用されていることを確認します。

node3:~ # ip r
default via 192.168.122.1 dev linux-br0 proto static metric 100
192.168.122.0/24 dev linux-br0 proto static scope link metric 100
192.168.122.0/24 dev linux-br0 proto kernel scope link src 192.168.122.70 metric 425

静的な接続ファイルが適切に利用されていることを確認します。

node3:~ # nmcli -f NAME,UUID,TYPE,DEVICE,FILENAME con show
NAME       UUID                                  TYPE      DEVICE     FILENAME
linux-br0  1f8f1469-ed20-5f2c-bacb-a6767bee9bc0  bridge    linux-br0  /etc/NetworkManager/system-connections/linux-br0.nmconnection
eth0       dfd202f5-562f-5f07-8f2a-a7717756fb70  ethernet  eth0       /etc/NetworkManager/system-connections/eth0.nmconnection

10.5.7.4 4つ目のノードのプロビジョニング

最後に、事前定義されたどの設定ともMACアドレスが一致しないノードをプロビジョニングします。このような場合は、DHCPをデフォルトにしてネットワークインタフェースを設定します。

仮想マシンを作成しましょう。

virt-install --name node4 --ram 10000 --vcpus 6 --disk path=node4.raw,format=raw --osinfo detect=on,name=sle-unknown --graphics none --console pty,target_type=serial --network default --virt-type kvm --import

仮想マシンが稼働したら、このノードがそのネットワークインタフェースにランダムなIPアドレスを使用していることを確認できます。

localhost:~ # ip a
1: lo: <LOOPBACK,UP,LOWER_UP> mtu 65536 qdisc noqueue state UNKNOWN group default qlen 1000
    link/loopback 00:00:00:00:00:00 brd 00:00:00:00:00:00
    inet 127.0.0.1/8 scope host lo
       valid_lft forever preferred_lft forever
    inet6 ::1/128 scope host
       valid_lft forever preferred_lft forever
2: eth0: <BROADCAST,MULTICAST,UP,LOWER_UP> mtu 1500 qdisc pfifo_fast state UP group default qlen 1000
    link/ether 52:54:00:56:63:71 brd ff:ff:ff:ff:ff:ff
    altname enp0s2
    altname ens2
    inet 192.168.122.86/24 brd 192.168.122.255 scope global dynamic noprefixroute eth0
       valid_lft 3542sec preferred_lft 3542sec
    inet6 fe80::5054:ff:fe56:6371/64 scope link noprefixroute
       valid_lft forever preferred_lft forever

nmcがこのノードに静的な設定を適用できなかったことを確認します。

localhost:~ # journalctl -u combustion | grep nmc
Apr 23 12:15:45 localhost.localdomain combustion[1357]: [2024-04-23T12:15:45Z ERROR nmc] Applying config failed: None of the preconfigured hosts match local NICs

EthernetインタフェースがDHCPを介して設定されていることを確認します。

localhost:~ # journalctl | grep eth0
Apr 23 12:15:29 localhost.localdomain NetworkManager[704]: <info>  [1713874529.7801] manager: (eth0): new Ethernet device (/org/freedesktop/NetworkManager/Devices/2)
Apr 23 12:15:29 localhost.localdomain NetworkManager[704]: <info>  [1713874529.7802] device (eth0): state change: unmanaged -> unavailable (reason 'managed', sys-iface-state: 'external')
Apr 23 12:15:29 localhost.localdomain NetworkManager[704]: <info>  [1713874529.7929] device (eth0): carrier: link connected
Apr 23 12:15:29 localhost.localdomain NetworkManager[704]: <info>  [1713874529.7931] device (eth0): state change: unavailable -> disconnected (reason 'carrier-changed', sys-iface-state: 'managed')
Apr 23 12:15:29 localhost.localdomain NetworkManager[704]: <info>  [1713874529.7944] device (eth0): Activation: starting connection 'Wired Connection' (300ed658-08d4-4281-9f8c-d1b8882d29b9)
Apr 23 12:15:29 localhost.localdomain NetworkManager[704]: <info>  [1713874529.7945] device (eth0): state change: disconnected -> prepare (reason 'none', sys-iface-state: 'managed')
Apr 23 12:15:29 localhost.localdomain NetworkManager[704]: <info>  [1713874529.7947] device (eth0): state change: prepare -> config (reason 'none', sys-iface-state: 'managed')
Apr 23 12:15:29 localhost.localdomain NetworkManager[704]: <info>  [1713874529.7953] device (eth0): state change: config -> ip-config (reason 'none', sys-iface-state: 'managed')
Apr 23 12:15:29 localhost.localdomain NetworkManager[704]: <info>  [1713874529.7964] dhcp4 (eth0): activation: beginning transaction (timeout in 90 seconds)
Apr 23 12:15:33 localhost.localdomain NetworkManager[704]: <info>  [1713874533.1272] dhcp4 (eth0): state changed new lease, address=192.168.122.86

localhost:~ # nmcli -f NAME,UUID,TYPE,DEVICE,FILENAME con show
NAME              UUID                                  TYPE      DEVICE  FILENAME
Wired Connection  300ed658-08d4-4281-9f8c-d1b8882d29b9  ethernet  eth0    /var/run/NetworkManager/system-connections/default_connection.nmconnection

10.5.8 統合されたノード設定

既知のMACアドレスに依存できない場合もあります。このような場合は、いわゆる「統合設定」を選択できます。これにより、_all.yamlファイルで設定を指定し、プロビジョニングされたノードすべてに適用することができます。

異なる設定構造を使用して、エッジノードを構築およびプロビジョニングします。10.5.3項 「イメージ設定ディレクトリの作成」から10.5.5項 「ネットワーク設定の定義」のすべての手順に従います。

この例では、2つのEthernetインタフェース(eth0とeth1)の望ましい状態を定義します。一方ではDHCPを使用し、他方には静的IPアドレスを割り当てます。

mkdir -p $CONFIG_DIR/network

cat <<- EOF > $CONFIG_DIR/network/_all.yaml
interfaces:
- name: eth0
  type: ethernet
  state: up
  ipv4:
    dhcp: true
    enabled: true
  ipv6:
    enabled: false
- name: eth1
  type: ethernet
  state: up
  ipv4:
    address:
    - ip: 10.0.0.1
      prefix-length: 24
    enabled: true
    dhcp: false
  ipv6:
    enabled: false
EOF

イメージを構築してみましょう。

podman run --rm -it -v $CONFIG_DIR:/eib registry.suse.com/edge/edge-image-builder:1.0.2 build --definition-file definition.yaml

イメージが正常に構築されたら、それを使用して仮想マシンを作成しましょう。

virt-install --name node1 --ram 10000 --vcpus 6 --disk path=$CONFIG_DIR/modified-image.raw,format=raw --osinfo detect=on,name=sle-unknown --graphics none --console pty,target_type=serial --network default --network default --virt-type kvm --import

プロビジョニングプロセスには数分かかる場合があります。終了したら、指定された資格情報でシステムにログインします。

ルーティングが適切に設定されていることを確認します。

localhost:~ # ip r
default via 192.168.122.1 dev eth0 proto dhcp src 192.168.122.100 metric 100
10.0.0.0/24 dev eth1 proto kernel scope link src 10.0.0.1 metric 101
192.168.122.0/24 dev eth0 proto kernel scope link src 192.168.122.100 metric 100

インターネット接続が利用できることを確認します。

localhost:~ # ping google.com
PING google.com (142.250.72.46) 56(84) bytes of data.
64 bytes from den16s08-in-f14.1e100.net (142.250.72.46): icmp_seq=1 ttl=56 time=14.3 ms
64 bytes from den16s08-in-f14.1e100.net (142.250.72.46): icmp_seq=2 ttl=56 time=14.2 ms
^C
--- google.com ping statistics ---
2 packets transmitted, 2 received, 0% packet loss, time 1001ms
rtt min/avg/max/mdev = 14.196/14.260/14.324/0.064 ms

Ethernetインタフェースが設定され、アクティブであることを確認します。

localhost:~ # ip a
1: lo: <LOOPBACK,UP,LOWER_UP> mtu 65536 qdisc noqueue state UNKNOWN group default qlen 1000
    link/loopback 00:00:00:00:00:00 brd 00:00:00:00:00:00
    inet 127.0.0.1/8 scope host lo
       valid_lft forever preferred_lft forever
    inet6 ::1/128 scope host
       valid_lft forever preferred_lft forever
2: eth0: <BROADCAST,MULTICAST,UP,LOWER_UP> mtu 1500 qdisc pfifo_fast state UP group default qlen 1000
    link/ether 52:54:00:26:44:7a brd ff:ff:ff:ff:ff:ff
    altname enp1s0
    inet 192.168.122.100/24 brd 192.168.122.255 scope global dynamic noprefixroute eth0
       valid_lft 3505sec preferred_lft 3505sec
3: eth1: <BROADCAST,MULTICAST,UP,LOWER_UP> mtu 1500 qdisc pfifo_fast state UP group default qlen 1000
    link/ether 52:54:00:ec:57:9e brd ff:ff:ff:ff:ff:ff
    altname enp7s0
    inet 10.0.0.1/24 brd 10.0.0.255 scope global noprefixroute eth1
       valid_lft forever preferred_lft forever

localhost:~ # nmcli -f NAME,UUID,TYPE,DEVICE,FILENAME con show
NAME  UUID                                  TYPE      DEVICE  FILENAME
eth0  dfd202f5-562f-5f07-8f2a-a7717756fb70  ethernet  eth0    /etc/NetworkManager/system-connections/eth0.nmconnection
eth1  0523c0a1-5f5e-5603-bcf2-68155d5d322e  ethernet  eth1    /etc/NetworkManager/system-connections/eth1.nmconnection

localhost:~ # cat /etc/NetworkManager/system-connections/eth0.nmconnection
[connection]
autoconnect=true
autoconnect-slaves=-1
id=eth0
interface-name=eth0
type=802-3-ethernet
uuid=dfd202f5-562f-5f07-8f2a-a7717756fb70

[ipv4]
dhcp-client-id=mac
dhcp-send-hostname=true
dhcp-timeout=2147483647
ignore-auto-dns=false
ignore-auto-routes=false
method=auto
never-default=false

[ipv6]
addr-gen-mode=0
dhcp-timeout=2147483647
method=disabled

localhost:~ # cat /etc/NetworkManager/system-connections/eth1.nmconnection
[connection]
autoconnect=true
autoconnect-slaves=-1
id=eth1
interface-name=eth1
type=802-3-ethernet
uuid=0523c0a1-5f5e-5603-bcf2-68155d5d322e

[ipv4]
address0=10.0.0.1/24
dhcp-timeout=2147483647
method=manual

[ipv6]
addr-gen-mode=0
dhcp-timeout=2147483647
method=disabled

10.5.9 カスタムネットワーク設定

ここまでは、NetworkManager Configuratorを利用した、Edge Image Builderのデフォルトのネットワーク設定について説明してきました。一方で、カスタムスクリプトを使用してネットワーク設定を変更するオプションもあります。このオプションは非常に柔軟性が高く、MACアドレスにも依存しませんが、1つのイメージで複数のノードをブートストラップする場合に使用してもあまり便利ではないという制限があります。

注記
注記

/networkディレクトリにある、望ましいネットワーク状態を記述したファイルを介して、デフォルトのネットワーク設定を使用することをお勧めします。カスタムスクリプトを選択するのは、デフォルト設定の動作がユースケースに当てはまらない場合のみにしてください。

異なる設定構造を使用して、エッジノードを構築およびプロビジョニングします。10.5.3項 「イメージ設定ディレクトリの作成」から10.5.5項 「ネットワーク設定の定義」のすべての手順に従います。

この例では、プロビジョニングされたすべてのノードでeth0インタフェースに静的設定を適用し、NetworkManagerによって自動的に作成された有線接続を削除して無効にするカスタムスクリプトを作成します。これは、クラスタ内のすべてのノードに同一のネットワーキング設定を確実に適用したい場合に便利です。その結果、イメージの作成前に各ノードのMACアドレスを気にする必要がなくなります。

まず、/custom/filesディレクトリに接続ファイルを保存しましょう。

mkdir -p $CONFIG_DIR/custom/files

cat << EOF > $CONFIG_DIR/custom/files/eth0.nmconnection
[connection]
autoconnect=true
autoconnect-slaves=-1
autoconnect-retries=1
id=eth0
interface-name=eth0
type=802-3-ethernet
uuid=dfd202f5-562f-5f07-8f2a-a7717756fb70
wait-device-timeout=60000

[ipv4]
dhcp-timeout=2147483647
method=auto

[ipv6]
addr-gen-mode=eui64
dhcp-timeout=2147483647
method=disabled
EOF

静的設定が作成されたので、カスタムネットワークスクリプトも作成します。

mkdir -p $CONFIG_DIR/network

cat << EOF > $CONFIG_DIR/network/configure-network.sh
#!/bin/bash
set -eux

# Remove and disable wired connections
mkdir -p /etc/NetworkManager/conf.d/
printf "[main]\nno-auto-default=*\n" > /etc/NetworkManager/conf.d/no-auto-default.conf
rm -f /var/run/NetworkManager/system-connections/* || true

# Copy pre-configured network configuration files into NetworkManager
mkdir -p /etc/NetworkManager/system-connections/
cp eth0.nmconnection /etc/NetworkManager/system-connections/
chmod 600 /etc/NetworkManager/system-connections/*.nmconnection
EOF

chmod a+x $CONFIG_DIR/network/configure-network.sh
注記
注記

nmcのバイナリはこれまで同様にデフォルトで含まれるため、必要に応じてconfigure-network.shスクリプトで使用することもできます。

警告
警告

カスタムスクリプトは常に設定ディレクトリの/network/configure-network.shで提供する必要があります。このファイルが存在する場合、他のファイルはすべて無視されます。YAML形式の静的設定とカスタムスクリプトの両方を同時に使用してネットワークを設定することはできません。

この時点では、設定ディレクトリは次のようになっているはずです。

├── definition.yaml
├── custom/
│   └── files/
│       └── eth0.nmconnection
├── network/
│   └── configure-network.sh
└── base-images/
    └── SLE-Micro.x86_64-5.5.0-Default-GM.raw

イメージを構築してみましょう。

podman run --rm -it -v $CONFIG_DIR:/eib registry.suse.com/edge/edge-image-builder:1.0.2 build --definition-file definition.yaml

イメージが正常に構築されたら、それを使用して仮想マシンを作成しましょう。

virt-install --name node1 --ram 10000 --vcpus 6 --disk path=$CONFIG_DIR/modified-image.raw,format=raw --osinfo detect=on,name=sle-unknown --graphics none --console pty,target_type=serial --network default --virt-type kvm --import

プロビジョニングプロセスには数分かかる場合があります。終了したら、指定された資格情報でシステムにログインします。

ルーティングが適切に設定されていることを確認します。

localhost:~ # ip r
default via 192.168.122.1 dev eth0 proto dhcp src 192.168.122.185 metric 100
192.168.122.0/24 dev eth0 proto kernel scope link src 192.168.122.185 metric 100

インターネット接続が利用できることを確認します。

localhost:~ # ping google.com
PING google.com (142.250.72.78) 56(84) bytes of data.
64 bytes from den16s09-in-f14.1e100.net (142.250.72.78): icmp_seq=1 ttl=56 time=13.6 ms
64 bytes from den16s09-in-f14.1e100.net (142.250.72.78): icmp_seq=2 ttl=56 time=13.6 ms
^C
--- google.com ping statistics ---
2 packets transmitted, 2 received, 0% packet loss, time 1001ms
rtt min/avg/max/mdev = 13.592/13.599/13.606/0.007 ms

接続ファイルを使用してEthernetインタフェースが静的に設定されていて、アクティブであることを確認します。

localhost:~ # ip a
1: lo: <LOOPBACK,UP,LOWER_UP> mtu 65536 qdisc noqueue state UNKNOWN group default qlen 1000
    link/loopback 00:00:00:00:00:00 brd 00:00:00:00:00:00
    inet 127.0.0.1/8 scope host lo
       valid_lft forever preferred_lft forever
    inet6 ::1/128 scope host
       valid_lft forever preferred_lft forever
2: eth0: <BROADCAST,MULTICAST,UP,LOWER_UP> mtu 1500 qdisc pfifo_fast state UP group default qlen 1000
    link/ether 52:54:00:31:d0:1b brd ff:ff:ff:ff:ff:ff
    altname enp0s2
    altname ens2
    inet 192.168.122.185/24 brd 192.168.122.255 scope global dynamic noprefixroute eth0

localhost:~ # nmcli -f NAME,UUID,TYPE,DEVICE,FILENAME con show
NAME  UUID                                  TYPE      DEVICE  FILENAME
eth0  dfd202f5-562f-5f07-8f2a-a7717756fb70  ethernet  eth0    /etc/NetworkManager/system-connections/eth0.nmconnection

localhost:~ # cat  /etc/NetworkManager/system-connections/eth0.nmconnection
[connection]
autoconnect=true
autoconnect-slaves=-1
autoconnect-retries=1
id=eth0
interface-name=eth0
type=802-3-ethernet
uuid=dfd202f5-562f-5f07-8f2a-a7717756fb70
wait-device-timeout=60000

[ipv4]
dhcp-timeout=2147483647
method=auto

[ipv6]
addr-gen-mode=eui64
dhcp-timeout=2147483647
method=disabled

11 Elemental

Elementalは、Kubernetesを使用した完全にクラウドネイティブな集中型のOS管理を可能にするソフトウェアスタックです。Elementalスタックは、Rancher自体またはエッジノード上に存在する多数のコンポーネントで構成されます。中核となるコンポーネントは次のとおりです。

  • elemental-operator - Rancher上に存在し、クライアントからの登録リクエストを処理するコアオペレータ。

  • elemental-register - エッジノード上で動作し、elemental-operatorを介して登録できるようにするクライアント。

  • elemental-system-agent - エッジノードに存在するエージェント。その設定はelemental-registerから提供され、rancher-system-agentを設定するためのplanを受け取ります。

  • rancher-system-agent - エッジノードが完全に登録された後に、elemental-system-agentから処理を引き継ぎ、Rancher Managerからの他のplansを待機します(Kubernetesのインストールなど)。

Elemental、およびElementalとRancherとの関係の詳細については、Elementalのアップストリームドキュメントを参照してください。

11.1 SUSE EdgeでのElementalの用途

SUSEでは、Metal3を選択できないリモート デバイス(たとえば、BMCがない、デバイスがNATゲートウェイの背後にあるなど)の管理にElementalの一部を使用しています。このツールにより、オペレータは、デバイスがいつどこに配置されるかがわかる前に、ラボでデバイスをブートストラップできます。すなわち、elemental-registerelemental-system-agentコンポーネントを利用して、「Phone Home」ネットワークプロビジョニングのユースケースでSLE MicroホストをRancherにオンボードできます。Edge Image Builder (EIB)を使用してデプロイメントイメージを作成する場合、EIBの設定ディレクトリで登録設定を指定することで、Rancherを使用してElemental経由で自動登録を行うことができます。

注記
注記

SUSE Edge 3.0では、Elementalのオペレーティング システム管理の側面を利用して「いない」ため、Rancher経由でオペレーティング システムのパッチを管理することはできません。SUSE Edgeでは、Elementalツールを使用してデプロイメント イメージを構築する代わりに、登録設定を使用するEdge Image Builderツールを使用します。

11.2 ベストプラクティス

11.2.1 インストールメディア

「Phone Homeネットワークプロビジョニング」のデプロイメントフットプリントでElementalを利用してRancherに登録可能なデプロイメントイメージを構築する場合、SUSE Edgeでは、Elementalを使用したリモートホストのオンボーディング(第2章 「Elementalを使用したリモートホストのオンボーディング)のクイックスタートで詳しく説明されている手順に従う方法をお勧めします。

11.2.2 ラベル

Elementalは、MachineInventory CRDを使用してインベントリを追跡し、インベントリを選択する方法を提供します。たとえば、Kubernetesクラスタのデプロイ先のマシンをラベルに基づいて選択できます。これにより、ユーザはハードウェアを購入する前に、インフラストラクチャのニーズの(すべてではないにしても)ほとんどを事前に定義しておくことができます。また、ノードはその各インベントリオブジェクトのラベルを追加/削除できるので(elemental-registerを、追加のフラグ--label "FOO=BAR "を指定して再実行する)、ノードがブートされた場所を検出してRancherに知らせるスクリプトを作成できます。

11.3 既知の問題

  • 現在のところ、Elemental UIは、インストールメディアの構築方法を認識したり、「Elemental Teal」以外のオペレーティングシステムを更新したりすることはできません。これは将来のリリースで対応予定です。

12 Akri

Akriは、リーフデバイスを検出してKubernetesネイティブリソースとして提供することを目的としたCNCF-Sandboxプロジェクトです。また、検出された各デバイスに対してPodやジョブをスケジュールすることもできます。デバイスはノードローカルでもネットワーク接続されていてもよく、さまざまなプロトコルを使用できます。

Akriのアップストリームドキュメントについては、https://docs.akri.shを参照してください。

12.1 SUSE EdgeでのAkriの用途

警告
警告

Akriは現在、SUSE Edgeスタックでの技術プレビュー中です。

Akriは、リーフデバイスに対するワークロードの検出とスケジューリングが必要な場合はいつでも、Edgeスタックの一部として利用できます。

12.1.1 Akriのインストール

AkriはEdge Helmリポジトリ内でHelmチャートとして利用できます。Akriを設定するための推奨方法は、指定したHelmチャートを使用してさまざまなコンポーネント(エージェント、コントローラ、ディスカバリハンドラ)をデプロイし、好みのデプロイメントメカニズムを使用してAkriの設定CRDをデプロイすることです。

12.1.2 Akriの設定

Akriは、akri.sh/Configurationオブジェクトを使用して設定します。このオブジェクトは、デバイスの検出方法、および一致するデバイスが検出されたときの処理に関するすべての情報を取得します。

以下に、設定例の内訳を示し、すべてのフィールドについて説明します。

apiVersion: akri.sh/v0
kind: Configuration
metadata:
  name: sample-configuration
spec:

次の部分では、ディスカバリハンドラの設定を記述しています。ディスカバリハンドラの名前を指定する必要があります(Akriのチャートの一部として利用可能なハンドラは、udevopcuaonvifです)。discoveryDetailsはハンドラ固有です。設定方法については、ハンドラのドキュメントを参照してください。

  discoveryHandler:
    name: debugEcho
    discoveryDetails: |+
      descriptions:
        - "foo"
        - "bar"

次のセクションでは、検出された各デバイスに対してデプロイするワークロードを定義します。この例では、brokerPodSpecPod設定の最小バージョンが示されています。ここでは、Podの仕様の通常のフィールドをすべて使用できます。また、resourcesセクションに、デバイスを要求するためのAkri固有の構文も示されています。

または、Podの代わりにJobを使用することもできます。その場合は、代わりにbrokerJobSpecキーを使用し、そこにJobの仕様部分を指定します。

  brokerSpec:
    brokerPodSpec:
      containers:
      - name: broker-container
        image: rancher/hello-world
        resources:
          requests:
            "{{PLACEHOLDER}}" : "1"
          limits:
            "{{PLACEHOLDER}}" : "1"

次の2つのセクションは、ブローカごとにサービスをデプロイするようにAkriを設定するか(instanceService)、またはすべてのブローカを指すようにAkriを設定する(configurationService)方法を示しています。これらには、通常のサービスに関連する要素がすべて含まれています。

  instanceServiceSpec:
    type: ClusterIp
    ports:
    - name: http
      port: 80
      protocol: tcp
      targetPort: 80
  configurationServiceSpec:
    type: ClusterIp
    ports:
    - name: https
      port: 443
      protocol: tcp
      targetPort: 443

brokerPropertiesフィールドは、検出されたデバイスを要求するPodに追加の環境変数として公開されるキー/値ストアです。

capacityは、検出されたデバイスの許容される同時ユーザ数です。

  brokerProperties:
    key: value
  capacity: 1

12.1.3 追加のディスカバリハンドラの記述とデプロイ

デバイスで使用されているプロトコルが既存のディスカバリハンドラでカバーされていない場合は、こちらのガイドを使用して、独自に記述できます。

12.1.4 Akri Rancher Dashboard拡張機能

Akriダッシュボード拡張機能を使用すると、Rancher Dashboardユーザインタフェースを使用して、リーフデバイスを管理および監視し、デバイスが検出されたらワークロードを実行できます。

拡張機能をインストールしたら、クラスタエクスプローラを使用してAkri対応の管理対象クラスタに移動できます。[Akri]ナビゲーショングループの下に[Configurations (設定)]セクションと[Instances (インスタンス)]セクションがあります。

Akri拡張機能の設定

[Configurations (設定)]リストには、設定ディスカバリハンドラとインスタンス数に関する情報が表示されます。名前をクリックすると、設定の詳細ページが開きます。

Akri拡張機能の設定の詳細

設定の編集や新規作成も行うことができます。拡張機能を使用すると、ディスカバリハンドラの選択、ブローカPodやブローカJobの設定、設定サービスやインスタンスサービスの設定、および設定容量の設定を行うことができます。

Akri拡張機能の設定の編集

検出されたデバイスが [Instances (インスタンス)]リストに一覧にされます。

Akri拡張機能インスタンスリスト

インスタンス名をクリックすると、詳細ページが開き、ワークロードおよびインスタンスサービスを表示できます。

Akri拡張機能のインスタンス詳細

13 K3s

K3sは、リソースに制約のあるリモートの無人の場所やIoTアプライアンス内の運用ワークロード向けに設計された、高可用性のKubernetes認定ディストリビューションです。

単一の小さなバイナリとしてパッケージ化されているため、迅速かつ簡単にインストールおよび更新できます。

13.1 SUSE EdgeでのK3sの用途

K3sは、SUSE Edgeスタックを支えるKubernetesディストリビューションとして使用できます。K3sはSLE Microオペレーティングシステムにインストールすることが意図されています。

K3sをSUSE EdgeスタックのKubernetesディストリビューションとして使用することは、etcdをバックエンドとして使用したのでは制約に合わない場合にのみ推奨します。etcdをバックエンドとして使用できる場合は、RKE2 (第14章 「RKE2)を使用することをお勧めします。

13.2 ベストプラクティス

13.2.1 インストール

K3sをSUSE Edgeスタックの一部としてインストールする場合に推奨する方法は、Edge Image Builder (EIB)を使用することです。K3sをデプロイするようにEIBを設定する方法の詳細については、EIBのドキュメント(第9章 「Edge Image Builder)を参照してください。

この方法では、自動的にHAセットアップとElementalセットアップがサポートされます。

13.2.2 GitOpsワークフローでのFleet

SUSE Edgeスタックでは、GitOpsの推奨ツールとしてFleetを使用します 。Fleetのインストールと使用の詳細については、このドキュメントの「Fleet」のセクション(第6章 「Fleet)を参照してください。

13.2.3 ストレージ管理

K3sではローカルパスストレージが事前設定されており、これはシングルノードクラスタに適しています。複数のノードにまたがるクラスタの場合は、Longhorn (第15章 「Longhorn)を使用することをお勧めします。

13.2.4 負荷分散とHA

EIBを使用してK3sをインストールした場合、ここで説明する部分は、EIBのドキュメントの「HA」のセクションで説明済みです。

EIBを使用しないでK3sをインストールした場合は、MetalLBのドキュメント(第19章 「K3s上のMetalLB (L2を使用))に従ってMetalLBをインストールおよび設定する必要があります。

14 RKE2

RKE2の公式ドキュメントを参照してください。

RKE2は、以下によってセキュリティとコンプライアンスに重点を置いた、完全準拠のKubernetesディストリビューションです。

  • クラスタがCIS Kubernetes Benchmark v1.6またはv1.23に合格できるデフォルト値と設定オプションを、オペレータの介入を最小限に抑えながら提供する

  • FIPS 140-2準拠を可能にする

  • trivyを使用し、コンポーネントを定期的にスキャンしてRKE2ビルドパイプラインにCVEがないかどうかを確認する

RKE2は、コントロールプレーンコンポーネントを、kubeletによって管理される静的Podとして起動します。組み込みコンテナランタイムはcontainerdです。

メモ: RKE2はRKE Governmentとしても知られます。これは、RKE2が現在ターゲットにしている別のユースケースと分野を表すためです。

14.1 RKE2とK3s

K3sは完全準拠の軽量なKubernetesディストリビューションであり、エッジ、IoT、ARMや、K8sのクラスタ技術では博士号を取得できそうにない状況に焦点を合わせています。

RKE2は、RKEの1.xバージョン(以下「RKE1」)とK3sの両方の長所を兼ね備えています。

RKE2は、K3sから使いやすさ、操作のしやすさ、およびデプロイメントモデルを継承しています。

RKE1から継承しているのは、アップストリームのKubernetesとの緊密な連携です。K3sはエッジデプロイメントに合わせて最適化されているため、アップストリームのKubernetesとは各所で異なりますが、RKE1とRKE2はアップストリームと緊密な連携を保つことができます。

14.2 SUSE EdgeでのRKE2の用途

RKE2はSUSE Edgeスタックの基礎を成す部分です。RKE2はSUSE Linux Micro (第7章 「SLE Micro)上に位置し、Edgeワークロードを最小限のフットプリントでデプロイするために必要な標準Kubernetesインタフェースを提供します。

14.3 ベストプラクティス

14.3.1 インストール

RKE2をSUSE Edgeスタックの一部としてインストールする場合に推奨される方法は、Edge Image Builder (EIB)を使用することです。RKE2をデプロイするようにEIBを設定する方法の詳細については、EIBのドキュメント(第9章 「Edge Image Builder)を参照してください。

EIBは十分な柔軟性を備えているため、RKE2のバージョン、サーバ、またはエージェント設定の指定など、RKE2で要求されるあらゆるパラメータをサポートすることができ、Edgeのすべてのユースケースに対応できます。

Metal3に関連する他のユースケースでも、RKE2が使用およびインストールされます。このような特定のケースでは、Cluster API Provider RKE2によって、Edgeスタックを使用してMetal3でプロビジョニングされるクラスタにRKE2が自動的にデプロイされます。

このような場合、関係する各種のCRDにRKE2設定を適用する必要があります。RKE2ControlPlane CRDを使用して異なるCNIを提供する方法の例は、次のようになります。

apiVersion: controlplane.cluster.x-k8s.io/v1alpha1
kind: RKE2ControlPlane
metadata:
  name: single-node-cluster
  namespace: default
spec:
  serverConfig:
    cni: calico
    cniMultusEnable: true
...

Metal3のユースケースの詳細については、第8章 「Metal3を参照してください。

14.3.2 高可用性

HAデプロイメントの場合、EIBはMetalLB (第17章 「MetalLB)とEndpoint Copier Operatorを自動的にデプロイして設定し、RKE2 APIエンドポイントを外部に公開します。

14.3.3 ネットワーキング

EdgeスタックでサポートされているCNIはCiliumで、オプションでmeta-plugin Multusを追加できますが、RKE2ではほかにもいくつかのプラグインがサポートされています。

14.3.4 ストレージ

RKE2は、どのような種類の永続ストレージクラスやオペレータも提供していません。複数のノードにまたがるクラスタの場合は、Longhorn (第15章 「Longhorn)を使用することをお勧めします。

15 Longhorn

Longhornは、Kubernetes向けに設計された、信頼性が高くユーザフレンドリな軽量の分散ブロックストレージシステムです。オープンソースプロジェクトとして、当初はRancher Labsによって開発されていましたが、現在はCNCFの下でインキュベートされています。

15.1 前提条件

このガイドに従って操作を進める場合、以下がすでに用意されていることを想定しています。

  • SLE Micro 5.5がインストールされた1つ以上のホスト(物理または仮想)

  • インストール済みのKubernetesクラスタ1つ(K3sまたはRKE2)

  • Helm

15.2 Longhornの手動インストール

15.2.1 Open-iSCSIのインストール

Longhornをデプロイして使用するための中心的な要件は、open-iscsiパッケージをインストールすることと、iscsidデーモンをすべてのKubernetesノード上で実行することです。これは、Longhornがホスト上のiscsiadmを利用してKubernetesに永続ボリュームを提供するために必要です。

インストールしてみましょう。

transactional-update pkg install open-iscsi

SLE Microはイミュータブルオペレーティングシステムであるため、操作が完了すると、パッケージは新しいスナップショットにのみインストールされることに注意することが重要です。パッケージをロードし、iscsidデーモンの実行を開始するには、作成した新しいスナップショットで再起動する必要があります。準備が整ったら、rebootコマンドを発行します。

reboot
ヒント
ヒント

open-iscsiのインストールに関する追加のヘルプについては、Longhorn公式ドキュメントを参照してください。

15.2.2 Longhornのインストール

LonghornをKubernetesクラスタにインストールする方法はいくつかあります。このガイドではHelmによるインストール手順に従いますが、別のアプローチが必要な場合は、公式ドキュメントに従ってください。

  1. LonghornのHelmリポジトリを追加します。

    helm repo add longhorn https://charts.longhorn.io
  2. リポジトリから最新のチャートをフェッチします。

    helm repo update
  3. Longhornをlonghorn-systemネームスペースにインストールします。

    helm install longhorn longhorn/longhorn --namespace longhorn-system --create-namespace --version 1.6.1
  4. デプロイメントが成功したことを確認します。

    kubectl -n longhorn-system get pods
    localhost:~ # kubectl -n longhorn-system get pod
    NAMESPACE         NAME                                                READY   STATUS      RESTARTS        AGE
    longhorn-system   longhorn-ui-5fc9fb76db-z5dc9                        1/1     Running     0               90s
    longhorn-system   longhorn-ui-5fc9fb76db-dcb65                        1/1     Running     0               90s
    longhorn-system   longhorn-manager-wts2v                              1/1     Running     1 (77s ago)     90s
    longhorn-system   longhorn-driver-deployer-5d4f79ddd-fxgcs            1/1     Running     0               90s
    longhorn-system   instance-manager-a9bf65a7808a1acd6616bcd4c03d925b   1/1     Running     0               70s
    longhorn-system   engine-image-ei-acb7590c-htqmp                      1/1     Running     0               70s
    longhorn-system   csi-attacher-5c4bfdcf59-j8xww                       1/1     Running     0               50s
    longhorn-system   csi-provisioner-667796df57-l69vh                    1/1     Running     0               50s
    longhorn-system   csi-attacher-5c4bfdcf59-xgd5z                       1/1     Running     0               50s
    longhorn-system   csi-provisioner-667796df57-dqkfr                    1/1     Running     0               50s
    longhorn-system   csi-attacher-5c4bfdcf59-wckt8                       1/1     Running     0               50s
    longhorn-system   csi-resizer-694f8f5f64-7n2kq                        1/1     Running     0               50s
    longhorn-system   csi-snapshotter-959b69d4b-rp4gk                     1/1     Running     0               50s
    longhorn-system   csi-resizer-694f8f5f64-r6ljc                        1/1     Running     0               50s
    longhorn-system   csi-resizer-694f8f5f64-k7429                        1/1     Running     0               50s
    longhorn-system   csi-snapshotter-959b69d4b-5k8pg                     1/1     Running     0               50s
    longhorn-system   csi-provisioner-667796df57-n5w9s                    1/1     Running     0               50s
    longhorn-system   csi-snapshotter-959b69d4b-x7b7t                     1/1     Running     0               50s
    longhorn-system   longhorn-csi-plugin-bsc8c                           3/3     Running     0               50s

15.3 Longhornボリュームの作成

Longhornは、StorageClassというKubernetesリソースを利用して、PodのPersistentVolumeオブジェクトを自動的にプロビジョニングします。StorageClassは、管理者が、自身が提供するクラスまたはプロファイルを記述する方法だと考えてください。

デフォルトのオプションをいくつか使用してStorageClassを作成しましょう。

kubectl apply -f - <<EOF
kind: StorageClass
apiVersion: storage.k8s.io/v1
metadata:
  name: longhorn-example
provisioner: driver.longhorn.io
allowVolumeExpansion: true
parameters:
  numberOfReplicas: "3"
  staleReplicaTimeout: "2880" # 48 hours in minutes
  fromBackup: ""
  fsType: "ext4"
EOF

StorageClassを作成したので、それを参照するPersistentVolumeClaimが必要です。PersistentVolumeClaim (PVC)は、ユーザによるストレージの要求です。PVCはPersistentVolumeリソースを使用します。クレームでは、特定のサイズとアクセスモードを要求できます(たとえば、1つのノードで読み取り/書き込み可能でマウントすることも、複数のノードで読み取り専用でマウントすることもできます)。

PersistentVolumeClaimを作成しましょう。

kubectl apply -f - <<EOF
apiVersion: v1
kind: PersistentVolumeClaim
metadata:
  name: longhorn-volv-pvc
  namespace: longhorn-system
spec:
  accessModes:
    - ReadWriteOnce
  storageClassName: longhorn-example
  resources:
    requests:
      storage: 2Gi
EOF

完了です。PersistentVolumeClaimを作成したら、それをPodにアタッチする手順に進むことができます。Podがデプロイされると、KubernetesはLonghornボリュームを作成し、ストレージが利用可能な場合はPodにバインドします。

kubectl apply -f - <<EOF
apiVersion: v1
kind: Pod
metadata:
  name: volume-test
  namespace: longhorn-system
spec:
  containers:
  - name: volume-test
    image: nginx:stable-alpine
    imagePullPolicy: IfNotPresent
    volumeMounts:
    - name: volv
      mountPath: /data
    ports:
    - containerPort: 80
  volumes:
  - name: volv
    persistentVolumeClaim:
      claimName: longhorn-volv-pvc
EOF
ヒント
ヒント

Kubernetesにおけるストレージの概念は複雑であると同時に重要なトピックです。最も一般的なKubernetesリソースのいくつかを簡単に説明しましたが、Longhornが提供している用語のドキュメントをよく理解しておくことをお勧めします。

この例では、結果は次のようになります。

localhost:~ # kubectl get storageclass
NAME                 PROVISIONER          RECLAIMPOLICY   VOLUMEBINDINGMODE   ALLOWVOLUMEEXPANSION   AGE
longhorn (default)   driver.longhorn.io   Delete          Immediate           true                   12m
longhorn-example     driver.longhorn.io   Delete          Immediate           true                   24s

localhost:~ # kubectl get pvc -n longhorn-system
NAME                STATUS   VOLUME                                     CAPACITY   ACCESS MODES   STORAGECLASS       AGE
longhorn-volv-pvc   Bound    pvc-f663a92e-ac32-49ae-b8e5-8a6cc29a7d1e   2Gi        RWO            longhorn-example   54s

localhost:~ # kubectl get pods -n longhorn-system
NAME                                                READY   STATUS    RESTARTS      AGE
csi-attacher-5c4bfdcf59-qmjtz                       1/1     Running   0             14m
csi-attacher-5c4bfdcf59-s7n65                       1/1     Running   0             14m
csi-attacher-5c4bfdcf59-w9xgs                       1/1     Running   0             14m
csi-provisioner-667796df57-fmz2d                    1/1     Running   0             14m
csi-provisioner-667796df57-p7rjr                    1/1     Running   0             14m
csi-provisioner-667796df57-w9fdq                    1/1     Running   0             14m
csi-resizer-694f8f5f64-2rb8v                        1/1     Running   0             14m
csi-resizer-694f8f5f64-z9v9x                        1/1     Running   0             14m
csi-resizer-694f8f5f64-zlncz                        1/1     Running   0             14m
csi-snapshotter-959b69d4b-5dpvj                     1/1     Running   0             14m
csi-snapshotter-959b69d4b-lwwkv                     1/1     Running   0             14m
csi-snapshotter-959b69d4b-tzhwc                     1/1     Running   0             14m
engine-image-ei-5cefaf2b-hvdv5                      1/1     Running   0             14m
instance-manager-0ee452a2e9583753e35ad00602250c5b   1/1     Running   0             14m
longhorn-csi-plugin-gd2jx                           3/3     Running   0             14m
longhorn-driver-deployer-9f4fc86-j6h2b              1/1     Running   0             15m
longhorn-manager-z4lnl                              1/1     Running   0             15m
longhorn-ui-5f4b7bbf69-bln7h                        1/1     Running   3 (14m ago)   15m
longhorn-ui-5f4b7bbf69-lh97n                        1/1     Running   3 (14m ago)   15m
volume-test                                         1/1     Running   0             26s

15.4 UIへのアクセス

kubectlまたはHelmを使用してLonghornをインストールした場合は、クラスタへの外部トラフィックを許可するようにIngressコントローラを設定する必要があります。認証はデフォルトでは有効になっていません。Rancherカタログアプリを使用していた場合、IngressコントローラはRancherによって自動的に作成され、アクセス制御が設定されています(rancher-proxy)。

  1. Longhornの外部サービスのIPアドレスを取得します。

    kubectl -n longhorn-system get svc
  2. longghorn-frontendのIPアドレスを取得したら、ブラウザでそのアドレスに移動してUIの使用を開始できます。

15.5 Edge Image Builderを使用したインストール

SUSE Edgeは、第9章 「Edge Image Builderを使用して、ベースとなるSLE Micro OSイメージをカスタマイズしています。ここでは、イメージをカスタマイズしてRKE2クラスタとLonghornをSLE Micro上にプロビジョニングする方法について説明します。

定義ファイルを作成しましょう。

export CONFIG_DIR=$HOME/eib
mkdir -p $CONFIG_DIR

cat << EOF > $CONFIG_DIR/iso-definition.yaml
apiVersion: 1.0
image:
  imageType: iso
  baseImage: SLE-Micro.x86_64-5.5.0-Default-SelfInstall-GM2.install.iso
  arch: x86_64
  outputImageName: eib-image.iso
kubernetes:
  version: v1.28.9+rke2r1
  helm:
    charts:
      - name: longhorn
        version: 1.6.1
        repositoryName: longhorn
        targetNamespace: longhorn-system
        createNamespace: true
        installationNamespace: kube-system
    repositories:
      - name: longhorn
        url: https://charts.longhorn.io
operatingSystem:
  packages:
    sccRegistrationCode: <reg-code>
    packageList:
      - open-iscsi
  users:
  - username: root
    encryptedPassword: \$6\$jHugJNNd3HElGsUZ\$eodjVe4te5ps44SVcWshdfWizrP.xAyd71CVEXazBJ/.v799/WRCBXxfYmunlBO2yp1hm/zb4r8EmnrrNCF.P/
EOF
注記
注記

Helmチャートの値のカスタマイズは、helm.charts[].valuesFileで提供されている別個のファイルを使用して実行できます。詳細については、アップストリームドキュメントを参照してください。

イメージを構築してみましょう。

podman run --rm --privileged -it -v $CONFIG_DIR:/eib registry.suse.com/edge/edge-image-builder:1.0.2 build --definition-file $CONFIG_DIR/iso-definition.yaml

イメージが構築されたら、それを使用して物理ホストまたは仮想ホストにOSをインストールできます。プロビジョニングが完了すると、root:eibの資格情報ペアを使用してシステムにログインできます。

Longhornが正常にデプロイされていることを確認します。

localhost:~ # /var/lib/rancher/rke2/bin/kubectl --kubeconfig /etc/rancher/rke2/rke2.yaml -n longhorn-system get pods
NAME                                                READY   STATUS    RESTARTS        AGE
csi-attacher-5c4bfdcf59-qmjtz                       1/1     Running   0               103s
csi-attacher-5c4bfdcf59-s7n65                       1/1     Running   0               103s
csi-attacher-5c4bfdcf59-w9xgs                       1/1     Running   0               103s
csi-provisioner-667796df57-fmz2d                    1/1     Running   0               103s
csi-provisioner-667796df57-p7rjr                    1/1     Running   0               103s
csi-provisioner-667796df57-w9fdq                    1/1     Running   0               103s
csi-resizer-694f8f5f64-2rb8v                        1/1     Running   0               103s
csi-resizer-694f8f5f64-z9v9x                        1/1     Running   0               103s
csi-resizer-694f8f5f64-zlncz                        1/1     Running   0               103s
csi-snapshotter-959b69d4b-5dpvj                     1/1     Running   0               103s
csi-snapshotter-959b69d4b-lwwkv                     1/1     Running   0               103s
csi-snapshotter-959b69d4b-tzhwc                     1/1     Running   0               103s
engine-image-ei-5cefaf2b-hvdv5                      1/1     Running   0               109s
instance-manager-0ee452a2e9583753e35ad00602250c5b   1/1     Running   0               109s
longhorn-csi-plugin-gd2jx                           3/3     Running   0               103s
longhorn-driver-deployer-9f4fc86-j6h2b              1/1     Running   0               2m28s
longhorn-manager-z4lnl                              1/1     Running   0               2m28s
longhorn-ui-5f4b7bbf69-bln7h                        1/1     Running   3 (2m7s ago)    2m28s
longhorn-ui-5f4b7bbf69-lh97n                        1/1     Running   3 (2m10s ago)   2m28s
注記
注記

このインストールは、完全なエアギャップ環境では動作しません。このような場合は、21.8項 「Longhornのインストール」を参照してください。

16 NeuVector

NeuVectorはKubernetes向けのセキュリティソリューションであり、L7ネットワークセキュリティ、ランタイムセキュリティ、サプライチェーンセキュリティ、およびコンプライアンスチェックを1つの統合パッケージで提供します。

NeuVectorは、複数のコンテナから成るプラットフォームとしてデプロイされ、各コンテナはさまざまなポートとインタフェースで相互に通信します。デプロイされる各種のコンテナは以下のとおりです。

  • Manager 。Webベースのコンソールを提供するステートレスコンテナです。通常、マネージャは1つだけ必要で、どこでも実行できます。Managerにエラーが発生しても、ControllerやEnforcerの動作には影響しません。ただし、特定の通知(イベント)と最近の接続データはManagerによってメモリ内にキャッシュされているため、これらの表示には影響があります。

  • Controller。NeuVectorの「コントロールプレーン」は必ずHA設定でデプロイされるため、ノードのエラーで設定が失われることはありません。Controllerはどこでも実行できますが、その重要性から、顧客はほとんどの場合、「管理」ノード、マスタノード、またはインフラノードに配置することを選択します。

  • Enforcer。このコンテナはDaemonSetとしてデプロイされるため、保護する各ノードに1つのEnforcerが存在します。通常はすべてのワーカーノードにデプロイされますが、スケジュールを有効にしてマスタノードやインフラノードにデプロイすることもできます。メモ: Enforcerがクラスタノードに存在しない状況で、そのノード上のPodから接続が行われた場合、その接続はNeuVectorによって「unmanaged」ワークロードとしてラベル付けされます。

  • Scanner。コントローラの指示に従って、ビルトインCVEデータベースを使用して脆弱性スキャンを実行します。複数のScannerをデプロイしてスキャン能力を拡張できます。Scannerはどこでも実行できますが、コントローラが実行されるノードで実行されることがほとんどです。Scannerノードのサイジングに関する考慮事項については、以下を参照してください。ビルドフェーズのスキャンに使用する場合、Scannerを独立して呼び出すこともできます。たとえば、スキャンをトリガし、結果を取得してScannerを停止するパイプライン内で使用する場合などです。Scannerには最新のCVEデータベースが含まれているため、毎日更新する必要があります。

  • Updater。Updaterは、CVEデータベースの更新が必要な場合に、Kubernetes cronジョブを通じてScannerの更新をトリガします。必ず使用環境に合わせて設定してください。

NeuVectorのオンボーディングの詳細とベストプラクティスのドキュメントについては、こちらをご覧ください。

16.1 SUSE EdgeでのNeuVectorの用途

SUSE Edgeは、エッジデプロイメントの開始点として簡潔なNeuVector設定を提供します。

NeuVectorの設定の変更については、こちらを参照してください。

16.2 重要なメモ

  • Scannerコンテナには、スキャンするイメージをメモリに取り込んで解凍するのに十分なメモリが必要です。1GBを超えるイメージをスキャンするには、Scannerのメモリを、予想される最大イメージサイズをわずかに上回るサイズまで増やしてください。

  • 保護モードでは、大量のネットワーク接続が予想されます。保護(インラインファイアウォールでのブロック)モードの場合、Enforcerでは、接続および想定されるペイロードを保持して検査(DLP)するためにCPUとメモリが必要です。メモリを増やし、1つのCPUコアをEnforcer専用にすることで、十分なパケットフィルタリング容量を確保できます。

16.3 Edge Image Builderを使用したインストール

SUSE Edgeでは、第9章 「Edge Image Builderを使用して、ベースとなるSLE Micro OSイメージをカスタマイズします。EIBでプロビジョニングしたKubernetesクラスタ上にNeuVectorをエアギャップインストールする場合は、21.7項 「NeuVectorのインストール」に従ってください。

17 MetalLB

MetalLBの公式ドキュメントを参照してください。

MetalLBは、標準のルーティングプロトコルを使用する、ベアメタルKubernetesクラスタ用のロードバランサの実装です。

ベアメタル環境では、ネットワークロードバランサの設定がクラウドセットアップよりも著しく複雑になります。クラウド設定でのわかりやすいAPIコールとは異なり、ベアメタルでは、高可用性(HA)を管理したり、シングルノードのロードバランサに特有の潜在的な単一障害点(SPOF)に対処したりするために、専用のネットワークアプライアンス、またはロードバランサと仮想IP (VIP)設定の組み合わせが必要になります。このような設定は自動化しにくく、コンポーネントが動的にスケールアップ/ダウンするKubernetesのデプロイメントでは課題となります。

MetalLBでは、こうした課題に対処するために、Kubernetesモデルを利用してLoadBalancerタイプのサービスを作成し、ベアメタルセットアップであってもクラウド環境であるかのように動作させます。

2つの異なるアプローチがあります。L2モード(ARP「トリック」を使用する)アプローチか、BGPを使用するアプローチです。主にL2では特別なネットワーク機器は必要ありませんが、一般的にはBGPのほうが優れています。これはユースケースによって異なります。

17.1 SUSE EdgeでのMetalLBの用途

SUSE Edgeでは、主に次の2つの方法でMetalLBを使用します。

  • ロードバランサソリューションとして: MetalLBは、ベアメタルマシン用のロードバランサソリューションとして機能します。

  • HA K3s/RKE2セットアップの場合: MetalLBでは、仮想IPアドレスを使用してKubernetes APIを負荷分散できます。

注記
注記

APIを公開できるようにするには、endpoint-copier-operatorを使用して、「kubernetes」サービスから「kubernetes-vip」LoadBalancerサービスへのK8s APIエンドポイントの同期を保ちます。

17.2 ベストプラクティス

L2モードでのMetalLBのインストールの詳細については、MetalLBガイド(第19章 「K3s上のMetalLB (L2を使用))を参照してください。

MetalLBをkube-api-serverの前面にインストールしてHAセットアップを実現する方法のガイドについては、「Kubernetes APIサーバの前面のMetalLB」(第20章 「Kubernetes APIサーバの前面のMetalLB)のチュートリアルを参照してください。

17.3 既知の問題

  • K3S LoadBalancerソリューション: K3Sには、Klipperというロードバランサソリューションが付属しています。MetalLBを使用するには、Klipperを無効にする必要があります。このためには、K3sのドキュメントで説明されているように、--disable servicelbオプションを指定してK3sサーバを起動します。

18 Edge Virtualization

このセクションでは、Edge Virtualizationを使用してエッジノードで仮想マシンを実行する方法について説明します。Edge Virtualizationは包括的なソリューションではなく、機能も限られていることを指摘しておくことが重要です。Edge Virtualizationは、基本的な仮想マシン機能が要求される軽量な仮想化の要件を解決しようとするものです。より包括的な仮想化(およびハイパーコンバージドインフラストラクチャ)ソリューションは、Harvesterで提供されています。

SUSE Edge Virtualizationでは、仮想マシンの実行方法として次の2つをサポートしています。

  1. libvirt+qemu-kvmを使用してホストレベルで手動で仮想マシンをデプロイする

  2. KubeVirtオペレータをデプロイし、Kubernetesベースで仮想マシンを管理する

どちらのオプションも有効ですが、以下では2番目のオプションのみを説明しています。SLE Microで提供されている、すぐに使用できる標準の仮想化メカニズムを使用する場合は、こちらで包括的なガイドを参照してください。このガイドは主にSUSE Linux Enterprise Server用に記載されていますが、概念はほぼ同じです。

このガイドではまず、事前にデプロイ済みのシステムに追加の仮想化コンポーネントをデプロイする方法について説明しますが、その後に続くセクションでは、Edge Image Builderを使用してこの設定を最初のデプロイメントに組み込む方法を説明しています。基本手順を実行して環境を手動で設定する必要がない場合は、そちらのセクションに進んでください。

18.1 KubeVirtの概要

KubeVirtでは、仮想マシンと他のコンテナ化ワークロードを併せてKubernetesで管理できます。これを実現するために、Linux仮想化スタックのユーザスペース部分をコンテナ内で実行します。これにより、ホストシステムの要件が最小限に抑えられ、セットアップと管理が容易になります。

KubeVirtのアーキテクチャの詳細については、アップストリームドキュメントを参照してください。

18.2 前提条件

このガイドに従って操作を進める場合、以下がすでに用意されていることを想定しています。

  • SLE Micro 5.5+がインストールされ、BIOSで仮想化拡張機能が有効になっている物理ホスト1台以上(詳細については、こちらを参照)。

  • ノード全体で、K3s/RKE2 Kubernetesクラスタがすでにデプロイされており、クラスタへのスーパーユーザアクセスを可能にする適切なkubeconfigが設定されている。

  • ルートユーザへのアクセス — 以下の説明では、自身がルートユーザであり、sudoを使用して特権を昇格して「いない」ことを想定しています。

  • Helmがローカルで利用可能で、適切なネットワーク接続を備えていて、Kubernetesクラスタに設定をプッシュし、必要なイメージをダウンロードできる。

18.3 Edge Virtualizationの手動インストール

このガイドでは、Kubernetesのデプロイメント手順については説明しませんが、SUSE Edgeに適したバージョンのK3sまたはRKE2がインストールされていること、およびkubeconfigが適切に設定されていて標準のkubectlコマンドをスーパーユーザとして実行できることを想定しています。また、シングルノードクラスタを形成することを想定していますが、マルチノードのデプロイメントでも大きな違いはないと考えられます。

SUSE Edge Virtualizationは、3つの別個のHelmチャートを使用してデプロイします。具体的には次のとおりです。

  • KubeVirt: 中心的な仮想化コンポーネント。つまり、Kubernetesが仮想マシンをデプロイおよび管理できるようにするために必要なKubernetes CRD、オペレータ、およびその他のコンポーネント。

  • KubeVirtダッシュボード拡張機能: 仮想マシンの起動/停止やコンソールへのアクセスなど、基本的な仮想マシン管理を実行できるオプションのRancher UI拡張機能。

  • Containerized Data Importer (CDI): KubeVirtの永続ストレージの統合を可能にする追加コンポーネント。仮想マシンが既存のKubernetesストレージバックエンドをデータ用に使用する機能を提供するだけでなく、ユーザが仮想マシンのデータボリュームのインポートまたはクローンの作成を行うことも可能にします。

これらの各Helmチャートは、現在使用しているSUSE Edgeのリリースに従ってバージョン管理されています。運用での使用/サポートされる使用のためには、SUSEレジストリにあるアーティファクトを使用してください。

まず、 kubectlのアクセスが機能していることを確認します。

$ kubectl get nodes

次のような画面が表示されます。

NAME                   STATUS   ROLES                       AGE     VERSION
node1.edge.rdo.wales   Ready    control-plane,etcd,master   4h20m   v1.28.9+rke2r1
node2.edge.rdo.wales   Ready    control-plane,etcd,master   4h15m   v1.28.9+rke2r1
node3.edge.rdo.wales   Ready    control-plane,etcd,master   4h15m   v1.28.9+rke2r1

これで、KubeVirtおよびContainerized Data Importer (CDI)のHelmチャートのインストールに進むことができます。

$ helm install kubevirt oci://registry.suse.com/edge/kubevirt-chart --namespace kubevirt-system --create-namespace
$ helm install cdi oci://registry.suse.com/edge/cdi-chart --namespace cdi-system --create-namespace

数分ですべてのKubeVirtおよびCDIコンポーネントがデプロイされるはずです。これを検証するには、kubevirt-systemおよびcdi-systemのネームスペース内にデプロイされたすべてのリソースを確認します。

KubeVirtリソースを確認します。

$ kubectl get all -n kubevirt-system

次のような画面が表示されます。

NAME                                   READY   STATUS    RESTARTS      AGE
pod/virt-operator-5fbcf48d58-p7xpm     1/1     Running   0             2m24s
pod/virt-operator-5fbcf48d58-wnf6s     1/1     Running   0             2m24s
pod/virt-handler-t594x                 1/1     Running   0             93s
pod/virt-controller-5f84c69884-cwjvd   1/1     Running   1 (64s ago)   93s
pod/virt-controller-5f84c69884-xxw6q   1/1     Running   1 (64s ago)   93s
pod/virt-api-7dfc54cf95-v8kcl          1/1     Running   1 (59s ago)   118s

NAME                                  TYPE        CLUSTER-IP      EXTERNAL-IP   PORT(S)   AGE
service/kubevirt-prometheus-metrics   ClusterIP   None            <none>        443/TCP   2m1s
service/virt-api                      ClusterIP   10.43.56.140    <none>        443/TCP   2m1s
service/kubevirt-operator-webhook     ClusterIP   10.43.201.121   <none>        443/TCP   2m1s
service/virt-exportproxy              ClusterIP   10.43.83.23     <none>        443/TCP   2m1s

NAME                          DESIRED   CURRENT   READY   UP-TO-DATE   AVAILABLE   NODE SELECTOR            AGE
daemonset.apps/virt-handler   1         1         1       1            1           kubernetes.io/os=linux   93s

NAME                              READY   UP-TO-DATE   AVAILABLE   AGE
deployment.apps/virt-operator     2/2     2            2           2m24s
deployment.apps/virt-controller   2/2     2            2           93s
deployment.apps/virt-api          1/1     1            1           118s

NAME                                         DESIRED   CURRENT   READY   AGE
replicaset.apps/virt-operator-5fbcf48d58     2         2         2       2m24s
replicaset.apps/virt-controller-5f84c69884   2         2         2       93s
replicaset.apps/virt-api-7dfc54cf95          1         1         1       118s

NAME                            AGE     PHASE
kubevirt.kubevirt.io/kubevirt   2m24s   Deployed

CDIリソースを確認します。

$ kubectl get all -n cdi-system

次のような画面が表示されます。

NAME                                   READY   STATUS    RESTARTS   AGE
pod/cdi-operator-55c74f4b86-692xb      1/1     Running   0          2m24s
pod/cdi-apiserver-db465b888-62lvr      1/1     Running   0          2m21s
pod/cdi-deployment-56c7d74995-mgkfn    1/1     Running   0          2m21s
pod/cdi-uploadproxy-7d7b94b968-6kxc2   1/1     Running   0          2m22s

NAME                             TYPE        CLUSTER-IP     EXTERNAL-IP   PORT(S)    AGE
service/cdi-uploadproxy          ClusterIP   10.43.117.7    <none>        443/TCP    2m22s
service/cdi-api                  ClusterIP   10.43.20.101   <none>        443/TCP    2m22s
service/cdi-prometheus-metrics   ClusterIP   10.43.39.153   <none>        8080/TCP   2m21s

NAME                              READY   UP-TO-DATE   AVAILABLE   AGE
deployment.apps/cdi-operator      1/1     1            1           2m24s
deployment.apps/cdi-apiserver     1/1     1            1           2m22s
deployment.apps/cdi-deployment    1/1     1            1           2m21s
deployment.apps/cdi-uploadproxy   1/1     1            1           2m22s

NAME                                         DESIRED   CURRENT   READY   AGE
replicaset.apps/cdi-operator-55c74f4b86      1         1         1       2m24s
replicaset.apps/cdi-apiserver-db465b888      1         1         1       2m21s
replicaset.apps/cdi-deployment-56c7d74995    1         1         1       2m21s
replicaset.apps/cdi-uploadproxy-7d7b94b968   1         1         1       2m22s

VirtualMachineカスタムリソース定義(CRD)がデプロイされていることを確認するには、次のコマンドで検証できます。

$ kubectl explain virtualmachine

VirtualMachineオブジェクトの定義が出力され、次のような画面が表示されます。

GROUP:      kubevirt.io
KIND:       VirtualMachine
VERSION:    v1

DESCRIPTION:
    VirtualMachine handles the VirtualMachines that are not running or are in a
    stopped state The VirtualMachine contains the template to create the
    VirtualMachineInstance. It also mirrors the running state of the created
    VirtualMachineInstance in its status.
(snip)

18.4 仮想マシンのデプロイ

KubeVirtとCDIがデプロイされたので、openSUSE Tumbleweedに基づくシンプルな仮想マシンを定義してみましょう。この仮想マシンは最もシンプルな設定であり、標準の「Podネットワーキング」を使用して、他のPodと同じネットワーキング設定を行います。また、非永続ストレージを使用するため、PVCを持たないコンテナと同様に、ストレージは一時的なものになります。

$ kubectl apply -f - <<EOF
apiVersion: kubevirt.io/v1
kind: VirtualMachine
metadata:
  name: tumbleweed
  namespace: default
spec:
  runStrategy: Always
  template:
    spec:
      domain:
        devices: {}
        machine:
          type: q35
        memory:
          guest: 2Gi
        resources: {}
      volumes:
      - containerDisk:
          image: registry.opensuse.org/home/roxenham/tumbleweed-container-disk/containerfile/cloud-image:latest
        name: tumbleweed-containerdisk-0
      - cloudInitNoCloud:
          userDataBase64: I2Nsb3VkLWNvbmZpZwpkaXNhYmxlX3Jvb3Q6IGZhbHNlCnNzaF9wd2F1dGg6IFRydWUKdXNlcnM6CiAgLSBkZWZhdWx0CiAgLSBuYW1lOiBzdXNlCiAgICBncm91cHM6IHN1ZG8KICAgIHNoZWxsOiAvYmluL2Jhc2gKICAgIHN1ZG86ICBBTEw9KEFMTCkgTk9QQVNTV0Q6QUxMCiAgICBsb2NrX3Bhc3N3ZDogRmFsc2UKICAgIHBsYWluX3RleHRfcGFzc3dkOiAnc3VzZScK
        name: cloudinitdisk
EOF

これにより、VirtualMachineが作成されたことを示すメッセージが出力されます。

virtualmachine.kubevirt.io/tumbleweed created

このVirtualMachine定義は最小限であり、設定はほとんど指定されていません。この定義は単に、この仮想マシンが、一時的なcontainerDiskに基づくディスクイメージ(つまり、リモートイメージリポジトリからのコンテナイメージに保存されるディスクイメージ)を使用する、2GBのメモリを備えたマシンタイプ「q35」であることを示しています。また、base64でエンコードされたcloudInitディスクを指定しており、このディスクはブート時にユーザを作成してパスワードを適用する目的にのみ使用します(デコードにはbase64 -dを使用します)。

注記
注記

この仮想マシンイメージはテスト専用です。このイメージは公式にサポートされておらず、ドキュメントの例としてのみ使用されています。

このマシンは、openSUSE Tumbleweedのディスクイメージをダウンロードする必要があるためブートに数分かかりますが、ブートが完了したら、次のコマンドで仮想マシンの情報をチェックして、仮想マシンの詳細を確認できます。

$ kubectl get vmi

これにより、仮想マシンが起動されたノードと、仮想マシンのIPアドレスが出力されます。Podネットワーキングを使用しているため、報告されるIPアドレスは他のPodと同様であり、ルーティング可能であることに注意してください。

NAME         AGE     PHASE     IP           NODENAME               READY
tumbleweed   4m24s   Running   10.42.2.98   node3.edge.rdo.wales   True

これらのコマンドをKubernetesクラスタノード自体で実行する場合は、トラフィックをPodに直接ルーティングするCNI (Ciliumなど)を使用して、マシン自体に直接sshで接続できるはずです。次のIPアドレスを、仮想マシンに割り当てられているIPアドレスに置き換えます。

$ ssh suse@10.42.2.98
(password is "suse")

この仮想マシンに接続すると、さまざまな操作を試すことができますが、リソースの点で制限があり、ディスク容量は1GBしかないことに注意してください。終了したら、Ctrl-DまたはexitでSSHセッションを切断します。

仮想マシンプロセスは、依然として標準のKubernetes Podでラップされています。VirtualMachine CRDは目的の仮想マシンを表していますが、仮想マシンが実際に起動されるプロセスは、他のアプリケーションと同様に、標準のKubernetes Podであるvirt-launcher Podを介して行われます。起動されたすべての仮想マシンに対して、virt-launcher Podが存在することがわかります。

$ kubectl get pods

次に、定義したTumbleweedマシンの1つのvirt-launcher Podが表示されます。

NAME                             READY   STATUS    RESTARTS   AGE
virt-launcher-tumbleweed-8gcn4   3/3     Running   0          10m

このvirt-launcher Podを調べてみると、libvirtプロセスとqemu-kvmプロセスを実行していることがわかります。このPod自体を起動して詳細を確認できます。次のコマンドは、使用しているPodの名前に合わせて調整する必要があることに注意してください。

$ kubectl exec -it virt-launcher-tumbleweed-8gcn4 -- bash

Podが起動したら、virshコマンドを実行するのと併せて、プロセスを確認してみます。qemu-system-x86_64バイナリに加え、仮想マシンを監視するための特定のプロセスも実行されていることがわかります。 また、ディスクイメージの場所と、ネットワーキングが(タップデバイスとして)どのように接続されているかもわかります。

qemu@tumbleweed:/> ps ax
  PID TTY      STAT   TIME COMMAND
    1 ?        Ssl    0:00 /usr/bin/virt-launcher-monitor --qemu-timeout 269s --name tumbleweed --uid b9655c11-38f7-4fa8-8f5d-bfe987dab42c --namespace default --kubevirt-share-dir /var/run/kubevirt --ephemeral-disk-dir /var/run/kubevirt-ephemeral-disks --container-disk-dir /var/run/kube
   12 ?        Sl     0:01 /usr/bin/virt-launcher --qemu-timeout 269s --name tumbleweed --uid b9655c11-38f7-4fa8-8f5d-bfe987dab42c --namespace default --kubevirt-share-dir /var/run/kubevirt --ephemeral-disk-dir /var/run/kubevirt-ephemeral-disks --container-disk-dir /var/run/kubevirt/con
   24 ?        Sl     0:00 /usr/sbin/virtlogd -f /etc/libvirt/virtlogd.conf
   25 ?        Sl     0:01 /usr/sbin/virtqemud -f /var/run/libvirt/virtqemud.conf
   83 ?        Sl     0:31 /usr/bin/qemu-system-x86_64 -name guest=default_tumbleweed,debug-threads=on -S -object {"qom-type":"secret","id":"masterKey0","format":"raw","file":"/var/run/kubevirt-private/libvirt/qemu/lib/domain-1-default_tumbleweed/master-key.aes"} -machine pc-q35-7.1,usb
  286 pts/0    Ss     0:00 bash
  320 pts/0    R+     0:00 ps ax

qemu@tumbleweed:/> virsh list --all
 Id   Name                 State
------------------------------------
 1    default_tumbleweed   running

qemu@tumbleweed:/> virsh domblklist 1
 Target   Source
---------------------------------------------------------------------------------------------
 sda      /var/run/kubevirt-ephemeral-disks/disk-data/tumbleweed-containerdisk-0/disk.qcow2
 sdb      /var/run/kubevirt-ephemeral-disks/cloud-init-data/default/tumbleweed/noCloud.iso

qemu@tumbleweed:/> virsh domiflist 1
 Interface   Type       Source   Model                     MAC
------------------------------------------------------------------------------
 tap0        ethernet   -        virtio-non-transitional   e6:e9:1a:05:c0:92

qemu@tumbleweed:/> exit
exit

最後に、この仮称マシンを削除して、クリーンアップしましょう。

$ kubectl delete vm/tumbleweed
virtualmachine.kubevirt.io "tumbleweed" deleted

18.5 virtctlの使用

KubeVirtには、標準のKubernetes CLIツールであるkubectlとともに、仮想化の世界とKubernetesが設計された世界との間のギャップを埋める方法でクラスタとのインタフェースを可能にするCLIユーティリティが付属しています。たとえば、 virtctlツールは、APIやCRDを直接使用することなく、仮想マシンのライフサイクル(起動、停止、再起動など)の管理、仮想コンソールへのアクセスの提供、仮想マシンイメージのアップロード、サービスなどのKubernetesコンストラクトとのインタフェースを行う機能を提供します。

virtctlツールの最新の安定バージョンをダウンロードしましょう。

$ export VERSION=v1.1.0
$ wget https://github.com/kubevirt/kubevirt/releases/download/${VERSION}/virtctl-${VERSION}-linux-amd64

別のアーキテクチャまたはLinux以外のマシンを使用している場合は、他のリリースをこちらで見つけることができます。続行する前に、この実行可能ファイルを作成する必要があります。また、実行可能ファイルを$PATH内の特定の場所に移動すると便利な場合があります。

$ mv virtctl-${VERSION}-linux-amd64 /usr/local/bin/virtctl
$ chmod a+x /usr/local/bin/virtctl

その後、virtctlコマンドラインツールを使用して、仮想マシンを作成できます。出力をkubectl applyに直接パイプしていることに注意して、前の仮想マシンを複製してみましょう。

$ virtctl create vm --name virtctl-example --memory=1Gi \
    --volume-containerdisk=src:registry.opensuse.org/home/roxenham/tumbleweed-container-disk/containerfile/cloud-image:latest \
    --cloud-init-user-data "I2Nsb3VkLWNvbmZpZwpkaXNhYmxlX3Jvb3Q6IGZhbHNlCnNzaF9wd2F1dGg6IFRydWUKdXNlcnM6CiAgLSBkZWZhdWx0CiAgLSBuYW1lOiBzdXNlCiAgICBncm91cHM6IHN1ZG8KICAgIHNoZWxsOiAvYmluL2Jhc2gKICAgIHN1ZG86ICBBTEw9KEFMTCkgTk9QQVNTV0Q6QUxMCiAgICBsb2NrX3Bhc3N3ZDogRmFsc2UKICAgIHBsYWluX3RleHRfcGFzc3dkOiAnc3VzZScK" | kubectl apply -f -

これで、仮想マシンが実行されているのがわかります(コンテナイメージがキャッシュされるため、今回はかなり早く起動するはずです)。

$ kubectl get vmi
NAME              AGE   PHASE     IP           NODENAME               READY
virtctl-example   52s   Running   10.42.2.29   node3.edge.rdo.wales   True

これで、 virtctlを使用して仮想マシンに直接接続できるようになりました。

$ virtctl ssh suse@virtctl-example
(password is "suse" - Ctrl-D to exit)

virtctlで使用可能なコマンドはほかにも多数あります。たとえば、 virtctl consoleを使用すると、ネットワーキングが機能していない場合にシリアルコンソールにアクセスでき、virtctl guestosinfoを使用すると、ゲストにqemu-guest-agentがインストールされていて実行されていれば、包括的なOS情報を取得できます。

最後に、仮想マシンを一時停止し、再開してみましょう。

$ virtctl pause vm virtctl-example
VMI virtctl-example was scheduled to pause

VirtualMachineオブジェクトが「Paused」と表示され、VirtualMachineInstanceオブジェクトは「Running」ですが「READY=False」と表示されているのがわかります。

$ kubectl get vm
NAME              AGE     STATUS   READY
virtctl-example   8m14s   Paused   False

$ kubectl get vmi
NAME              AGE     PHASE     IP           NODENAME               READY
virtctl-example   8m15s   Running   10.42.2.29   node3.edge.rdo.wales   False

また、仮想マシンに接続できなくなっていることもわかります。

$ virtctl ssh suse@virtctl-example
can't access VMI virtctl-example: Operation cannot be fulfilled on virtualmachineinstance.kubevirt.io "virtctl-example": VMI is paused

仮想マシンを再開して、もう一度試してみましょう。

$ virtctl unpause vm virtctl-example
VMI virtctl-example was scheduled to unpause

これで、接続を再確立できるはずです。

$ virtctl ssh suse@virtctl-example
suse@vmi/virtctl-example.default's password:
suse@virtctl-example:~> exit
logout

最後に、仮想マシンを削除しましょう。

$ kubectl delete vm/virtctl-example
virtualmachine.kubevirt.io "virtctl-example" deleted

18.6 シンプルなIngressネットワーキング

このセクションでは、仮想マシンを標準のKubernetesサービスとして公開し、NGINXとRKE2TraefikとK3sなどのKubernetes Ingressサービスを介して利用可能にする方法を示します。このドキュメントでは、これらのコンポーネントがすでに適切に設定されていること、およびKubernetesサーバノードまたはIngress仮想IPを指す適切なDNSポインタが設定されていて(ワイルドカードを使用するなど)、Ingressを適切に解決できることを前提としています。

注記
注記

SUSE Edge 3.0以降では、K3sをマルチサーバノード設定で使用している場合、MetalLBベースのVIPをIngress用に設定しなければならなかった可能性があります。これはRKE2では必要ありません。

この例の環境では、別のopenSUSE Tumbleweed仮想マシンをデプロイし、cloud-initを使用して、ブート時にNGINXをシンプルなWebサーバとしてインストールしています。また、呼び出しの実行時に期待どおりに動作することを確認するためにシンプルなメッセージを返すように設定しています。この処理を確認するには、以下の出力のcloud-initのセクションに対してbase64 -dを実行するだけです。

では、この仮想マシンを作成してみましょう。

$ kubectl apply -f - <<EOF
apiVersion: kubevirt.io/v1
kind: VirtualMachine
metadata:
  name: ingress-example
  namespace: default
spec:
  runStrategy: Always
  template:
    metadata:
      labels:
        app: nginx
    spec:
      domain:
        devices: {}
        machine:
          type: q35
        memory:
          guest: 2Gi
        resources: {}
      volumes:
      - containerDisk:
          image: registry.opensuse.org/home/roxenham/tumbleweed-container-disk/containerfile/cloud-image:latest
        name: tumbleweed-containerdisk-0
      - cloudInitNoCloud:
          userDataBase64: I2Nsb3VkLWNvbmZpZwpkaXNhYmxlX3Jvb3Q6IGZhbHNlCnNzaF9wd2F1dGg6IFRydWUKdXNlcnM6CiAgLSBkZWZhdWx0CiAgLSBuYW1lOiBzdXNlCiAgICBncm91cHM6IHN1ZG8KICAgIHNoZWxsOiAvYmluL2Jhc2gKICAgIHN1ZG86ICBBTEw9KEFMTCkgTk9QQVNTV0Q6QUxMCiAgICBsb2NrX3Bhc3N3ZDogRmFsc2UKICAgIHBsYWluX3RleHRfcGFzc3dkOiAnc3VzZScKcnVuY21kOgogIC0genlwcGVyIGluIC15IG5naW54CiAgLSBzeXN0ZW1jdGwgZW5hYmxlIC0tbm93IG5naW54CiAgLSBlY2hvICJJdCB3b3JrcyEiID4gL3Nydi93d3cvaHRkb2NzL2luZGV4Lmh0bQo=
        name: cloudinitdisk
EOF

この仮想マシンが正常に起動したら、virtctlコマンドを使用して、外部ポート8080とターゲットポート80 (NGINXがデフォルトでリスンするポート)でVirtualMachineInstanceを公開できます。virtctlコマンドは、仮想マシンオブジェクトとPodのマッピングを理解しているため、ここではこのコマンドを使用します。これにより、新しいサービスが作成されます。

$ virtctl expose vmi ingress-example --port=8080 --target-port=80 --name=ingress-example
Service ingress-example successfully exposed for vmi ingress-example

これで、適切なサービスが自動的に作成されます。

$ kubectl get svc/ingress-example
NAME              TYPE           CLUSTER-IP      EXTERNAL-IP       PORT(S)                         AGE
ingress-example   ClusterIP      10.43.217.19    <none>            8080/TCP                        9s

次に、kubectl create ingressを使用すると、このサービスを指すIngressオブジェクトを作成できます。ここでURL (ingressオブジェクトの「ホスト」として知られている)をDNS設定に合わせて調整し、ポート8080を指すようにします。

$ kubectl create ingress ingress-example --rule=ingress-example.suse.local/=ingress-example:8080

DNSが正しく設定されたら、URLに対してすぐにcurlを実行できます。

$ curl ingress-example.suse.local
It works!

この仮想マシンとそのサービス、およびIngressリソースを削除して、クリーンアップしましょう。

$ kubectl delete vm/ingress-example svc/ingress-example ingress/ingress-example
virtualmachine.kubevirt.io "ingress-example" deleted
service "ingress-example" deleted
ingress.networking.k8s.io "ingress-example" deleted

18.7 Rancher UI拡張機能の使用

SUSE Edge VirtualizationはRancher Manager用のUI拡張機能を提供しており、Rancher Dashboard UIを使用して基本的な仮想マシン管理を行うことができます。

18.7.1 インストール

インストールのガイダンスについては、Rancher Dashboard拡張機能に関するセクションを参照してください。

18.7.2 KubeVirt Rancher Dashboard拡張機能の使用

この拡張機能により、Cluster Explorerに新たに[KubeVirt]セクションが導入されます。このセクションは、KubeVirtがインストールされている管理対象クラスタに追加されます。

この拡張機能を使用すると、次の2つのKubeVirtリソースを直接操作できます。

  1. Virtual Machine Instances — 実行中の1つの仮想マシンインスタンスを表すリソース。

  2. Virtual Machines — 仮想マシンのライフサイクルを管理するために使用されるリソース。

18.7.2.1 仮想マシンの作成

  1. 左側のナビゲーションでKubeVirtが有効な管理対象クラスタをクリックして、[Cluster Explorer]に移動します。

  2. KubeVirt ] > [Virtual Machines (仮想マシン)]ページで、画面の右上にある[ Create from YAML (YAMLから作成)]をクリックします。

  3. 仮想マシンの定義を入力するか貼り付けて、[Create (作成)]を押します。「仮想マシンのデプロイ 」セクションの仮想マシンの定義を参考にしてください。

[Virtual Machines (仮想マシン)]ページ

18.7.2.2 仮想マシンの起動と停止

仮想マシンを起動および停止するには、各仮想マシンの右側にあるドロップダウンリストからアクセスできるアクションメニューを使用するか、アクションを実行する仮想マシンを選択してリストの上部にあるグループアクションを使用します。

spec.runningプロパティが定義されている仮想マシンに対してのみ、起動および停止アクションを実行できます。spec.runStrategyが使用されている場合、そのようなマシンは直接起動および停止できません。詳細については、KubeVirtのドキュメントを参照してください。

18.7.2.3 仮想マシンコンソールへのアクセス

[Virtual Machines (仮想マシン)]リストには[Console (コンソール)]ドロップダウンリストがあり、ここからVNCまたはシリアルコンソールを使用してマシンに接続できます。このアクションは、実行中のマシンでのみ使用できます。

新しく起動した仮想マシンでは、コンソールにアクセスできるようになるまでにしばらく時間がかかることがあります。

VNCコンソールUI

18.8 Edge Image Builderを使用したインストール

SUSE Edgeは、ベースとなるSLE Micro OSイメージをカスタマイズするために第9章 「Edge Image Builderを使用しています。EIBによってプロビジョニングされたKubernetesクラスタ上にKubeVirtとCDIの両方をエアギャップインストールするには、21.9項 「KubeVirtとCDIのインストール」に従ってください。

パート III ハウツーガイド

ハウツーガイドとベストプラクティス

  • 19 K3s上のMetalLB (L2を使用)
  • MetalLBは、標準のルーティングプロトコルを使用する、ベアメタルKubernetesクラスタ用のロードバランサの実装です。

  • 20 Kubernetes APIサーバの前面のMetalLB
  • このガイドでは、MetalLBサービスを使用して、3つのコントロールプレーンノードを持つHA K3sクラスタ上でK3s APIを外部に公開する方法を示します。これを実現するために、LoadBalancerタイプのKubernetes ServiceとEndpointsを手動で作成します。Endpointsは、クラスタで使用可能なすべてのコントロールプレーンノードのIPを保持します。Endpointsをクラスタで発生するイベント(ノードの追加/削除やノードのオフライン化)と継続的に同期するためにEndpoint Copier Operatorがデプロイされます。Operatorはデフォルトのku…

  • 21 Edge Image Builderを使用したエアギャップデプロイメント
  • このガイドでは、Edge Image Builder(EIB) (第9章 「Edge Image Builder」)を使用し、完全にエアギャップされた環境で複数のSUSE EdgeコンポーネントをSLE Micro 5.5上にデプロイする方法を示します。これにより、EIBで作成したCustomized, Ready to Boot (CRB)イメージでブートし、指定したコンポーネントをインターネット接続や手動手順なしにRKE2クラスタまたはK3sクラスタにデプロイできます。この設定は、デプロイメントに必要なアーティファクトをすべてOSイメージにプリベイクし、ブート後すぐに利用できるようにしたい…

19 K3s上のMetalLB (L2を使用)

MetalLBは、標準のルーティングプロトコルを使用する、ベアメタルKubernetesクラスタ用のロードバランサの実装です。

このガイドでは、MetalLBをレイヤ2モードでデプロイする方法について説明します。

19.1 この方法を使用する理由

レイヤ2モードでは、1つのノードがローカルネットワークにサービスをアドバタイズする責任を負います。ネットワークの視点からは、マシンのネットワークインタフェースに複数のIPアドレスが割り当てられているように見えます。

レイヤ2モードの主な利点は、その汎用性です。あらゆるEthernetネットワークで動作し、特別なハードウェアも、高価なルータも必要ありません。

19.2 K3s上のMetalLB (L2を使用)

このクイックスタートではL2モードを使用するので、特別なネットワーク機器は必要なく、ネットワーク範囲内の空きIPをいくつか用意するだけで十分です。DHCPプール外のIPであれば割り当てられることがないため理想的です。

この例では、DHCPプールは、192.168.122.0/24のネットワークに対して192.168.122.100-192.168.122.200です(IPは3つです。余分なIPの理由については、「TraefikとMetalLB」 (19.3.3項 「TraefikとMetalLB」)を参照してください)。そのため、この範囲外であれば何でも構いません(ゲートウェイと、すでに実行されている可能性のある他のホストは除きます)。

19.3 前提条件

  • MetalLBがデプロイされるK3sクラスタ。

警告
警告

K3sには、Klipperという名前の独自のサービスロードバランサが付属しています。MetalLBを実行するにはKlipperを無効にする必要があります。Klipperを無効にするには、--disable=servicelbフラグを使用してK3sをインストールする必要があります。

  • Helm

  • ネットワーク範囲内の数個の空きIP (ここでは192.168.122.10-192.168.122.12)

19.3.1 デプロイメント

MetalLBはHelm (および他の方法)を利用するため、次のようになります。

helm repo add metallb https://metallb.github.io/metallb
helm install --create-namespace -n metallb-system metallb metallb/metallb

while ! kubectl wait --for condition=ready -n metallb-system $(kubectl get\
 pods -n metallb-system -l app.kubernetes.io/component=controller -o name)\
 --timeout=10s; do
 sleep 2
done

19.3.2 設定

この時点でインストールは完了しています。次に、サンプル値を使用して設定を行います。

cat <<-EOF | kubectl apply -f -
apiVersion: metallb.io/v1beta1
kind: IPAddressPool
metadata:
  name: ip-pool
  namespace: metallb-system
spec:
  addresses:
  - 192.168.122.10/32
  - 192.168.122.11/32
  - 192.168.122.12/32
EOF
cat <<-EOF | kubectl apply -f -
apiVersion: metallb.io/v1beta1
kind: L2Advertisement
metadata:
  name: ip-pool-l2-adv
  namespace: metallb-system
spec:
  ipAddressPools:
  - ip-pool
EOF

これで、MetalLBを使用する準備ができました。L2モードでは、次のようにさまざまな設定をカスタマイズできます。

また、BGPについても、さらに多くのカスタマイズが可能です。

19.3.3 TraefikとMetalLB

Traefikは、デフォルトではK3sとともにデプロイされます(--disable=traefikを使用してK3sを無効にできます)。また、デフォルトでLoadBalancerとして公開されます(Klipperで使用するため)。ただし、Klipperを無効にする必要があるため、Ingress用TraefikサービスはLoadBalancerタイプのままです。そのため、MetalLBをデプロイした時点では、最初のIPは自動的にTraefik Ingressに割り当てられます。

# Before deploying MetalLB
kubectl get svc -n kube-system traefik
NAME      TYPE           CLUSTER-IP     EXTERNAL-IP   PORT(S)                      AGE
traefik   LoadBalancer   10.43.44.113   <pending>     80:31093/TCP,443:32095/TCP   28s
# After deploying MetalLB
kubectl get svc -n kube-system traefik
NAME      TYPE           CLUSTER-IP     EXTERNAL-IP      PORT(S)                      AGE
traefik   LoadBalancer   10.43.44.113   192.168.122.10   80:31093/TCP,443:32095/TCP   3m10s

これは、このプロセスの後半(19.4項 「IngressとMetalLB」)で適用されます。

19.3.4 使用法

デプロイメントの例を作成してみましょう。

cat <<- EOF | kubectl apply -f -
---
apiVersion: v1
kind: Namespace
metadata:
  name: hello-kubernetes
---
apiVersion: v1
kind: ServiceAccount
metadata:
  name: hello-kubernetes
  namespace: hello-kubernetes
  labels:
    app.kubernetes.io/name: hello-kubernetes
---
apiVersion: apps/v1
kind: Deployment
metadata:
  name: hello-kubernetes
  namespace: hello-kubernetes
  labels:
    app.kubernetes.io/name: hello-kubernetes
spec:
  replicas: 2
  selector:
    matchLabels:
      app.kubernetes.io/name: hello-kubernetes
  template:
    metadata:
      labels:
        app.kubernetes.io/name: hello-kubernetes
    spec:
      serviceAccountName: hello-kubernetes
      containers:
        - name: hello-kubernetes
          image: "paulbouwer/hello-kubernetes:1.10"
          imagePullPolicy: IfNotPresent
          ports:
            - name: http
              containerPort: 8080
              protocol: TCP
          livenessProbe:
            httpGet:
              path: /
              port: http
          readinessProbe:
            httpGet:
              path: /
              port: http
          env:
          - name: HANDLER_PATH_PREFIX
            value: ""
          - name: RENDER_PATH_PREFIX
            value: ""
          - name: KUBERNETES_NAMESPACE
            valueFrom:
              fieldRef:
                fieldPath: metadata.namespace
          - name: KUBERNETES_POD_NAME
            valueFrom:
              fieldRef:
                fieldPath: metadata.name
          - name: KUBERNETES_NODE_NAME
            valueFrom:
              fieldRef:
                fieldPath: spec.nodeName
          - name: CONTAINER_IMAGE
            value: "paulbouwer/hello-kubernetes:1.10"
EOF

最終的にサービスは次のようになります。

cat <<- EOF | kubectl apply -f -
apiVersion: v1
kind: Service
metadata:
  name: hello-kubernetes
  namespace: hello-kubernetes
  labels:
    app.kubernetes.io/name: hello-kubernetes
spec:
  type: LoadBalancer
  ports:
    - port: 80
      targetPort: http
      protocol: TCP
      name: http
  selector:
    app.kubernetes.io/name: hello-kubernetes
EOF

実際の動作を見てみましょう。

kubectl get svc -n hello-kubernetes
NAME               TYPE           CLUSTER-IP     EXTERNAL-IP      PORT(S)        AGE
hello-kubernetes   LoadBalancer   10.43.127.75   192.168.122.11   80:31461/TCP   8s

curl http://192.168.122.11
<!DOCTYPE html>
<html>
<head>
    <title>Hello Kubernetes!</title>
    <link rel="stylesheet" type="text/css" href="/css/main.css">
    <link rel="stylesheet" href="https://fonts.googleapis.com/css?family=Ubuntu:300" >
</head>
<body>

  <div class="main">
    <img src="/images/kubernetes.png"/>
    <div class="content">
      <div id="message">
  Hello world!
</div>
<div id="info">
  <table>
    <tr>
      <th>namespace:</th>
      <td>hello-kubernetes</td>
    </tr>
    <tr>
      <th>pod:</th>
      <td>hello-kubernetes-7c8575c848-2c6ps</td>
    </tr>
    <tr>
      <th>node:</th>
      <td>allinone (Linux 5.14.21-150400.24.46-default)</td>
    </tr>
  </table>
</div>
<div id="footer">
  paulbouwer/hello-kubernetes:1.10 (linux/amd64)
</div>
    </div>
  </div>

</body>
</html>

19.4 IngressとMetalLB

TraefikはすでにIngressコントローラとして機能しているため、次のようなIngressオブジェクトを介してHTTP/HTTPSトラフィックを公開できます。

IP=$(kubectl get svc -n kube-system traefik -o jsonpath="{.status.loadBalancer.ingress[0].ip}")
cat <<- EOF | kubectl apply -f -
apiVersion: networking.k8s.io/v1
kind: Ingress
metadata:
  name: hello-kubernetes-ingress
  namespace: hello-kubernetes
spec:
  rules:
  - host: hellok3s.${IP}.sslip.io
    http:
      paths:
        - path: "/"
          pathType: Prefix
          backend:
            service:
              name: hello-kubernetes
              port:
                name: http
EOF

これにより、次のような結果が返されます。

curl http://hellok3s.${IP}.sslip.io
<!DOCTYPE html>
<html>
<head>
    <title>Hello Kubernetes!</title>
    <link rel="stylesheet" type="text/css" href="/css/main.css">
    <link rel="stylesheet" href="https://fonts.googleapis.com/css?family=Ubuntu:300" >
</head>
<body>

  <div class="main">
    <img src="/images/kubernetes.png"/>
    <div class="content">
      <div id="message">
  Hello world!
</div>
<div id="info">
  <table>
    <tr>
      <th>namespace:</th>
      <td>hello-kubernetes</td>
    </tr>
    <tr>
      <th>pod:</th>
      <td>hello-kubernetes-7c8575c848-fvqm2</td>
    </tr>
    <tr>
      <th>node:</th>
      <td>allinone (Linux 5.14.21-150400.24.46-default)</td>
    </tr>
  </table>
</div>
<div id="footer">
  paulbouwer/hello-kubernetes:1.10 (linux/amd64)
</div>
    </div>
  </div>

</body>
</html>

また、MetalLB が正しく動作していることを確認するため、arpingを次のように使用できます:

arping hellok3s.${IP}.sslip.io

予期される結果は次のとおりです。

ARPING 192.168.64.210
60 bytes from 92:12:36:00:d3:58 (192.168.64.210): index=0 time=1.169 msec
60 bytes from 92:12:36:00:d3:58 (192.168.64.210): index=1 time=2.992 msec
60 bytes from 92:12:36:00:d3:58 (192.168.64.210): index=2 time=2.884 msec

上記の例では、トラフィックは次のように流れます。

  1. hellok3s.${IP}.sslip.ioが実際のIPに解決されます。

  2. 続いて、トラフィックがmetallb-speaker Podによって処理されます。

  3. metallb-speakerがトラフィックをtraefikコントローラにリダイレクトします。

  4. 最後に、Traefikが要求をhello-kubernetesサービスに転送します。

20 Kubernetes APIサーバの前面のMetalLB

このガイドでは、MetalLBサービスを使用して、3つのコントロールプレーンノードを持つHA K3sクラスタ上でK3s APIを外部に公開する方法を示します。これを実現するために、LoadBalancerタイプのKubernetes ServiceとEndpointsを手動で作成します。Endpointsは、クラスタで使用可能なすべてのコントロールプレーンノードのIPを保持します。Endpointsをクラスタで発生するイベント(ノードの追加/削除やノードのオフライン化)と継続的に同期するためにEndpoint Copier Operatorがデプロイされます。Operatorはデフォルトのkubernetes Endpointで発生するイベントを監視し、管理対象を自動的に更新して同期を維持します。管理対象のServiceはLoadBalancerタイプであるため、MetalLBは静的なExternalIPを割り当てます。このExternalIPはAPI Serverとの通信に使用されます。

20.1 前提条件

  • K3sをデプロイするための3つのホスト。

    • ホスト名は各ホストで違う名前にしてください。

    • テストの場合は仮想マシンを使用できます。

  • ネットワーク内で2つ以上のIPが使用可能(Traefik用に1つ、管理対象サービス用に1つ)。

  • Helm

20.2 K3sのインストール

注記
注記

新しいクラスタが必要なく、既存のクラスタを使用する場合は、この手順をスキップして次の手順に進んでください。

まず、ネットワーク内の空きIPを、後で管理対象のServiceのExternalIPで使用できるように予約する必要があります。

最初のホストにSSHで接続して、次のようにクラスタモードでK3sをインストールします。

# Export the free IP mentioned above
export VIP_SERVICE_IP=<ip>
export INSTALL_K3S_SKIP_START=false

curl -sfL https://get.k3s.io | INSTALL_K3S_EXEC="server --cluster-init \
 --disable=servicelb --write-kubeconfig-mode=644 --tls-san=${VIP_SERVICE_IP} \
 --tls-san=https://${VIP_SERVICE_IP}.sslip.io" K3S_TOKEN=foobar sh -
注記
注記

必ず、k3s serverコマンドで--disable=servicelbフラグを指定してください。

重要
重要

これ以降、コマンドはローカルマシンで実行する必要があります。

APIサーバに外部からアクセスするには、K3s VMのIPを使用します。

# Replace <node-ip> with the actual IP of the machine
export NODE_IP=<node-ip>
scp ${NODE_IP}:/etc/rancher/k3s/k3s.yaml ~/.kube/config && sed \
 -i '' "s/127.0.0.1/${NODE_IP}/g" ~/.kube/config && chmod 600 ~/.kube/config

20.3 既存のK3sクラスタの設定

注記
注記

この手順は、既存のK3sクラスタを使用する 場合にのみ有効です。

既存のK3sクラスタを使用するには、servicelb LBを無効にし、tls-sanフラグも変更する必要があります。

K3sフラグを変更するには、クラスタのすべてのVMで/etc/systemd/system/k3s.serviceを変更する必要があります。

フラグはExecStartに挿入する必要があります。例:

# Replace the <vip-service-ip> with the actual ip
ExecStart=/usr/local/bin/k3s \
    server \
        '--cluster-init' \
        '--write-kubeconfig-mode=644' \
        '--disable=servicelb' \
        '--tls-san=<vip-service-ip>' \
        '--tls-san=https://<vip-service-ip>.sslip.io' \

次に、次のコマンドを実行して、K3sに新しい設定をロードする必要があります。

systemctl daemon-reload
systemctl restart k3s

20.4 MetalLBのインストール

MetalLBをデプロイするには、「K3s上のMetalLB」のガイドを使用できます。

メモ: ip-pool IPAddressPoolのIPアドレスが、以前にLoadBalancerサービスに対して選択したIPアドレスと重複していないことを確認してください。

管理対象サービスにのみ使用するIpAddressPoolを別途作成します。

# Export the VIP_SERVICE_IP on the local machine
# Replace with the actual IP
export VIP_SERVICE_IP=<ip>

cat <<-EOF | kubectl apply -f -
apiVersion: metallb.io/v1beta1
kind: IPAddressPool
metadata:
  name: kubernetes-vip-ip-pool
  namespace: metallb-system
spec:
  addresses:
  - ${VIP_SERVICE_IP}/32
  serviceAllocation:
    priority: 100
    namespaces:
      - default
EOF
cat <<-EOF | kubectl apply -f -
apiVersion: metallb.io/v1beta1
kind: L2Advertisement
metadata:
  name: ip-pool-l2-adv
  namespace: metallb-system
spec:
  ipAddressPools:
  - ip-pool
  - kubernetes-vip-ip-pool
EOF

20.5 Endpoint Copier Operatorのインストール

helm repo add endpoint-copier-operator \
 https://suse-edge.github.io/endpoint-copier-operator

helm install --create-namespace -n endpoint-copier-operator \
 endpoint-copier-operator endpoint-copier-operator/endpoint-copier-operator

上記のコマンドは、クラスタに3つの異なるリソースをデプロイします。

  1. 2つのレプリカを持つendpoint-copier-operatorオペレータのデプロイメント。一方がリーダーとなり、他方は必要に応じてリーダーの役割を引き継ぎます。

  2. defaultネームスペース内のkubernetes-vipという名前のKubernetesサービス。これはkubernetesサービスのコピーですが、LoadBalancerタイプです。

  3. defaultネームスペース内のkubernetes-vipという名前のEndpointリソース。これはkubernetes Endpointのコピーです。

kubernetes-vipサービスのIPアドレスが正しいことを確認します。

kubectl get service kubernetes-vip -n default \
 -o=jsonpath='{.status.loadBalancer.ingress[0].ip}'

defaultネームスペースのkubernetes-vipおよびkubernetes のEndpointsリソースが同じIPを指していることを確認します。

kubectl get endpoints kubernetes kubernetes-vip

すべて問題なければ、最後にKubeconfigVIP_SERVICE_IPを使用します。

sed -i '' "s/${NODE_IP}/${VIP_SERVICE_IP}/g" ~/.kube/config

これ以降、kubectlはすべてkubernetes-vipサービスを経由するようになります。

20.6 コントロールプレーンノードの追加

プロセス全体を監視するため、端末タブを2つ以上開くことができます。

最初の端末:

watch kubectl get nodes

2つ目の端末:

watch kubectl get endpoints

次に、以下のコマンドを2つ目のノードと3つ目のノードで実行します。

# Export the VIP_SERVICE_IP in the VM
# Replace with the actual IP
export VIP_SERVICE_IP=<ip>
export INSTALL_K3S_SKIP_START=false

curl -sfL https://get.k3s.io | INSTALL_K3S_EXEC="server \
 --server https://${VIP_SERVICE_IP}:6443 --disable=servicelb \
 --write-kubeconfig-mode=644" K3S_TOKEN=foobar sh -

21 Edge Image Builderを使用したエアギャップデプロイメント

21.1 概要

このガイドでは、Edge Image Builder(EIB) (第9章 「Edge Image Builder)を使用し、完全にエアギャップされた環境で複数のSUSE EdgeコンポーネントをSLE Micro 5.5上にデプロイする方法を示します。これにより、EIBで作成したCustomized, Ready to Boot (CRB)イメージでブートし、指定したコンポーネントをインターネット接続や手動手順なしにRKE2クラスタまたはK3sクラスタにデプロイできます。この設定は、デプロイメントに必要なアーティファクトをすべてOSイメージにプリベイクし、ブート後すぐに利用できるようにしたいお客様にとって非常に便利です。

ここでは、以下のエアギャップインストールについて説明します。

警告
警告

EIBは、指定したHelmチャートとKubernetesマニフェストで参照されているイメージをすべて解析し、事前にダウンロードします。ただし、その一部がコンテナイメージをプルし、そのイメージに基づいて実行時にKubernetesリソースを作成しようとする場合があります。このような場合、完全なエアギャップ環境を設定するには、必要なイメージを定義ファイルに手動で指定する必要があります。

21.2 前提条件

このガイドに従って操作を進める場合、すでにEIB (第9章 「Edge Image Builder)に精通していることを想定しています。まだEIBに精通していない場合は、クイックスタートガイド(第3章 「Edge Image Builderを使用したスタンドアロンクラスタ)に従って、以下の演習で示されている概念の理解を深めてください。

21.3 Libvirtのネットワーク設定

注記
注記

エアギャップデプロイメントのデモを示すため、このガイドはシミュレートされたエアギャップlibvirtネットワークを使用して実施し、それに合わせて以下の設定を調整します。ご自身のデプロイメントでは、host1.local.yamlの設定の変更が必要になる場合があります。これについては、次の手順で説明します。

同じlibvirtネットワーク設定を使用する場合は、このまま読み進めてください。そうでない場合は、21.4項 「ベースディレクトリの設定」までスキップしてください。

DHCPのIPアドレス範囲192.168.100.2/24で、分離されたネットワーク設定を作成してみましょう。

cat << EOF > isolatednetwork.xml
<network>
  <name>isolatednetwork</name>
  <bridge name='virbr1' stp='on' delay='0'/>
  <ip address='192.168.100.1' netmask='255.255.255.0'>
    <dhcp>
      <range start='192.168.100.2' end='192.168.100.254'/>
    </dhcp>
  </ip>
</network>
EOF

あとはネットワークを作成して起動するだけです。

virsh net-define isolatednetwork.xml
virsh net-start isolatednetwork

21.4 ベースディレクトリの設定

ベースディレクトリの設定は、各種のコンポーネントすべてで同じであるため、ここで設定します。

まず、必要なサブディレクトリを作成します。

export CONFIG_DIR=$HOME/config
mkdir -p $CONFIG_DIR/base-images
mkdir -p $CONFIG_DIR/network
mkdir -p $CONFIG_DIR/kubernetes/helm/values

必ず、使用する予定のゴールデンイメージをbase-imagesディレクトリに追加してください。このガイドでは、こちらにあるセルフインストールISOに焦点を当てて説明します。

ダウンロードしたイメージをコピーしましょう。

cp SLE-Micro.x86_64-5.5.0-Default-SelfInstall-GM2.install.iso $CONFIG_DIR/base-images/slemicro.iso
注記
注記

EIBは、ゴールデンイメージの入力を変更することはありません。

目的のネットワーク設定を含むファイルを作成しましょう。

cat << EOF > $CONFIG_DIR/network/host1.local.yaml
routes:
  config:
  - destination: 0.0.0.0/0
    metric: 100
    next-hop-address: 192.168.100.1
    next-hop-interface: eth0
    table-id: 254
  - destination: 192.168.100.0/24
    metric: 100
    next-hop-address:
    next-hop-interface: eth0
    table-id: 254
dns-resolver:
  config:
    server:
    - 192.168.100.1
    - 8.8.8.8
interfaces:
- name: eth0
  type: ethernet
  state: up
  mac-address: 34:8A:B1:4B:16:E7
  ipv4:
    address:
    - ip: 192.168.100.50
      prefix-length: 24
    dhcp: false
    enabled: true
  ipv6:
    enabled: false
EOF

この設定により、プロビジョニングされたシステムに以下が確実に存在するようになります(指定されたMACアドレスを使用)。

  • 静的IPアドレスを持つEthernetインタフェース

  • ルーティング

  • DNS

  • ホスト名(host1.local)

結果のファイル構造は次のようになります。

├── kubernetes/
│   └── helm/
│       └── values/
├── base-images/
│   └── slemicro.iso
└── network/
    └── host1.local.yaml

21.5 ベース定義ファイル

Edge Image Builderでは、定義ファイルを使用してSLE Microイメージを変更します。定義ファイルには、設定可能なオプションの大部分が含まれています。これらのオプションの多くは、異なるコンポーネントのセクションで繰り返し使用されるため、ここで一覧にして説明します。

ヒント
ヒント

定義ファイルのカスタマイズオプションの全リストについては、アップストリームドキュメントを参照してください。

すべての定義ファイルに存在する次のフィールドを見てみましょう。

apiVersion: 1.0
image:
  imageType: iso
  arch: x86_64
  baseImage: slemicro.iso
  outputImageName: eib-image.iso
operatingSystem:
  users:
    - username: root
      encryptedPassword: $6$jHugJNNd3HElGsUZ$eodjVe4te5ps44SVcWshdfWizrP.xAyd71CVEXazBJ/.v799/WRCBXxfYmunlBO2yp1hm/zb4r8EmnrrNCF.P/
kubernetes:
  version: v1.28.9+rke2r1
embeddedArtifactRegistry:
  images:
    - ...

imageセクションは必須であり、入力イメージ、そのアーキテクチャとタイプ、および出力イメージの名前を指定します。

operatingSystemセクションはオプションであり、プロビジョニングされたシステムにroot/eibのユーザ名/パスワードでログインできるようにするための設定が含まれます。

kubernetesセクションはオプションであり、 Kubernetesのタイプとバージョンを定義します。デフォルトではKubernetes 1.28.9とRKE2を使用します。代わりにK3sが必要な場合は、kubernetes.version: v1.28.9+k3s1を使用します。kubernetes.nodesフィールドで明示的に設定しない限り、このガイドでブートストラップするすべてのクラスタはシングルノードクラスタになります。

embeddedArtifactRegistryセクションには、実行時に特定のコンポーネントでのみ参照されてプルされるイメージがすべて含まれます。

21.6 Rancherのインストール

注記
注記

デモで示すRancher (第4章 「Rancher)のデプロイメントは、デモのために非常にスリム化されています。実際のデプロイメントでは、設定に応じて追加のアーティファクトが必要な場合があります。

Rancher v2.8.4リリースアセットには、エアギャップインストールに必要なすべてのイメージを一覧にしたrancher-images.txtファイルが含まれています。

コンテナイメージは合計で約602個あります。つまり、生成されるCRBイメージは約28GB以上になります。ここでのRancherのインストールでは、そのリストを最小の動作設定に減らします。そこから、自身のデプロイメントに必要なイメージを追加し直すことができます。

定義ファイルを作成し、必要最小限のイメージリストを含めます。

apiVersion: 1.0
image:
  imageType: iso
  arch: x86_64
  baseImage: slemicro.iso
  outputImageName: eib-image.iso
operatingSystem:
  users:
    - username: root
      encryptedPassword: $6$jHugJNNd3HElGsUZ$eodjVe4te5ps44SVcWshdfWizrP.xAyd71CVEXazBJ/.v799/WRCBXxfYmunlBO2yp1hm/zb4r8EmnrrNCF.P/
kubernetes:
  version: v1.28.9+rke2r1
  network:
    apiVIP: 192.168.100.151
  manifests:
    urls:
    - https://github.com/cert-manager/cert-manager/releases/download/v1.14.2/cert-manager.crds.yaml
  helm:
    charts:
      - name: rancher
        version: 2.8.4
        repositoryName: rancher-prime
        valuesFile: rancher-values.yaml
        targetNamespace: cattle-system
        createNamespace: true
        installationNamespace: kube-system
      - name: cert-manager
        installationNamespace: kube-system
        createNamespace: true
        repositoryName: jetstack
        targetNamespace: cert-manager
        version: 1.14.2
    repositories:
      - name: jetstack
        url: https://charts.jetstack.io
      - name: rancher-prime
        url:  https://charts.rancher.com/server-charts/prime
embeddedArtifactRegistry:
  images:
    - name: registry.rancher.com/rancher/backup-restore-operator:v4.0.2
    - name: registry.rancher.com/rancher/calico-cni:v3.27.0-rancher1
    - name: registry.rancher.com/rancher/cis-operator:v1.0.13
    - name: registry.rancher.com/rancher/coreos-kube-state-metrics:v1.9.7
    - name: registry.rancher.com/rancher/coreos-prometheus-config-reloader:v0.38.1
    - name: registry.rancher.com/rancher/coreos-prometheus-operator:v0.38.1
    - name: registry.rancher.com/rancher/flannel-cni:v0.3.0-rancher9
    - name: registry.rancher.com/rancher/fleet-agent:v0.9.4
    - name: registry.rancher.com/rancher/fleet:v0.9.4
    - name: registry.rancher.com/rancher/gitjob:v0.9.7
    - name: registry.rancher.com/rancher/grafana-grafana:7.1.5
    - name: registry.rancher.com/rancher/hardened-addon-resizer:1.8.20-build20240410
    - name: registry.rancher.com/rancher/hardened-calico:v3.27.3-build20240423
    - name: registry.rancher.com/rancher/hardened-cluster-autoscaler:v1.8.10-build20240124
    - name: registry.rancher.com/rancher/hardened-cni-plugins:v1.4.1-build20240325
    - name: registry.rancher.com/rancher/hardened-coredns:v1.11.1-build20240305
    - name: registry.rancher.com/rancher/hardened-dns-node-cache:1.22.28-build20240125
    - name: registry.rancher.com/rancher/hardened-etcd:v3.5.9-k3s1-build20240418
    - name: registry.rancher.com/rancher/hardened-flannel:v0.25.1-build20240423
    - name: registry.rancher.com/rancher/hardened-k8s-metrics-server:v0.7.1-build20240401
    - name: registry.rancher.com/rancher/hardened-kubernetes:v1.28.9-rke2r1-build20240416
    - name: registry.rancher.com/rancher/hardened-multus-cni:v4.0.2-build20240208
    - name: registry.rancher.com/rancher/hardened-node-feature-discovery:v0.14.1-build20230926
    - name: registry.rancher.com/rancher/hardened-whereabouts:v0.6.3-build20240208
    - name: registry.rancher.com/rancher/helm-project-operator:v0.2.1
    - name: registry.rancher.com/rancher/istio-kubectl:1.5.10
    - name: registry.rancher.com/rancher/jimmidyson-configmap-reload:v0.3.0
    - name: registry.rancher.com/rancher/k3s-upgrade:v1.28.9-k3s1
    - name: registry.rancher.com/rancher/klipper-helm:v0.8.3-build20240228
    - name: registry.rancher.com/rancher/klipper-lb:v0.4.7
    - name: registry.rancher.com/rancher/kube-api-auth:v0.2.1
    - name: registry.rancher.com/rancher/kubectl:v1.28.7
    - name: registry.rancher.com/rancher/library-nginx:1.19.2-alpine
    - name: registry.rancher.com/rancher/local-path-provisioner:v0.0.26
    - name: registry.rancher.com/rancher/machine:v0.15.0-rancher112
    - name: registry.rancher.com/rancher/mirrored-cluster-api-controller:v1.4.4
    - name: registry.rancher.com/rancher/nginx-ingress-controller:nginx-1.9.6-rancher1
    - name: registry.rancher.com/rancher/pause:3.6
    - name: registry.rancher.com/rancher/prom-alertmanager:v0.21.0
    - name: registry.rancher.com/rancher/prom-node-exporter:v1.0.1
    - name: registry.rancher.com/rancher/prom-prometheus:v2.18.2
    - name: registry.rancher.com/rancher/prometheus-auth:v0.2.2
    - name: registry.rancher.com/rancher/prometheus-federator:v0.3.4
    - name: registry.rancher.com/rancher/pushprox-client:v0.1.0-rancher2-client
    - name: registry.rancher.com/rancher/pushprox-proxy:v0.1.0-rancher2-proxy
    - name: registry.rancher.com/rancher/rancher-agent:v2.8.4
    - name: registry.rancher.com/rancher/rancher-csp-adapter:v3.0.1
    - name: registry.rancher.com/rancher/rancher-webhook:v0.4.5
    - name: registry.rancher.com/rancher/rancher:v2.8.4
    - name: registry.rancher.com/rancher/rke-tools:v0.1.96
    - name: registry.rancher.com/rancher/rke2-cloud-provider:v1.29.3-build20240412
    - name: registry.rancher.com/rancher/rke2-runtime:v1.28.9-rke2r1
    - name: registry.rancher.com/rancher/rke2-upgrade:v1.28.9-rke2r1
    - name: registry.rancher.com/rancher/security-scan:v0.2.15
    - name: registry.rancher.com/rancher/shell:v0.1.24
    - name: registry.rancher.com/rancher/system-agent-installer-k3s:v1.28.9-k3s1
    - name: registry.rancher.com/rancher/system-agent-installer-rke2:v1.28.9-rke2r1
    - name: registry.rancher.com/rancher/system-agent:v0.3.6-suc
    - name: registry.rancher.com/rancher/system-upgrade-controller:v0.13.1
    - name: registry.rancher.com/rancher/ui-plugin-catalog:1.3.0
    - name: registry.rancher.com/rancher/ui-plugin-operator:v0.1.1
    - name: registry.rancher.com/rancher/webhook-receiver:v0.2.5
    - name: registry.rancher.com/rancher/kubectl:v1.20.2

602個のコンテナイメージがすべて含まれるリストと比較すると、この縮小バージョンには62個しか含まれていません。その結果、新しいCRBイメージは約7GBほどになります。

RancherのHelm値も作成する必要があります。

cat << EOF > $CONFIG_DIR/kubernetes/helm/values/rancher-values.yaml
hostname: 192.168.100.50.sslip.io
replicas: 1
bootstrapPassword: "adminadminadmin"
systemDefaultRegistry: registry.rancher.com
useBundledSystemChart: true
EOF
警告
警告

systemDefaultRegistryregistry.rancher.comに設定することで、Rancherは、ブート時にCRBイメージ内で起動される組み込みのアーティファクトレジストリ内でイメージを自動的に検索できます。このフィールドを省略すると、ノードでコンテナイメージを見つけられない場合があります。

イメージを構築してみましょう。

podman run --rm -it --privileged -v $CONFIG_DIR:/eib \
registry.suse.com/edge/edge-image-builder:1.0.2 \
build --definition-file eib-iso-definition.yaml

出力は次のようになります。

Generating image customization components...
Identifier ................... [SUCCESS]
Custom Files ................. [SKIPPED]
Time ......................... [SKIPPED]
Network ...................... [SUCCESS]
Groups ....................... [SKIPPED]
Users ........................ [SUCCESS]
Proxy ........................ [SKIPPED]
Rpm .......................... [SKIPPED]
Systemd ...................... [SKIPPED]
Elemental .................... [SKIPPED]
Suma ......................... [SKIPPED]
Downloading file: dl-manifest-1.yaml 100% (437/437 kB, 17 MB/s)
Populating Embedded Artifact Registry... 100% (69/69, 26 it/min)
Embedded Artifact Registry ... [SUCCESS]
Keymap ....................... [SUCCESS]
Configuring Kubernetes component...
The Kubernetes CNI is not explicitly set, defaulting to 'cilium'.
Downloading file: rke2_installer.sh
Downloading file: rke2-images-core.linux-amd64.tar.zst 100% (780/780 MB, 115 MB/s)
Downloading file: rke2-images-cilium.linux-amd64.tar.zst 100% (367/367 MB, 108 MB/s)
Downloading file: rke2.linux-amd64.tar.gz 100% (34/34 MB, 117 MB/s)
Downloading file: sha256sum-amd64.txt 100% (3.9/3.9 kB, 34 MB/s)
Downloading file: dl-manifest-1.yaml 100% (437/437 kB, 106 MB/s)
Kubernetes ................... [SUCCESS]
Certificates ................. [SKIPPED]
Building ISO image...
Kernel Params ................ [SKIPPED]
Image build complete!

構築したイメージを使用するノードがプロビジョニングされたら、Rancherのインストールを確認できます。

/var/lib/rancher/rke2/bin/kubectl get all -A --kubeconfig /etc/rancher/rke2/rke2.yaml

出力は次のようになり、すべてが正常にデプロイされていることがわかります。

NAMESPACE                         NAME                                                        READY   STATUS      RESTARTS   AGE
cattle-fleet-local-system         pod/fleet-agent-68f4d5d5f7-tdlk7                            1/1     Running     0          34s
cattle-fleet-system               pod/fleet-controller-85564cc978-pbtvk                       1/1     Running     0          5m51s
cattle-fleet-system               pod/gitjob-9dc58fb5b-7cwsw                                  1/1     Running     0          5m51s
cattle-provisioning-capi-system   pod/capi-controller-manager-5c57b4b8f7-wlp5k                1/1     Running     0          4m52s
cattle-system                     pod/helm-operation-4fk5c                                    0/2     Completed   0          37s
cattle-system                     pod/helm-operation-6zgbq                                    0/2     Completed   0          4m54s
cattle-system                     pod/helm-operation-cjds5                                    0/2     Completed   0          5m37s
cattle-system                     pod/helm-operation-kt5c2                                    0/2     Completed   0          5m21s
cattle-system                     pod/helm-operation-ppgtw                                    0/2     Completed   0          5m30s
cattle-system                     pod/helm-operation-tvcwk                                    0/2     Completed   0          5m54s
cattle-system                     pod/helm-operation-wpxd4                                    0/2     Completed   0          53s
cattle-system                     pod/rancher-58575f9575-svrg2                                1/1     Running     0          6m34s
cattle-system                     pod/rancher-webhook-5c6556f7ff-vgmkt                        1/1     Running     0          5m19s
cert-manager                      pod/cert-manager-6c69f9f796-fkm8f                           1/1     Running     0          7m14s
cert-manager                      pod/cert-manager-cainjector-584f44558c-wg7p6                1/1     Running     0          7m14s
cert-manager                      pod/cert-manager-webhook-76f9945d6f-lv2nv                   1/1     Running     0          7m14s
endpoint-copier-operator          pod/endpoint-copier-operator-58964b659b-l64dk               1/1     Running     0          7m16s
endpoint-copier-operator          pod/endpoint-copier-operator-58964b659b-z9t9d               1/1     Running     0          7m16s
kube-system                       pod/cilium-fht55                                            1/1     Running     0          7m32s
kube-system                       pod/cilium-operator-558bbf6cfd-gwfwf                        1/1     Running     0          7m32s
kube-system                       pod/cilium-operator-558bbf6cfd-qsxb5                        0/1     Pending     0          7m32s
kube-system                       pod/cloud-controller-manager-host1.local                    1/1     Running     0          7m21s
kube-system                       pod/etcd-host1.local                                        1/1     Running     0          7m8s
kube-system                       pod/helm-install-cert-manager-fvbtt                         0/1     Completed   0          8m12s
kube-system                       pod/helm-install-endpoint-copier-operator-5kkgw             0/1     Completed   0          8m12s
kube-system                       pod/helm-install-metallb-zfphb                              0/1     Completed   0          8m12s
kube-system                       pod/helm-install-rancher-nc4nt                              0/1     Completed   2          8m12s
kube-system                       pod/helm-install-rke2-cilium-7wq87                          0/1     Completed   0          8m12s
kube-system                       pod/helm-install-rke2-coredns-nl4gc                         0/1     Completed   0          8m12s
kube-system                       pod/helm-install-rke2-ingress-nginx-svjqd                   0/1     Completed   0          8m12s
kube-system                       pod/helm-install-rke2-metrics-server-gqgqz                  0/1     Completed   0          8m12s
kube-system                       pod/helm-install-rke2-snapshot-controller-crd-r6b5p         0/1     Completed   0          8m12s
kube-system                       pod/helm-install-rke2-snapshot-controller-ss9v4             0/1     Completed   1          8m12s
kube-system                       pod/helm-install-rke2-snapshot-validation-webhook-vlkpn     0/1     Completed   0          8m12s
kube-system                       pod/kube-apiserver-host1.local                              1/1     Running     0          7m29s
kube-system                       pod/kube-controller-manager-host1.local                     1/1     Running     0          7m30s
kube-system                       pod/kube-proxy-host1.local                                  1/1     Running     0          7m30s
kube-system                       pod/kube-scheduler-host1.local                              1/1     Running     0          7m42s
kube-system                       pod/rke2-coredns-rke2-coredns-6c8d9bb6d-qlwc8               1/1     Running     0          7m31s
kube-system                       pod/rke2-coredns-rke2-coredns-autoscaler-55fb4bbbcf-j5r2z   1/1     Running     0          7m31s
kube-system                       pod/rke2-ingress-nginx-controller-4h2mm                     1/1     Running     0          7m3s
kube-system                       pod/rke2-metrics-server-544c8c66fc-lsrc6                    1/1     Running     0          7m15s
kube-system                       pod/rke2-snapshot-controller-59cc9cd8f4-4wx75               1/1     Running     0          7m14s
kube-system                       pod/rke2-snapshot-validation-webhook-54c5989b65-5kp2x       1/1     Running     0          7m15s
metallb-system                    pod/metallb-controller-5895d8446d-z54lm                     1/1     Running     0          7m15s
metallb-system                    pod/metallb-speaker-fxwgk                                   1/1     Running     0          7m15s

NAMESPACE                         NAME                                              TYPE           CLUSTER-IP      EXTERNAL-IP       PORT(S)
         AGE
cattle-fleet-system               service/gitjob                                    ClusterIP      10.43.30.8      <none>            80/TCP
         5m51s
cattle-provisioning-capi-system   service/capi-webhook-service                      ClusterIP      10.43.7.100     <none>            443/TCP
         4m52s
cattle-system                     service/rancher                                   ClusterIP      10.43.100.229   <none>            80/TCP,443/TCP
         6m34s
cattle-system                     service/rancher-webhook                           ClusterIP      10.43.121.133   <none>            443/TCP
         5m19s
cert-manager                      service/cert-manager                              ClusterIP      10.43.140.65    <none>            9402/TCP
         7m14s
cert-manager                      service/cert-manager-webhook                      ClusterIP      10.43.108.158   <none>            443/TCP
         7m14s
default                           service/kubernetes                                ClusterIP      10.43.0.1       <none>            443/TCP
         8m26s
default                           service/kubernetes-vip                            LoadBalancer   10.43.138.138   192.168.100.151   9345:31006/TCP,6443:31599/TCP   8m21s
kube-system                       service/cilium-agent                              ClusterIP      None            <none>            9964/TCP
         7m32s
kube-system                       service/rke2-coredns-rke2-coredns                 ClusterIP      10.43.0.10      <none>            53/UDP,53/TCP
         7m31s
kube-system                       service/rke2-ingress-nginx-controller-admission   ClusterIP      10.43.157.19    <none>            443/TCP
         7m3s
kube-system                       service/rke2-metrics-server                       ClusterIP      10.43.4.123     <none>            443/TCP
         7m15s
kube-system                       service/rke2-snapshot-validation-webhook          ClusterIP      10.43.91.161    <none>            443/TCP
         7m16s
metallb-system                    service/metallb-webhook-service                   ClusterIP      10.43.71.192    <none>            443/TCP
         7m15s

NAMESPACE        NAME                                           DESIRED   CURRENT   READY   UP-TO-DATE   AVAILABLE   NODE SELECTOR            AGE
kube-system      daemonset.apps/cilium                          1         1         1       1            1           kubernetes.io/os=linux   7m32s
kube-system      daemonset.apps/rke2-ingress-nginx-controller   1         1         1       1            1           kubernetes.io/os=linux   7m3s
metallb-system   daemonset.apps/metallb-speaker                 1         1         1       1            1           kubernetes.io/os=linux   7m15s

NAMESPACE                         NAME                                                   READY   UP-TO-DATE   AVAILABLE   AGE
cattle-fleet-local-system         deployment.apps/fleet-agent                            1/1     1            1           34s
cattle-fleet-system               deployment.apps/fleet-controller                       1/1     1            1           5m51s
cattle-fleet-system               deployment.apps/gitjob                                 1/1     1            1           5m51s
cattle-provisioning-capi-system   deployment.apps/capi-controller-manager                1/1     1            1           4m52s
cattle-system                     deployment.apps/rancher                                1/1     1            1           6m34s
cattle-system                     deployment.apps/rancher-webhook                        1/1     1            1           5m19s
cert-manager                      deployment.apps/cert-manager                           1/1     1            1           7m14s
cert-manager                      deployment.apps/cert-manager-cainjector                1/1     1            1           7m14s
cert-manager                      deployment.apps/cert-manager-webhook                   1/1     1            1           7m14s
endpoint-copier-operator          deployment.apps/endpoint-copier-operator               2/2     2            2           7m16s
kube-system                       deployment.apps/cilium-operator                        1/2     2            1           7m32s
kube-system                       deployment.apps/rke2-coredns-rke2-coredns              1/1     1            1           7m31s
kube-system                       deployment.apps/rke2-coredns-rke2-coredns-autoscaler   1/1     1            1           7m31s
kube-system                       deployment.apps/rke2-metrics-server                    1/1     1            1           7m15s
kube-system                       deployment.apps/rke2-snapshot-controller               1/1     1            1           7m14s
kube-system                       deployment.apps/rke2-snapshot-validation-webhook       1/1     1            1           7m15s
metallb-system                    deployment.apps/metallb-controller                     1/1     1            1           7m15s

NAMESPACE                         NAME                                                              DESIRED   CURRENT   READY   AGE
cattle-fleet-local-system         replicaset.apps/fleet-agent-68f4d5d5f7                            1         1         1       34s
cattle-fleet-system               replicaset.apps/fleet-controller-85564cc978                       1         1         1       5m51s
cattle-fleet-system               replicaset.apps/gitjob-9dc58fb5b                                  1         1         1       5m51s
cattle-provisioning-capi-system   replicaset.apps/capi-controller-manager-5c57b4b8f7                1         1         1       4m52s
cattle-system                     replicaset.apps/rancher-58575f9575                                1         1         1       6m34s
cattle-system                     replicaset.apps/rancher-webhook-5c6556f7ff                        1         1         1       5m19s
cert-manager                      replicaset.apps/cert-manager-6c69f9f796                           1         1         1       7m14s
cert-manager                      replicaset.apps/cert-manager-cainjector-584f44558c                1         1         1       7m14s
cert-manager                      replicaset.apps/cert-manager-webhook-76f9945d6f                   1         1         1       7m14s
endpoint-copier-operator          replicaset.apps/endpoint-copier-operator-58964b659b               2         2         2       7m16s
kube-system                       replicaset.apps/cilium-operator-558bbf6cfd                        2         2         1       7m32s
kube-system                       replicaset.apps/rke2-coredns-rke2-coredns-6c8d9bb6d               1         1         1       7m31s
kube-system                       replicaset.apps/rke2-coredns-rke2-coredns-autoscaler-55fb4bbbcf   1         1         1       7m31s
kube-system                       replicaset.apps/rke2-metrics-server-544c8c66fc                    1         1         1       7m15s
kube-system                       replicaset.apps/rke2-snapshot-controller-59cc9cd8f4               1         1         1       7m14s
kube-system                       replicaset.apps/rke2-snapshot-validation-webhook-54c5989b65       1         1         1       7m15s
metallb-system                    replicaset.apps/metallb-controller-5895d8446d                     1         1         1       7m15s

NAMESPACE     NAME                                                      COMPLETIONS   DURATION   AGE
kube-system   job.batch/helm-install-cert-manager                       1/1           85s        8m21s
kube-system   job.batch/helm-install-endpoint-copier-operator           1/1           59s        8m21s
kube-system   job.batch/helm-install-metallb                            1/1           60s        8m21s
kube-system   job.batch/helm-install-rancher                            1/1           100s       8m21s
kube-system   job.batch/helm-install-rke2-cilium                        1/1           44s        8m18s
kube-system   job.batch/helm-install-rke2-coredns                       1/1           45s        8m18s
kube-system   job.batch/helm-install-rke2-ingress-nginx                 1/1           76s        8m16s
kube-system   job.batch/helm-install-rke2-metrics-server                1/1           60s        8m16s
kube-system   job.batch/helm-install-rke2-snapshot-controller           1/1           61s        8m15s
kube-system   job.batch/helm-install-rke2-snapshot-controller-crd       1/1           60s        8m16s
kube-system   job.batch/helm-install-rke2-snapshot-validation-webhook   1/1           60s        8m14s

そして、https://192.168.100.50.sslip.ioにアクセスし、前に設定したadminadminadminのパスワードでログインすると、Rancher Dashboardが表示されます。

エアギャップRancher

21.7 NeuVectorのインストール

Rancherのインストールとは異なり、NeuVectorのインストールではEIBで特別な処理を行う必要はありません。EIBはNeuVectorに必要なすべてのイメージを自動的にエアギャップ化します。

定義ファイルを作成します。

apiVersion: 1.0
image:
  imageType: iso
  arch: x86_64
  baseImage: slemicro.iso
  outputImageName: eib-image.iso
operatingSystem:
  users:
    - username: root
      encryptedPassword: $6$jHugJNNd3HElGsUZ$eodjVe4te5ps44SVcWshdfWizrP.xAyd71CVEXazBJ/.v799/WRCBXxfYmunlBO2yp1hm/zb4r8EmnrrNCF.P/
kubernetes:
  version: v1.28.9+rke2r1
  helm:
    charts:
      - name: neuvector-crd
        version: 103.0.3+up2.7.6
        repositoryName: rancher-charts
        targetNamespace: neuvector
        createNamespace: true
        installationNamespace: kube-system
        valuesFile: neuvector-values.yaml
      - name: neuvector
        version: 103.0.3+up2.7.6
        repositoryName: rancher-charts
        targetNamespace: neuvector
        createNamespace: true
        installationNamespace: kube-system
        valuesFile: neuvector-values.yaml
    repositories:
      - name: rancher-charts
        url: https://charts.rancher.io/

NeuVector用のHelm値ファイルも作成します。

cat << EOF > $CONFIG_DIR/kubernetes/helm/values/neuvector-values.yaml
controller:
  replicas: 1
manager:
  enabled: false
cve:
  scanner:
    enabled: false
    replicas: 1
k3s:
  enabled: true
crdwebhook:
  enabled: false
EOF

イメージを構築してみましょう。

podman run --rm -it --privileged -v $CONFIG_DIR:/eib \
registry.suse.com/edge/edge-image-builder:1.0.2 \
build --definition-file eib-iso-definition.yaml

出力は次のようになります。

Generating image customization components...
Identifier ................... [SUCCESS]
Custom Files ................. [SKIPPED]
Time ......................... [SKIPPED]
Network ...................... [SUCCESS]
Groups ....................... [SKIPPED]
Users ........................ [SUCCESS]
Proxy ........................ [SKIPPED]
Rpm .......................... [SKIPPED]
Systemd ...................... [SKIPPED]
Elemental .................... [SKIPPED]
Suma ......................... [SKIPPED]
Populating Embedded Artifact Registry... 100% (6/6, 20 it/min)
Embedded Artifact Registry ... [SUCCESS]
Keymap ....................... [SUCCESS]
Configuring Kubernetes component...
The Kubernetes CNI is not explicitly set, defaulting to 'cilium'.
Downloading file: rke2_installer.sh
Kubernetes ................... [SUCCESS]
Certificates ................. [SKIPPED]
Building ISO image...
Kernel Params ................ [SKIPPED]
Image build complete!

構築したイメージを使用するノードがプロビジョニングされたら、NeuVectorのインストールを確認できます。

/var/lib/rancher/rke2/bin/kubectl get all -n neuvector --kubeconfig /etc/rancher/rke2/rke2.yaml

出力は次のようになり、すべてが正常にデプロイされていることがわかります。

NAME                                           READY   STATUS    RESTARTS   AGE
pod/neuvector-controller-pod-bc74745cf-x9fsc   1/1     Running   0          13m
pod/neuvector-enforcer-pod-vzw7t               1/1     Running   0          13m

NAME                                      TYPE        CLUSTER-IP     EXTERNAL-IP   PORT(S)                         AGE
service/neuvector-svc-admission-webhook   ClusterIP   10.43.240.25   <none>        443/TCP                         13m
service/neuvector-svc-controller          ClusterIP   None           <none>        18300/TCP,18301/TCP,18301/UDP   13m

NAME                                    DESIRED   CURRENT   READY   UP-TO-DATE   AVAILABLE   NODE SELECTOR   AGE
daemonset.apps/neuvector-enforcer-pod   1         1         1       1            1           <none>          13m

NAME                                       READY   UP-TO-DATE   AVAILABLE   AGE
deployment.apps/neuvector-controller-pod   1/1     1            1           13m

NAME                                                 DESIRED   CURRENT   READY   AGE
replicaset.apps/neuvector-controller-pod-bc74745cf   1         1         1       13m

NAME                                  SCHEDULE    SUSPEND   ACTIVE   LAST SCHEDULE   AGE
cronjob.batch/neuvector-updater-pod   0 0 * * *   False     0        <none>          13m

21.8 Longhornのインストール

Longhornの公式ドキュメント には、エアギャップインストールに必要なすべてのイメージを一覧にしたlonghorn-images.txtファイルが含まれています。

apiVersion: 1.0
image:
  imageType: iso
  arch: x86_64
  baseImage: slemicro.iso
  outputImageName: eib-image.iso
operatingSystem:
  users:
    - username: root
      encryptedPassword: $6$jHugJNNd3HElGsUZ$eodjVe4te5ps44SVcWshdfWizrP.xAyd71CVEXazBJ/.v799/WRCBXxfYmunlBO2yp1hm/zb4r8EmnrrNCF.P/
kubernetes:
  version: v1.28.9+rke2r1
  helm:
    charts:
      - name: longhorn
        repositoryName: longhorn
        targetNamespace: longhorn-system
        createNamespace: true
        version: 1.6.1
    repositories:
      - name: longhorn
        url: https://charts.longhorn.io
embeddedArtifactRegistry:
  images:
    - name: longhornio/csi-attacher:v4.4.2
    - name: longhornio/csi-provisioner:v3.6.2
    - name: longhornio/csi-resizer:v1.9.2
    - name: longhornio/csi-snapshotter:v6.3.2
    - name: longhornio/csi-node-driver-registrar:v2.9.2
    - name: longhornio/livenessprobe:v2.12.0
    - name: longhornio/backing-image-manager:v1.6.1
    - name: longhornio/longhorn-engine:v1.6.1
    - name: longhornio/longhorn-instance-manager:v1.6.1
    - name: longhornio/longhorn-manager:v1.6.1
    - name: longhornio/longhorn-share-manager:v1.6.1
    - name: longhornio/longhorn-ui:v1.6.1
    - name: longhornio/support-bundle-kit:v0.0.36

イメージを構築してみましょう。

podman run --rm -it --privileged -v $CONFIG_DIR:/eib \
registry.suse.com/edge/edge-image-builder:1.0.2 \
build --definition-file eib-iso-definition.yaml

出力は次のようになります。

Generating image customization components...
Identifier ................... [SUCCESS]
Custom Files ................. [SKIPPED]
Time ......................... [SKIPPED]
Network ...................... [SUCCESS]
Groups ....................... [SKIPPED]
Users ........................ [SUCCESS]
Proxy ........................ [SKIPPED]
Rpm .......................... [SKIPPED]
Systemd ...................... [SKIPPED]
Elemental .................... [SKIPPED]
Suma ......................... [SKIPPED]
Populating Embedded Artifact Registry... 100% (13/13, 20 it/min)
Embedded Artifact Registry ... [SUCCESS]
Keymap ....................... [SUCCESS]
Configuring Kubernetes component...
The Kubernetes CNI is not explicitly set, defaulting to 'cilium'.
Downloading file: rke2_installer.sh
Downloading file: rke2-images-core.linux-amd64.tar.zst 100% (782/782 MB, 108 MB/s)
Downloading file: rke2-images-cilium.linux-amd64.tar.zst 100% (367/367 MB, 104 MB/s)
Downloading file: rke2.linux-amd64.tar.gz 100% (34/34 MB, 108 MB/s)
Downloading file: sha256sum-amd64.txt 100% (3.9/3.9 kB, 7.5 MB/s)
Kubernetes ................... [SUCCESS]
Certificates ................. [SKIPPED]
Building ISO image...
Kernel Params ................ [SKIPPED]
Image build complete!

構築したイメージを使用するノードがプロビジョニングされたら、Longhornのインストールを確認できます。

/var/lib/rancher/rke2/bin/kubectl get all -n longhorn-system --kubeconfig /etc/rancher/rke2/rke2.yaml

出力は次のようになり、すべてが正常にデプロイされていることがわかります。

NAME                                                    READY   STATUS    RESTARTS      AGE
pod/csi-attacher-5c4bfdcf59-9hgvv                       1/1     Running   0             35s
pod/csi-attacher-5c4bfdcf59-dt6jl                       1/1     Running   0             35s
pod/csi-attacher-5c4bfdcf59-swpwq                       1/1     Running   0             35s
pod/csi-provisioner-667796df57-dfrzw                    1/1     Running   0             35s
pod/csi-provisioner-667796df57-tvsrt                    1/1     Running   0             35s
pod/csi-provisioner-667796df57-xszsx                    1/1     Running   0             35s
pod/csi-resizer-694f8f5f64-6khlb                        1/1     Running   0             35s
pod/csi-resizer-694f8f5f64-gnr45                        1/1     Running   0             35s
pod/csi-resizer-694f8f5f64-sbl4k                        1/1     Running   0             35s
pod/csi-snapshotter-959b69d4b-2k4v8                     1/1     Running   0             35s
pod/csi-snapshotter-959b69d4b-9d8wl                     1/1     Running   0             35s
pod/csi-snapshotter-959b69d4b-l2w95                     1/1     Running   0             35s
pod/engine-image-ei-5cefaf2b-cwd8f                      1/1     Running   0             43s
pod/instance-manager-f0d17f96bc92f3cc44787a2a347f6a98   1/1     Running   0             43s
pod/longhorn-csi-plugin-szv7t                           3/3     Running   0             35s
pod/longhorn-driver-deployer-9f4fc86-q8fz2              1/1     Running   0             83s
pod/longhorn-manager-zp66l                              1/1     Running   0             83s
pod/longhorn-ui-5f4b7bbf69-k645d                        1/1     Running   3 (65s ago)   83s
pod/longhorn-ui-5f4b7bbf69-t7xt4                        1/1     Running   3 (62s ago)   83s

NAME                                  TYPE        CLUSTER-IP     EXTERNAL-IP   PORT(S)    AGE
service/longhorn-admission-webhook    ClusterIP   10.43.74.59    <none>        9502/TCP   83s
service/longhorn-backend              ClusterIP   10.43.45.206   <none>        9500/TCP   83s
service/longhorn-conversion-webhook   ClusterIP   10.43.83.108   <none>        9501/TCP   83s
service/longhorn-engine-manager       ClusterIP   None           <none>        <none>     83s
service/longhorn-frontend             ClusterIP   10.43.84.55    <none>        80/TCP     83s
service/longhorn-recovery-backend     ClusterIP   10.43.75.200   <none>        9503/TCP   83s
service/longhorn-replica-manager      ClusterIP   None           <none>        <none>     83s

NAME                                      DESIRED   CURRENT   READY   UP-TO-DATE   AVAILABLE   NODE SELECTOR   AGE
daemonset.apps/engine-image-ei-5cefaf2b   1         1         1       1            1           <none>          43s
daemonset.apps/longhorn-csi-plugin        1         1         1       1            1           <none>          35s
daemonset.apps/longhorn-manager           1         1         1       1            1           <none>          83s

NAME                                       READY   UP-TO-DATE   AVAILABLE   AGE
deployment.apps/csi-attacher               3/3     3            3           35s
deployment.apps/csi-provisioner            3/3     3            3           35s
deployment.apps/csi-resizer                3/3     3            3           35s
deployment.apps/csi-snapshotter            3/3     3            3           35s
deployment.apps/longhorn-driver-deployer   1/1     1            1           83s
deployment.apps/longhorn-ui                2/2     2            2           83s

NAME                                               DESIRED   CURRENT   READY   AGE
replicaset.apps/csi-attacher-5c4bfdcf59            3         3         3       35s
replicaset.apps/csi-provisioner-667796df57         3         3         3       35s
replicaset.apps/csi-resizer-694f8f5f64             3         3         3       35s
replicaset.apps/csi-snapshotter-959b69d4b          3         3         3       35s
replicaset.apps/longhorn-driver-deployer-9f4fc86   1         1         1       83s
replicaset.apps/longhorn-ui-5f4b7bbf69             2         2         2       83s

21.9 KubeVirtとCDIのインストール

KubeVirtとCDIの両方のHelmチャートでインストールされるのは、それぞれのオペレータのみです。残りのシステムのデプロイはオペレータに任されています。つまり、必要なコンテナイメージすべてを定義ファイルに含める必要があります。作成してみましょう。

apiVersion: 1.0
image:
  imageType: iso
  arch: x86_64
  baseImage: slemicro.iso
  outputImageName: eib-image.iso
operatingSystem:
  users:
    - username: root
      encryptedPassword: $6$jHugJNNd3HElGsUZ$eodjVe4te5ps44SVcWshdfWizrP.xAyd71CVEXazBJ/.v799/WRCBXxfYmunlBO2yp1hm/zb4r8EmnrrNCF.P/
kubernetes:
  version: v1.28.9+rke2r1
  helm:
    charts:
      - name: kubevirt-chart
        repositoryName: suse-edge
        version: 0.2.4
        targetNamespace: kubevirt-system
        createNamespace: true
        installationNamespace: kube-system
      - name: cdi-chart
        repositoryName: suse-edge
        version: 0.2.3
        targetNamespace: cdi-system
        createNamespace: true
        installationNamespace: kube-system
    repositories:
      - name: suse-edge
        url: oci://registry.suse.com/edge
embeddedArtifactRegistry:
  images:
    - name: registry.suse.com/suse/sles/15.5/cdi-uploadproxy:1.58.0-150500.6.12.1
    - name: registry.suse.com/suse/sles/15.5/cdi-uploadserver:1.58.0-150500.6.12.1
    - name: registry.suse.com/suse/sles/15.5/cdi-apiserver:1.58.0-150500.6.12.1
    - name: registry.suse.com/suse/sles/15.5/cdi-controller:1.58.0-150500.6.12.1
    - name: registry.suse.com/suse/sles/15.5/cdi-importer:1.58.0-150500.6.12.1
    - name: registry.suse.com/suse/sles/15.5/cdi-cloner:1.58.0-150500.6.12.1
    - name: registry.suse.com/suse/sles/15.5/virt-api:1.1.1-150500.8.12.1
    - name: registry.suse.com/suse/sles/15.5/virt-controller:1.1.1-150500.8.12.1
    - name: registry.suse.com/suse/sles/15.5/virt-launcher:1.1.1-150500.8.12.1
    - name: registry.suse.com/suse/sles/15.5/virt-handler:1.1.1-150500.8.12.1
    - name: registry.suse.com/suse/sles/15.5/virt-exportproxy:1.1.1-150500.8.12.1
    - name: registry.suse.com/suse/sles/15.5/virt-exportserver:1.1.1-150500.8.12.1

イメージを構築してみましょう。

podman run --rm -it --privileged -v $CONFIG_DIR:/eib \
registry.suse.com/edge/edge-image-builder:1.0.2 \
build --definition-file eib-iso-definition.yaml

出力は次のようになります。

Generating image customization components...
Identifier ................... [SUCCESS]
Custom Files ................. [SKIPPED]
Time ......................... [SKIPPED]
Network ...................... [SUCCESS]
Groups ....................... [SKIPPED]
Users ........................ [SUCCESS]
Proxy ........................ [SKIPPED]
Rpm .......................... [SKIPPED]
Systemd ...................... [SKIPPED]
Elemental .................... [SKIPPED]
Suma ......................... [SKIPPED]
Populating Embedded Artifact Registry... 100% (13/13, 6 it/min)
Embedded Artifact Registry ... [SUCCESS]
Keymap ....................... [SUCCESS]
Configuring Kubernetes component...
The Kubernetes CNI is not explicitly set, defaulting to 'cilium'.
Downloading file: rke2_installer.sh
Kubernetes ................... [SUCCESS]
Certificates ................. [SKIPPED]
Building ISO image...
Kernel Params ................ [SKIPPED]
Image build complete!

構築したイメージを使用するノードがプロビジョニングされたら、KubeVirtとCDIの両方のインストールを確認できます。

KubeVirtを確認します。

/var/lib/rancher/rke2/bin/kubectl get all -n kubevirt-system --kubeconfig /etc/rancher/rke2/rke2.yaml

出力は次のようになり、すべてが正常にデプロイされていることがわかります。

NAME                                   READY   STATUS    RESTARTS   AGE
pod/virt-api-7c45477984-z226r          1/1     Running   0          2m4s
pod/virt-controller-664d9986b5-8p8gm   1/1     Running   0          98s
pod/virt-controller-664d9986b5-v2n4h   1/1     Running   0          98s
pod/virt-handler-2fx8c                 1/1     Running   0          98s
pod/virt-operator-5cf69867dc-hz5s8     1/1     Running   0          2m30s
pod/virt-operator-5cf69867dc-kp266     1/1     Running   0          2m30s

NAME                                  TYPE        CLUSTER-IP      EXTERNAL-IP   PORT(S)   AGE
service/kubevirt-operator-webhook     ClusterIP   10.43.210.235   <none>        443/TCP   2m7s
service/kubevirt-prometheus-metrics   ClusterIP   None            <none>        443/TCP   2m7s
service/virt-api                      ClusterIP   10.43.226.140   <none>        443/TCP   2m7s
service/virt-exportproxy              ClusterIP   10.43.213.201   <none>        443/TCP   2m7s

NAME                          DESIRED   CURRENT   READY   UP-TO-DATE   AVAILABLE   NODE SELECTOR            AGE
daemonset.apps/virt-handler   1         1         1       1            1           kubernetes.io/os=linux   98s

NAME                              READY   UP-TO-DATE   AVAILABLE   AGE
deployment.apps/virt-api          1/1     1            1           2m4s
deployment.apps/virt-controller   2/2     2            2           98s
deployment.apps/virt-operator     2/2     2            2           2m30s

NAME                                         DESIRED   CURRENT   READY   AGE
replicaset.apps/virt-api-7c45477984          1         1         1       2m4s
replicaset.apps/virt-controller-664d9986b5   2         2         2       98s
replicaset.apps/virt-operator-5cf69867dc     2         2         2       2m30s

CDIを確認します。

/var/lib/rancher/rke2/bin/kubectl get all -n cdi-system --kubeconfig /etc/rancher/rke2/rke2.yaml

出力は次のようになり、すべてが正常にデプロイされていることがわかります。

NAME                                   READY   STATUS    RESTARTS   AGE
pod/cdi-apiserver-db465b888-mdsmm      1/1     Running   0          3m6s
pod/cdi-deployment-56c7d74995-vt9sw    1/1     Running   0          3m6s
pod/cdi-operator-55c74f4b86-gkt58      1/1     Running   0          3m10s
pod/cdi-uploadproxy-7d7b94b968-msg2h   1/1     Running   0          3m6s

NAME                             TYPE        CLUSTER-IP      EXTERNAL-IP   PORT(S)    AGE
service/cdi-api                  ClusterIP   10.43.161.135   <none>        443/TCP    3m6s
service/cdi-prometheus-metrics   ClusterIP   10.43.161.159   <none>        8080/TCP   3m6s
service/cdi-uploadproxy          ClusterIP   10.43.25.136    <none>        443/TCP    3m6s

NAME                              READY   UP-TO-DATE   AVAILABLE   AGE
deployment.apps/cdi-apiserver     1/1     1            1           3m6s
deployment.apps/cdi-deployment    1/1     1            1           3m6s
deployment.apps/cdi-operator      1/1     1            1           3m10s
deployment.apps/cdi-uploadproxy   1/1     1            1           3m6s

NAME                                         DESIRED   CURRENT   READY   AGE
replicaset.apps/cdi-apiserver-db465b888      1         1         1       3m6s
replicaset.apps/cdi-deployment-56c7d74995    1         1         1       3m6s
replicaset.apps/cdi-operator-55c74f4b86      1         1         1       3m10s
replicaset.apps/cdi-uploadproxy-7d7b94b968   1         1         1       3m6s

21.10 トラブルシューティング

イメージの構築中に問題が発生した場合、またはプロセスをさらにテストおよびデバッグしたい場合は、アップストリームドキュメントを参照してください。

パート IV サードパーティの統合

サードパーティツールの統合方法

  • 22 NATS
  • NATSは、ますますハイパーコネクテッド化が進む世界のために構築された接続テクノロジです。NATSは、クラウドベンダ、オンプレミス、エッジ、Web、モバイルデバイスがどのように組み合わさっていてもアプリケーションが安全に通信することを可能にする単一のテクノロジです。NATSはオープンソース製品ファミリで構成されており、各製品は緊密に統合されている一方で、簡単に個別にデプロイできます。NATSは世界中で数千社もの企業で使用されており、マイクロサービス、エッジコンピューティング、モバイル、IoTなどのユースケースに幅広く対応しているため、NATSを使用して従来のメッセージングの強化や置き換えを図る…

  • 23 SLE Micro上のNVIDIA GPU
  • このガイドでは、事前構築済みのオープンソースドライバを使用してホストレベルのNVIDIA GPUサポートをSLE Micro 5.5に実装する方法を説明します。これらのドライバは、NVIDIAのGPU Operatorによって動的にロードされるのではなく、オペレーティングシステムにベイクされているドライバです。この設定は、デプロイメントに必要なすべてのアーティファクトをあらかじめイメージにベイクしておき、ドライバのバージョンを動的に選択する必要がない(つまり、ユーザがKubernetesを介してドライバのバージョンを選択する必要がない)お客様に非常に適しています。このガイドでは最初に、すでに事…

22 NATS

NATSは、ますますハイパーコネクテッド化が進む世界のために構築された接続テクノロジです。NATSは、クラウドベンダ、オンプレミス、エッジ、Web、モバイルデバイスがどのように組み合わさっていてもアプリケーションが安全に通信することを可能にする単一のテクノロジです。NATSはオープンソース製品ファミリで構成されており、各製品は緊密に統合されている一方で、簡単に個別にデプロイできます。NATSは世界中で数千社もの企業で使用されており、マイクロサービス、エッジコンピューティング、モバイル、IoTなどのユースケースに幅広く対応しているため、NATSを使用して従来のメッセージングの強化や置き換えを図ることができます。

22.1 アーキテクチャ

NATSは、メッセージの形式でアプリケーション間のデータ交換を可能にするインフラストラクチャです。

22.1.1 NATSクライアントアプリケーション

NATSクライアントライブラリを使用すると、アプリケーションが異なるインスタンス間でパブリッシュ、サブスクライブ、要求、および応答できるようになります。このようなアプリケーションを一般的にクライアントアプリケーションと呼びます。

22.1.2 NATSサービスインフラストラクチャ

NATSサービスは、相互接続されてNATSサービスインフラストラクチャを提供するように設定された1つ以上のNATSサーバプロセスによって提供されます。NATSサービスインフラストラクチャは、1つのエンドデバイスで動作する単一のNATSサーバプロセスから、すべての主要クラウドプロバイダと世界のあらゆる地域にまたがる多数のクラスタからなるパブリックなグローバルスーパークラスタまで拡張可能です。

22.1.3 シンプルなメッセージングデザイン

NATSを使用すると、アプリケーションはメッセージを送受信して簡単に通信できます。これらのメッセージはサブジェクト文字列によってアドレス指定および識別され、ネットワークの場所には依存しません。データはエンコードされてメッセージとしてフレーム化され、パブリッシャによって送信されます。メッセージは1人以上のサブスクライバによって受信、デコード、処理されます。

22.1.4 NATS JetStream

NATSにはJetStreamと呼ばれる分散型の永続化システムが組み込まれています。JetStreamは、今日のテクノロジにおけるストリーミングで明らかになった問題、すなわち複雑性、脆弱性、スケーラビリティの欠如を解決するために作成されました。また、JetStreamは、パブリッシャとサブスクライバのカップリングに関する問題(パブリッシュされたメッセージを受信するにはサブスクライバが稼働している必要がある)も解決します。NATS JetStreamの詳細については、こちらを参照してください。

22.2 インストール

22.2.1 K3s上へのNATSのインストール

NATSは複数のアーキテクチャ向けに構築されているため、K3s (第13章 「K3s)上に簡単にインストールできます。

NATSのデフォルト値を上書きするvaluesファイルを作成しましょう。

cat > values.yaml <<EOF
cluster:
  # Enable the HA setup of the NATS
  enabled: true
  replicas: 3

nats:
  jetstream:
    # Enable JetStream
    enabled: true

    memStorage:
      enabled: true
      size: 2Gi

    fileStorage:
      enabled: true
      size: 1Gi
      storageDirectory: /data/
EOF

では、Helmを介してNATSをインストールしてみましょう。

helm repo add nats https://nats-io.github.io/k8s/helm/charts/
helm install nats nats/nats --namespace nats --values values.yaml \
 --create-namespace

上記のvalues.yamlファイルでは、次のコンポーネントがnatsネームスペースに配置されます。

  1. NATS StatefulsetのHAバージョン。3つのコンテナ(NATSサーバ + ConfigリローダとMetricsサイドカー)が含まれます。

  2. NATS boxコンテナ。セットアップの確認に使用できる一連のNATSユーティリティが付属します。

  3. JetStreamは、PodにバインドされたPVCが付属するKey-Valueバックエンドも利用します。

22.2.1.1 セットアップのテスト

kubectl exec -n nats -it deployment/nats-box -- /bin/sh -l
  1. テストサブジェクトのサブスクリプションを作成します。

    nats sub test &
  2. テストサブジェクトにメッセージを送信します。

    nats pub test hi

22.2.1.2 クリーンアップ

helm -n nats uninstall nats
rm values.yaml

22.2.2 K3sのバックエンドとしてのNATS

K3sが利用するコンポーネントの1つがKINEです。KINEは、最初からリレーショナルデータベースをターゲットとした代替ストレージバックエンドでetcdを置き換えることを可能にするシムです。JetStreamはKey Value APIを備えているので、NATSをK3sクラスタのバックエンドとして利用することが可能です。

K3sのビルトインNATSが容易になるマージ済みのPRがありますが、この変更はまだK3sリリースに含まれていません

このため、K3sのバイナリを手動で構築する必要があります。

このチュートリアルでは、Appleシリコン上のOSX上のSLE Micro (UTM)のVMを使用します。

注記
注記

以下のコマンドはOSX PC上で実行してください。

22.2.2.1 K3sの構築

git clone --depth 1 https://github.com/k3s-io/k3s.git && cd k3s

次のコマンドは、ビルドタグにnatsを追加して、K3sでNATSビルトイン機能を有効にします。

sed -i '' 's/TAGS="ctrd/TAGS="nats ctrd/g' scripts/build
make local

<node-ip>は、K3sを起動するノードの実際のIPに置き換えます。

export NODE_IP=<node-ip>
sudo scp dist/artifacts/k3s-arm64 ${NODE_IP}:/usr/local/bin/k3s
注記
注記

K3sをローカルで構築するには、buildx Docker CLIプラグインが必要です。$ make localが失敗する場合は、手動でインストールできます。

22.2.2.2 NATS CLIのインストール

TMPDIR=$(mktemp -d)
nats_version="nats-0.0.35-linux-arm64"
curl -o "${TMPDIR}/nats.zip" -sfL https://github.com/nats-io/natscli/releases/download/v0.0.35/${nats_version}.zip
unzip "${TMPDIR}/nats.zip" -d "${TMPDIR}"

sudo scp ${TMPDIR}/${nats_version}/nats ${NODE_IP}:/usr/local/bin/nats
rm -rf ${TMPDIR}

22.2.2.3 K3sのバックエンドとしてのNATSの実行

ノードでsshを実行し、--datastore-endpointフラグでnatsを指してK3sを実行しましょう。

注記
注記

次のコマンドでは、K3sをフォアグランドプロセスとして起動するので、ログを簡単に追跡して問題がないかどうかを確認できます。現在の端末をブロックしないようにするには、コマンドの前に&フラグを追加して、バックグラウンドプロセスとして起動できます。

k3s server  --datastore-endpoint=nats://
注記
注記

NATSバックエンドを使用するK3sサーバをslemicro VM上で永続化するには、次のスクリプトを実行して、必要な設定でsystemdサービスを作成します。

export INSTALL_K3S_SKIP_START=false
export INSTALL_K3S_SKIP_DOWNLOAD=true

curl -sfL https://get.k3s.io | INSTALL_K3S_EXEC="server \
 --datastore-endpoint=nats://"  sh -

22.2.2.4 トラブルシューティング

次のコマンドをノード上で実行して、ストリームのすべてが適切に動作していることを確認できます。

nats str report -a
nats str view -a

23 SLE Micro上のNVIDIA GPU

23.1 概要

このガイドでは、事前構築済みのオープンソースドライバを使用してホストレベルのNVIDIA GPUサポートをSLE Micro 5.5に実装する方法を説明します。これらのドライバは、NVIDIAのGPU Operatorによって動的にロードされるのではなく、オペレーティングシステムにベイクされているドライバです。この設定は、デプロイメントに必要なすべてのアーティファクトをあらかじめイメージにベイクしておき、ドライバのバージョンを動的に選択する必要がない(つまり、ユーザがKubernetesを介してドライバのバージョンを選択する必要がない)お客様に非常に適しています。このガイドでは最初に、すでに事前にデプロイされているシステムに追加コンポーネントをデプロイする方法を説明しますが、その後のセクションでは、Edge Image Builderを使用してこの設定を初期デプロイメントに組み込む方法について説明します。基本的な操作を読む必要がない場合や、手動でセットアップしたくない場合は、スキップしてそちらのセクションに進んでください。

これらのドライバのサポートは、SUSEとNVIDIAの両社が緊密に連携して提供しており、ドライバはパッケージリポジトリの一部としてSUSEによって構築および出荷されている点を強調しておくことが重要です。ただし、ドライバを使用する組み合わせについて不安や質問がある場合は、SUSEまたはNVIDIAのアカウントマネージャに問い合わせてサポートを受けてください。NVIDIA AI Enterprise (NVAIE)を使用する予定の場合は、NVAIE認定GPUを使用していることを確認してください。NVAIE認定GPUでは、独自のNVIDIAドライバを使用する必要がある「場合があります」。不明な点がある場合は、NVIDIAの担当者に問い合わせてください。

NVIDIA GPU Operatorの統合の詳細は、このガイドでは説明「しません」。Kubernetes用のNVIDIA GPU Operatorの統合についてはここでは説明しませんが、このガイドのほとんどの手順に従って、基礎となるオペレーティングシステムをセットアップできます。そして、NVIDIA GPU OperatorのHelmチャートのdriver.enabled=falseフラグを使用して「プリインストール」されたドライバをGPU Operatorが使用できるようにするだけで、ホスト上にインストールされたドライバが取得されます。より包括的な手順については、 NVIDIA (こちら)で参照できます。さらにSUSEは先日、テクニカルリファレンスドキュメント (TRD)も公開しました。このドキュメントでは、ご自身のユースケースにGPU OperatorとNVIDIA独自のドライバが必須の場合にこれらを使用する方法を説明しています。

23.2 前提条件

このガイドに従って操作を進める場合、以下がすでに用意されていることを想定しています。

  • SLE Micro 5.5がインストールされたホストが少なくとも1台。このホストは物理でも仮想でも構いません。

  • パッケージへのアクセスにはサブスクリプションが必要であるため、ホストがサブスクリプションに接続されていること。評価版は こちらから入手できます。

  • 互換性のあるNVIDIA GPUがインストールされていること(またはSLE Microが実行されている仮想マシンに「完全に」 パススルーされていること)。

  • ルートユーザへのアクセス — 以下の説明では、自身がルートユーザであり、sudoを使用して特権を昇格して「いない」ことを想定しています。

23.3 手動インストール

このセクションでは、NVIDIAドライバをSLE Microオペレーティングシステムに直接インストールします。これはopen版NVIDIAドライバがSLE Microのコアパッケージリポジトリの一部となったためであり、必須のRPMパッケージをインストールするのと同じように簡単にインストールできるようになりました。実行可能パッケージのコンパイルやダウンロードは必要ありません。以下では、最新のGPUをサポートする「G06」世代ドライバのデプロイについて手順を追って説明します(詳細については こちらを参照してください)。ご使用のシステムに搭載されているNVIDIA GPUに適切なドライバ世代を選択してください。最新のGPUでは、「G06」ドライバが最も一般的な選択肢です。

始める前に、SUSEがSLE Microの一部として出荷するopen版NVIDIAドライバのほかに、ご自身のセットアップに追加のNVIDIAコンポーネントも必要な場合があることを認識しておくことが重要です。たとえば、OpenGLライブラリ、CUDAツールキット、 nvidia-smiなどのコマンドラインユーティリティ、nvidia-container-toolkitなどのコンテナ統合コンポーネントです。これらのコンポーネントの多くはNVIDIA独自のソフトウェアであるため、SUSEからは出荷されません。また、NVIDIAの代わりにSUSEが出荷しても意味がありません。そのため、説明の一環として、これらのコンポーネントにアクセスできるようにする追加のリポジトリを設定し、これらのツールの使用方法の例をいくつか説明し、完全に機能するシステムを作成します。SUSEのリポジトリとNVIDIAのリポジトリを区別することが重要です。これは、NVIDIAが提供するパッケージのバージョンとSUSEが構築したものが一致しない場合があるためです。これは通常、SUSEがopen版ドライバの新バージョンを利用可能にしたときに発生し、NVIDIAのリポジトリで同等のパッケージが利用可能になるまでに数日かかります。

以下をチェックして、選択するドライババージョンがGPUと互換性があり、CUDAの要件を満たしていることを確認することをお勧めします。

  • CUDAリリースノート

  • デプロイを予定しているドライババージョンと一致するバージョンがNVIDIA SLE15-SP5リポジトリにあり、サポートコンポーネントと同等のパッケージバージョンが利用可能であることを確認する

ヒント
ヒント

open版NVIDIAドライバのバージョンを見つけるには、ターゲットマシンでzypper se -s nvidia-open-driverを実行するか、「または」SUSE Customer CenterのSLE Micro 5.5 x86_64で「nvidia-open-driver」を検索します。

ここでは、4つのバージョンが利用可能で、545.29.064が最新です。

SUSE Customer Centre

NVIDIAリポジトリで同等のバージョンが利用可能であることを確認したら、ホストオペレーティングシステムにパッケージをインストールできます。そのためには、transactional-updateセッションを開く必要があります。これにより、基礎となるオペレーティング システムの読み込み/書き込みスナップショットが新しく作成され、イミュータブルプラットフォームに変更を加えることが可能になります(transactional-updateの詳細については、こちらを参照してください)。

transactional-update shell

transactional-updateシェルを起動したら、NVIDIAからパッケージリポジトリを追加します。これにより、nvidia-smiなどの追加ユーティリティをプルできます。

zypper ar https://download.nvidia.com/suse/sle15sp5/ nvidia-sle15sp5-main
zypper --gpg-auto-import-keys refresh

その後、ドライバと、追加ユーティリティのnvidia-compute-utilsをインストールできます。ユーティリティが不要の場合は省略できますが、テスト目的の場合は、この段階でインストールする価値があります。

zypper install -y --auto-agree-with-licenses nvidia-open-driver-G06-signed-kmp nvidia-compute-utils-G06
注記
注記

インストールが失敗する場合、選択したドライババージョンとNVIDIAがリポジトリで配布しているバージョンとの間に依存関係の不一致があることを示している可能性があります。前のセクションを参照して、バージョンが一致していることを確認してください。また、別のドライババージョンをインストールしてみてください。たとえば、NVIDIAリポジトリに以前のバージョンがある場合、インストールコマンドにnvidia-open-driver-G06-signed-kmp=545.29.06を指定して、一致するバージョンを指定してみることができます。

次に、サポートされているGPUを使用して「いない」場合は(こちらでリストを確認できます)、モジュールレベルでサポートを有効にすることで、ドライバが動作するかどうかを確認できますが、結果はユーザによって異なります。「サポートされている」GPUを使用している場合は、この手順はスキップしてください。

sed -i '/NVreg_OpenRmEnableUnsupportedGpus/s/^#//g' /etc/modprobe.d/50-nvidia-default.conf

これらのパッケージをインストールしたので、transactional-updateセッションを終了します。

exit
注記
注記

次に進む前に、transactional-updateセッションを終了していることを確認してください。

ドライバをインストールしたら、再起動します。SLE Microはイミュータブルオペレーティングシステムであるため、前の手順で作成した新しいスナップショットで再起動する必要があります。ドライバはこの新しいスナップショットにのみインストールされるため、この新しいスナップショットで再起動しないとドライバをロードできません(新しいスナップショットでの再起動は自動的に実行されます)。準備ができたらrebootコマンドを発行します。

reboot

システムが正常に再起動したら、ログインし直し、 nvidia-smiツールを使用して、ドライバが正常にロードされていて、GPUへのアクセスと列挙をどちらも実行できることを確認します。

nvidia-smi

このコマンドの出力は次のような出力になります。以下の例では、GPUが2つあることに注意してください。

Wed Feb 28 12:31:06 2024
+---------------------------------------------------------------------------------------+
| NVIDIA-SMI 545.29.06              Driver Version: 545.29.06    CUDA Version: 12.3     |
|-----------------------------------------+----------------------+----------------------+
| GPU  Name                 Persistence-M | Bus-Id        Disp.A | Volatile Uncorr. ECC |
| Fan  Temp   Perf          Pwr:Usage/Cap |         Memory-Usage | GPU-Util  Compute M. |
|                                         |                      |               MIG M. |
|=========================================+======================+======================|
|   0  NVIDIA A100-PCIE-40GB          Off | 00000000:17:00.0 Off |                    0 |
| N/A   29C    P0              35W / 250W |      4MiB / 40960MiB |      0%      Default |
|                                         |                      |             Disabled |
+-----------------------------------------+----------------------+----------------------+
|   1  NVIDIA A100-PCIE-40GB          Off | 00000000:CA:00.0 Off |                    0 |
| N/A   30C    P0              33W / 250W |      4MiB / 40960MiB |      0%      Default |
|                                         |                      |             Disabled |
+-----------------------------------------+----------------------+----------------------+

+---------------------------------------------------------------------------------------+
| Processes:                                                                            |
|  GPU   GI   CI        PID   Type   Process name                            GPU Memory |
|        ID   ID                                                             Usage      |
|=======================================================================================|
|  No running processes found                                                           |
+---------------------------------------------------------------------------------------+

これで、SLE MicroシステムへのNVIDIAドライバのインストールと検証プロセスは完了です。

23.4 手動インストールの追加検証

この段階で確認できるのは、ホストレベルでNVIDIAデバイスにアクセスできること、およびドライバが正常にロードされていることだけです。ただし、それが機能していることを確認したい場合は、簡単なテストを実施して、GPUがユーザスペースアプリケーションから、理想的にはコンテナ経由で命令を受け取れること、および実際のワークロードが通常使用するものであるCUDAライブラリを通じて命令を受け取れることを検証します。このためには、nvidia-container-toolkit (NVIDIA Container Toolkit)をインストールしてホストOSにさらに変更を加えることができます。まず、別のtransactional-updateシェルを開きます。前の手順ではこれを1つのトランザクションで実行できたことに注目し、後のセクションでこれを完全に自動的に実行する方法を確認します。

transactional-update shell

次に、NVIDIA Container Toolkitリポジトリからnvidia-container-toolkitパッケージをインストールします。

  • 次のnvidia-container-toolkit.repoには、安定版(nvidia-container-toolkit)と実験版(nvidia-container-toolkit-experimental)のリポジトリが含まれています。運用環境での使用には、安定版リポジトリをお勧めします。実験版リポジトリはデフォルトで無効になっています。

zypper ar https://nvidia.github.io/libnvidia-container/stable/rpm/nvidia-container-toolkit.repo
zypper --gpg-auto-import-keys install -y nvidia-container-toolkit

準備ができたら、transactional-updateシェルを終了できます。

exit

…​そして新しいスナップショットでマシンを再起動します。

reboot
注記
注記

前述同様に、変更を有効にするには、必ずtransactional-shellを終了し、マシンを再起動する必要があります。

マシンが再起動したら、システムがNVIDIA Container Toolkitを使用してデバイスを正常に列挙できることを確認できます。出力は詳細で、INFOとWARNのメッセージがありますが、ERRORのメッセージはありません。

nvidia-ctk cdi generate --output=/etc/cdi/nvidia.yaml

これにより、そのマシンで起動するコンテナはすべて、検出されたNVIDIA GPUデバイスを使用できることが確認されます。準備ができたら、podmanベースのコンテナを実行できます。これをpodmanを介して行うことで、コンテナ内からNVIDIAデバイスへのアクセスを効果的に検証することができ、後の段階でKubernetesで同じ操作を実行するための自信が得られます。podmanに対し、前のコマンドでSLE BCIに基づいて処理したラベル付きのNVIDIAデバイスへのアクセス権を与え、バッシュコマンドを実行します。

podman run --rm --device nvidia.com/gpu=all --security-opt=label=disable -it registry.suse.com/bci/bci-base:latest bash

続いて、一時的なpodmanコンテナ内からコマンドを実行します。このコンテナは基盤となるシステムにはアクセスできず一時的であるため、ここで行う操作は永続せず、基盤となるホスト上にあるものを壊すことは一切できないはずです。現在はコンテナ内で作業しているため、必要なCUDAライブラリをインストールできます。ここでもう一度、ご使用のドライバにあったCUDAバージョンをこちらで確認してください。ただし、必要なCUDAバージョンはnvidia-smiの前の出力に表示されているはずです。以下の例では、CUDA 12.3をインストールして多数の例、デモ、開発キットをプルし、GPUを完全に検証できるようにしています。

zypper ar http://developer.download.nvidia.com/compute/cuda/repos/sles15/x86_64/ cuda-sle15-sp5
zypper in -y cuda-libraries-devel-12-3 cuda-minimal-build-12-3 cuda-demo-suite-12-3

これが正常にインストールされた後にコンテナを終了しないでください。deviceQuery CUDAの例を実行し、CUDAを介して、およびコンテナ自体からGPUアクセスを包括的に検証します。

/usr/local/cuda-12/extras/demo_suite/deviceQuery

成功すると、次のような出力が表示されます。コマンドの最後にある「Result = PASS」というメッセージに注意してください。また、次の出力では2つのGPUが正しく識別されていますが、ご使用の環境では1つしかない場合があることにも注意してください。

/usr/local/cuda-12/extras/demo_suite/deviceQuery Starting...

 CUDA Device Query (Runtime API) version (CUDART static linking)

Detected 2 CUDA Capable device(s)

Device 0: "NVIDIA A100-PCIE-40GB"
  CUDA Driver Version / Runtime Version          12.2 / 12.1
  CUDA Capability Major/Minor version number:    8.0
  Total amount of global memory:                 40339 MBytes (42298834944 bytes)
  (108) Multiprocessors, ( 64) CUDA Cores/MP:     6912 CUDA Cores
  GPU Max Clock rate:                            1410 MHz (1.41 GHz)
  Memory Clock rate:                             1215 Mhz
  Memory Bus Width:                              5120-bit
  L2 Cache Size:                                 41943040 bytes
  Maximum Texture Dimension Size (x,y,z)         1D=(131072), 2D=(131072, 65536), 3D=(16384, 16384, 16384)
  Maximum Layered 1D Texture Size, (num) layers  1D=(32768), 2048 layers
  Maximum Layered 2D Texture Size, (num) layers  2D=(32768, 32768), 2048 layers
  Total amount of constant memory:               65536 bytes
  Total amount of shared memory per block:       49152 bytes
  Total number of registers available per block: 65536
  Warp size:                                     32
  Maximum number of threads per multiprocessor:  2048
  Maximum number of threads per block:           1024
  Max dimension size of a thread block (x,y,z): (1024, 1024, 64)
  Max dimension size of a grid size    (x,y,z): (2147483647, 65535, 65535)
  Maximum memory pitch:                          2147483647 bytes
  Texture alignment:                             512 bytes
  Concurrent copy and kernel execution:          Yes with 3 copy engine(s)
  Run time limit on kernels:                     No
  Integrated GPU sharing Host Memory:            No
  Support host page-locked memory mapping:       Yes
  Alignment requirement for Surfaces:            Yes
  Device has ECC support:                        Enabled
  Device supports Unified Addressing (UVA):      Yes
  Device supports Compute Preemption:            Yes
  Supports Cooperative Kernel Launch:            Yes
  Supports MultiDevice Co-op Kernel Launch:      Yes
  Device PCI Domain ID / Bus ID / location ID:   0 / 23 / 0
  Compute Mode:
     < Default (multiple host threads can use ::cudaSetDevice() with device simultaneously) >

Device 1: <snip to reduce output for multiple devices>
     < Default (multiple host threads can use ::cudaSetDevice() with device simultaneously) >
> Peer access from NVIDIA A100-PCIE-40GB (GPU0) -> NVIDIA A100-PCIE-40GB (GPU1) : Yes
> Peer access from NVIDIA A100-PCIE-40GB (GPU1) -> NVIDIA A100-PCIE-40GB (GPU0) : Yes

deviceQuery, CUDA Driver = CUDART, CUDA Driver Version = 12.3, CUDA Runtime Version = 12.3, NumDevs = 2, Device0 = NVIDIA A100-PCIE-40GB, Device1 = NVIDIA A100-PCIE-40GB
Result = PASS

ここから、続いて他のCUDAワークロードを実行できます。コンパイラやCUDAエコシステムの他の側面を使用して、さらにテストを実行できます。完了したら、コンテナを終了できます。コンテナにインストールしたものはすべて一時的なものであるため(したがって失われるため)、基盤となるオペレーティングシステムには影響がないことに注意してください。

exit

23.5 Kubernetesを使用した実装

open版NVIDIAドライバをSLE Microにインストールして使用できることが証明されたので、同じマシンにKubernetesを設定してみましょう。このガイドでは、Kubernetesのデプロイについては説明しませんが、K3sまたはRKE2をインストール済みで、kubeconfigが適宜設定されており、標準のkubectlコマンドをスーパーユーザとして実行できることを前提としています。ここではノードがシングルノードクラスタを形成していることを想定していますが、中心となる手順はマルチノードクラスタでも同様です。まず、kubectlのアクセスが機能していることを確認します。

kubectl get nodes

次のような画面が表示されます。

NAME       STATUS   ROLES                       AGE   VERSION
node0001   Ready    control-plane,etcd,master   13d   v1.28.9+rke2r1

k3s/rke2のインストールによってホスト上のNVIDIA Container Toolkitが検出され、NVIDIAランタイム統合がcontainerd (k3s/rke2が使用するContainer Runtime Interface)に自動設定されていることを確認する必要があります。確認するには、containerdのconfig.tomlファイルをチェックします。

tail -n8 /var/lib/rancher/rke2/agent/etc/containerd/config.toml

次のような画面が表示される必要があります。K3sの場合に相当する場所は/var/lib/rancher/k3s/agent/etc/containerd/config.tomlです。

[plugins."io.containerd.grpc.v1.cri".containerd.runtimes."nvidia"]
  runtime_type = "io.containerd.runc.v2"
[plugins."io.containerd.grpc.v1.cri".containerd.runtimes."nvidia".options]
  BinaryName = "/usr/bin/nvidia-container-runtime"
注記
注記

これらのエントリが存在しない場合は、検出が失敗している可能性があります。この原因として考えられるのは、マシンまたはKubernetesサービスを再起動していないことです。必要に応じて、上記のようにこれらを手動で追加してください。

次に、NVIDIA RuntimeClassを追加のKubernetesランタイムとしてデフォルト値に設定する必要があります。これにより、GPUへのアクセスが必要なPodに対するユーザ要求が、 containerdの設定に従って、NVIDIA Container Toolkitを使用してnvidia-container-runtimeを介してアクセスできるようにします。

kubectl apply -f - <<EOF
apiVersion: node.k8s.io/v1
kind: RuntimeClass
metadata:
  name: nvidia
handler: nvidia
EOF

次の手順は、NVIDIA Device Pluginを設定することです。これにより、NVIDIA Container Toolkitと連携して、クラスタ内で使用可能なリソースとしてNVIDIA GPUを利用するようにKubernetesを設定します。このツールはまず、基盤となるホスト上のすべての機能(GPU、ドライバ、その他の機能(GLなど)を含む)を検出し、その後、ユーザがGPUリソースを要求してアプリケーションの一部として使用できるようにします。

まず、NVIDIA Device Plugin用のHelmリポジトリを追加して更新する必要があります。

helm repo add nvdp https://nvidia.github.io/k8s-device-plugin
helm repo update

これで、NVIDIA Device Pluginをインストールできます。

helm upgrade -i nvdp nvdp/nvidia-device-plugin --namespace nvidia-device-plugin --create-namespace --version 0.14.5 --set runtimeClassName=nvidia

数分後、新しいPodが実行されているのがわかります。これで、利用可能なノード上での検出は完了し、検出されたGPUの数を示すタグがノードに付けられます。

kubectl get pods -n nvidia-device-plugin
NAME                              READY   STATUS    RESTARTS      AGE
nvdp-nvidia-device-plugin-jp697   1/1     Running   2 (12h ago)   6d3h

kubectl get node node0001 -o json | jq .status.capacity
{
  "cpu": "128",
  "ephemeral-storage": "466889732Ki",
  "hugepages-1Gi": "0",
  "hugepages-2Mi": "0",
  "memory": "32545636Ki",
  "nvidia.com/gpu": "1",                      <----
  "pods": "110"
}

これで、このGPUを使用するNVIDIA Podを作成する準備ができました。CUDA Benchmarkコンテナで試してみましょう。

kubectl apply -f - <<EOF
apiVersion: v1
kind: Pod
metadata:
  name: nbody-gpu-benchmark
  namespace: default
spec:
  restartPolicy: OnFailure
  runtimeClassName: nvidia
  containers:
  - name: cuda-container
    image: nvcr.io/nvidia/k8s/cuda-sample:nbody
    args: ["nbody", "-gpu", "-benchmark"]
    resources:
      limits:
        nvidia.com/gpu: 1
    env:
    - name: NVIDIA_VISIBLE_DEVICES
      value: all
    - name: NVIDIA_DRIVER_CAPABILITIES
      value: all
EOF

すべて問題なければ、ログを見て、ベンチマーク情報を確認できます。

kubectl logs nbody-gpu-benchmark
Run "nbody -benchmark [-numbodies=<numBodies>]" to measure performance.
	-fullscreen       (run n-body simulation in fullscreen mode)
	-fp64             (use double precision floating point values for simulation)
	-hostmem          (stores simulation data in host memory)
	-benchmark        (run benchmark to measure performance)
	-numbodies=<N>    (number of bodies (>= 1) to run in simulation)
	-device=<d>       (where d=0,1,2.... for the CUDA device to use)
	-numdevices=<i>   (where i=(number of CUDA devices > 0) to use for simulation)
	-compare          (compares simulation results running once on the default GPU and once on the CPU)
	-cpu              (run n-body simulation on the CPU)
	-tipsy=<file.bin> (load a tipsy model file for simulation)

NOTE: The CUDA Samples are not meant for performance measurements. Results may vary when GPU Boost is enabled.

> Windowed mode
> Simulation data stored in video memory
> Single precision floating point simulation
> 1 Devices used for simulation
GPU Device 0: "Turing" with compute capability 7.5

> Compute 7.5 CUDA device: [Tesla T4]
40960 bodies, total time for 10 iterations: 101.677 ms
= 165.005 billion interactions per second
= 3300.103 single-precision GFLOP/s at 20 flops per interaction

最後に、アプリケーションでOpenGLが必要な場合は、必要なNVIDIA OpenGLライブラリをホストレベルでインストールし、 NVIDIA Device PluginとNVIDIA Container Toolkitを使用してそのライブラリをコンテナで利用できるようにすることができます。これを行うには、次のようにパッケージをインストールします。

transactional-update pkg install nvidia-gl-G06
注記
注記

このパッケージをアプリケーションで使用できるようにするには再起動が必要です。NVIDIA Device Pluginは、NVIDIA Container Toolkitを介してこれを自動的に再検出します。

23.6 Edge Image Builderを使用した統合

さて、SLE Micro上のアプリケーションとGPUの全機能をデモで示したので、 第9章 「Edge Image Builderを使用してすべてをまとめ、デプロイ可能/使用可能なISOまたはRAWディスクイメージで提供したいと思います。このガイドでは、Edge Image Builderの使用方法は説明せずに、このようなイメージを構築するために必要な設定について説明します。以下に、必要なすべてのコンポーネントを追加設定なしにデプロイするためのイメージ定義の例と、必要なKubernetes設定ファイルを示します。以下に示す例では、Edge Image Builderディレクトリは次のようなディレクトリ構造になっています。

.
├── base-images
│   └── SLE-Micro.x86_64-5.5.0-Default-SelfInstall-GM2.install.iso
├── eib-config-iso.yaml
├── kubernetes
│   ├── config
│   │   └── server.yaml
│   ├── helm
│   │   └── values
│   │       └── nvidia-device-plugin.yaml
│   └── manifests
│       └── nvidia-runtime-class.yaml
└── rpms
    └── gpg-keys
        └── nvidia-container-toolkit.key

これらのファイルを調べてみましょう。まず、K3sを実行するシングルノードクラスタのサンプルイメージ定義を次に示します。このイメージ定義では、ユーティリティとOpenGLパッケージもデプロイします(eib-config-iso.yaml)。

apiVersion: 1.0
image:
  arch: x86_64
  imageType: iso
  baseImage: SLE-Micro.x86_64-5.5.0-Default-SelfInstall-GM2.install.iso
  outputImageName: deployimage.iso
operatingSystem:
  time:
    timezone: Europe/London
    ntp:
      pools:
        - 2.suse.pool.ntp.org
  isoConfiguration:
    installDevice: /dev/sda
  users:
    - username: root
      encryptedPassword: $6$XcQN1xkuQKjWEtQG$WbhV80rbveDLJDz1c93K5Ga9JDjt3mF.ZUnhYtsS7uE52FR8mmT8Cnii/JPeFk9jzQO6eapESYZesZHO9EslD1
  packages:
    packageList:
      - nvidia-open-driver-G06-signed-kmp-default
      - nvidia-compute-utils-G06
      - nvidia-gl-G06
      - nvidia-container-toolkit
    additionalRepos:
      - url: https://download.nvidia.com/suse/sle15sp5/
      - url: https://nvidia.github.io/libnvidia-container/stable/rpm/x86_64
    sccRegistrationCode: <snip>
kubernetes:
  version: v1.28.9+k3s1
  helm:
    charts:
      - name: nvidia-device-plugin
        version: v0.14.5
        installationNamespace: kube-system
        targetNamespace: nvidia-device-plugin
        createNamespace: true
        valuesFile: nvidia-device-plugin.yaml
        repositoryName: nvidia
    repositories:
      - name: nvidia
        url: https://nvidia.github.io/k8s-device-plugin
注記
注記

これは単なる例です。要件や期待に合うようにカスタマイズする必要がある場合があります。また、SLE Microを使用する場合は、パッケージの依存関係を解決してNVIDIAドライバをプルするために、独自の sccRegistrationCodeを指定する必要があります。

これに加えて、他のコンポーネントを追加して、ブート時にKubernetesによってロードされるようにする必要があります。EIBディレクトリにはまずkubernetesディレクトリが必要で、その下に設定、Helmチャート値、必要な追加のマニフェスト用のサブディレクトリが必要です。

mkdir -p kubernetes/config kubernetes/helm/values kubernetes/manifests

CNIを選択し(選択しない場合はデフォルトでCiliumになります)、SELinuxを有効にして、(オプションの)Kubernetes設定を行いましょう。

cat << EOF > kubernetes/config/server.yaml
cni: cilium
selinux: true
EOF

続いて、NVIDIA RuntimeClassがKubernetesクラスタ上に作成されていることを確認します。

cat << EOF > kubernetes/manifests/nvidia-runtime-class.yaml
apiVersion: node.k8s.io/v1
kind: RuntimeClass
metadata:
  name: nvidia
handler: nvidia
EOF

ビルトインHelmコントローラを使用して、Kubernetes自体を使用してNVIDIA Device Pluginをデプロイします。チャートの値ファイルでランタイムクラスを指定しましょう。

cat << EOF > kubernetes/helm/values/nvidia-device-plugin.yaml
runtimeClassName: nvidia
EOF

次に進む前に、NVIDIA Container Toolkit RPMの公開鍵を取得する必要があります。

mkdir -p rpms/gpg-keys
curl -o rpms/gpg-keys/nvidia-container-toolkit.key https://nvidia.github.io/libnvidia-container/gpgkey

Kubernetesバイナリ、コンテナイメージ、Helmチャート(および参照イメージ)など、必要なアーティファクトがすべて自動的にエアギャップ化されます。つまり、デプロイ時のシステムにはデフォルトでインターネット接続は不要です。ここで必要なのはSUSEダウンロードページからSLE Micro ISOを取得する(そしてそれをbase-imagesディレクトリに配置する)ことだけです。そうすれば、Edge Image Builderツールを呼び出してISOを生成できます。この例を完了するために、イメージの構築に使用したコマンドを次に示します。

podman run --rm --privileged -it -v /path/to/eib-files/:/eib \
registry.suse.com/edge/edge-image-builder:1.0.2 \
build --definition-file eib-config-iso.yaml

Edge Image Builderの詳細については、ドキュメントを参照してください。

23.7 問題の解決

23.7.1 nvidia-smiでGPUが検出されない

dmesgを使用してカーネルメッセージを確認します。NvKMSKapDeviceを割り当てることができないことを示している場合は、サポート対象外のGPUの回避策を適用します。

sed -i '/NVreg_OpenRmEnableUnsupportedGpus/s/^#//g' /etc/modprobe.d/50-nvidia-default.conf

メモ: 上記の手順でカーネルモジュールの設定を変更した場合は、変更を有効にするために、カーネルモジュールを再ロードするか、再起動する必要があります。

パート V Day 2操作

このセクションでは、管理者がさまざまな「Day 2」操作タスクを管理クラスタとダウンストリームクラスタの両方で処理する方法について説明します。

  • 24 管理クラスタ
  • このセクションでは、さまざまなDay 2操作を管理クラスタで実行する方法について説明します。

  • 25 ダウンストリームクラスタ
  • このセクションでは、管理クラスタを使用して、ダウンストリームクラスタのさまざまな部分に対して、各種のDay 2操作を行う方法について説明します。

24 管理クラスタ

このセクションでは、さまざまなDay 2操作を管理クラスタで実行する方法について説明します。

24.1 RKE2のアップグレード

注記
注記

確実な障害復旧のため、RKE2クラスタデータをバックアップすることをお勧めします。バックアップの実行方法については、こちらをご確認ください。rke2バイナリのデフォルトの場所は、/opt/rke2/binです。

次のようなRKE2インストールスクリプトを使用して、RKE2バージョンをアップグレードできます。

curl -sfL https://get.rke2.io | INSTALL_RKE2_VERSION=vX.Y.Z+rke2rN sh -

インストール後にrke2プロセスを再起動することを忘れないでください。

# For server nodes:
systemctl restart rke2-server

# For agent nodes:
systemctl restart rke2-agent
重要
重要

アップグレードに関する予期しない問題を避けるために、ノードのアップグレードは次の順序で行ってください。

  1. サーバノード - 一度に1ノードずつアップグレードする必要があります。

  2. エージェントノード - すべてのサーバノードのアップグレードが完了した後でアップグレードする必要があります。並行してアップグレード可能です。

詳細については、RKE2のアップグレードに関するドキュメントを参照してください。

24.2 OSのアップグレード

注記
注記

このセクションでは、システムをhttps://scc.suse.comに登録済みであることを想定しています。

SUSEでは、新しいSLE Microパッケージの更新を定期的にリリースしています。更新されたパッケージバージョンを取得するために、SLE Microではtransactional-upgradeを使用します。

transactional-upgradeでは、Linuxオペレーティングシステムをトランザクション方式で更新するためのアプリケーションとライブラリを用意しています。すなわち、更新をバックグラウンドで実行しながら、システムはそのまま動作を継続します。システムを再起動した後でのみ、更新が有効になります。詳細については、GitHubtransactional-updateのページを参照してください。

システム内のすべてのパッケージを更新するには、次のコマンドを実行します。. 

transactional-update

ノードを「再起動」すると、ノードはしばらくの間利用不可能になるため、マルチノードクラスタを実行している場合は、ノードに対してcordonおよびdrainを実行してから 再起動できます。

ノードに対してcordonを実行するには、次のコマンドを実行します。. 

kubectl cordon <node>

これにより、ノードはデフォルトのスケジューリングメカニズムから除外され、誤ってPodが割り当てられることがなくなります。

ノードに対してdrainを実行するには、次のコマンドを実行します。. 

kubectl drain <node>

これにより、ノード上のすべてのワークロードが他の利用可能なノードに転送されるようになります。

注記
注記

ノードで実行されているワークロードによっては、追加のフラグ(--delete-emptydir-data--ignore-daemonsetsなど)をコマンドに指定する必要がある場合があります。

ノードを再起動します。. 

sudo reboot

正常に再起動すると、ノードのパッケージが更新されます。残る手順は、uncordonコマンドを使用して、ノードをデフォルトのスケジューリングメカニズムに戻すことのみです。

ノードに対してCordonを解除します。. 

kubectl uncordon <node>

注記
注記

更新を元に戻す場合は、上記の手順と次のtransactional-updateコマンドを使用します。

transactional-update rollback last

24.3 Helmのアップグレード

注記
注記

このセクションでは、システムにhelmがインストール済みであることを想定しています。helmのインストール手順については、こちらをご確認ください。

このセクションでは、EIBでデプロイされたHelmチャート(24.3.1項 「EIBでデプロイされたHelmチャート」)とEIB以外でデプロイされたHelmチャート(24.3.2項 「EIB以外でデプロイされたHelmチャート」)の両方をアップグレードする方法について説明します。

24.3.1 EIBでデプロイされたHelmチャート

EIBは、そのイメージ定義ファイル(3.3項 「イメージ定義ファイルの作成」)で定義されたHelmチャートを、RKE2のマニフェストであるauto-deploy機能を使用してデプロイします。

このような方法でデプロイされたチャートをアップグレードするには、EIBが初期化ノードの/var/lib/rancher/rke2/server/manifestsディレクトリの下に作成する、チャートマニフェストファイルをアップグレードする必要があります。

注記
注記

確実な障害復旧のために、必ずチャートマニフェストファイルをバックアップするとともに、チャートで提供されている障害復旧に関連するドキュメントに従うことをお勧めします。

チャートマニフェストファイルをアップグレードするには、次の手順に従います。

  1. 初期化ノードを見つけます。

    • マルチノードクラスタの場合 - EIBのイメージ定義ファイルで、ノードの1つに対してinitializer: trueプロパティが指定されている必要があります。このプロパティが指定されていない場合、ノードリストで最初のサーバノードが初期化ノードになります。

    • シングルノードクラスタの場合 - 初期化ノードは現在実行中のノードです。

  2. 初期化ノードにSSHで接続します。

    ssh root@<node_ip>
  3. Helmチャートをプルします。

    • HelmチャートリポジトリでホストされているHelmチャートの場合:

      helm repo add <chart_repo_name> <chart_repo_urls>
      helm pull <chart_repo_name>/<chart_name>
      
      # Alternatively if you want to pull a specific verison
      helm pull <chart_repo_name>/<chart_name> --version=X.Y.Z
    • OCIベースのHelmチャートの場合:

      helm pull oci://<chart_oci_url>
      
      # Alternatively if you want to pull a specific verison
      helm pull oci://<chart_oci_url> --version=X.Y.Z
  4. プルした.tgzアーカイブをエンコードして、HelmChart CR設定に渡せるようにします。

    base64 -w 0 <chart_name>-X.Y.Z.tgz  > <chart_name>-X.Y.Z.txt
  5. 編集するチャートマニフェストファイルのコピーを作成します。

    cp /var/lib/rancher/rke2/server/manifests/<chart_name>.yaml ./<chart_name>.yaml
  6. bar.yamlファイルのchartContentversionの設定を変更します。

    sed -i -e "s|chartContent:.*|chartContent: $(<chart-name-X.Y.Z.txt)|" -e "s|version:.*|version: X.Y.Z|" <chart_name>.yaml
    注記
    注記

    チャートにアップグレードの追加の変更(新しいカスタムチャート値の追加など)を加える必要がある場合は、チャートマニフェストファイルを手動で編集する必要があります。

  7. 元のチャートマニフェストファイルを置き換えます。

    cp <chart_name>.yaml /var/lib/rancher/rke2/server/manifests/

上記のコマンドにより、Helmチャートのアップグレードがトリガされます。アップグレードは、helm-controllerによって処理されます。

Helmチャートのアップグレードを追跡するには、helm-controllerがチャートのアップグレード時に作成するPodのログを表示する必要があります。詳細については、例(24.3.1.1項 「例」)のセクションを参照してください。

24.3.1.1

注記
注記

このセクションの例では、初期化ノードをすでに特定して接続していることを想定しています。

このセクションでは、以下をアップグレードする方法の例を示します。

24.3.1.1.1 Rancherのアップグレード
注記
注記

確実な障害復旧のために、Rancherのバックアップを作成することをお勧めします。方法については、こちらでご確認ください。

この例では、Rancherを2.8.4バージョンにアップグレードする方法を説明します。

  1. Rancher Prime Helmリポジトリを追加します。

    helm repo add rancher-prime https://charts.rancher.com/server-charts/prime
  2. Rancher Primeの最新のHelmチャートバージョンをプルします。

    helm pull rancher-prime/rancher --version=2.8.4
  3. .tgzアーカイブをエンコードし、HelmChart CR設定に渡せるようにします。

    base64 -w 0 rancher-2.8.4.tgz  > rancher-2.8.4-encoded.txt
  4. 編集するrancher.yamlファイルのコピーを作成します。

    cp /var/lib/rancher/rke2/server/manifests/rancher.yaml ./rancher.yaml
  5. rancher.yamlファイルのchartContentversionの設定を変更します。

    sed -i -e "s|chartContent:.*|chartContent: $(<rancher-2.8.4-encoded.txt)|" -e "s|version:.*|version: 2.8.4|" rancher.yaml
    注記
    注記

    アップグレードの追加の変更( 新しいカスタムチャート値の追加など)を加える必要がある場合は、rancher.yamlファイルを手動で編集する必要があります。

  6. 元のrancher.yamlファイルを置き換えます。

    cp rancher.yaml /var/lib/rancher/rke2/server/manifests/

更新を確認するには、次の手順に従います。

  1. defaultネームスペースのPodを一覧にします。

    kubectl get pods -n default
    
    # Example output
    NAME                              READY   STATUS      RESTARTS   AGE
    helm-install-cert-manager-7v7nm   0/1     Completed   0          88m
    helm-install-rancher-p99k5        0/1     Completed   0          3m21s
  2. helm-install-rancher-* Podのログを確認します。

    kubectl logs <helm_install_rancher_pod> -n default
    
    # Example
    kubectl logs helm-install-rancher-p99k5 -n default
  3. RancherのPodが実行されていることを確認します。

    kubectl get pods -n cattle-system
    
    # Example output
    NAME                               READY   STATUS      RESTARTS   AGE
    helm-operation-mccvd               0/2     Completed   0          3m52s
    helm-operation-np8kn               0/2     Completed   0          106s
    helm-operation-q8lf7               0/2     Completed   0          2m53s
    rancher-648d4fbc6c-qxfpj           1/1     Running     0          5m27s
    rancher-648d4fbc6c-trdnf           1/1     Running     0          9m57s
    rancher-648d4fbc6c-wvhbf           1/1     Running     0          9m57s
    rancher-webhook-649dcc48b4-zqjs7   1/1     Running     0          100s
  4. Rancherのバージョンがアップグレードされていることを確認します。

    kubectl get settings.management.cattle.io server-version
    
    # Example output
    NAME             VALUE
    server-version   v2.8.4
24.3.1.1.2 Metal3のアップグレード

この例では、Metal30.7.1バージョンにアップグレードする方法を説明します。

  1. Metal3の最新のHelmチャートバージョンをプルします。

    helm pull oci://registry.suse.com/edge/metal3-chart --version 0.7.1
  2. .tgzアーカイブをエンコードし、HelmChart CR設定に渡せるようにします。

    base64 -w 0 metal3-chart-0.7.1.tgz  > metal3-chart-0.7.1-encoded.txt
  3. 編集するMetal3マニフェストファイルのコピーを作成します。

    cp /var/lib/rancher/rke2/server/manifests/metal3.yaml ./metal3.yaml
  4. Metal3マニフェストファイルのchartContentversionの設定を変更します。

    sed -i -e "s|chartContent:.*|chartContent: $(<metal3-chart-0.7.1-encoded.txt)|" -e "s|version:.*|version: 0.7.1|" metal3.yaml
    注記
    注記

    チャートにアップグレードの追加の変更( 新しいカスタムチャート値の追加など)を加える必要がある場合は、metal3.yamlファイルを手動で編集する必要があります。

  5. 元のMetal3マニフェストファイルを置き換えます。

    cp metal3.yaml /var/lib/rancher/rke2/server/manifests/

更新を確認するには、次の手順に従います。

  1. defaultネームスペースのPodを一覧にします。

    kubectl get pods -n default
    
    # Example output
    NAME                              READY   STATUS      RESTARTS   AGE
    helm-install-metal3-7p7bl         0/1     Completed   0          27s
  2. helm-install-rancher-* Podのログを確認します。

    kubectl logs <helm_install_rancher_pod> -n default
    
    # Example
    kubectl logs helm-install-metal3-7p7bl -n default
  3. Metal3のPodが実行されていることを確認します。

    kubectl get pods -n metal3-system
    
    # Example output
    NAME                                                     READY   STATUS    RESTARTS      AGE
    baremetal-operator-controller-manager-785f99c884-9z87p   2/2     Running   2 (25m ago)   36m
    metal3-metal3-ironic-96fb66cdd-lkss2                     4/4     Running   0             3m54s
    metal3-metal3-mariadb-55fd44b648-q6zhk                   1/1     Running   0             36m
  4. HelmChartのリソースバージョンがアップグレードされていることを確認します。

    kubectl get helmchart metal3 -n default
    
    # Example output
    NAME     JOB                   CHART   TARGETNAMESPACE   VERSION   REPO   HELMVERSION   BOOTSTRAP
    metal3   helm-install-metal3           metal3-system     0.7.1

24.3.2 EIB以外でデプロイされたHelmチャート

  1. 現在実行中のHelmチャートの.yamlファイルの値を取得し、必要に応じて値を変更します。

    helm get values <chart_name> -n <chart_namespace> -o yaml > <chart_name>-values.yaml
  2. Helmチャートを更新します。

    # For charts using a chart repository
    helm upgrade <chart_name> <chart_repo_name>/<chart_name> \
      --namespace <chart_namespace> \
      -f <chart_name>-values.yaml \
      --version=X.Y.Z
    
    # For OCI based charts
    helm upgrade <chart_name> oci://<oci_registry_url>/<chart_name> \
      --namespace <chart_namespace> \
      -f <chart_name>-values.yaml \
      --version=X.Y.Z
  3. チャートがアップグレードされていることを確認します。チャートによっては、さまざまなリソースを確認しなければならない場合があります。チャートのアップグレードの例については、例(24.3.2.1項 「例」)のセクションを参照してください。

24.3.2.1

このセクションでは、以下をアップグレードする方法の例を示します。

24.3.2.1.1 Rancher
注記
注記

確実な障害復旧のために、Rancherのバックアップを作成することをお勧めします。方法については、こちらでご確認ください。

この例では、Rancherを2.8.4バージョンにアップグレードする方法を説明します。

  1. Rancherの現在のリリースの値を取得し、それらの値をrancher-values.yamlファイルに出力します。

    helm get values rancher -n cattle-system -o yaml > rancher-values.yaml
  2. Helmチャートを更新します。

    helm upgrade rancher rancher-prime/rancher \
      --namespace cattle-system \
      -f rancher-values.yaml \
      --version=2.8.4
  3. Rancherのバージョンがアップグレードされていることを確認します。

    kubectl get settings.management.cattle.io server-version
    
    # Example output
    NAME             VALUE
    server-version   v2.8.4

RancherのHelmチャートのアップグレードに関する追加情報については、こちらをご確認ください。

24.3.2.1.2 Metal3

この例では、Metal30.7.1バージョンにアップグレードする方法を説明します。

  1. Rancherの現在のリリースの値を取得し、それらの値をrancher-values.yamlファイルに出力します。

    helm get values metal3 -n metal3-system -o yaml > metal3-values.yaml
  2. Helmチャートを更新します。

    helm upgrade metal3 oci://registry.suse.com/edge/metal3-chart \
      --namespace metal3-system \
      -f metal3-values.yaml \
      --version=0.7.1
  3. Metal3のPodが実行されていることを確認します。

    kubectl get pods -n metal3-system
    
    # Example output
    NAME                                                     READY   STATUS    RESTARTS   AGE
    baremetal-operator-controller-manager-785f99c884-fvsx4   2/2     Running   0          12m
    metal3-metal3-ironic-96fb66cdd-j9mgf                     4/4     Running   0          2m41s
    metal3-metal3-mariadb-55fd44b648-7fmvk                   1/1     Running   0          12m
  4. Metal3のHelmリリースバージョンが変更されていることを確認します。

    helm ls -n metal3-system
    
    # Expected output
    NAME  	NAMESPACE    	REVISION	UPDATED                                	STATUS  	CHART       	APP VERSION
    metal3	metal3-system	2       	2024-06-17 12:43:06.774802846 +0000 UTC	deployed	metal3-0.7.1	1.16.0

25 ダウンストリームクラスタ

このセクションでは、管理クラスタを使用して、ダウンストリームクラスタのさまざまな部分に対して、各種のDay 2操作を行う方法について説明します。

25.1 はじめに

このセクションは、Day 2操作に関するドキュメントの「出発点」となることを目的としています。次の情報を確認できます。

  1. 複数のダウンストリームクラスタでDay 2操作を実行するために使用するデフォルトコンポーネント(25.1.1項 「コンポーネント」)。

  2. 自身の特定のユースケース(25.1.2項 「ユースケースの決定」)にどのDay 2リソースを使用するかの判断。

  3. Day 2操作に推奨されるワークフローシーケンス(25.1.3項 「Day 2ワークフロー」)。

25.1.1 コンポーネント

以下に、Day 2操作を正常に実行できるように、管理クラスタまたはダウンストリームクラスタのいずれかでセットアップする必要があるデフォルトコンポーネントについて説明します。

25.1.1.1 Rancher

注記
注記

Rancherを使用せずにFleet (第6章 「Fleet)を利用するユースケースの場合は、Rancherコンポーネントはまとめてスキップできます。

ダウンストリームクラスタの管理を担当します。管理クラスタ上にデプロイする必要があります。

詳細については、第4章 「Rancherを参照してください。

25.1.1.2 Fleet

マルチクラスタリソースのデプロイメントを担当します。

通常は、Rancherコンポーネントによって提供されます。 Rancherを使用しないユースケースでは、スタンドアロンコンポーネントとしてデプロイできます。

Fleetをスタンドアロンコンポーネントとしてインストールする方法の詳細については、Fleetのインストールの詳細を参照してください。

Fleetコンポーネントに関する詳細については、第6章 「Fleetを参照してください。

重要
重要

このドキュメントは、GitOps方式でDay 2操作に関連するリソースのデプロイメントを自動化するために、Fleet、具体的にはGitRepoBundleリソース(この詳細は25.1.2項 「ユースケースの決定」で詳しく説明します)に大きく依存しています。

サードパーティのGitOpsツールの使用が必要なユースケースの場合は、以下を参照してください。

  1. OSパッケージの更新の場合 - 25.3.4.3項 「SUC Planのデプロイメント - サードパーティのGitOpsワークフロー」

  2. Kubernetesディストリビューションの更新の場合 - 25.4.4.3項 「SUC Planのデプロイメント - サードパーティのGitOpsワークフロー」

  3. Helmチャートのアップグレードの場合 - 33.1項 「要約」のページから目的のEdgeリリースでサポートされているチャートバージョンを取得して、そのチャートバージョンとURLをサードパーティのGitOpsツールに入力します

25.1.1.3 System-upgrade-controller (SUC)

system-upgrade-controller (SUC)は、 カスタムリソースを通じて提供される設定データ(Plan)に基づいて、指定したノード上でタスクを実行する役割を担います。SUCは、何らかのDay 2操作が必要な各ダウンストリームクラスタに配置する必要があります。

SUCに関する詳細については、アップストリームリポジトリを参照してください。

ダウンストリームクラスタにSUCをデプロイする方法については、まず、ユースケース(25.1.2項 「ユースケースの決定」)を決定してから、25.2.1.1項 「GitRepoリソースを使用したSUCのデプロイメント」または25.2.1.2項 「バンドルリソースを使用したSUCのデプロイメント」でSUCのデプロイメントに関する情報を参照してください。

25.1.2 ユースケースの決定

前述のように、Day 2操作に関連するリソースは、FleetのGitRepoリソースとBundleリソースを使用してダウンストリームクラスタに伝播されます。

以下に、これらのリソースの機能と、 Day 2操作に使用する必要があるユースケースに関する詳細を説明します。

25.1.2.1 GitRepo

GitRepoは、Fleetバンドルの作成元として使用できるGitリポジトリを表すFleet (第6章 「Fleet)リソースです。各バンドルは、GitRepoリソースの内部で定義された設定パスに基づいて作成されます。詳細については、GitRepoのドキュメントを参照してください。

Day 2操作の観点では、GitRepoリソースは通常、Fleet GitOpsアプローチを利用する非エアギャップ環境に SUCまたはSUC Planをデプロイするために使用されます。

または、リポジトリのセットアップをローカルGitサーバ経由でミラーリングするとGitRepoリソースを使用して、SUCまたはSUC Planエアギャップ環境にデプロイすることもできます。

25.1.2.2 Bundle

バンドルは、ターゲットクラスタにデプロイする 「生」のKubernetesリソースを保持します。バンドルは通常、GitRepoリソースから作成されますが、手動でデプロイできるユースケースもあります。詳細については、バンドルのドキュメントを参照してください。

Day 2操作の観点では、バンドルリソースは通常、 何らかの形態のローカルGitOps手法を使用しないエアギャップ環境(「ローカルGitサーバ」など )でSUCまたはSUC Planをデプロイするために使用されます。

または、ご自身のユースケースでGitOpsワークフローを使用できない場合は(Gitリポジトリを使用する場合など)、バンドルリソースを使用して、SUCまたはSUC Plan非エアギャップ環境にデプロイすることもできます。

25.1.3 Day 2ワークフロー

以下に、ダウンストリームクラスタを特定のEdgeリリースにアップグレードする際に従う必要があるDay 2ワークフローを示します。

  1. OSパッケージの更新(25.3項 「OSパッケージの更新」)

  2. Kubernetesバージョンアップグレード(25.4項 「Kubernetesバージョンアップグレード」)

  3. Helmチャートのアップグレード(25.5項 「Helmチャートのアップグレード」)

25.2 システムアップグレードコントローラのデプロイメントガイド

system-upgrade-controller (SUC)は、Planと呼ばれるカスタムリソースで定義された設定に基づいてクラスタの特定のノード上にリソースをデプロイする役割を担います。詳細については、アップストリームドキュメントを参照してください。

注記
注記

このセクションは、system-upgrade-controllerのデプロイにのみ焦点を当てています。Planリソースは次のドキュメントからデプロイする必要があります。

  1. OSパッケージの更新(25.3項 「OSパッケージの更新」)

  2. Kubernetesバージョンアップグレード(25.4項 「Kubernetesバージョンアップグレード」)

  3. Helmチャートのアップグレード(25.5項 「Helmチャートのアップグレード」)

25.2.1 デプロイメント

注記
注記

このセクションでは、 Fleet (第6章 「Fleet)を使用してSUCのデプロイメントを調整することを想定しています。サードパーティのGitOpsワークフローを使用しているユーザは、25.2.1.3項 「サードパーティのGitOpsワークフローの使用時におけるsystem-upgrade-controllerのデプロイ」で、そのワークフローでのセットアップに必要なリソースを参照してください。

使用するリソースを判断するには、25.1.2項 「ユースケースの決定」を参照してください。

25.2.1.1 GitRepoリソースを使用したSUCのデプロイメント

このセクションでは、SUCを正常にデプロイするために必要なSUC Planターゲットダウンストリームクラスタに配布するGitRepoリソースを作成する方法について説明します。

Edgeチームは、suse-edge/fleet-examplesの各リリースにおいて、SUCに対してすぐに使えるGitRepoリソースをgitrepos/day2/system-upgrade-controller-gitrepo.yamlで維持しています。

重要
重要

suse-edge/fleet-examplesリポジトリを使用している場合は、必ず、専用のリリースタグのリソースを使用してください。

GitRepoは、次の方法のいずれかで作成できます。

作成されると、Fleetは、リソースを取得し、SUCリソースをすべてのターゲットクラスタにデプロイする役割を担います。デプロイメントプロセスを追跡する方法については、25.2.2.1項 「SUCデプロイメントの監視」を参照してください。

25.2.1.1.1 GitRepoのデプロイメント - Rancher UI
  1. 左上隅で、☰ → [Continuous Delivery (継続的デリバリ)]に移動します。

  2. [Git Repos (Gitリポジトリ)]→[ Add Repository (リポジトリの追加)]に移動します。

suse-edge/fleet-examplesリポジトリを使用する場合:

  1. Repository URL (リポジトリのURL) - https://github.com/suse-edge/fleet-examples.git

  2. [Watch (ウォッチ)]→[Revision (リビジョン)] - 使用するsuse-edge/fleet-examplesリポジトリのリリースタグを選択します(release-3.0.1など)。

  3. [Paths (パス)]の下に、system-upgrade-controllerへのパスを、リリースタグ - fleets/day2/system-upgrade-controllerのとおりに追加します。

  4. [Next (次へ)]を選択して、ターゲットの設定セクションに移動します。

  5. system-upgrade-controllerをデプロイするクラスタのみを選択します。 設定に問題がなければ、[Create (作成)]をクリックします。

または、独自のリポジトリを使用してこれらのファイルをホストする場合は、上の手順で自身のリポジトリデータを指定する必要があります。

25.2.1.1.2 GitRepoの作成 - 手動
  1. SUC GitRepoのデプロイ元にする、目的のEdgeリリース タグを選択します(以下では${REVISION}として参照)。

  2. GitRepoリソースをプルします。

    curl -o system-upgrade-controller-gitrepo.yaml https://raw.githubusercontent.com/suse-edge/fleet-examples/{REVISION}/gitrepos/day2/system-upgrade-controller-gitrepo.yaml
  3. GitRepoの設定を編集し、spec.targetsに目的のターゲットリストを指定します。デフォルトでは、suse-edge/fleet-examplesGitRepoリソースはダウンストリームクラスタにマップ「されません」

  4. GitRepoリソースを管理クラスタに適用します。

    kubectl apply -f system-upgrade-controller-gitrepo.yaml
  5. fleet-defaultネームスペースで、作成した GitRepoリソースを表示します。

    kubectl get gitrepo system-upgrade-controller -n fleet-default
    
    # Example output
    NAME                        REPO                                               COMMIT       BUNDLEDEPLOYMENTS-READY   STATUS
    system-upgrade-controller   https://github.com/suse-edge/fleet-examples.git   release-3.0.1   0/0

25.2.1.2 バンドルリソースを使用したSUCのデプロイメント

このセクションでは、SUCを正常にデプロイするために必要なSUC Planターゲットのダウンストリームクラスタに配布するバンドルリソースを作成する方法について説明します。

Edgeチームは、suse-edge/fleet-examplesの各リリースにおいて、SUCに対してすぐに使えるバンドルリソースをbundles/day2/system-upgrade-controller/controller-bundle.yamlで維持しています。

重要
重要

suse-edge/fleet-examplesリポジトリを使用している場合は、必ず、専用のリリースタグのリソースを使用してください。

バンドルは次のいずれかの方法で作成できます。

作成されると、Fleetは、リソースを取得し、 SUCリソースをすべてのターゲットクラスタにデプロイする役割を担います。デプロイメントプロセスを追跡する方法については、25.2.2.1項 「SUCデプロイメントの監視」を参照してください。

25.2.1.2.1 バンドルの作成 - Rancher UI
  1. 左上隅で、☰ → [Continuous Delivery (継続的デリバリ)]に移動します。

  2. [Advanced (詳細)]>[Bundles (バンドル)] に移動します。

  3. [Create from YAML (YAMLから作成)]を選択します。

  4. ここから次のいずれかの方法でバンドルを作成できます。

    • ファイルコンテンツを[Create from YAML (YAMLから作成)]ページに手動でコピーする。ファイルコンテンツは、https://raw.githubusercontent.com/suse-edge/fleet-examples/${REVISION}/bundles/day2/system-upgrade-controller/controller-bundle.yamlから取得できます。ここで、${REVISION}は、目的のEdge リリースタグです(release-3.0.1など)。

    • suse-edge/fleet-examplesリポジトリを目的のリリースタグに複製し、[Create from YAML (YAMLから作成)]ページの[Read from File (ファイルから読み取り)]オプションを選択する。そこからbundles/day2/system-upgrade-controllerディレクトリに移動し、controller-bundle.yamlを選択します。[Create from YAML (YAMLから作成)]ページにバンドルコンテンツが自動的に入力されます。

  5. バンドルターゲットクラスタを次のように変更します。

  6. 作成します

25.2.1.2.2 バンドルの作成 - 手動
  1. SUCバンドルのデプロイ元にするEdgeリリースタグを選択します(以下では${REVISION}として参照)。

  2. バンドルリソースをプルします。

    curl -o controller-bundle.yaml https://raw.githubusercontent.com/suse-edge/fleet-examples/${REVISION}/bundles/day2/system-upgrade-controller/controller-bundle.yaml
  3. バンドルターゲット設定を編集し、spec.targetsに目的のターゲットリストを指定します。デフォルトでは、suse-edge/fleet-examplesバンドルリソースは、どのダウンストリームクラスタにもマップ「されません」

  4. バンドルリソースを管理クラスタに適用します。

    kubectl apply -f controller-bundle.yaml
  5. fleet-defaultネームスペースで、作成したバンドルリソースを表示します。

    kubectl get bundles system-upgrade-controller -n fleet-default
    
    # Example output
    NAME                        BUNDLEDEPLOYMENTS-READY   STATUS
    system-upgrade-controller   0/0

25.2.1.3 サードパーティのGitOpsワークフローの使用時におけるsystem-upgrade-controllerのデプロイ

サードパーティのGitOpsツールを使用してsystem-upgrade-controllerをデプロイする場合、ツールによっては、system-upgrade-controller HelmチャートまたはKubernetesリソース、あるいはその両方の情報が必要な場合があります。

SUCを使用するための特定のEdgeリリースを選択します。

そこから、SUCのHelmチャートデータをファイルfleets/day2/system-upgrade-controller/fleet.ymalhelm設定セクションで見つけることができます。

SUCのKubernetesリソースは、.spec.resources.contentSUCバンドル設定にあります。バンドルの場所はbundles/day2/system-upgrade-controller/controller-bundle.yamlです。

上記のリソースを使用して、SUCをデプロイするためにサードパーティのGitOpsワークフローで必要なデータを入力します。

25.2.2 Rancherを使用したSUCリソースの監視

このセクションでは、Rancher UIを使用してSUCデプロイメントのライフサイクルおよびデプロイしたSUC Planを監視する方法を説明します。

25.2.2.1 SUCデプロイメントの監視

特定のクラスタのSUC Podのログを確認するには、次の手順を実行します。

  1. 左上隅で、☰ → <クラスタ名>を選択します。

  2. [Workloads (ワークロード)] → [Pods]を選択します。

  3. ネームスペースのドロップダウンメニューで、cattle-systemネームスペースを選択します。

    day2 sucデプロイメントの監視1
  4. [Pods]フィルタバーに、SUCの名前 - system-upgrade-controllerと入力します。

  5. Podの右側で⋮ → [View Logs (ログの表示)]を選択します。

    day2 sucデプロイメントの監視2
  6. SUCのログは次のようになります。

    day2 sucデプロイメントの監視3

25.2.2.2 SUC Planの監視

重要
重要

SUC PlanのPodの存続時間は15分です。この時間を過ぎると、Podを作成した該当するジョブにより削除されます。SUC PlanのPodのログにアクセスするには、クラスタのログを有効にする必要があります。Rancherでログを有効にする方法については、「Rancher Integration with Logging Services (Rancherとログサービスの統合)」を参照してください。

特定のSUC PlanのPodのログを確認するには、次の手順を実行します。

  1. 左上隅で、☰ → <クラスタ名>を選択します。

  2. [Workloads (ワークロード)] → [Pods]を選択します。

  3. ネームスペースのドロップダウンメニューで、cattle-systemネームスペースを選択します。

    day2 sucデプロイメントの監視1
  4. [Pods]フィルタバーにSUC Plan Podの名前を入力します。名前はapply-<plan_name>-on-<node_name>のテンプレート形式に従います。

    day2 k8s planの監視
    図 25.1: KubernetesアップグレードPlanのPodの例

    図1に注目してください。一方のPodが[Completed (完了)]、他方が[Unknown (不明)]になっています。これは想定内であり、ノードのKubernetesバージョンアップグレードによるものです。

    day2 osパッケージplanの監視
    図 25.2: OSパッケージ更新PlanのPodの例
    day2チャートアップグレードPlanの監視
    図 25.3: EIBによってHAクラスタにデプロイされるHelmチャートのアップグレードPlanのPodの例
  5. ログを確認するPodを選択し、⋮ → [View Logs (ログの表示)]に移動します。

25.3 OSパッケージの更新

25.3.1 コンポーネント

このセクションでは、OSパッケージの更新プロセスがデフォルトのDay 2コンポーネント(25.1.1項 「コンポーネント」)よりも優先して使用するカスタムコンポーネントについて説明します。

25.3.1.1 edge-update.service

OSパッケージの更新を実行するSystemdサービスです。transactional-updateコマンドを使用してディストリビューションのアップグレード(dup)を実行します。

注記
注記

通常アップグレードの方法を使用する場合、各ノードの/etc/edge/にファイルedge-update.confを作成します。このファイル内に、UPDATE_METHOD=up変数を追加します。

SUC Planによって配布されます。OSパッケージの更新が必要な各ダウンストリームクラスタに配置する必要があります。

25.3.2 要件

全般:

  1. SCC登録マシン - すべてのダウンストリームクラスタノードは、https://scc.suse.com/に登録する必要があります。これは、edge-update.serviceを必要なOS RPMリポジトリに正しく接続するために必要です。

  2. SUC PlanのTolerationがノードのTolerationと一致すること - KubernetesクラスタノードにカスタムのTaintが設定されている場合は、SUC PlanにそのTaintに対するTolerationを追加してください。デフォルトでは、SUC Planには、control-planeノードのTolerationのみが含まれます。デフォルトのTolerationは次のとおりです。

    • CriticalAddonsOnly=true:NoExecute

    • node-role.kubernetes.io/control-plane:NoSchedule

    • node-role.kubernetes.io/etcd:NoExecute

      注記
      注記

      追加のTolerationは、各Planの.spec.tolerationsセクションに追加する必要があります。OSパッケージの更新に関連するSUC Planは、fleets/day2/system-upgrade-controller-plans/os-pkg-updateの下のsuse-edge/fleet-examplesリポジトリにあります。有効なリポジトリリリースタグからのPlanを使用してください。

      control-plane SUC Planに対してカスタムのTolerationを定義する例は次のようになります。

      apiVersion: upgrade.cattle.io/v1
      kind: Plan
      metadata:
        name: os-pkg-plan-control-plane
      spec:
        ...
        tolerations:
        # default tolerations
        - key: "CriticalAddonsOnly"
          operator: "Equal"
          value: "true"
          effect: "NoExecute"
        - key: "node-role.kubernetes.io/control-plane"
          operator: "Equal"
          effect: "NoSchedule"
        - key: "node-role.kubernetes.io/etcd"
          operator: "Equal"
          effect: "NoExecute"
        # custom toleration
        - key: "foo"
          operator: "Equal"
          value: "bar"
          effect: "NoSchedule"
      ...

エアギャップ:

  1. SUSE RPMリポジトリのミラーリング - OS RPMリポジトリをローカルにミラーリングし、edge-update.serviceがそのリポジトリにアクセスできるようにする必要があります。このためには、RMTを使用します。

25.3.3 更新手順

注記
注記

このセクションでは、Fleet (第6章 「Fleet)を使用してOSパッケージの更新SUC Planをデプロイすることを想定しています。異なる方法でSUC Planをデプロイする場合は、25.3.4.3項 「SUC Planのデプロイメント - サードパーティのGitOpsワークフロー」を参照してください。

OSパッケージの更新手順は、SUC Planをダウンストリームクラスタにデプロイする手順が中心になります。その後、これらのPlanには、edge-update.service systemd.serviceをどのような方法でどのノードにデプロイするかに関する情報が保持されます。SUC Planの構造の詳細については、アップストリームドキュメントを参照してください。

OSパッケージの更新 SUC Planは次の方法で配布されます。

どのリソースを使用すべきかを判断するには、25.1.2項 「ユースケースの決定」を参照してください。

更新手順中の処理の概要については、25.3.3.1項 「概要」のセクションを参照してください。

25.3.3.1 概要

このセクションは、OSパッケージの更新プロセスが開始から終了までに経由するワークフロー全体について説明することを目的としています。

day2 osパッケージ更新の図
図 25.4: OSパッケージの更新ワークフロー

OSパッケージの更新手順:

  1. ユーザは、OSパッケージの更新SUC Planを目的のダウンストリームクラスタにデプロイするために、GitRepoリソースを使用するか、それともバンドルリソースを使用するかをそのユースケースに基づいて判断します。GitRepo/バンドルを特定のダウンストリームクラスタセットにマップする方法の詳細については、「Mapping to Downstream Clusters (ダウンストリームクラスタへのマップ)」を参照してください。

    1. SUC PlanのデプロイメントにGitRepoリソースまたはバンドルリソースのどちらを使用すべきかわからない場合は、25.1.2項 「ユースケースの決定」を参照してください。

    2. GitRepo/バンドルの設定オプションについては、25.3.4.1項 「SUC Planのデプロイメント - GitRepoリソース」または25.3.4.2項 「SUC Planのデプロイメント - バンドルリソース」を参照してください。

  2. ユーザは、設定したGitRepo/バンドルリソースを管理クラスタfleet-defaultのネームスペースにデプロイします。これは、手動で実行するか、Rancher UI (利用可能な場合)を使用して実行します。

  3. Fleet (第6章 「Fleet)は、fleet-defaultネームスペースを絶えず監視し、新しくデプロイされたGitRepo/バンドルリソースをすぐに検出します。Fleetが監視するネームスペースの詳細については、Fleetの「Namespaces (ネームスペース)」のドキュメントを参照してください。

  4. ユーザがGitRepoリソースをデプロイした場合、Fleetは、GitRepoを調整し、そのパスfleet.yamlの設定に基づいて、バンドルリソースをfleet-defaultネームスペースにデプロイします。詳細については、Fleetの「Git Repository Contents (Gitリポジトリの内容)」のドキュメントを参照してください。

  5. Fleetは続いて、Kubernetesリソースをこのバンドルから、ターゲットとするすべてのダウンストリームクラスタにデプロイします。OSパッケージの更新のコンテキストでは、Fleetは、次のリソースをバンドルからデプロイします。

    1. os-pkg-plan-agent SUC Plan - クラスタのエージェントノード上でパッケージの更新を行う方法をSUCに指示します。 クラスタがcontrol-planeノードのみで構成されている場合は、解釈「されません」

    2. os-pkg-plan-control-plane SUC Plan - クラスタのcontrol-planeノードに対してパッケージの更新を実行する方法をSUCに指示します。

    3. os-pkg-update シークレット - 各SUC Planで参照され、実際にパッケージの更新を実行するedge-update.service sustemd.serviceを作成するupdate.shスクリプトを配布します。

      注記
      注記

      上記のリソースは、各ダウンストリームクラスタのcattle-systemネームスペースにデプロイされます。

  6. ダウンストリームクラスタで、SUCは、新しくデプロイされたSUC Planを検出し、 SUC Planで定義されたノードセレクタと一致する各ノードに更新Podをデプロイします。SUC Plan Podを監視する方法については、25.2.2.2項 「SUC Planの監視」を参照してください。

  7. 更新Pod (各ノードにデプロイ)は、os-pkg-updateシークレットをマウントし、シークレットによって配布されるupdate.shスクリプトを実行します。

  8. update.shは、処理を進めて以下を実行します。

    1. edge-update.serviceの作成 - 作成されるサービスはワンショットのタイプで、次のワークフローを採用します。

      1. 以下を実行して、ノードのOS上のすべてのパッケージバージョンを更新します。

        transactional-update cleanup dup
      2. transactional-updateが正常に実行されたら、システムの再起動をスケジュールして、パッケージバージョンの更新を有効にできるようにします。

        注記
        注記

        システムの再起動は、transactional-updateが正常に実行されてから1分の間にスケジュールされます。

    2. edge-update.serviceを起動し、完了するまで待機します。

    3. edge-update.serviceのクリーンアップ - systemd.serviceは、ジョブの完了後にシステムから削除されます。これは今後、誤って実行/再起動されないようにするためです。

OSパッケージの更新手順は、システムの再起動で完了します。再起動後、すべてのOSパッケージバージョンを、利用可能なOS RPMリポジトリに表示されている対応する最新バージョンに更新する必要があります。

25.3.4 OSパッケージの更新 - SUC Planのデプロイメント

このセクションでは、FleetのGitRepoリソースおよびバンドルリソースを使用して、SUC Planに関連するOSパッケージの更新のデプロイメントを調整する方法について説明します。

25.3.4.1 SUC Planのデプロイメント - GitRepoリソース

必要なOSパッケージの更新 SUC Planを配布するGitRepoリソースは、次のいずれかの方法でデプロイできます。

  1. Rancher UIを使用する - 25.3.4.1.1項 「GitRepoの作成 - Rancher UI」 (Rancherが利用可能な場合)。

  2. リソースを管理クラスタに手動でデプロイする(25.3.4.1.2項 「GitRepoの作成 - 手動」)。

デプロイ後に、ターゲットクラスタのノードのOSパッケージの更新プロセスを監視するには、25.2.2.2項 「SUC Planの監視」のドキュメントを参照してください。

25.3.4.1.1 GitRepoの作成 - Rancher UI
  1. 左上隅で、☰ → [Continuous Delivery (継続的デリバリ)]に移動します。

  2. [Git Repos (Gitリポジトリ)]→[ Add Repository (リポジトリの追加)]に移動します。

suse-edge/fleet-examplesリポジトリを使用する場合:

  1. Repository URL (リポジトリのURL) - https://github.com/suse-edge/fleet-examples.git

  2. [Watch (ウォッチ)] → [Revision (リビジョン)] - 使用するsuse-edge/fleet-examplesリポジトリのリリースタグを選択します。

  3. [Paths (パス)]に、使用するOSパッケージ更新用のFleetのパスfleets/day2/system-upgrade-controller-plans/os-pkg-updateを追加します。

  4. [Next (次へ)]を選択してターゲットの設定セクションに移動します。アップグレードするノードのパッケージを含むクラスタのみを選択してください。

  5. 作成します

または、独自のリポジトリを使用してこれらのファイルをホストする場合は、上の手順で自身のリポジトリデータを指定する必要があります。

25.3.4.1.2 GitRepoの作成 - 手動
  1. OSのSUC更新Planの適用元にするEdgeリリースタグを選択します(以下では${REVISION}として参照)。

  2. GitRepoリソースをプルします。

    curl -o os-pkg-update-gitrepo.yaml https://raw.githubusercontent.com/suse-edge/fleet-examples/${REVISION}/gitrepos/day2/os-pkg-update-gitrepo.yaml
  3. GitRepo設定を編集し、spec.targetsで目的のターゲットリストを指定します。デフォルトでは、suse-edge/fleet-examplesGitRepoリソースはどのダウンストリームクラスタにもマップ「されません」

  4. GitRepoリソースを管理クラスタに適用します。

    kubectl apply -f os-pkg-update-gitrepo.yaml
  5. fleet-defaultネームスペースで、作成した GitRepoリソースを表示します。

    kubectl get gitrepo os-pkg-update -n fleet-default
    
    # Example output
    NAME            REPO                                              COMMIT         BUNDLEDEPLOYMENTS-READY   STATUS
    os-pkg-update   https://github.com/suse-edge/fleet-examples.git   release-3.0.1  0/0

25.3.4.2 SUC Planのデプロイメント - バンドルリソース

必要なOSパッケージの更新SUC Planを配布するバンドルリソースは、次のいずれかの方法でデプロイできます。

  1. Rancher UIを使用する - 25.3.4.2.1項 「バンドルの作成 - Rancher UI」 (Rancherが利用可能な場合)。

  2. リソースを管理クラスタに手動でデプロイする(25.3.4.2.2項 「バンドルの作成 - 手動」)。

デプロイ後に、ターゲットクラスタのノードのOSパッケージの更新プロセスを監視するには、25.2.2.2項 「SUC Planの監視」のドキュメントを参照してください。

25.3.4.2.1 バンドルの作成 - Rancher UI
  1. 左上隅で、[☰] → [Continuous Delivery (継続的デリバリ)]をクリックします。

  2. [Advanced (詳細)]>[Bundles (バンドル)] に移動します。

  3. [Create from YAML (YAMLから作成)]を選択します。

  4. ここから次のいずれかの方法でバンドルを作成できます。

    1. バンドルコンテンツを[Create from YAML (YAMLから作成)]ページに手動コピーする。コンテンツは、https://raw.githubusercontent.com/suse-edge/fleet-examples/${REVISION}/bundles/day2/system-upgrade-controller-plans/os-pkg-update/pkg-update-bundle.yamlから取得できます。ここで、${REVISION}は、使用しているEdgeのリリースです。

    2. suse-edge/fleet-examplesリポジトリを目的のリリースタグに複製し、[Create from YAML (YAMLから作成)]ページで[Read from File (ファイルから読み取り)]オプションを選択する。そこから、bundles/day2/system-upgrade-controller-plans/os-pkg-updateディレクトリに移動し、pkg-update-bundle.yamlを選択します。[Create from YAML (YAMLから作成)]ページにバンドルコンテンツが自動的に入力されます。

  5. バンドルターゲットクラスタを次のように変更します。

  6. [Create (作成)]を選択します。

25.3.4.2.2 バンドルの作成 - 手動
  1. OSパッケージの更新SUC Planの適用元にするEdgeのリリースタグを選択します(以下では${REVISION}として参照)。

  2. バンドルリソースをプルします。

    curl -o pkg-update-bundle.yaml https://raw.githubusercontent.com/suse-edge/fleet-examples/${REVISION}/bundles/day2/system-upgrade-controller-plans/os-pkg-update/pkg-update-bundle.yaml
  3. バンドルターゲット設定を編集し、spec.targetsに目的のターゲットリストを指定します。デフォルトでは、suse-edge/fleet-examplesバンドルリソースは、どのダウンストリームクラスタにもマップ「されません」

  4. バンドルリソースを管理クラスタに適用します。

    kubectl apply -f pkg-update-bundle.yaml
  5. fleet-defaultネームスペースで、作成したバンドルリソースを表示します。

    kubectl get bundles os-pkg-update -n fleet-default
    
    # Example output
    NAME            BUNDLEDEPLOYMENTS-READY   STATUS
    os-pkg-update   0/0

25.3.4.3 SUC Planのデプロイメント - サードパーティのGitOpsワークフロー

ユーザがOSパッケージの更新SUC Planを独自のサードパーティGitOpsワークフロー(Fluxなど)に統合したいユースケースが存在する場合があります。

必要なOSパッケージの更新リソースを取得するには、まず、使用するsuse-edge/fleet-examplesリポジトリのEdgeリリースタグを特定します。

その後、リソースをfleets/day2/system-upgrade-controller-plans/os-pkg-updateで特定できます。

  • plan-control-plane.yaml - control-planeノードのsystem-upgrade-controllerのPlanリソース

  • plan-agent.yaml - system-upgrade-controller agentノードのPlanリソース

  • secret.yaml - edge-update.service systemd.serviceを作成するスクリプトを配布するシークレット

重要
重要

これらのPlanリソースは、system-upgrade-controllerによって解釈され、アップグレードする各ダウンストリームクラスタにデプロイする必要があります。system-upgrade-controllerをデプロイする方法については、25.2.1.3項 「サードパーティのGitOpsワークフローの使用時におけるsystem-upgrade-controllerのデプロイ」を参照してください。

GitOpsワークフローを使用してOSパッケージの更新用のSUC Planをデプロイする方法について理解を深めるには、Fleetを使用した更新手順の概要(25.3.3.1項 「概要」)を確認すると役に立ちます。

25.4 Kubernetesバージョンアップグレード

重要
重要

このセクションでは、Rancher (第4章 「Rancher)インスタンスを使用して作成されて「いない」ダウンストリームクラスタのアップグレードについて説明します。Rancherで作成したクラスタのKubernetesバージョンをアップグレードする方法については、「Upgrading and Rolling Back Kubernetes (Kubernetesのアップグレードとロールバック)」を参照してください。

25.4.1 コンポーネント

このセクションでは、KubernetesアップグレードプロセスがデフォルトのDay 2コンポーネント(25.1.1項 「コンポーネント」)よりも優先して使用するカスタムコンポーネントについて説明します。

25.4.1.1 rke2-upgrade

特定ノードのRKE2バージョンのアップグレードを行うイメージです。

SUC Planに基づいてSUCによって作成されたPodを通じて配布されます。このPlanは、RKE2のアップグレードが必要な各ダウンストリームクラスタに配置する必要があります。

rke2-upgradeイメージによるアップグレードの実行方法の詳細については、アップストリームドキュメントを参照してください。

25.4.1.2 k3s-upgrade

特定のノードのK3sバージョンをアップグレードするイメージです。

SUC Planに基づいてSUCによって作成されたPodを通じて配布されます。このPlanは、K3sのアップグレードが必要な各ダウンストリームクラスタに配置する必要があります。

k3s-upgradeイメージによるアップグレードの実行方法の詳細については、アップストリームドキュメントを参照してください。

25.4.2 要件

  1. Kubernetesディストリビューションをバックアップします。

    1. インポートしたRKE2クラスタについては、RKE2のバックアップと復元に関するドキュメントを参照してください。

    2. インポートしたK3sクラスタについては、K3sのバックアップと復元に関するドキュメントを参照してください。

  2. SUC PlanのTolerationがノードのTolerationと一致すること - KubernetesクラスタノードにカスタムのTaintが設定されている場合は、SUC PlanにそのTaintに対するTolerationを追加してください。デフォルトでは、SUC Planには、control-planeノードのTolerationのみが含まれます。デフォルトのTolerationは次のとおりです。

    • CriticalAddonsOnly=true:NoExecute

    • node-role.kubernetes.io/control-plane:NoSchedule

    • node-role.kubernetes.io/etcd:NoExecute

      注記
      注記

      追加のTolerationは、各Planの.spec.tolerationsセクションに追加する必要があります。Kubernetesバージョンアップグレードに関するSUC Planは、次の場所のsuse-edge/fleet-examplesリポジトリにあります。

      • RKE2 - fleets/day2/system-upgrade-controller-plans/rke2-upgrade

      • K3s - fleets/day2/system-upgrade-controller-plans/k3s-upgrade

      必ず、有効なリポジトリリリースタグからのPlanを使用してください。

      RKE2 control-plane SUC PlanのカスタムTolerationの定義例は次のようになります。

      apiVersion: upgrade.cattle.io/v1
      kind: Plan
      metadata:
        name: rke2-plan-control-plane
      spec:
        ...
        tolerations:
        # default tolerations
        - key: "CriticalAddonsOnly"
          operator: "Equal"
          value: "true"
          effect: "NoExecute"
        - key: "node-role.kubernetes.io/control-plane"
          operator: "Equal"
          effect: "NoSchedule"
        - key: "node-role.kubernetes.io/etcd"
          operator: "Equal"
          effect: "NoExecute"
        # custom toleration
        - key: "foo"
          operator: "Equal"
          value: "bar"
          effect: "NoSchedule"
      ...

25.4.3 アップグレード手順

注記
注記

このセクションでは、SUC PlanをFleet (第6章 「Fleet)を使用してデプロイすることを想定しています。別の方法でSUC Planをデプロイする場合は、25.4.4.3項 「SUC Planのデプロイメント - サードパーティのGitOpsワークフロー」を参照してください。

Kubernetesバージョンアップグレード手順は、SUC Planをダウンストリームクラスタにデプロイする手順が中心になります。その後、これらのPlanには、SUCに対し、rke2/k3s-upgradeイメージを実行するPodをどのノード上に作成するかを指示する情報が保持されます。SUC Planの構造については、アップストリームドキュメントを参照してください。

KubernetesアップグレードPlanは次のように配布されます。

どのリソースを使用すべきかを判断するには、25.1.2項 「ユースケースの決定」を参照してください。

更新手順中の処理の概要については、25.4.3.1項 「概要」のセクションを参照してください。

25.4.3.1 概要

このセクションは、Kubernetesバージョンアップグレードプロセスが開始から終了までに経由するワークフロー全体について説明することを目的としています。

day2 k8sバージョンアップグレードの図
図 25.5: Kubernetesバージョンアップグレードのワークフロー

Kubernetesバージョンアップグレードの手順:

  1. ユーザは、KubernetesアップグレードSUC Planを目的のダウンストリームクラスタにデプロイするために、GitRepoリソースを使用するか、それともバンドルリソースを使用するかをそのユースケースに基づいて判断します。GitRepo/バンドルを特定のダウンストリームクラスタセットにマップする方法の詳細については、「Mapping to Downstream Cluster (ダウンストリームクラスタへのマップ)」を参照してください。

    1. SUC PlanのデプロイメントにGitRepoリソースまたはバンドルリソースのどちらを使用すべきかわからない場合は、25.1.2項 「ユースケースの決定」を参照してください。

    2. GitRepo/バンドルの設定オプションについては、25.4.4.1項 「SUC Planのデプロイメント - GitRepoリソース」または25.4.4.2項 「SUC Planのデプロイメント - バンドルリソース」を参照してください。

  2. ユーザは、設定したGitRepo/バンドルリソースを管理クラスタfleet-defaultのネームスペースにデプロイします。これは、手動で実行するか、Rancher UI (利用可能な場合)を使用して実行します。

  3. Fleet (第6章 「Fleet)は、fleet-defaultネームスペースを絶えず監視し、新しくデプロイされたGitRepo/バンドルリソースをすぐに検出します。Fleetが監視するネームスペースの詳細については、Fleetの「Namespaces (ネームスペース)」のドキュメントを参照してください。

  4. ユーザがGitRepoリソースをデプロイした場合、Fleetは、GitRepoを調整し、そのパスfleet.yamlの設定に基づいて、バンドルリソースをfleet-defaultネームスペースにデプロイします。詳細については、Fleetの「Git Repository Contents (Gitリポジトリの内容)」のドキュメントを参照してください。

  5. Fleetは続いて、Kubernetesリソースをこのバンドルから、ターゲットとするすべてのダウンストリームクラスタにデプロイします。Kubernetesバージョンアップグレードのコンテキストでは、Fleetは、次のリソースをバンドルからデプロイします(Kubernetesディストリビューションによって異なる)。

    1. rke2-plan-agent/k3s-plan-agent - クラスタエージェントノードでKubernetesをアップグレードする方法をSUCに指示します。クラスタがcontrol-planeノードのみで構成されている場合は、解釈「されません」

    2. rke2-plan-control-plane/k3s-plan-control-plane - クラスタのcontrol-planeノードでKubernetesをアップグレードする方法をSUCに指示します。

      注記
      注記

      上記のSUC Planは、各ダウンストリームクラスタのcattle-systemネームスペースにデプロイされます。

  6. ダウンストリームクラスタで、SUCは、新しくデプロイされたSUC Planを検出し、 SUC Planで定義されたノードセレクタと一致する各ノードに更新Podをデプロイします。SUC Plan Podを監視する方法については、25.2.2.2項 「SUC Planの監視」を参照してください。

  7. デプロイしたSUC Planに応じて、更新Podは、rke2-upgradeイメージまたはk3s-upgradeイメージのいずれかを実行して、それぞれのクラスタノードで次のワークフローを実行します。

    1. Cordonクラスタノード - ノードのアップグレード時にこのノードにPodが誤ってスケジュールされないようにするために、このノードをunschedulableとマークします。

    2. ノードOSにインストールされているrke2/k3sバイナリを、Podが現在実行しているrke2-upgrade/k3s-upgradeイメージによって配布されるバイナリに置き換えます。

    3. ノードOSで実行されているrke2/k3sプロセスを強制終了します - これにより、新しいバージョンを使用してrke2/k3sプロセスを自動的に再起動するようにスーパーバイザに指示します。

    4. Uncordonクラスタノード - Kubernetesディストリビューションが正常にアップグレードされると、このノードは再びscheduableとマークされます。

      注記
      注記

      rke2-upgradeイメージおよびk3s-upgradeイメージの機能の詳細については、rke2-upgradeおよびk3s-upgradeのアップストリームプロジェクトを参照してください。

上記の手順を実行すると、各クラスタノードのKubernetesバージョンが目的のEdge互換リリースにアップグレードされているはずです。

25.4.4 Kubernetesバージョンアップグレード - SUC Planのデプロイメント

25.4.4.1 SUC Planのデプロイメント - GitRepoリソース

必要なKubernetesアップグレードSUC Planを配布するGitRepoリソースは、次のいずれかの方法でデプロイできます。

  1. Rancher UIを使用する - 25.4.4.1.1項 「GitRepoの作成 - Rancher UI」 (Rancherが利用可能な場合)。

  2. リソースを管理クラスタに手動でデプロイする(25.4.4.1.2項 「GitRepoの作成 - 手動」)。

デプロイ後に、ターゲットクラスタのノードのKubernetesのアップグレードプロセスを監視するには、25.2.2.2項 「SUC Planの監視」のドキュメントを参照してください。

25.4.4.1.1 GitRepoの作成 - Rancher UI
  1. 左上隅で、☰ → [Continuous Delivery (継続的デリバリ)]に移動します。

  2. [Git Repos (Gitリポジトリ)]→[ Add Repository (リポジトリの追加)]に移動します。

suse-edge/fleet-examplesリポジトリを使用する場合:

  1. Repository URL (リポジトリのURL) - https://github.com/suse-edge/fleet-examples.git

  2. [Watch (ウォッチ)] → [Revision (リビジョン)] - 使用するsuse-edge/fleet-examplesリポジトリのリリースタグを選択します。

  3. [Paths (パス)]の下に、KubernetesディストリビューションのアップグレードFleetへのパスを、リリースタグに表示されているとおりに追加します。

    1. RKE2の場合 - fleets/day2/system-upgrade-controller-plans/rke2-upgrade

    2. K3sの場合 - fleets/day2/system-upgrade-controller-plans/k3s-upgrade

  4. [Next (次へ)]を選択し、ターゲットの設定セクションに移動します。目的のKubernetesディストリビューションをアップグレードするクラスタのみを選択します

  5. 作成します

または、独自のリポジトリを使用してこれらのファイルをホストする場合は、上の手順で自身のリポジトリデータを指定する必要があります。

25.4.4.1.2 GitRepoの作成 - 手動
  1. Kubernetes SUCアップグレードPlanを適用する目的のEdgeリリースタグを選択します(以下では${REVISION}として参照)。

  2. GitRepoリソースをプルします。

    • RKE2クラスタの場合:

      curl -o rke2-upgrade-gitrepo.yaml https://raw.githubusercontent.com/suse-edge/fleet-examples/${REVISION}/gitrepos/day2/rke2-upgrade-gitrepo.yaml
    • K3sクラスタの場合:

      curl -o k3s-upgrade-gitrepo.yaml https://raw.githubusercontent.com/suse-edge/fleet-examples/${REVISION}/gitrepos/day2/k3s-upgrade-gitrepo.yaml
  3. GitRepo設定を編集し、spec.targetsで目的のターゲットリストを指定します。デフォルトでは、suse-edge/fleet-examplesGitRepoリソースはどのダウンストリームクラスタにもマップ「されません」

  4. GitRepoリソースを管理クラスタに適用します。

    # RKE2
    kubectl apply -f rke2-upgrade-gitrepo.yaml
    
    # K3s
    kubectl apply -f k3s-upgrade-gitrepo.yaml
  5. fleet-defaultネームスペースで、作成した GitRepoリソースを表示します。

    # RKE2
    kubectl get gitrepo rke2-upgrade -n fleet-default
    
    # K3s
    kubectl get gitrepo k3s-upgrade -n fleet-default
    
    # Example output
    NAME           REPO                                              COMMIT          BUNDLEDEPLOYMENTS-READY   STATUS
    k3s-upgrade    https://github.com/suse-edge/fleet-examples.git   release-3.0.1   0/0
    rke2-upgrade   https://github.com/suse-edge/fleet-examples.git   release-3.0.1   0/0

25.4.4.2 SUC Planのデプロイメント - バンドルリソース

必要なKubernetesアップグレードSUC Planを配布するバンドルリソースは、次のいずれかの方法でデプロイできます。

  1. Rancher UIを使用する - 25.4.4.2.1項 「バンドルの作成 - Rancher UI」 (Rancherが利用可能な場合)。

  2. リソースを管理クラスタに手動でデプロイする(25.4.4.2.2項 「バンドルの作成 - 手動」)。

デプロイ後に、ターゲットクラスタのノードのKubernetesのアップグレードプロセスを監視するには、25.2.2.2項 「SUC Planの監視」のドキュメントを参照してください。

25.4.4.2.1 バンドルの作成 - Rancher UI
  1. 左上隅で、[☰] → [Continuous Delivery (継続的デリバリ)]をクリックします。

  2. [Advanced (詳細)]>[Bundles (バンドル)] に移動します。

  3. [Create from YAML (YAMLから作成)]を選択します。

  4. ここから次のいずれかの方法でバンドルを作成できます。

    1. バンドルコンテンツを[Create from YAML (YAMLから作成)]ページに手動でコピーする。コンテンツは次の場所から取得できます。

    2. suse-edge/fleet-examplesリポジトリを目的のリリースタグに複製し、[Create from YAML (YAMLから作成)]ページの[Read from File (ファイルから読み取り)]オプションを選択します。そこから、必要なバンドルに移動します(RKE2の場合は/bundles/day2/system-upgrade-controller-plans/rke2-upgrade/plan-bundle.yaml、K3sの場合は/bundles/day2/system-upgrade-controller-plans/k3s-upgrade/plan-bundle.yaml)。[Create from YAML (YAMLから作成)]ページにバンドルコンテンツが自動的に入力されます。

  5. バンドルターゲットクラスタを次のように変更します。

  6. 作成します

25.4.4.2.2 バンドルの作成 - 手動
  1. Kubernetes SUCアップグレードPlanを適用する目的のEdgeリリースタグを選択します(以下では${REVISION}として参照)。

  2. バンドルリソースをプルします。

    • RKE2クラスタの場合:

      curl -o rke2-plan-bundle.yaml https://raw.githubusercontent.com/suse-edge/fleet-examples/${REVISION}/bundles/day2/system-upgrade-controller-plans/rke2-upgrade/plan-bundle.yaml
    • K3sクラスタの場合:

      curl -o k3s-plan-bundle.yaml https://raw.githubusercontent.com/suse-edge/fleet-examples/${REVISION}/bundles/day2/system-upgrade-controller-plans/k3s-upgrade/plan-bundle.yaml
  3. バンドルターゲット設定を編集し、spec.targetsに目的のターゲットリストを指定します。デフォルトでは、suse-edge/fleet-examplesバンドルリソースは、どのダウンストリームクラスタにもマップ「されません」

  4. バンドルリソースを管理クラスタに適用します。

    # For RKE2
    kubectl apply -f rke2-plan-bundle.yaml
    
    # For K3s
    kubectl apply -f k3s-plan-bundle.yaml
  5. fleet-defaultネームスペースで、作成したバンドルリソースを表示します。

    # For RKE2
    kubectl get bundles rke2-upgrade -n fleet-default
    
    # For K3s
    kubectl get bundles k3s-upgrade -n fleet-default
    
    # Example output
    NAME           BUNDLEDEPLOYMENTS-READY   STATUS
    k3s-upgrade    0/0
    rke2-upgrade   0/0

25.4.4.3 SUC Planのデプロイメント - サードパーティのGitOpsワークフロー

ユーザがKubernetesアップグレードリソースを独自のサードパーティGitOpsワークフロー(Fluxなど)に統合したいユースケースが存在する場合があります。

必要なアップグレードリソースを取得するには、まず、使用するsuse-edge/fleet-examplesリポジトリのEdgeリリースタグを特定します。

その後、次の場所でリソースを確認できます。

  • RKE2クラスタのアップグレードの場合:

    • control-planeノード用 - fleets/day2/system-upgrade-controller-plans/rke2-upgrade/plan-control-plane.yaml

    • エージェントノード用 - fleets/day2/system-upgrade-controller-plans/rke2-upgrade/plan-agent.yaml

  • K3sクラスタのアップグレードの場合:

    • control-planeノード用 - fleets/day2/system-upgrade-controller-plans/k3s-upgrade/plan-control-plane.yaml

    • agentノード用 - fleets/day2/system-upgrade-controller-plans/k3s-upgrade/plan-agent.yaml

重要
重要

これらのPlanリソースは、system-upgrade-controllerによって解釈され、アップグレードする各ダウンストリームクラスタにデプロイする必要があります。system-upgrade-controllerをデプロイする方法については、25.2.1.3項 「サードパーティのGitOpsワークフローの使用時におけるsystem-upgrade-controllerのデプロイ」を参照してください。

GitOpsワークフローを使用してKubernetesバージョンアップグレード用のSUC Planをデプロイする方法について理解を深めるには、Fleetを使用した更新手順の概要(25.4.3.1項 「概要」)を確認すると役に立ちます。

25.5 Helmチャートのアップグレード

注記
注記

以下の各セクションでは、Fleetの機能を使用してHelmチャートの更新を実現する方法を中心に説明します。

サードパーティのGitOpsワークフローを採用するユーザは、fleets/day2/chart-templates/<chart-name>にあるfleet.yamlから目的のHelmチャートの設定を取得する必要があります。有効な「Day 2」Edgeリリースからチャートデータを取得してください。

25.5.1 コンポーネント

この操作には、デフォルトのDay 2コンポーネント(25.1.1項 「コンポーネント」)以外のカスタムコンポーネントは不要です。

25.5.2 エアギャップ環境の準備

25.5.2.1 Helmチャートのアップグレードfleet.yamlファイルにアクセスできることの確認

必要なリソースを管理クラスタがアクセスできるローカルGitサーバにホストします。

25.5.2.2 Edgeリリースバージョンに必要なアセットの検索

  1. Day 2リリースのページに移動し、チャートのアップグレード先のEdge 3.X.Yリリースを見つけ、[Assets (アセット)]をクリックします。

  2. そのリリースの[Assets (アセット)]セクションから、次のファイルをダウンロードします。これは、SUSEがサポートするHelmチャートのエアギャップアップグレードに必要です。

    リリースファイル

    説明

    edge-save-images.sh

    このスクリプトは、ファイルedge-release-images.txtに記載されたイメージをプルし、エアギャップ環境で使用できる「.tar.gz」アーカイブに保存します。

    edge-save-oci-artefacts.sh

    このスクリプトは、ファイルedge-release-helm-oci-artefacts.txtに記載されたSUSE OCIチャートアーティファクトを取得し、その他すべてのチャートOCIアーカイブを含むディレクトリの「.tar.gz」アーカイブを作成します。

    edge-load-images.sh

    このスクリプトは、edge-save-images.shによって生成された「.tar.gz」アーカイブのイメージを読み込み、そのイメージに再度タグを付けて、プライベートレジストリにプッシュします。

    edge-load-oci-artefacts.sh

    このスクリプトは、「.tgz」SUSE OCIチャートを含むディレクトリを取得し、すべてのOCIチャートをプライベートレジストリに読み込みます。ディレクトリは、edge-save-oci-artefacts.shスクリプトによって生成された「.tar.gz」アーカイブから取得されます。

    edge-release-helm-oci-artefacts.txt

    このファイルには、SUSE EdgeリリースHelmチャートのOCIアーティファクトが含まれています。

    edge-release-images.txt

    このファイルには、EdgeリリースHelmチャートに必要なイメージのリストが含まれています。

25.5.2.3 SUSE Edgeリリースイメージのアーカイブの作成

インターネットにアクセスできるマシンで次の手順を実行します。

  1. edge-save-images.shを実行可能にします。

    chmod +x edge-save-images.sh
  2. edge-save-images.shスクリプトを使用して、Dockerのインポート可能な「.tar.gz」アーカイブを作成します。

    ./edge-save-images.sh --source-registry registry.suse.com
  3. -i|--imagesオプションを指定していない場合、すぐに読み込めるedge-images.tar.gzアーカイブが必要なイメージとともに作成されます。

  4. このアーカイブをエアギャップマシンにコピーします

    scp edge-images.tar.gz <user>@<machine_ip>:/path

25.5.2.4 SUSE Edge HelmチャートOCIイメージのアーカイブの作成

インターネットにアクセスできるマシンで次の手順を実行します。

  1. edge-save-oci-artefacts.shを実行可能にします。

    chmod +x edge-save-oci-artefacts.sh
  2. edge-save-oci-artefacts.shスクリプトを使用して、すべてのSUSE Edge HelmチャートOCIイメージの「.tar.gz」アーカイブを作成します。

    ./edge-save-oci-artefacts.sh --source-registry registry.suse.com
  3. すべてのSUSE Edge HelmチャートOCIイメージを含むoci-artefacts.tar.gzアーカイブが作成されます。

  4. このアーカイブをエアギャップマシンにコピーします

    scp oci-artefacts.tar.gz <user>@<machine_ip>:/path

25.5.2.5 エアギャップマシンへのSUSE Edgeリリースイメージの読み込み

エアギャップマシンで次の手順を実行します。

  1. プライベートレジストリにログインします(必要な場合)。

    podman login <REGISTRY.YOURDOMAIN.COM:PORT>
  2. edge-load-images.shを実行可能にします。

    chmod +x edge-load-images.sh
  3. edge-load-images.shを使用して、コピーした edge-images.tar.gzアーカイブからイメージを読み込み、そのイメージに再度タグを付けて、プライベートレジストリにプッシュします。

    ./edge-load-images.sh --source-registry registry.suse.com --registry <REGISTRY.YOURDOMAIN.COM:PORT> --images edge-images.tar.gz

25.5.2.6 エアギャップマシンへのSUSE Edge HelmチャートOCIイメージの読み込み

エアギャップマシンで次の手順を実行します。

  1. プライベートレジストリにログインします(必要な場合)。

    podman login <REGISTRY.YOURDOMAIN.COM:PORT>
  2. edge-load-oci-artefacts.shを実行可能にします。

    chmod +x edge-load-oci-artefacts.sh
  3. コピーしたoci-artefacts.tar.gzアーカイブをuntarします。

    tar -xvf oci-artefacts.tar.gz
  4. 命名テンプレートedge-release-oci-tgz-<date>を含むディレクトリが生成されます。

  5. このディレクトリをedge-load-oci-artefacts.shスクリプトに渡し、SUSE Edge HelmチャートOCIイメージをプライベートレジストリに読み込みます。

    注記
    注記

    このスクリプトは、Helm CLIが環境にプリインストールされていることを想定しています。Helmのインストール手順については、「Helmのインストール」を参照してください。

    ./edge-load-oci-artefacts.sh --archive-directory edge-release-oci-tgz-<date> --registry <REGISTRY.YOURDOMAIN.COM:PORT> --source-registry registry.suse.com

25.5.2.7 Kubernetesディストリビューションのプライベートレジストリを指すレジストリミラーの作成

RKE2の場合は、「Containerd Registry Configuration (Containerdレジストリの設定)」を参照してください。

K3sの場合は、「埋め込みレジストリミラー」を参照してください。

25.5.3 アップグレード手順

注記
注記

以下のアップグレード手順は、RancherのFleet (第6章 「Fleet)機能を利用します。サードパーティのGitOpsワークフローを使用するユーザは、33.1項 「要約」から各Edgeリリースでサポートされるチャートバージョンを取得し、そのバージョンをサードパーティのGitOpsワークフローに入力する必要があります。

このセクションでは、Helmアップグレード手順の次のユースケースを中心に説明します。

  1. 新しいクラスタがあり、SUSE Helmチャートをデプロイして管理したい(25.5.3.1項 「新しいクラスタがあり、SUSE Helmチャートをデプロイして管理したい場合」)

  2. Fleetで管理されているHelmチャートをアップグレードしたい(25.5.3.2項 「Fleetで管理されているHelmチャートをアップグレードしたい場合」)

  3. EIBで作成されたHelmチャートをアップグレードしたい(25.5.3.3項 「EIBで作成されたHelmチャートをアップグレードしたい場合」)

重要
重要

手動でデプロイしたHelmチャートを確実にアップグレードすることはできません。25.5.3.1項 「新しいクラスタがあり、SUSE Helmチャートをデプロイして管理したい場合」で説明する方法を使用してHelmチャートを再デプロイすることをお勧めします。

25.5.3.1 新しいクラスタがあり、SUSE Helmチャートをデプロイして管理したい場合

Fleetを使用してHelmチャートのライフサイクルを管理したいユーザが対象です。

25.5.3.1.1 Fleetリソースの準備
  1. チャートのFleetリソースを、使用するEdgeリリースタグから取得します。

    1. 選択したEdgeリリースタグのリビジョンから、HelmチャートのFleet (fleets/day2/chart-templates/<chart>)に移動します。

    2. チャートのFleetディレクトリを、GitOpsワークフローで使用するGitリポジトリにコピーします。

    3. (任意) Helmチャートでを設定する必要がある場合は、コピーしたディレクトリのfleet.yamlファイルに含まれる設定.helm.valuesを編集します。

    4. (任意) 環境に合わせて、チャートのFleetにリソースを追加しなければならないユースケースがあります。Fleetディレクトリを拡張する方法については、「Git Repository Contents (Gitリポジトリのコンテンツ)」を参照してください。

longhorn Helmチャートのは次のようになります。

  • ユーザのGitリポジトリの構造:

    <user_repository_root>
    └── longhorn
        └── fleet.yaml
  • ユーザのlonghornデータが入力されたfleet.yaml の内容:

    defaultNamespace: longhorn-system
    
    helm:
      releaseName: "longhorn"
      chart: "longhorn"
      repo: "https://charts.longhorn.io"
      version: "1.6.1"
      takeOwnership: true
      # custom chart value overrides
      values:
        # Example for user provided custom values content
        defaultSettings:
          deletingConfirmationFlag: true
    
    # https://fleet.rancher.io/bundle-diffs
    diff:
      comparePatches:
      - apiVersion: apiextensions.k8s.io/v1
        kind: CustomResourceDefinition
        name: engineimages.longhorn.io
        operations:
        - {"op":"remove", "path":"/status/conditions"}
        - {"op":"remove", "path":"/status/storedVersions"}
        - {"op":"remove", "path":"/status/acceptedNames"}
      - apiVersion: apiextensions.k8s.io/v1
        kind: CustomResourceDefinition
        name: nodes.longhorn.io
        operations:
        - {"op":"remove", "path":"/status/conditions"}
        - {"op":"remove", "path":"/status/storedVersions"}
        - {"op":"remove", "path":"/status/acceptedNames"}
      - apiVersion: apiextensions.k8s.io/v1
        kind: CustomResourceDefinition
        name: volumes.longhorn.io
        operations:
        - {"op":"remove", "path":"/status/conditions"}
        - {"op":"remove", "path":"/status/storedVersions"}
        - {"op":"remove", "path":"/status/acceptedNames"}
    注記
    注記

    これらは値の例であり、longhornチャートのカスタム設定を示すために使用しているだけです。longhornチャートのデプロイメントのガイドラインと「みなさない」でください。

25.5.3.1.2 GitRepoの作成

リポジトリにチャートのFleetリソースを入力した後、GitRepoリソースを作成する必要があります。このリソースは、チャートのFleetリソースへのアクセス方法と、これらのリソースを適用する必要があるクラスタに関する情報を保持します。

GitRepoリソースは、Rancher UIを使用するか、リソースを管理クラスタに手動でデプロイすることによって作成できます。

GitRepoリソースを手動で作成してデプロイする方法については、「Creating a Deployment (デプロイメントの作成)」を参照してください。

Rancher UIを使用してGitRepoリソースを作成するには、「Accessing Fleet in the Rancher UI (Rancher UIでのFleetへのアクセス)」を参照してください。

手動デプロイメントのLonghorn GitRepoリソースの例

apiVersion: fleet.cattle.io/v1alpha1
kind: GitRepo
metadata:
  name: longhorn-git-repo
  namespace: fleet-default
spec:
  # If using a tag
  # revision: <user_repository_tag>
  #
  # If using a branch
  # branch: <user_repository_branch>
  paths:
  # As seen in the 'Prepare your Fleet resources' example
  - longhorn
  repo: <user_repository_url>
  targets:
  # Match all clusters
  - clusterSelector: {}
25.5.3.1.3 デプロイされたHelmチャートの管理

Fleetでデプロイした後のHelmチャートのアップグレードについては、25.5.3.2項 「Fleetで管理されているHelmチャートをアップグレードしたい場合」を参照してください。

25.5.3.2 Fleetで管理されているHelmチャートをアップグレードしたい場合

  1. チャートのアップグレード後のバージョンを確認し、Edge 3.X.Yリリースとの互換性を確保します。各Edgeリリースに対応するHelmチャートのバージョンは、33.1項 「要約」で確認できます。

  2. Fleetで監視されているGitリポジトリで、Helmチャートのfleet.yamlファイルを、33.1項 「要約」から取得した正しいチャートバージョンリポジトリで編集します。

  3. リポジトリの変更をコミットしてプッシュすると、目的のHelmチャートのアップグレードがトリガされます。

25.5.3.3 EIBで作成されたHelmチャートをアップグレードしたい場合

注記
注記

このセクションでは、system-upgrade-controller (SUC)を事前にデプロイ済みであることを想定しています。まだデプロイしていないか、SUCが必要な理由がわからない場合は、デフォルトのDay 2コンポーネント(25.1.1項 「コンポーネント」)のリストを参照してください。

EIBでは、Helmチャートをデプロイするために、rke2/k3sのマニフェストの自動デプロイ機能を利用します。具体的には、Helmチャートのリソース定義マニフェストを初期化ノードの/var/lib/rancher/<rke2/k3s>/server/manifestsに作成し、rke2/k3sがこれを検出してクラスタ内に自動デプロイします。

Day 2の観点から見ると、これは、特定のチャートのHelmChartマニフェストファイルを編集してHelmチャートをアップグレードする必要があることを意味します。このプロセスを複数のクラスタで自動化するために、このセクションではSUC Planを使用します。

以下に関する情報が提供されています。

25.5.3.3.1 概要

このセクションは、1つまたは複数のHelmチャートをアップグレードするためにユーザが行うワークフローの概要を説明することを意図しています。Helmチャートのアップグレードに必要な手順の詳細な説明については、25.5.3.3.2項 「アップグレード手順」を参照してください。

day2 helmチャートアップグレードの図
図 25.6: Helmチャートのアップグレードワークフロー
  1. このワークフローでは最初に、チャートのアップグレード先にする新しいHelmチャートアーカイブをユーザがプルします。

  2. 続いて、アーカイブをエンコードし、関連するSUC PlanのFleetディレクトリにあるeib-chart-upgrade-user-data.yamlファイルに設定として渡す必要があります。これは、アップグレード手順(25.5.3.3.2項 「アップグレード手順」)のセクションで詳しく説明しています。

  3. ユーザは次の操作に進み、必要なすべてのリソース(SUC Plan、シークレットなど)をダウンストリームクラスタに配布するGitRepoリソースを設定してデプロイします。

    1. リソースはfleet-defaultネームスペースの管理クラスタにデプロイされます。

  4. Fleet (第6章 「Fleet)はデプロイされたリソースを検出し、設定されているすべてのリソースを指定のダウンストリームクラスタにデプロイします。デプロイされたリソースには次のようなものがあります。

    1. eib-chart-upgrade SUC Plan。各ノードにアップグレードPodを作成するためにSUCで使用されます。

    2. eib-chart-upgrade-scriptシークレット。アップグレードPodが初期化ノードでHelmChartマニフェストをアップグレードするために使用するアップグレードスクリプトを配布します。

    3. eib-chart-upgrade-user-dataシークレット。アップグレードする必要があるチャートマニフェストを理解するためにアップグレードスクリプトで使用するチャートデータを配布します。

  5. eib-chart-upgrade SUC Planがデプロイされると、SUCは、アップグレードPodをデプロイするジョブを選択して作成します。

  6. デプロイされると、アップグレードPodは、eib-chart-upgrade-scriptシークレットとeib-chart-upgrade-user-dataシークレットをマウントし、eib-chart-upgrade-scriptシークレットによって配布されるアップグレードスクリプトを実行します。

  7. アップグレードスクリプトは以下を実行します。

    1. スクリプトが実行されているPodが初期化ノードにデプロイされているかどうかを判断します。初期化ノードは、HelmChartマニフェストをホストしているノードです。シングルノードクラスタの場合は、単一のコントロールプレーンノードです。HAクラスタの場合は、EIBでクラスタを作成したときにinitializerとマークされたノードです。initializerプロパティを指定しなかった場合は、nodesリストの最初のノードがinitializerとマークされます。詳細については、EIBのアップストリームドキュメントを参照してください。

      注記
      注記

      アップグレードスクリプトが初期化ノード以外で動作している場合、スクリプトは直ちに実行を停止し、以下の手順には進みません。

    2. 編集するマニフェストをバックアップし、障害復旧を確実に行えるようにします。

      注記
      注記

      デフォルトでは、マニフェストのバックアップは、/tmp/eib-helm-chart-upgrade-<date>ディレクトリに保存されます。カスタムの場所を使用する場合、MANIFEST_BACKUP_DIR環境変数をHelmチャートアップグレードSUC Planに渡すことができます(Planの例)。

    3. HelmChartマニフェストを編集します。このバージョンの時点で、チャートアップグレードをトリガするために、次のプロパティが変更されます。

      1. chartContentプロパティの内容は、eib-chart-upgrade-user-dataシークレットで指定されているエンコードされたアーカイブに置き換えられます。

      2. versionプロパティの値は、eib-chart-upgrade-user-dataシークレットで指定されているバージョンに置き換えられます。

  8. アップグレードスクリプトが正常に実行されると、RKE2/K3sのHelm統合が変更を検出し、Helmチャートのアップグレードを自動的にトリガします。

25.5.3.3.2 アップグレード手順
  1. Helmチャートアップグレードのロジックのコピー元のEdge リリースタグを特定します。

  2. fleets/day2/system-upgrade-controller-plans/eib-chart-upgrade Fleetを、FleetでGitOpsを行うために使用するリポジトリにコピーします。

  3. アップグレード先のHelmチャートアーカイブをプルします。

    helm pull [chart URL | repo/chartname]
    
    # Alternatively if you want to pull a specific version:
    # helm pull [chart URL | repo/chartname] --version 0.0.0
  4. プルしたチャートアーカイブをエンコードします。

    # Encode the archive and disable line wrapping
    base64 -w 0 <chart-archive>.tgz
  5. 手順2でコピーしたeib-chart-upgrade Fleetにあるeib-chart-upgrade-user-data.yamlシークレットを設定します。

    1. このシークレットは、chart_upgrade_data.txtというファイルを配布します。このファイルにはチャートアップグレードのデータが保持されており、アップグレードスクリプトではこのデータを使用して、アップグレードする必要があるチャートを把握します。このファイルではチャートエントリにつき1行が必要で、形式は「<name>|<version>|<base64_encoded_archive>」です。

      1. name - EIB定義ファイルのkubernetes.helm.charts.name[]プロパティに表示される、Helmチャートの名前です。

      2. version - Helmチャートの新しいバージョンを保持する必要があります。アップグレード時に、この値を使用してHelmChartマニフェストの古いversionを置き換えます。

      3. base64_encoded_archive - ここでbase64 -w 0 <chart-archive>.tgzの出力を渡します。アップグレード時に、この値を使用してHelmChartマニフェストの古いchartContent値を置き換えます。

        注記
        注記

        <name>|<version>|<base64_encoded_archive>の行は、データの追加を始める前にファイルから削除する必要があります。この行は、チャートデータをどこで、どのように設定する必要があるかの例を示すためのものです。

  6. チャートアップグレードのfleetを配布するGitRepoリソースを設定します。GitRepoの詳細については、「GitRepo Resource (GitRepoリソース)」を参照してください。

    1. Rancher UIを使用してGitRepoを設定します。

      1. 左上隅で、☰ → [Continuous Delivery (継続的デリバリ)]に移動します。

      2. [Git Repos (Gitリポジトリ)]→[ Add Repository (リポジトリの追加)]に移動します。

      3. ここで、リポジトリデータパスをチャートのアップグレードFleetに渡します。

      4. [Next (次へ)]を選択し、設定されたチャートをアップグレードするターゲットクラスタを指定します。

      5. 作成します

    2. お使いのセットアップでRancherを使用できない場合は、管理クラスタGitRepoを手動で設定できます。

      1. 次のテンプレートにデータを入力します。

        apiVersion: fleet.cattle.io/v1alpha1
        kind: GitRepo
        metadata:
          name: CHANGE_ME
          namespace: fleet-default
        spec:
          # if running from a tag
          # revision: CHANGE_ME
          # if running from a branch
          # branch: CHANGE_ME
          paths:
          # path to your chart upgrade fleet relative to your repository
          - CHANGE_ME
          # your repository URL
          repo: CHANGE_ME
          targets:
          # Select target clusters
          - clusterSelector: CHANGE_ME
          # To match all clusters:
          # - clusterSelector: {}

        GitRepoリソースのセットアップとデプロイの方法の詳細については、「GitRepo Resource (GitRepoリソース)」および「Create a GitRepo Resource (GitRepoリソースの作成)」を参照してください。

        より細かいレベルでターゲットクラスタに一致させる方法については、「Mapping to Downstream Clusters (ダウンストリームクラスタへのマップ)」を参照してください。

      2. 設定したGitRepoリソースを管理クラスタfleet-defaultネームスペースにデプロイします。

この手順を実行すると、GitRepoリソースが正常に作成されるはずです。続いてこのリソースがFleetによって検出されて、バンドルが作成されます。このバンドルには、GitRepoがFleetディレクトリの下に設定した「生」のKubernetesリソースが保持されます。

次にFleetは、すべてのKubernetesリソースをバンドルから指定のダウンストリームクラスタにデプロイします。このリソースの1つは、チャートのアップグレードをトリガするSUC Planです。デプロイされるリソースのリストとアップグレードプロセスのワークフローについては、「概要」(25.5.3.3.1項 「概要」)のセクションを参照してください。

アップグレードプロセス自体を追跡するには、「SUC Planの監視」(25.2.2.2項 「SUC Planの監視」)のセクションを参照してください。

25.5.3.3.3

次のセクションは、25.5.3.3.2項 「アップグレード手順」セクションに実際の例を提供することを目的としています。

EIBでデプロイされた次の2つのクラスタがあります。

  • longhorn-single-k3s - シングルノードK3sクラスタ

  • longhorn-ha-rke2 - HA RKE2クラスタ

どちらのクラスタでもLonghornが実行されており、次のイメージ定義スニペットを使用してEIBによってデプロイされています。

kubernetes:
  # HA RKE2 cluster specific snippet
  # nodes:
  # - hostname: cp1rke2.example.com
  #   initializer: true
  #   type: server
  # - hostname: cp2rke2.example.com
  #   type: server
  # - hostname: cp3rke2.example.com
  #   type: server
  # - hostname: agent1rke2.example.com
  #   type: agent
  # - hostname: agent2rke2.example.com
  #   type: agent
  # version depending on the distribution
  version: v1.28.9+k3s1/v1.28.9+rke2r1
  helm:
    charts:
    - name: longhorn
      repositoryName: longhorn
      targetNamespace: longhorn-system
      createNamespace: true
      version: 1.5.5
    repositories:
    - name: longhorn
      url: https://charts.longhorn.io
...
day2 helmチャートアップグレード例 k3s 古い
図 25.7: longhorn-single-k3sにインストールされているLonghornバージョン
day2 helmチャートアップグレード例rke2古い
図 25.8: longhorn-ha-rke2にインストールされているLonghornバージョン

ここでの問題は、現在のところlonghorn-single-k3slonghorn-ha-rke2がどのEdgeリリースとも互換性のないLonghornバージョンで実行されていることです。

両方のクラスタのチャートをEdgeでサポートされるLonghornバージョンにアップグレードする必要があります。

これを実行するには、次の手順を実行します。

  1. アップグレードロジックを取得するEdgeリリースタグを特定します。たとえば、この例では、サポートされているLonghornバージョンが1.6.1であるrelease-3.0.1リリースタグを使用します。

  2. release-3.0.1リリースタグのクローンを作成し、fleets/day2/system-upgrade-controller-plans/eib-chart-upgradeディレクトリを自身のリポジトリにコピーします。

    単純化するために、このセクションではsuse-edge/fleet-examplesリポジトリのブランチから作業します。したがって、ディレクトリ構造は同じですが、eib-chart-upgrade Fleetはリポジトリ内の任意の場所に配置できます。

    ディレクトリ構造の例. 

    .
    ...
    |-- fleets
    |   `-- day2
    |       `-- system-upgrade-controller-plans
    |           `-- eib-chart-upgrade
    |               |-- eib-chart-upgrade-script.yaml
    |               |-- eib-chart-upgrade-user-data.yaml
    |               |-- fleet.yaml
    |               `-- plan.yaml
    ...

  3. Longhornチャートリポジトリを追加します。

    helm repo add longhorn https://charts.longhorn.io
  4. Longhornチャートバージョン1.6.1をプルします。

    helm pull longhorn/longhorn --version 1.6.1

    Longhornがlonghorn-1.6.1.tgzという名前のアーカイブとしてプルされます。

  5. Longhornアーカイブをエンコードします。

    base64 -w 0 longhorn-1.6.1.tgz

    アーカイブがbase64でエンコードされた長い1行の文字列で出力されます。

  6. eib-chart-upgrade-user-data.yamlファイルを設定するために必要なデータがすべて揃いました。ファイル設定は次のようになります。

    apiVersion: v1
    kind: Secret
    metadata:
      name: eib-chart-upgrade-user-data
    type: Opaque
    stringData:
      # <name>|<version>|<base64_encoded_archive>
      chart_upgrade_data.txt: |
        longhorn|1.6.1|H4sIFAAAAAAA/ykAK2FIUjBjSE02THk5NWIzV...
    1. longhornは、EIB定義ファイルにあるチャートの名前です。

    2. 1.6.1は、Longhorn HelmChartマニフェストのversionプロパティのアップグレード先のバージョンです。

    3. H4sIFAAAAAAA/ykAK2FIUjBjSE02THk5NWIzV…​は、エンコードされたLonghorn 1.6.1アーカイブのスニペットです。スニペットがここに追加されているのは読みやすくするためです。ここには必ず、base64エンコードアーカイブの文字列全体を追加してください。

      注記
      注記

      この例は、1つのチャートのアップグレードの設定を示していますが、複数のクラスタで複数のチャートをアップグレードする必要がある場合、以下に示すように追加のチャートデータを付加できます。

      apiVersion: v1
      kind: Secret
      metadata:
        name: eib-chart-upgrade-user-data
      type: Opaque
      stringData:
        # <name>|<version>|<base64_encoded_archive>
        chart_upgrade_data.txt: |
          chartA|0.0.0|<chartA_base64_archive>
          chartB|0.0.0|<chartB_base64_archive>
          chartC|0.0.0|<chartC_base64_archive>
          ...
  7. また、マニフェストのバックアップを/tmpに保持しないことにしたため、次の設定がplan.yamlファイルに追加されました。

    apiVersion: upgrade.cattle.io/v1
    kind: Plan
    metadata:
      name: eib-chart-upgrade
    spec:
      ...
      upgrade:
        ...
        # For when you want to backup your chart
        # manifest data under a specific directory
        #
        envs:
        - name: MANIFEST_BACKUP_DIR
          value: "/root"

    これにより、マニフェストのバックアップは、/tmpではなく/rootディレクトリに保存されます。

  8. これで必要な設定はすべて完了したので、後はGitRepoリソースを作成するだけです。この例では、Rancher UIを使用してGitRepoリソースを作成します。

  9. アップグレード手順(25.5.3.3.2項 「アップグレード手順」)で説明されている手順に従い、次の項目を実行しました。

    1. GitRepoに「longhorn-upgrade」という名前を付けました。

    2. 使用するリポジトリにURLを渡しました - https://github.com/suse-edge/fleet-examples.git

    3. リポジトリのブランチを渡しました - 「doc-example」。

    4. リポジトリのとおりにeib-chart-upgradeフリートへのパスを渡しました - fleets/day2/system-upgrade-controller-plans/eib-chart-upgrade

    5. ターゲットクラスタを選択し、リソースを作成しました。

      day2 helmチャートアップグレード例gitrepo
      図 25.9: 正常にデプロイされたSUCとlonghorn GitRepo

続いてクラスタでアップグレード手順を監視する必要があります。

  1. 「SUC Planの監視」(25.2.2.2項 「SUC Planの監視」)のセクションの指示に従い、アップグレードPodのステータスを確認します。

    1. 初期化ノードで動作している、正常に完了したアップグレードPodには、次のようなログが保持されているはずです。

      day2 helmチャートアップグレード例の初期化ノードログ
      図 25.10: 初期化ノードで実行されているアップグレードPod
    2. 非初期化ノードで動作している、正常に完了したアップグレードPodには、次のようなログが保持されているはずです。

      day2 helmチャートアップグレード例の非初期化ノードログ
      図 25.11: 非初期化ノードで実行されているアップグレードPod
  2. アップグレードPodが正常に完了した後は、Helmコントローラによって作成されるPodについても待機して監視する必要があります。これらのPodは、アップグレードPodHelmChartマニフェストファイルに加えたファイルの変更に基づいて、実際のアップグレードを行います。

    1. クラスタ内で[Workloads (ワークロード)] → [Pods]にアクセスし、文字列longhornを含むPodをdefaultネームスペース内で検索します。これにより、命名テンプレートhelm-install-longhorn-*を使用してPodが生成されます。このPodのログを確認します。

      day2 helmチャートアップグレード例のhelmインストール
      図 25.12: 正常に完了したhelm-install Pod
    2. ログは次のようになります。

      day2 helmチャートアップグレード例の正常にアップグレードされたPod
      図 25.13: 正常に完了したhelm-install Podのログ

すべてが正常に完了したことを確認したので、次にバージョン変更を検証する必要があります。

  1. クラスタ上で、[More Resources (追加のリソース)] → [Helm] → [HelmCharts]に移動し、longhorn HelmChartリソースをdefaultネームスペース内で検索する必要があります。

    day2 helmチャートアップグレード例のk3s longhornアップグレード
    図 25.14: longhorn-single-k3のアップグレードされたLonghornバージョン
    day2 helmチャートアップグレード例のrke2 longhornアップグレード
    図 25.15: longhorn-ha-rke2のアップグレードされたLonghornバージョン

これにより、Longhorn helmチャートが正常にアップグレードされたことを確認します。以上でこの例は完了です。

何かの理由でLonghornの以前のチャートバージョンに戻す必要がある場合、以前のLonghornマニフェストは、初期化ノードの/root/longhorn.yamlに保存されています。これは、SUC PlanでMANIFEST_BACKUP_DIRを指定したためです。

25.5.3.3.4 サードパーティのGitOpsツールを使用したHelmチャートのアップグレード

ユーザがこのアップグレード手順をFleet以外のGitOpsワークフロー(Fluxなど)で実行したいユースケースが存在する場合があります。

EIBでデプロイされたHelmチャートのアップグレードに関連するリソースを取得するには、まず、使用するsuse-edge/fleet-examplesリポジトリのEdgeリリースタグを特定する必要があります。

その後、fleets/day2/system-upgrade-controller-plans/eib-chart-upgradeでリソースを見つけることができます。

  • plan.yaml - アップグレード手順に関連するsystem-upgrade-controller Plan。

  • eib-chart-upgrade-script.yaml - HelmChartマニフェストファイルを編集してアップグレードするアップグレードスクリプトを保持しているシークレット。

  • eib-chart-upgrade-user-data.yaml - アップグレードスクリプトが利用するファイルを保持しているシークレット。関連するチャートアップグレードデータがあらかじめユーザによって入力されています。

重要
重要

これらのPlanリソースはsystem-upgrade-controllerによって解釈され、アップグレードが必要なチャートを保持する各ダウンストリームクラスタにデプロイする必要があります。system-upgrade-controllerをデプロイする方法については、25.2.1.3項 「サードパーティのGitOpsワークフローの使用時におけるsystem-upgrade-controllerのデプロイ」を参照してください。

GitOpsワークフローを使用してアップグレードプロセス用のSUC Planをデプロイする方法の理解を深めるには、 Fleetを使用したプロセスの概要(25.5.3.3.1項 「概要」)を確認すると役に立ちます。

パート VI 製品マニュアル

ATIPのマニュアルはここにあります

  • 26 SUSE Adaptive Telco Infrastructure Platform (ATIP)
  • SUSE Adaptive Telco Infrastructure Platform (ATIP)は、通信事業者向けに最適化されたエッジコンピューティングプラットフォームであり、通信事業者はそのネットワークを刷新し、その最新化を加速できます。

  • 27 コンセプトとアーキテクチャ
  • SUSE ATIPは、クラウドネイティブな最新の通信事業者向けアプリケーションをコアからエッジまで大規模にホストするために設計されたプラットフォームです。

  • 28 要件と前提
  • ATIPノードのハードウェア要件は次のコンポーネントに基づきます。

  • 29 管理クラスタの設定
  • 管理クラスタは、ATIP内でランタイムスタックのプロビジョニングとライフサイクルを管理するために使用されます。技術的観点からは、管理クラスタには次のコンポーネントが含まれています。

  • 30 通信機能の設定
  • このセクションでは、ATIPがデプロイされたクラスタの通信事業者固有の機能について記述および説明します。

  • 31 完全に自動化されたダイレクトネットワークプロビジョニング
  • ダイレクトネットワークプロビジョニングは、ダウンストリームクラスタのプロビジョニングを自動化できる機能です。この機能は、プロビジョニングするダウンストリームクラスタが多数あり、そのプロセスを自動化したい場合に便利です。

  • 32 ライフサイクルのアクション
  • このセクションでは、デプロイしたATIPクラスタのライフサイクル管理アクションについて説明します。

26 SUSE Adaptive Telco Infrastructure Platform (ATIP)

SUSE Adaptive Telco Infrastructure Platform (ATIP)は、通信事業者向けに最適化されたエッジコンピューティングプラットフォームであり、通信事業者はそのネットワークを刷新し、その最新化を加速できます。

ATIPは、5G Packet CoreやCloud RANなどのCNFをホストするための、通信事業者向けの充実したクラウドスタックです。

  • エッジスタックの複雑な設定を通信事業者の規模で自動的にゼロタッチでロールアウトし、ライフサイクルを管理します。

  • 通信事業者に固有の設定とワークロードを使用して、通信事業者グレードのハードウェアの品質を継続的に保証します。

  • エッジ専用に設計されたコンポーネントで構成されているため、フットプリントが小さく、ワットパフォーマンスが高くなっています。

  • ベンダに依存しないAPIを備え、100%オープンソースであるため、柔軟なプラットフォーム戦略を維持します。

27 コンセプトとアーキテクチャ

SUSE ATIPは、クラウドネイティブな最新の通信事業者向けアプリケーションをコアからエッジまで大規模にホストするために設計されたプラットフォームです。

このページでは、ATIPで使用されるアーキテクチャとコンポーネントについて説明します。これを理解しておくと、ATIPをデプロイおよび使用する際に役立ちます。

27.1 ATIPのアーキテクチャ

次の図は、ATIPのアーキテクチャの概要を示しています。

製品atipアーキテクチャ1

27.2 コンポーネント

異なる2つのブロックがあります。管理スタックとランタイムスタックです。

  • 管理スタック: ATIP内でランタイムスタックのプロビジョニングとライフサイクルを管理するために使用される部分です。次のコンポーネントが含まれます。

    • Rancher (第4章 「Rancher)を使用した、パブリッククラウド環境とプライベートクラウド環境のマルチクラスタ管理

    • Metal3 (第8章 「Metal3)、MetalLB (第17章 「MetalLB)、およびCAPI (Cluster API)インフラストラクチャプロバイダを使用したベアメタルサポート

    • 包括的なテナント分離とIDP (IDプロバイダ)の統合

    • サードパーティ統合と拡張機能の大規模なマーケットプレイス

    • ベンダに依存しないAPIと充実したプロバイダエコシステム

    • SLE Microのトランザクション更新の制御

    • GitリポジトリとFleet (第6章 「Fleet)を使用してクラスタのライフサイクルを管理するGitOpsエンジン

  • ランタイムスタック: ATIP内でワークロードを実行するために使用される要素です。

    • Kubernetesと、K3s (第13章 「K3s)やRKE2 (第14章 「RKE2)などの安全で軽量なディストリビューション(RKE2は、政府機関での使用や規制対象産業向けに強化、認証、最適化されています)。

    • NeuVector (第16章 「NeuVector)。イメージの脆弱性スキャン、ディープパケットインスペクション、クラスタ内の自動トラフィック制御などのセキュリティ機能を実現します。

    • ブロックストレージとLonghorn (第15章 「Longhorn)。クラウドネイティブのストレージソリューションをシンプルかつ簡単に使用できます。

    • SLE Micro(第7章 「SLE Micro)で最適化されたオペレーティングシステム。コンテナ運用のための、安全、軽量でイミュータブルな(トランザクショナルファイルシステムを備えた) OSを実現します。SLE Microはaarch64アーキテクチャとx86_64アーキテクチャで利用でき、通信事業者およびエッジのユースケース向けにリアルタイムカーネルもサポートしています。

27.3 デプロイメントフローの例

管理コンポーネントとランタイムコンポーネントの関係を理解できるように、以下にワークフローの概要の例を示します。

ダイレクトネットワークプロビジョニングは、すべてのコンポーネントを事前設定した状態で新しいダウンストリームクラスタをデプロイできるワークフローであり、手動操作なしですぐにワークロードを実行できます。

27.3.1 例1: すべてのコンポーネントがインストールされた新しい管理クラスタをデプロイする

Edge Image Builder (第9章 「Edge Image Builder)を使用して、管理スタックが含まれる新しいISOイメージを作成します。その後、このISOイメージを使用して、新しい管理クラスタをVMまたはベアメタルにインストールできます。

製品atipアーキテクチャ2
注記
注記

新しい管理クラスタをデプロイする方法については、ATIPの管理クラスタに関するガイド(第29章 「管理クラスタの設定)を参照してください。

注記
注記

Edge Image Builderの使用方法については、Edge Image Builderのガイド(第3章 「Edge Image Builderを使用したスタンドアロンクラスタ)を参照してください。

27.3.2 例2: 通信事業者プロファイルを使用してシングルノードのダウンストリームクラスタをデプロイして通信ワークロードを実行可能にする

管理クラスタが稼働したら、その管理クラスタを使用して、ダイレクトネットワークプロビジョニングワークフローにより、すべての通信機能が有効化および設定された状態でシングルノードのダウンストリームクラスタをデプロイすることができます。

次の図に、これをデプロイするワークフローの概要を示します。

製品atipアーキテクチャ3
注記
注記

ダウンストリームクラスタをデプロイする方法については、ATIPの自動プロビジョニングに関するガイド(第31章 「完全に自動化されたダイレクトネットワークプロビジョニング)を参照してください。

注記
注記

通信機能の詳細については、ATIPの通信機能に関するガイド(第30章 「通信機能の設定)を参照してください。

27.3.3 例3: MetalLBをロードバランサとして使用して高可用性ダウンストリームクラスタをデプロイする

管理クラスタが稼働したら、その管理クラスタを使用して、ダイレクトネットワークプロビジョニングワークフローにより、MetalLBをロードバランサとして使用する高可用性ダウンストリームクラスタをデプロイすることができます。

次の図に、これをデプロイするワークフローの概要を示します。

製品atipアーキテクチャ4
注記
注記

ダウンストリームクラスタをデプロイする方法については、ATIPの自動プロビジョニングに関するガイド(第31章 「完全に自動化されたダイレクトネットワークプロビジョニング)を参照してください。

注記
注記

MetalLBの詳細については、第17章 「MetalLBを参照してください。

28 要件と前提

28.1 ハードウェア

ATIPノードのハードウェア要件は次のコンポーネントに基づきます。

  • 管理クラスタ: 管理クラスタには、SLE MicroRKE2Rancher PrimeMetal3などのコンポーネントが含まれ、管理クラスタを使用して複数のダウンストリームクラスタを管理します。管理するダウンストリームクラスタの数によっては、サーバのハードウェア要件は変わる場合があります。

    • サーバ(VMまたはベアメタル)の最小要件は次のとおりです。

      • RAM: 8GB以上(16GB以上を推奨)

      • CPU: 2個以上(4個以上を推奨)

  • ダウンストリームクラスタ: ダウンストリームクラスタは、ATIPノードにデプロイされて通信ワークロードを実行するクラスタです。SR-IOVCPUパフォーマンス最適化などの特定の通信機能を有効にするには、固有の要件が必要になります。

    • SR-IOV: VF (仮想関数)をCNF/VNFにパススルーモードでアタッチするには、NICがSR-IOVをサポートしていて、BIOSでVT-d/AMD-Viが有効化されている必要があります。

    • CPUプロセッサ: 特定の通信ワークロードを実行するには、こちらの参照表(第30章 「通信機能の設定)に記載されているほとんどの機能を利用できるようにCPUプロセッサモデルを適応させる必要があります。

    • 仮想メディアでインストールするためのファームウェア要件:

サーバハードウェア

BMCモデル

管理

Dell製ハードウェア

第15世代

iDRAC9

Supermicro製ハードウェア

01.00.25

Supermicro SMC - redfish

HPE製ハードウェア

1.50

iLO6

28.2 ネットワーク

ネットワークアーキテクチャの参考として、次の図に、通信事業者環境の一般的なネットワークアーキテクチャを示します。

製品atip要件1

このネットワークアーキテクチャは次のコンポーネントに基づきます。

  • 管理ネットワーク: このネットワークは、ATIPノードの管理や帯域外管理に使用されます。通常は独立した管理スイッチに接続しますが、同じサービススイッチに接続し、VLANを使ってトラフィックを分離することもできます。

  • コントロールプレーンネットワーク: このネットワークは、ATIPノードと、そこで実行されているサービスとの間の通信に使用されます。また、ATIPノードと外部サービス(DHCPサーバやDNSサーバなど)との間の通信にも使用されます。接続環境では、スイッチやルータでインターネット経由のトラフィックを処理できる場合もあります。

  • その他のネットワーク: 場合によっては、お客様の特定の目的に合わせてATIPノードを他のネットワークに接続できます。

注記
注記

ダイレクトネットワークプロビジョニングワークフローを使用するには、管理クラスタがダウンストリームクラスタサーバのBaseboard Management Controller (BMC)とネットワークで接続されていて、ホストの準備とプロビジョニングを自動化できる必要があります。

28.3 サービス(DHCP、DNSなど)

デプロイ先の環境の種類によっては、DHCPDNSなどの外部サービスが必要な場合があります。

  • 接続環境: この場合、ATIPノードはインターネットに接続され(L3ルーティングプロトコルを使用)、外部サービスはお客様が提供します。

  • 非接続/エアギャップ環境: この場合、ATIPノードはインターネットにIPで接続されないため、サービスを追加して、ATIPのダイレクトネットワークプロビジョニングワークフローに必要なコンテンツをローカルにミラーリングする必要があります。

  • ファイルサーバ: ファイルサーバは、ダイレクトネットワークプロビジョニングワークフローの中で、ATIPノードにプロビジョニングするISOイメージを保存するために使用されます。metal3 HelmチャートでメディアサーバをデプロイしてISOイメージを保存できます。次のセクション(注記)を確認してください。ただし、既存のローカルWebサーバを使用することもできます。

28.4 rebootmgrの無効化

rebootmgrは、システムに保留中の更新がある場合の再起動方針を設定できるサービスです。通信ワークロードでは、システムによってスケジュールされた更新がある場合、rebootmgrサービスを無効にするか正しく設定してノードの再起動を回避し、ノードで実行中のサービスへの影響を避けることが非常に重要です。

注記
注記

rebootmgrの詳細については、rebootmgrのGitHubリポジトリを参照してください。

次のコマンドを実行して、使用する方針を検証します。

cat /etc/rebootmgr.conf
[rebootmgr]
window-start=03:30
window-duration=1h30m
strategy=best-effort
lock-group=default

また、次のコマンドを実行すると無効にすることができます。

sed -i 's/strategy=best-effort/strategy=off/g' /etc/rebootmgr.conf

または、rebootmgrctlコマンドを次のように使用できます。

rebootmgrctl strategy off
注記
注記

rebootmgrの方針を設定するこの設定は、ダイレクトネットワークプロビジョニングワークフローを使用して自動化できます。詳細については、ATIPの自動化されたプロビジョニングに関するドキュメント(第31章 「完全に自動化されたダイレクトネットワークプロビジョニング)を確認してください。

29 管理クラスタの設定

29.1 はじめに

管理クラスタは、ATIP内でランタイムスタックのプロビジョニングとライフサイクルを管理するために使用されます。技術的観点からは、管理クラスタには次のコンポーネントが含まれています。

  • SUSE Linux Enterprise Micro (OS)。ユースケースに応じて、ネットワーキング、ストレージ、ユーザ、カーネル引数などの一部の設定をカスタマイズできます。

  • RKE2 (Kubernetesクラスタ)。ユースケースに応じて、MultusCiliumなどの特定のCNIプラグインを使用するように設定できます。

  • Rancher (管理プラットフォーム)。クラスタのライフサイクルを管理します。

  • Metal3 (コンポーネント)。ベアメタルノードのライフサイクルを管理します。

  • CAPI (コンポーネント)。Kubernetesクラスタ (ダウンストリームクラスタ)のライフサイクルを管理します。ATIPでは、RKE2クラスタ(ダウンストリームクラスタ)のライフサイクルを管理するためにRKE2 CAPI Providerも使用します。

上記のコンポーネントをすべて使用すると、管理クラスタは、宣言型アプローチを使用してインフラストラクチャやアプリケーションを管理し、ダウンストリームクラスタのライフサイクルを管理できます。

注記
注記

SUSE Linux Enterprise Microの詳細については、「SLE Micro」(第7章 「SLE Micro)を参照してください。

RKE2の詳細については、「RKE2」(第14章 「RKE2)を参照してください。

Rancherの詳細については、「Rancher」(第4章 「Rancher)を参照してください。

Metal3の詳細については、「Metal3」(第8章 「Metal3)を参照してください。

29.2 管理クラスタの設定手順

管理クラスタを設定するには、次の手順が必要です(シングルノードを使用)。

製品atip管理クラスタ1

宣言型アプローチを使用して管理クラスタを設定するには、主に3つの手順があります。

  1. 接続環境のイメージの準備(29.3項 「接続環境用のイメージの準備」): 最初の手順では、接続環境で使用する必要がある設定をすべて含むマニフェストとファイルを準備します。

    • 接続環境のディレクトリ構造(29.3.1項 「ディレクトリ構造」): この手順では、Edge Image Builderで使用するディレクトリ構造を作成し、設定ファイルとイメージそのものを保存します。

    • 管理クラスタ定義ファイル(29.3.2項 「管理クラスタ定義ファイル」): mgmt-cluster.yamlファイルが管理クラスタのメイン定義ファイルです。このファイルには、作成するイメージに関する次の情報が含まれています。

      • イメージ情報: ゴールデンイメージを使用して作成するイメージに関する情報。

      • オペレーティングシステム: イメージで使用するオペレーティングシステムの設定。

      • Kubernetes: Helmチャートとリポジトリ、Kubernetesのバージョン、ネットワーク設定、およびクラスタで使用するノード。

    • Customフォルダ(29.3.3項 「Customフォルダ」): customフォルダには設定ファイルとスクリプトが含まれ、Edge Image Builderはこれらを使用して完全に機能する管理クラスタをデプロイします。

      • ファイル: 管理クラスタが使用する設定ファイルが含まれています。

      • スクリプト: 管理クラスタが使用するスクリプトが含まれています。

    • Kubernetesフォルダ(29.3.4項 「Kubernetesフォルダ」): kubernetesフォルダには、管理クラスタが使用する設定ファイルが含まれています。

      • Manifests: 管理クラスタが使用するマニフェストが含まれています。

      • Helm: 管理クラスタが使用するHelmチャートが含まれています。

      • Config: 管理クラスタが使用する設定ファイルが含まれています。

    • Networkフォルダ(29.3.5項 「ネットワーキングフォルダ」): networkフォルダには、管理クラスタノードが使用するネットワーク設定ファイルが含まれています。

  2. エアギャップ環境でのイメージの準備(29.4項 「エアギャップ環境のイメージの準備」): この手順では、エアギャップシナリオで使用するマニフェストとファイルを準備する際の相違点を示します。

    • エアギャップ環境のディレクトリ構造(29.4.1項 「エアギャップ環境のディレクトリ構造」): ディレクトリ構造を変更して、管理クラスタをエアギャップ環境で実行するために必要なリソースを含める必要があります。

    • 定義ファイルの変更(29.4.2項 「定義ファイルの変更」): mgmt-cluster.yamlファイルを変更してembeddedArtifactRegistryセクションを含め、imagesフィールドに、EIBの出力イメージに組み込むすべてのコンテナイメージを設定する必要があります。

    • customeフォルダの変更(29.4.3項 「カスタムフォルダの変更」): customフォルダを変更し、管理クラスタをエアギャップ環境で実行するために必要なリソースを含める必要があります。

      • 登録スクリプト: エアギャップ環境を使用する場合、custom/scripts/99-register.shスクリプトを削除する必要があります。

      • エアギャップリソース: custom/files/airgap-resources.tar.gzファイルを、管理クラスタをエアギャップ環境で運用するために必要なすべてのリソースとともにcustom/filesフォルダに含める必要があります。

      • スクリプト: custom/scripts/99-mgmt-setup.shスクリプトを変更し、airgap-resources.tar.gzファイルを抽出して最終的な場所にコピーするようにする必要があります。また、custom/files/metal3.shスクリプトを変更し、インターネットからリソースをダウンロードするのではなく、airgap-resources.tar.gzファイルに含まれるローカルリソースを使用するようにする必要があります。

  3. イメージの作成(29.5項 「イメージの作成」): この手順では、Edge Image Builderツールを使用してイメージを作成します(接続環境とエアギャップ環境の両方が対象です)。ご使用のシステムでEdge Image Builderツールを実行するための前提条件(第9章 「Edge Image Builder)を確認してください。

  4. 管理クラスタのプロビジョニング(29.6項 「管理クラスタのプロビジョニング」): この手順では、前の手順で作成したイメージを使用して管理クラスタをプロビジョニングする方法について説明します(接続シナリオとエアギャップシナリオの両方が対象です)。この手順は、ラップトップ、サーバ、VM、またはUSBポートを搭載した他の任意のx86_64システムを使用して実行できます。

注記
注記

Edge Image Builderの詳細については、「Edge Image Builder」(第9章 「Edge Image Builder)およびEdge Image Builderのクイックスタート(第3章 「Edge Image Builderを使用したスタンドアロンクラスタ)を参照してください。

29.3 接続環境用のイメージの準備

Edge Image Builderを使用して管理クラスタのイメージを作成すると、多くの設定をカスタマイズできますが、このドキュメントでは、管理クラスタの設定に必要な最小設定について説明します。Edge Image Builderは通常、コンテナ内から実行されるため、まだコンテナを実行する手段がない場合は、まずコンテナランタイム(PodmanRancher Desktop)などのコンテナランタイムをインストールする必要があります。このガイドでは、コンテナランタイムをすでに使用できる状況であることを想定しています。

また、高可用性管理クラスタをデプロイするための前提条件として、ネットワークで次の3つのIPを予約する必要があります。- apiVIP (API VIPアドレス用(Kubernetes APIサーバへのアクセスに使用))、- ingressVIP (Ingress VIPアドレス(Rancher UIなどで使用))、- metal3VIP (Metal3 VIPアドレス用)。

29.3.1 ディレクトリ構造

EIBを実行する場合、ディレクトリはホストからマウントされます。したがって、最初に実行する手順は、EIBが設定ファイルとイメージ自体を保存するために使用するディレクトリ構造を作成することです。このディレクトリの構造は次のとおりです。

eib
├── mgmt-cluster.yaml
├── network
│ └── mgmt-cluster-node1.yaml
├── kubernetes
│ ├── manifests
│ │ ├── rke2-ingress-config.yaml
│ │ ├── neuvector-namespace.yaml
│ │ ├── ingress-l2-adv.yaml
│ │ └── ingress-ippool.yaml
│ ├── helm
│ │ └── values
│ │     ├── rancher.yaml
│ │     ├── neuvector.yaml
│ │     ├── metal3.yaml
│ │     └── certmanager.yaml
│ └── config
│     └── server.yaml
├── custom
│ ├── scripts
│ │ ├── 99-register.sh
│ │ ├── 99-mgmt-setup.sh
│ │ └── 99-alias.sh
│ └── files
│     ├── rancher.sh
│     ├── mgmt-stack-setup.service
│     ├── metal3.sh
│     └── basic-setup.sh
└── base-images
注記
注記

イメージSLE-Micro.x86_64-5.5.0-Default-SelfInstall-GM2.install.isoは、SUSE Customer CenterまたはSUSEダウンロードページからダウンロードして、base-imagesフォルダに配置する必要があります。

イメージのSHA256チェックサムを確認し、イメージが改ざんされていないことを確認する必要があります。このチェックサムは、イメージをダウンロードした場所と同じ場所にあります。

ディレクトリ構造の例は、 SUSE Edge GitHubリポジトリの「telco-examples」フォルダにあります。

29.3.2 管理クラスタ定義ファイル

mgmt-cluster.yamlファイルは管理クラスタのメイン定義ファイルで、次の情報が含まれます。

apiVersion: 1.0
image:
  imageType: iso
  arch: x86_64
  baseImage: SLE-Micro.x86_64-5.5.0-Default-SelfInstall-GM2.install.iso
  outputImageName: eib-mgmt-cluster-image.iso
operatingSystem:
  isoConfiguration:
    installDevice: /dev/sda
  users:
  - username: root
    encryptedPassword: ${ROOT_PASSWORD}
  packages:
    packageList:
    - git
    - jq
    sccRegistrationCode: ${SCC_REGISTRATION_CODE}
kubernetes:
  version: ${KUBERNETES_VERSION}
  helm:
    charts:
      - name: cert-manager
        repositoryName: jetstack
        version: 1.14.2
        targetNamespace: cert-manager
        valuesFile: certmanager.yaml
        createNamespace: true
        installationNamespace: kube-system
      - name: longhorn-crd
        version: 103.3.0+up1.6.1
        repositoryName: rancher-charts
        targetNamespace: longhorn-system
        createNamespace: true
        installationNamespace: kube-system
      - name: longhorn
        version: 103.3.0+up1.6.1
        repositoryName: rancher-charts
        targetNamespace: longhorn-system
        createNamespace: true
        installationNamespace: kube-system
      - name: metal3-chart
        version: 0.7.1
        repositoryName: suse-edge-charts
        targetNamespace: metal3-system
        createNamespace: true
        installationNamespace: kube-system
        valuesFile: metal3.yaml
      - name: neuvector-crd
        version: 103.0.3+up2.7.6
        repositoryName: rancher-charts
        targetNamespace: neuvector
        createNamespace: true
        installationNamespace: kube-system
        valuesFile: neuvector.yaml
      - name: neuvector
        version: 103.0.3+up2.7.6
        repositoryName: rancher-charts
        targetNamespace: neuvector
        createNamespace: true
        installationNamespace: kube-system
        valuesFile: neuvector.yaml
      - name: rancher
        version: 2.8.4
        repositoryName: rancher-prime
        targetNamespace: cattle-system
        createNamespace: true
        installationNamespace: kube-system
        valuesFile: rancher.yaml
    repositories:
      - name: jetstack
        url: https://charts.jetstack.io
      - name: rancher-charts
        url: https://charts.rancher.io/
      - name: suse-edge-charts
        url: oci://registry.suse.com/edge
      - name: rancher-prime
        url: https://charts.rancher.com/server-charts/prime
    network:
      apiHost: ${API_HOST}
      apiVIP: ${API_VIP}
    nodes:
      - hostname: mgmt-cluster-node1
        initializer: true
        type: server
#     - hostname: mgmt-cluster-node2
#       initializer: true
#       type: server
#     - hostname: mgmt-cluster-node3
#       initializer: true
#       type: server

mgmt-cluster.yaml定義ファイルのフィールドと値について説明するために、ここではこのファイルを次のセクションに分割しています。

  • イメージセクション(定義ファイル):

image:
  imageType: iso
  arch: x86_64
  baseImage: SLE-Micro.x86_64-5.5.0-Default-SelfInstall-GM2.install.iso
  outputImageName: eib-mgmt-cluster-image.iso

ここで、baseImageは、SUSE Customer CenterまたはSUSEダウンロードページからダウンロードした元のイメージです。outputImageNameは、管理クラスタのプロビジョニングに使用する新しいイメージの名前です。

  • オペレーティングシステムセクション(定義ファイル):

operatingSystem:
  isoConfiguration:
    installDevice: /dev/sda
  users:
  - username: root
    encryptedPassword: ${ROOT_PASSWORD}
  packages:
    packageList:
    - jq
    sccRegistrationCode: ${SCC_REGISTRATION_CODE}

ここで、installDeviceはオペレーティングシステムのインストールに使用するデバイス、usernameおよびencryptedPasswordはシステムへのアクセスに使用する資格情報、packageListはインストールするパッケージのリスト(jqはインストールプロセス中に内部的に必要)です。sccRegistrationCodeは構築時にパッケージと依存関係を取得するために使用する登録コードで、SUSE Customer Centerから取得できます。暗号化パスワードは次のようにopensslコマンドを使用して生成できます。

openssl passwd -6 MyPassword!123

この出力は次のようになります。

$6$UrXB1sAGs46DOiSq$HSwi9GFJLCorm0J53nF2Sq8YEoyINhHcObHzX2R8h13mswUIsMwzx4eUzn/rRx0QPV4JIb0eWCoNrxGiKH4R31
  • Kubernetesセクション(定義ファイル):

kubernetes:
  version: ${KUBERNETES_VERSION}
  helm:
    charts:
      - name: cert-manager
        repositoryName: jetstack
        version: 1.14.2
        targetNamespace: cert-manager
        valuesFile: certmanager.yaml
        createNamespace: true
        installationNamespace: kube-system
      - name: longhorn-crd
        version: 103.3.0+up1.6.1
        repositoryName: rancher-charts
        targetNamespace: longhorn-system
        createNamespace: true
        installationNamespace: kube-system
      - name: longhorn
        version: 103.3.0+up1.6.1
        repositoryName: rancher-charts
        targetNamespace: longhorn-system
        createNamespace: true
        installationNamespace: kube-system
      - name: metal3-chart
        version: 0.7.1
        repositoryName: suse-edge-charts
        targetNamespace: metal3-system
        createNamespace: true
        installationNamespace: kube-system
        valuesFile: metal3.yaml
      - name: neuvector-crd
        version: 103.0.3+up2.7.6
        repositoryName: rancher-charts
        targetNamespace: neuvector
        createNamespace: true
        installationNamespace: kube-system
        valuesFile: neuvector.yaml
      - name: neuvector
        version: 103.0.3+up2.7.6
        repositoryName: rancher-charts
        targetNamespace: neuvector
        createNamespace: true
        installationNamespace: kube-system
        valuesFile: neuvector.yaml
      - name: rancher
        version: 2.8.4
        repositoryName: rancher-prime
        targetNamespace: cattle-system
        createNamespace: true
        installationNamespace: kube-system
        valuesFile: rancher.yaml
    repositories:
      - name: jetstack
        url: https://charts.jetstack.io
      - name: rancher-charts
        url: https://charts.rancher.io/
      - name: suse-edge-charts
        url: oci://registry.suse.com/edge
      - name: rancher-prime
        url: https://charts.rancher.com/server-charts/prime
    network:
      apiHost: ${API_HOST}
      apiVIP: ${API_VIP}
    nodes:
      - hostname: mgmt-cluster1
        initializer: true
        type: server
#      - hostname: mgmt-cluster2
#        type: server
#      - hostname: mgmt-cluster3
#        type: server

ここで、versionはインストールするKubernetesのバージョンです。ここでは、RKE2クラスタを使用しているため、バージョンは1.29未満のマイナーバージョンにしてRancherとの互換性を保つ必要があります(v1.28.9+rke2r1など)。

helmセクションには、インストールするHelmチャートのリスト、使用するリポジトリ、およびこれらすべてのバージョン設定が含まれます。

networkセクションには、RKE2コンポーネントが使用するapiHostapiVIPなどのネットワーク設定が含まれます。apiVIPは、ネットワーク内で使用されていないIPアドレスにし、DHCPを使用する場合はDHCPプールから除外してください。マルチノードクラスタでは、apiVIPがKubernetes APIサーバへのアクセスに使用されます。apiHostは、RKE2コンポーネントが使用するapiVIPへの名前解決として機能します。

nodesセクションには、クラスタで使用するノードのリストが含まれています。nodesセクションには、クラスタで使用するノードのリストが含まれています。この例では、シングルノードクラスタを使用していますが、リストにノードを追加する(行のコメントを解除する)ことによってマルチノードクラスタに拡張できます。

注記
注記

ノードの名前はクラスタ内で一意にし、リストの最初のノードのinitializerフィールドはtrueに設定する必要があります。ノードの名前は、networkセクションで定義したホスト名と同じにする必要があります。これはnetworkセクションのファイル名と直接照合されます。

29.3.3 Customフォルダ

customフォルダには次のサブフォルダが含まれます。

...
├── custom
│ ├── scripts
│ │ ├── 99-register.sh
│ │ ├── 99-mgmt-setup.sh
│ │ └── 99-alias.sh
│ └── files
│     ├── rancher.sh
│     ├── mgmt-stack-setup.service
│     ├── metal3.sh
│     └── basic-setup.sh
...
  • custom/filesフォルダには、管理クラスタが使用する設定ファイルが含まれます。

  • custom/scriptsフォルダには、管理クラスタが使用するスクリプトが含まれます。

custom/filesフォルダには、次のファイルが含まれます。

  • basic-setup.sh: 使用するMetal3バージョンに関する設定パラメータ、およびRancherMetalLBの基本パラメータが含まれます。このファイルを変更するのは、使用するコンポーネントのバージョンまたはネームスペースを変更する場合のみにしてください。

    #!/bin/bash
    # Pre-requisites. Cluster already running
    export KUBECTL="/var/lib/rancher/rke2/bin/kubectl"
    export KUBECONFIG="/etc/rancher/rke2/rke2.yaml"
    
    ##################
    # METAL3 DETAILS #
    ##################
    export METAL3_CHART_TARGETNAMESPACE="metal3-system"
    export METAL3_CLUSTERCTLVERSION="1.6.2"
    export METAL3_CAPICOREVERSION="1.6.2"
    export METAL3_CAPIMETAL3VERSION="1.6.0"
    export METAL3_CAPIRKE2VERSION="0.2.6"
    export METAL3_CAPIPROVIDER="rke2"
    export METAL3_CAPISYSTEMNAMESPACE="capi-system"
    export METAL3_RKE2BOOTSTRAPNAMESPACE="rke2-bootstrap-system"
    export METAL3_CAPM3NAMESPACE="capm3-system"
    export METAL3_RKE2CONTROLPLANENAMESPACE="rke2-control-plane-system"
    export METAL3_CAPI_IMAGES="registry.suse.com/edge"
    # Or registry.opensuse.org/isv/suse/edge/clusterapi/containerfile/suse for the upstream ones
    
    ###########
    # METALLB #
    ###########
    export METALLBNAMESPACE="metallb-system"
    
    ###########
    # RANCHER #
    ###########
    export RANCHER_CHART_TARGETNAMESPACE="cattle-system"
    export RANCHER_FINALPASSWORD="adminadminadmin"
    
    die(){
      echo ${1} 1>&2
      exit ${2}
    }
  • metal3.sh: 使用するMetal3コンポーネントの設定が含まれます(変更不要)。今後のバージョンでは、このスクリプトは代わりにRancher Turtlesを使用するように置き換えられて、使いやすくなる予定です。

    #!/bin/bash
    set -euo pipefail
    
    BASEDIR="$(dirname "$0")"
    source ${BASEDIR}/basic-setup.sh
    
    METAL3LOCKNAMESPACE="default"
    METAL3LOCKCMNAME="metal3-lock"
    
    trap 'catch $? $LINENO' EXIT
    
    catch() {
      if [ "$1" != "0" ]; then
        echo "Error $1 occurred on $2"
        ${KUBECTL} delete configmap ${METAL3LOCKCMNAME} -n ${METAL3LOCKNAMESPACE}
      fi
    }
    
    # Get or create the lock to run all those steps just in a single node
    # As the first node is created WAY before the others, this should be enough
    # TODO: Investigate if leases is better
    if [ $(${KUBECTL} get cm -n ${METAL3LOCKNAMESPACE} ${METAL3LOCKCMNAME} -o name | wc -l) -lt 1 ]; then
      ${KUBECTL} create configmap ${METAL3LOCKCMNAME} -n ${METAL3LOCKNAMESPACE} --from-literal foo=bar
    else
      exit 0
    fi
    
    # Wait for metal3
    while ! ${KUBECTL} wait --for condition=ready -n ${METAL3_CHART_TARGETNAMESPACE} $(${KUBECTL} get pods -n ${METAL3_CHART_TARGETNAMESPACE} -l app.kubernetes.io/name=metal3-ironic -o name) --timeout=10s; do sleep 2 ; done
    
    # Get the ironic IP
    IRONICIP=$(${KUBECTL} get cm -n ${METAL3_CHART_TARGETNAMESPACE} ironic-bmo -o jsonpath='{.data.IRONIC_IP}')
    
    # If LoadBalancer, use metallb, else it is NodePort
    if [ $(${KUBECTL} get svc -n ${METAL3_CHART_TARGETNAMESPACE} metal3-metal3-ironic -o jsonpath='{.spec.type}') == "LoadBalancer" ]; then
      # Wait for metallb
      while ! ${KUBECTL} wait --for condition=ready -n ${METALLBNAMESPACE} $(${KUBECTL} get pods -n ${METALLBNAMESPACE} -l app.kubernetes.io/component=controller -o name) --timeout=10s; do sleep 2 ; done
    
      # Do not create the ippool if already created
      ${KUBECTL} get ipaddresspool -n ${METALLBNAMESPACE} ironic-ip-pool -o name || cat <<-EOF | ${KUBECTL} apply -f -
      apiVersion: metallb.io/v1beta1
      kind: IPAddressPool
      metadata:
        name: ironic-ip-pool
        namespace: ${METALLBNAMESPACE}
      spec:
        addresses:
        - ${IRONICIP}/32
        serviceAllocation:
          priority: 100
          serviceSelectors:
          - matchExpressions:
            - {key: app.kubernetes.io/name, operator: In, values: [metal3-ironic]}
    	EOF
    
      # Same for L2 Advs
      ${KUBECTL} get L2Advertisement -n ${METALLBNAMESPACE} ironic-ip-pool-l2-adv -o name || cat <<-EOF | ${KUBECTL} apply -f -
      apiVersion: metallb.io/v1beta1
      kind: L2Advertisement
      metadata:
        name: ironic-ip-pool-l2-adv
        namespace: ${METALLBNAMESPACE}
      spec:
        ipAddressPools:
        - ironic-ip-pool
    	EOF
    fi
    
    # If clusterctl is not installed, install it
    if ! command -v clusterctl > /dev/null 2>&1; then
      LINUXARCH=$(uname -m)
      case $(uname -m) in
        "x86_64")
          export GOARCH="amd64" ;;
        "aarch64")
          export GOARCH="arm64" ;;
        "*")
          echo "Arch not found, asumming amd64"
          export GOARCH="amd64" ;;
      esac
    
      # Clusterctl bin
      # Maybe just use the binary from hauler if available
      curl -L https://github.com/kubernetes-sigs/cluster-api/releases/download/v${METAL3_CLUSTERCTLVERSION}/clusterctl-linux-${GOARCH} -o /usr/local/bin/clusterctl
      chmod +x /usr/local/bin/clusterctl
    fi
    
    # If rancher is deployed
    if [ $(${KUBECTL} get pods -n ${RANCHER_CHART_TARGETNAMESPACE} -l app=rancher -o name | wc -l) -ge 1 ]; then
      cat <<-EOF | ${KUBECTL} apply -f -
    	apiVersion: management.cattle.io/v3
    	kind: Feature
    	metadata:
    	  name: embedded-cluster-api
    	spec:
    	  value: false
    	EOF
    
      # Disable Rancher webhooks for CAPI
      ${KUBECTL} delete mutatingwebhookconfiguration.admissionregistration.k8s.io mutating-webhook-configuration
      ${KUBECTL} delete validatingwebhookconfigurations.admissionregistration.k8s.io validating-webhook-configuration
      ${KUBECTL} wait --for=delete namespace/cattle-provisioning-capi-system --timeout=300s
    fi
    
    # Deploy CAPI
    if [ $(${KUBECTL} get pods -n ${METAL3_CAPISYSTEMNAMESPACE} -o name | wc -l) -lt 1 ]; then
    
      # https://github.com/rancher-sandbox/cluster-api-provider-rke2#setting-up-clusterctl
      mkdir -p ~/.cluster-api
      cat <<-EOF > ~/.cluster-api/clusterctl.yaml
    	images:
    	  all:
    	    repository: ${METAL3_CAPI_IMAGES}
    	EOF
    
      # Try this command 3 times just in case, stolen from https://stackoverflow.com/a/33354419
      if ! (r=3; while ! clusterctl init \
        --core "cluster-api:v${METAL3_CAPICOREVERSION}"\
        --infrastructure "metal3:v${METAL3_CAPIMETAL3VERSION}"\
        --bootstrap "${METAL3_CAPIPROVIDER}:v${METAL3_CAPIRKE2VERSION}"\
        --control-plane "${METAL3_CAPIPROVIDER}:v${METAL3_CAPIRKE2VERSION}" ; do
                ((--r))||exit
                echo "Something went wrong, let's wait 10 seconds and retry"
                sleep 10;done) ; then
          echo "clusterctl failed"
          exit 1
      fi
    
      # Wait for capi-controller-manager
      while ! ${KUBECTL} wait --for condition=ready -n ${METAL3_CAPISYSTEMNAMESPACE} $(${KUBECTL} get pods -n ${METAL3_CAPISYSTEMNAMESPACE} -l cluster.x-k8s.io/provider=cluster-api -o name) --timeout=10s; do sleep 2 ; done
    
      # Wait for capm3-controller-manager, there are two pods, the ipam and the capm3 one, just wait for the first one
      while ! ${KUBECTL} wait --for condition=ready -n ${METAL3_CAPM3NAMESPACE} $(${KUBECTL} get pods -n ${METAL3_CAPM3NAMESPACE} -l cluster.x-k8s.io/provider=infrastructure-metal3 -o name | head -n1 ) --timeout=10s; do sleep 2 ; done
    
      # Wait for rke2-bootstrap-controller-manager
      while ! ${KUBECTL} wait --for condition=ready -n ${METAL3_RKE2BOOTSTRAPNAMESPACE} $(${KUBECTL} get pods -n ${METAL3_RKE2BOOTSTRAPNAMESPACE} -l cluster.x-k8s.io/provider=bootstrap-rke2 -o name) --timeout=10s; do sleep 2 ; done
    
      # Wait for rke2-control-plane-controller-manager
      while ! ${KUBECTL} wait --for condition=ready -n ${METAL3_RKE2CONTROLPLANENAMESPACE} $(${KUBECTL} get pods -n ${METAL3_RKE2CONTROLPLANENAMESPACE} -l cluster.x-k8s.io/provider=control-plane-rke2 -o name) --timeout=10s; do sleep 2 ; done
    
    fi
    
    # Clean up the lock cm
    
    ${KUBECTL} delete configmap ${METAL3LOCKCMNAME} -n ${METAL3LOCKNAMESPACE}
    • rancher.sh: 使用するRancherコンポーネントの設定が含まれます(変更不要)。

      #!/bin/bash
      set -euo pipefail
      
      BASEDIR="$(dirname "$0")"
      source ${BASEDIR}/basic-setup.sh
      
      RANCHERLOCKNAMESPACE="default"
      RANCHERLOCKCMNAME="rancher-lock"
      
      if [ -z "${RANCHER_FINALPASSWORD}" ]; then
        # If there is no final password, then finish the setup right away
        exit 0
      fi
      
      trap 'catch $? $LINENO' EXIT
      
      catch() {
        if [ "$1" != "0" ]; then
          echo "Error $1 occurred on $2"
          ${KUBECTL} delete configmap ${RANCHERLOCKCMNAME} -n ${RANCHERLOCKNAMESPACE}
        fi
      }
      
      # Get or create the lock to run all those steps just in a single node
      # As the first node is created WAY before the others, this should be enough
      # TODO: Investigate if leases is better
      if [ $(${KUBECTL} get cm -n ${RANCHERLOCKNAMESPACE} ${RANCHERLOCKCMNAME} -o name | wc -l) -lt 1 ]; then
        ${KUBECTL} create configmap ${RANCHERLOCKCMNAME} -n ${RANCHERLOCKNAMESPACE} --from-literal foo=bar
      else
        exit 0
      fi
      
      # Wait for rancher to be deployed
      while ! ${KUBECTL} wait --for condition=ready -n ${RANCHER_CHART_TARGETNAMESPACE} $(${KUBECTL} get pods -n ${RANCHER_CHART_TARGETNAMESPACE} -l app=rancher -o name) --timeout=10s; do sleep 2 ; done
      until ${KUBECTL} get ingress -n ${RANCHER_CHART_TARGETNAMESPACE} rancher > /dev/null 2>&1; do sleep 10; done
      
      RANCHERBOOTSTRAPPASSWORD=$(${KUBECTL} get secret -n ${RANCHER_CHART_TARGETNAMESPACE} bootstrap-secret -o jsonpath='{.data.bootstrapPassword}' | base64 -d)
      RANCHERHOSTNAME=$(${KUBECTL} get ingress -n ${RANCHER_CHART_TARGETNAMESPACE} rancher -o jsonpath='{.spec.rules[0].host}')
      
      # Skip the whole process if things have been set already
      if [ -z $(${KUBECTL} get settings.management.cattle.io first-login -ojsonpath='{.value}') ]; then
        # Add the protocol
        RANCHERHOSTNAME="https://${RANCHERHOSTNAME}"
        TOKEN=""
        while [ -z "${TOKEN}" ]; do
          # Get token
          sleep 2
          TOKEN=$(curl -sk -X POST ${RANCHERHOSTNAME}/v3-public/localProviders/local?action=login -H 'content-type: application/json' -d "{\"username\":\"admin\",\"password\":\"${RANCHERBOOTSTRAPPASSWORD}\"}" | jq -r .token)
        done
      
        # Set password
        curl -sk ${RANCHERHOSTNAME}/v3/users?action=changepassword -H 'content-type: application/json' -H "Authorization: Bearer $TOKEN" -d "{\"currentPassword\":\"${RANCHERBOOTSTRAPPASSWORD}\",\"newPassword\":\"${RANCHER_FINALPASSWORD}\"}"
      
        # Create a temporary API token (ttl=60 minutes)
        APITOKEN=$(curl -sk ${RANCHERHOSTNAME}/v3/token -H 'content-type: application/json' -H "Authorization: Bearer ${TOKEN}" -d '{"type":"token","description":"automation","ttl":3600000}' | jq -r .token)
      
        curl -sk ${RANCHERHOSTNAME}/v3/settings/server-url -H 'content-type: application/json' -H "Authorization: Bearer ${APITOKEN}" -X PUT -d "{\"name\":\"server-url\",\"value\":\"${RANCHERHOSTNAME}\"}"
        curl -sk ${RANCHERHOSTNAME}/v3/settings/telemetry-opt -X PUT -H 'content-type: application/json' -H 'accept: application/json' -H "Authorization: Bearer ${APITOKEN}" -d '{"value":"out"}'
      fi
      
      # Clean up the lock cm
      ${KUBECTL} delete configmap ${RANCHERLOCKCMNAME} -n ${RANCHERLOCKNAMESPACE}
    • mgmt-stack-setup.service: systemdサービスを作成して初回ブート時にスクリプトを実行するための設定が含まれます(変更不要)。

      [Unit]
      Description=Setup Management stack components
      Wants=network-online.target
      # It requires rke2 or k3s running, but it will not fail if those services are not present
      After=network.target network-online.target rke2-server.service k3s.service
      # At least, the basic-setup.sh one needs to be present
      ConditionPathExists=/opt/mgmt/bin/basic-setup.sh
      
      [Service]
      User=root
      Type=forking
      # Metal3 can take A LOT to download the IPA image
      TimeoutStartSec=1800
      
      ExecStartPre=/bin/sh -c "echo 'Setting up Management components...'"
      # Scripts are executed in StartPre because Start can only run a single on
      ExecStartPre=/opt/mgmt/bin/rancher.sh
      ExecStartPre=/opt/mgmt/bin/metal3.sh
      ExecStart=/bin/sh -c "echo 'Finished setting up Management components'"
      RemainAfterExit=yes
      KillMode=process
      # Disable & delete everything
      ExecStartPost=rm -f /opt/mgmt/bin/rancher.sh
      ExecStartPost=rm -f /opt/mgmt/bin/metal3.sh
      ExecStartPost=rm -f /opt/mgmt/bin/basic-setup.sh
      ExecStartPost=/bin/sh -c "systemctl disable mgmt-stack-setup.service"
      ExecStartPost=rm -f /etc/systemd/system/mgmt-stack-setup.service
      
      [Install]
      WantedBy=multi-user.target

custom/scriptsフォルダには次のファイルが含まれます。

  • 99-alias.shスクリプト: 管理クラスタが初回ブート時にkubeconfigファイルを読み込むために使用するエイリアスが含まれます(変更不要)。

    #!/bin/bash
    echo "alias k=kubectl" >> /etc/profile.local
    echo "alias kubectl=/var/lib/rancher/rke2/bin/kubectl" >> /etc/profile.local
    echo "export KUBECONFIG=/etc/rancher/rke2/rke2.yaml" >> /etc/profile.local
  • 99-mgmt-setup.shスクリプト: 初回ブート時にスクリプトをコピーするための設定が含まれます(変更不要)。

    #!/bin/bash
    
    # Copy the scripts from combustion to the final location
    mkdir -p /opt/mgmt/bin/
    for script in basic-setup.sh rancher.sh metal3.sh; do
    	cp ${script} /opt/mgmt/bin/
    done
    
    # Copy the systemd unit file and enable it at boot
    cp mgmt-stack-setup.service /etc/systemd/system/mgmt-stack-setup.service
    systemctl enable mgmt-stack-setup.service
  • 99-register.shスクリプト: SCC登録コードを使用してシステムを登録するための設定が含まれます。アカウントにシステムを登録するには、${SCC_ACCOUNT_EMAIL}および${SCC_REGISTRATION_CODE}が正しく設定されている必要があります。

    #!/bin/bash
    set -euo pipefail
    
    # Registration https://www.suse.com/support/kb/doc/?id=000018564
    if ! which SUSEConnect > /dev/null 2>&1; then
    	zypper --non-interactive install suseconnect-ng
    fi
    SUSEConnect --email "${SCC_ACCOUNT_EMAIL}" --url "https://scc.suse.com" --regcode "${SCC_REGISTRATION_CODE}"

29.3.4 Kubernetesフォルダ

kubernetesフォルダには次のサブフォルダが含まれます。

...
├── kubernetes
│ ├── manifests
│ │ ├── rke2-ingress-config.yaml
│ │ ├── neuvector-namespace.yaml
│ │ ├── ingress-l2-adv.yaml
│ │ └── ingress-ippool.yaml
│ ├── helm
│ │ └── values
│ │     ├── rancher.yaml
│ │     ├── neuvector.yaml
│ │     ├── metal3.yaml
│ │     └── certmanager.yaml
│ └── config
│     └── server.yaml
...

kubernetes/configフォルダには次のファイルが含まれます。

  • server.yaml: デフォルトでは、デフォルトでインストールされているCNIプラグインはCiliumであるため、このフォルダとファイルを作成する必要はありません。CNIプラグインをカスタマイズする必要がある場合に備えて、kubernetes/configフォルダにあるserver.yamlファイルを使用できます。このファイルには次の情報が含まれます。

    cni:
    - multus
    - cilium
注記
注記

これは、使用するCNIプラグインなどの特定のKubernetesカスタマイズを定義する任意のファイルです。さまざまなオプションについては、公式ドキュメントで確認できます。

kubernetes/manifestsフォルダには次のファイルが含まれます。

  • rke2-ingress-config.yaml: 管理クラスタ用のIngressサービスを作成するための設定が含まれます(変更不要)。

    apiVersion: helm.cattle.io/v1
    kind: HelmChartConfig
    metadata:
      name: rke2-ingress-nginx
      namespace: kube-system
    spec:
      valuesContent: |-
        controller:
          config:
            use-forwarded-headers: "true"
            enable-real-ip: "true"
          publishService:
            enabled: true
          service:
            enabled: true
            type: LoadBalancer
            externalTrafficPolicy: Local
  • neuvector-namespace.yaml: NeuVectorネームスペースを作成するための設定が含まれます(変更不要)。

    apiVersion: v1
    kind: Namespace
    metadata:
      labels:
        pod-security.kubernetes.io/enforce: privileged
      name: neuvector
  • ingress-l2-adv.yaml: MetalLBコンポーネントのL2Advertisementを作成するための設定が含まれます(変更不要)。

    apiVersion: metallb.io/v1beta1
    kind: L2Advertisement
    metadata:
      name: ingress-l2-adv
      namespace: metallb-system
    spec:
      ipAddressPools:
        - ingress-ippool
  • ingress-ippool.yaml: rke2-ingress-nginxコンポーネントのIPAddressPoolを作成するための設定が含まれます。${INGRESS_VIP}を正しく設定し、rke2-ingress-nginxコンポーネントで使用するために予約するIPアドレスを定義する必要があります。

    apiVersion: metallb.io/v1beta1
    kind: IPAddressPool
    metadata:
      name: ingress-ippool
      namespace: metallb-system
    spec:
      addresses:
        - ${INGRESS_VIP}/32
      serviceAllocation:
        priority: 100
        serviceSelectors:
          - matchExpressions:
              - {key: app.kubernetes.io/name, operator: In, values: [rke2-ingress-nginx]}

kubernetes/helm/valuesフォルダには次のファイルが含まれます。

  • rancher.yaml: Rancherコンポーネントを作成するための設定が含まれます。${INGRESS_VIP}を正しく設定して、Rancherコンポーネントで使用するIPアドレスを定義する必要があります。RancherコンポーネントにアクセスするためのURLは、https://rancher-${INGRESS_VIP}.sslip.ioです。

    hostname: rancher-${INGRESS_VIP}.sslip.io
    bootstrapPassword: "foobar"
    replicas: 1
    global.cattle.psp.enabled: "false"
  • neuvector.yaml: NeuVectorコンポーネントを作成するための設定が含まれます(変更不要)。

    controller:
      replicas: 1
      ranchersso:
        enabled: true
    manager:
      enabled: false
    cve:
      scanner:
        enabled: false
        replicas: 1
    k3s:
      enabled: true
    crdwebhook:
      enabled: false
  • metal3.yaml: Metal3コンポーネントを作成するための設定が含まれます。${METAL3_VIP}を正しく設定して、Metal3コンポーネントで使用するIPアドレスを定義する必要があります。

    global:
      ironicIP: ${METAL3_VIP}
      enable_vmedia_tls: false
      additionalTrustedCAs: false
    metal3-ironic:
      global:
        predictableNicNames: "true"
      persistence:
        ironic:
          size: "5Gi"
注記
注記

メディアサーバは、Metal3に含まれるオプションの機能です(デフォルトでは無効になっています)。このMetal3の機能を使用するには、以前のマニフェストで設定する必要があります。Metal3メディアサーバを使用するには、次の変数を指定します。

  • メディアサーバ機能を有効にするために、globalセクションにenable_metal3_media_serverを追加してtrueに設定します。

  • メディアサーバ設定に次の内容を含めます。${MEDIA_VOLUME_PATH}はメディアボリュームのパスです(例: /home/metal3/bmh-image-cache)。

    metal3-media:
      mediaVolume:
        hostPath: ${MEDIA_VOLUME_PATH}

外部のメディアサーバを使用してイメージを保存できます。外部のメディアサーバをTLSで使用する場合は、次の設定を変更する必要があります。

  • 前のmetal3.yamlファイルでadditionalTrustedCAstrueに設定し、外部のメディアサーバから、信頼できる追加のCAを有効にします。

  • kubernetes/manifests/metal3-cacert-secret.yamlフォルダに次のシークレット設定を含めて、外部のメディアサーバのCA証明書を保存します。

    apiVersion: v1
    kind: Namespace
    metadata:
      name: metal3-system
    ---
    apiVersion: v1
    kind: Secret
    metadata:
      name: tls-ca-additional
      namespace: metal3-system
    type: Opaque
    data:
      ca-additional.crt: {{ additional_ca_cert | b64encode }}

additional_ca_certは、外部のメディアサーバのbase64エンコードCA証明書です。次のコマンドを使用し、証明書をエンコードして手動でシークレットを生成できます。

kubectl -n meta3-system create secret generic tls-ca-additional --from-file=ca-additional.crt=./ca-additional.crt
  • certmanager.yaml: Cert-Managerコンポーネントを作成するための設定が含まれます(変更不要)。

    installCRDs: "true"

29.3.5 ネットワーキングフォルダ

networkフォルダには、管理クラスタのノードと同じ数のファイルが含まれます。ここでは、ノードは1つのみであるため、mgmt-cluster-node1.yamlというファイルが1つあるだけです。ファイルの名前は、上述のnetwork/nodeセクションでmgmt-cluster.yaml定義ファイルに定義されているホスト名と一致させる必要があります。

ネットワーキング設定をカスタマイズして特定の静的IPアドレスを使用する必要がある場合(たとえばDHCPを使用しないシナリオの場合)、networkフォルダにあるmgmt-cluster-node1.yamlファイルを使用できます。このファイルには次の情報が含まれます。

  • ${MGMT_GATEWAY}: ゲートウェイのIPアドレス。

  • ${MGMT_DNS}: DNSサーバのIPアドレス。

  • ${MGMT_MAC}: ネットワークインタフェースのMACアドレス。

  • ${MGMT_NODE_IP}: 管理クラスタのIPアドレス。

routes:
  config:
  - destination: 0.0.0.0/0
    metric: 100
    next-hop-address: ${MGMT_GATEWAY}
    next-hop-interface: eth0
    table-id: 254
dns-resolver:
  config:
    server:
    - ${MGMT_DNS}
    - 8.8.8.8
interfaces:
- name: eth0
  type: ethernet
  state: up
  mac-address: ${MGMT_MAC}
  ipv4:
    address:
    - ip: ${MGMT_NODE_IP}
      prefix-length: 24
    dhcp: false
    enabled: true
  ipv6:
    enabled: false

DHCPを使用してIPアドレスを取得する場合、次の設定を使用できます(${MGMT_MAC}変数を使用して、MACアドレスを正しく設定する必要があります)。

## This is an example of a dhcp network configuration for a management cluster
## interfaces:
- name: eth0
  type: ethernet
  state: up
  mac-address: ${MGMT_MAC}
  ipv4:
    dhcp: true
    enabled: true
  ipv6:
    enabled: false
注記
注記
  • 管理クラスタのノード数に応じて、mgmt-cluster-node2.yamlmgmt-cluster-node3.yamlなどのように追加のファイルを作成して残りのノードを設定できます。

  • routesセクションは、管理クラスタのルーティングテーブルを定義するために使用します。

29.4 エアギャップ環境のイメージの準備

このセクションでは、エアギャップ環境を準備する方法について説明し、前の各セクションとの相違点のみを示します。エアギャップ環境のイメージを準備するには、前のセクション(接続環境のイメージの準備(29.3項 「接続環境用のイメージの準備」))を次のように変更する必要があります。

  • mgmt-cluster.yamlファイルを変更してembeddedArtifactRegistryセクションを含め、imagesフィールドに、EIB出力イメージに組み込むすべてのコンテナイメージを設定する必要があります。

  • エアギャップ環境を使用する場合、custom/scripts/99-register.shスクリプトは削除する必要があります。

  • custom/files/airgap-resources.tar.gzファイルを、管理クラスタをエアギャップ環境で実行するために必要なすべてのリソースとともにcustom/filesフォルダに含める必要があります。

  • custom/scripts/99-mgmt-setup.shスクリプトを変更し、airgap-resources.tar.gzファイルを抽出して最終的な場所にコピーするようにする必要があります。

  • custom/files/metal3.shスクリプトを変更し、インターネットからリソースをダウンロードするのではなく、airgap-resources.tar.gzファイルに含まれるローカルリソースを使用するように必要があります。

29.4.1 エアギャップ環境のディレクトリ構造

エアギャップ環境のディレクトリ構造は接続環境とほぼ同じです。相違点を次に説明します。

eib
|-- base-images
|   |-- SLE-Micro.x86_64-5.5.0-Default-SelfInstall-GM2.install.iso
|-- custom
|   |-- files
|   |   |-- airgap-resources.tar.gz
|   |   |-- basic-setup.sh
|   |   |-- metal3.sh
|   |   |-- mgmt-stack-setup.service
|   |   |-- rancher.sh
|   |-- scripts
|       |-- 99-alias.sh
|       |-- 99-mgmt-setup.sh
|-- kubernetes
|   |-- config
|   |   |-- server.yaml
|   |-- helm
|   |   |-- values
|   |       |-- certmanager.yaml
|   |       |-- metal3.yaml
|   |       |-- neuvector.yaml
|   |       |-- rancher.yaml
|   |-- manifests
|       |-- neuvector-namespace.yaml
|-- mgmt-cluster.yaml
|-- network
    |-- mgmt-cluster-network.yaml
注記
注記

イメージSLE-Micro.x86_64-5.5.0-Default-SelfInstall-GM2.install.isoSUSE Customer CenterまたはSUSEダウンロードページからダウンロードし、プロセスを開始する前にbase-imagesフォルダに配置する必要があります。

イメージのSHA256チェックサムを確認し、イメージが改ざんされていないことを確認する必要があります。このチェックサムは、イメージをダウンロードした場所と同じ場所にあります。

ディレクトリ構造の例は、 SUSE Edge GitHubリポジトリの「telco-examples」フォルダにあります。

29.4.2 定義ファイルの変更

mgmt-cluster.yamlファイルを変更してembeddedArtifactRegistryセクションを含め、imagesフィールドに、EIB出力イメージに組み込むすべてのコンテナイメージを設定する必要があります。imagesフィールドには、出力イメージに含めるすべてのコンテナイメージのリストを含める必要があります。次に、embeddedArtifactRegistryセクションが含まれるmgmt-cluster.yamlファイルの例を示します。

apiVersion: 1.0
image:
  imageType: iso
  arch: x86_64
  baseImage: SLE-Micro.x86_64-5.5.0-Default-SelfInstall-GM2.install.iso
  outputImageName: eib-mgmt-cluster-image.iso
operatingSystem:
  isoConfiguration:
    installDevice: /dev/sda
  users:
  - username: root
    encryptedPassword: ${ROOT_PASSWORD}
  packages:
    packageList:
    - jq
    sccRegistrationCode: ${SCC_REGISTRATION_CODE}
kubernetes:
  version: ${KUBERNETES_VERSION}
  helm:
    charts:
      - name: cert-manager
        repositoryName: jetstack
        version: 1.14.2
        targetNamespace: cert-manager
        valuesFile: certmanager.yaml
        createNamespace: true
        installationNamespace: kube-system
      - name: longhorn-crd
        version: 103.3.0+up1.6.1
        repositoryName: rancher-charts
        targetNamespace: longhorn-system
        createNamespace: true
        installationNamespace: kube-system
      - name: longhorn
        version: 103.3.0+up1.6.1
        repositoryName: rancher-charts
        targetNamespace: longhorn-system
        createNamespace: true
        installationNamespace: kube-system
      - name: metal3-chart
        version: 0.7.1
        repositoryName: suse-edge-charts
        targetNamespace: metal3-system
        createNamespace: true
        installationNamespace: kube-system
        valuesFile: metal3.yaml
      - name: neuvector-crd
        version: 103.0.3+up2.7.6
        repositoryName: rancher-charts
        targetNamespace: neuvector
        createNamespace: true
        installationNamespace: kube-system
        valuesFile: neuvector.yaml
      - name: neuvector
        version: 103.0.3+up2.7.6
        repositoryName: rancher-charts
        targetNamespace: neuvector
        createNamespace: true
        installationNamespace: kube-system
        valuesFile: neuvector.yaml
      - name: rancher
        version: 2.8.4
        repositoryName: rancher-prime
        targetNamespace: cattle-system
        createNamespace: true
        installationNamespace: kube-system
        valuesFile: rancher.yaml
    repositories:
      - name: jetstack
        url: https://charts.jetstack.io
      - name: rancher-charts
        url: https://charts.rancher.io/
      - name: suse-edge-charts
        url: oci://registry.suse.com/edge
      - name: rancher-prime
        url: https://charts.rancher.com/server-charts/prime
    network:
      apiHost: ${API_HOST}
      apiVIP: ${API_VIP}
    nodes:
      - hostname: mgmt-cluster-node1
        initializer: true
        type: server
#     - hostname: mgmt-cluster-node2
#       initializer: true
#       type: server
#     - hostname: mgmt-cluster-node3
#       initializer: true
#       type: server
embeddedArtifactRegistry:
  images:
    - name: registry.rancher.com/rancher/backup-restore-operator:v4.0.2
    - name: registry.rancher.com/rancher/calico-cni:v3.27.0-rancher1
    - name: registry.rancher.com/rancher/cis-operator:v1.0.13
    - name: registry.rancher.com/rancher/coreos-kube-state-metrics:v1.9.7
    - name: registry.rancher.com/rancher/coreos-prometheus-config-reloader:v0.38.1
    - name: registry.rancher.com/rancher/coreos-prometheus-operator:v0.38.1
    - name: registry.rancher.com/rancher/flannel-cni:v0.3.0-rancher9
    - name: registry.rancher.com/rancher/fleet-agent:v0.9.4
    - name: registry.rancher.com/rancher/fleet:v0.9.4
    - name: registry.rancher.com/rancher/gitjob:v0.9.7
    - name: registry.rancher.com/rancher/grafana-grafana:7.1.5
    - name: registry.rancher.com/rancher/hardened-addon-resizer:1.8.20-build20240410
    - name: registry.rancher.com/rancher/hardened-calico:v3.27.3-build20240423
    - name: registry.rancher.com/rancher/hardened-cluster-autoscaler:v1.8.10-build20240124
    - name: registry.rancher.com/rancher/hardened-cni-plugins:v1.4.1-build20240325
    - name: registry.rancher.com/rancher/hardened-coredns:v1.11.1-build20240305
    - name: registry.rancher.com/rancher/hardened-dns-node-cache:1.22.28-build20240125
    - name: registry.rancher.com/rancher/hardened-etcd:v3.5.9-k3s1-build20240418
    - name: registry.rancher.com/rancher/hardened-flannel:v0.25.1-build20240423
    - name: registry.rancher.com/rancher/hardened-k8s-metrics-server:v0.7.1-build20240401
    - name: registry.rancher.com/rancher/hardened-kubernetes:v1.28.9-rke2r1-build20240416
    - name: registry.rancher.com/rancher/hardened-multus-cni:v4.0.2-build20240208
    - name: registry.rancher.com/rancher/hardened-node-feature-discovery:v0.14.1-build20230926
    - name: registry.rancher.com/rancher/hardened-whereabouts:v0.6.3-build20240208
    - name: registry.rancher.com/rancher/helm-project-operator:v0.2.1
    - name: registry.rancher.com/rancher/istio-kubectl:1.5.10
    - name: registry.rancher.com/rancher/jimmidyson-configmap-reload:v0.3.0
    - name: registry.rancher.com/rancher/k3s-upgrade:v1.28.9-k3s1
    - name: registry.rancher.com/rancher/klipper-helm:v0.8.3-build20240228
    - name: registry.rancher.com/rancher/klipper-lb:v0.4.7
    - name: registry.rancher.com/rancher/kube-api-auth:v0.2.1
    - name: registry.rancher.com/rancher/kubectl:v1.28.7
    - name: registry.rancher.com/rancher/library-nginx:1.19.2-alpine
    - name: registry.rancher.com/rancher/local-path-provisioner:v0.0.26
    - name: registry.rancher.com/rancher/machine:v0.15.0-rancher112
    - name: registry.rancher.com/rancher/mirrored-cluster-api-controller:v1.4.4
    - name: registry.rancher.com/rancher/nginx-ingress-controller:nginx-1.9.6-rancher1
    - name: registry.rancher.com/rancher/pause:3.6
    - name: registry.rancher.com/rancher/prom-alertmanager:v0.21.0
    - name: registry.rancher.com/rancher/prom-node-exporter:v1.0.1
    - name: registry.rancher.com/rancher/prom-prometheus:v2.18.2
    - name: registry.rancher.com/rancher/prometheus-auth:v0.2.2
    - name: registry.rancher.com/rancher/prometheus-federator:v0.3.4
    - name: registry.rancher.com/rancher/pushprox-client:v0.1.0-rancher2-client
    - name: registry.rancher.com/rancher/pushprox-proxy:v0.1.0-rancher2-proxy
    - name: registry.rancher.com/rancher/rancher-agent:v2.8.4
    - name: registry.rancher.com/rancher/rancher-csp-adapter:v3.0.1
    - name: registry.rancher.com/rancher/rancher-webhook:v0.4.5
    - name: registry.rancher.com/rancher/rancher:v2.8.4
    - name: registry.rancher.com/rancher/rke-tools:v0.1.96
    - name: registry.rancher.com/rancher/rke2-cloud-provider:v1.29.3-build20240412
    - name: registry.rancher.com/rancher/rke2-runtime:v1.28.9-rke2r1
    - name: registry.rancher.com/rancher/rke2-upgrade:v1.28.9-rke2r1
    - name: registry.rancher.com/rancher/security-scan:v0.2.15
    - name: registry.rancher.com/rancher/shell:v0.1.24
    - name: registry.rancher.com/rancher/system-agent-installer-k3s:v1.28.9-k3s1
    - name: registry.rancher.com/rancher/system-agent-installer-rke2:v1.28.9-rke2r1
    - name: registry.rancher.com/rancher/system-agent:v0.3.6-suc
    - name: registry.rancher.com/rancher/system-upgrade-controller:v0.13.1
    - name: registry.rancher.com/rancher/ui-plugin-catalog:1.3.0
    - name: registry.rancher.com/rancher/ui-plugin-operator:v0.1.1
    - name: registry.rancher.com/rancher/webhook-receiver:v0.2.5
    - name: registry.rancher.com/rancher/kubectl:v1.20.2
    - name: registry.rancher.com/rancher/mirrored-longhornio-csi-attacher:v4.4.2
    - name: registry.rancher.com/rancher/mirrored-longhornio-csi-provisioner:v3.6.2
    - name: registry.rancher.com/rancher/mirrored-longhornio-csi-resizer:v1.9.2
    - name: registry.rancher.com/rancher/mirrored-longhornio-csi-snapshotter:v6.3.2
    - name: registry.rancher.com/rancher/mirrored-longhornio-csi-node-driver-registrar:v2.9.2
    - name: registry.rancher.com/rancher/mirrored-longhornio-livenessprobe:v2.12.0
    - name: registry.rancher.com/rancher/mirrored-longhornio-backing-image-manager:v1.6.1
    - name: registry.rancher.com/rancher/mirrored-longhornio-longhorn-engine:v1.6.1
    - name: registry.rancher.com/rancher/mirrored-longhornio-longhorn-instance-manager:v1.6.1
    - name: registry.rancher.com/rancher/mirrored-longhornio-longhorn-manager:v1.6.1
    - name: registry.rancher.com/rancher/mirrored-longhornio-longhorn-share-manager:v1.6.1
    - name: registry.rancher.com/rancher/mirrored-longhornio-longhorn-ui:v1.6.1
    - name: registry.rancher.com/rancher/mirrored-longhornio-support-bundle-kit:v0.0.36
    - name: registry.suse.com/edge/cluster-api-provider-rke2-bootstrap:v0.2.6
    - name: registry.suse.com/edge/cluster-api-provider-rke2-controlplane:v0.2.6
    - name: registry.suse.com/edge/cluster-api-controller:v1.6.2
    - name: registry.suse.com/edge/cluster-api-provider-metal3:v1.6.0
    - name: registry.suse.com/edge/ip-address-manager:v1.6.0

29.4.3 カスタムフォルダの変更

  • エアギャップ環境を使用する場合、custom/scripts/99-register.shスクリプトを削除する必要があります。ディレクトリ構造からわかるように、99-register.shスクリプトはcustom/scriptsフォルダに含まれていません。

  • custom/scripts/99-mgmt-setup.shスクリプトを変更し、airgap-resources.tar.gzファイルを抽出して最終的な場所にコピーするようにする必要があります。次に、airgap-resources.tar.gzファイルを抽出してコピーするように変更した99-mgmt-setup.shスクリプトの例を示します。

    #!/bin/bash
    
    # Copy the scripts from combustion to the final location
    mkdir -p /opt/mgmt/bin/
    for script in basic-setup.sh rancher.sh metal3.sh; do
    	cp ${script} /opt/mgmt/bin/
    done
    
    # Copy the systemd unit file and enable it at boot
    cp mgmt-stack-setup.service /etc/systemd/system/mgmt-stack-setup.service
    systemctl enable mgmt-stack-setup.service
    
    # Extract the airgap resources
    tar zxf airgap-resources.tar.gz
    
    # Copy the clusterctl binary to the final location
    cp airgap-resources/clusterctl /opt/mgmt/bin/ && chmod +x /opt/mgmt/bin/clusterctl
    
    # Copy the clusterctl.yaml and override
    mkdir -p /root/cluster-api
    cp -r airgap-resources/clusterctl.yaml airgap-resources/overrides /root/cluster-api/
  • custom/files/metal3.shスクリプトを変更し、インターネットからリソースをダウンロードするのではなく、airgap-resources.tar.gzファイルに含まれるローカルリソースを使用するようにする必要があります。次に、ローカルリソースを使用するように変更したmetal3.shスクリプトの例を示します。

    #!/bin/bash
    set -euo pipefail
    
    BASEDIR="$(dirname "$0")"
    source ${BASEDIR}/basic-setup.sh
    
    METAL3LOCKNAMESPACE="default"
    METAL3LOCKCMNAME="metal3-lock"
    
    trap 'catch $? $LINENO' EXIT
    
    catch() {
      if [ "$1" != "0" ]; then
        echo "Error $1 occurred on $2"
        ${KUBECTL} delete configmap ${METAL3LOCKCMNAME} -n ${METAL3LOCKNAMESPACE}
      fi
    }
    
    # Get or create the lock to run all those steps just in a single node
    # As the first node is created WAY before the others, this should be enough
    # TODO: Investigate if leases is better
    if [ $(${KUBECTL} get cm -n ${METAL3LOCKNAMESPACE} ${METAL3LOCKCMNAME} -o name | wc -l) -lt 1 ]; then
      ${KUBECTL} create configmap ${METAL3LOCKCMNAME} -n ${METAL3LOCKNAMESPACE} --from-literal foo=bar
    else
      exit 0
    fi
    
    # Wait for metal3
    while ! ${KUBECTL} wait --for condition=ready -n ${METAL3_CHART_TARGETNAMESPACE} $(${KUBECTL} get pods -n ${METAL3_CHART_TARGETNAMESPACE} -l app.kubernetes.io/name=metal3-ironic -o name) --timeout=10s; do sleep 2 ; done
    
    # If rancher is deployed
    if [ $(${KUBECTL} get pods -n ${RANCHER_CHART_TARGETNAMESPACE} -l app=rancher -o name | wc -l) -ge 1 ]; then
      cat <<-EOF | ${KUBECTL} apply -f -
    	apiVersion: management.cattle.io/v3
    	kind: Feature
    	metadata:
    	  name: embedded-cluster-api
    	spec:
    	  value: false
    	EOF
    
      # Disable Rancher webhooks for CAPI
      ${KUBECTL} delete mutatingwebhookconfiguration.admissionregistration.k8s.io mutating-webhook-configuration
      ${KUBECTL} delete validatingwebhookconfigurations.admissionregistration.k8s.io validating-webhook-configuration
      ${KUBECTL} wait --for=delete namespace/cattle-provisioning-capi-system --timeout=300s
    fi
    
    # Deploy CAPI
    if [ $(${KUBECTL} get pods -n ${METAL3_CAPISYSTEMNAMESPACE} -o name | wc -l) -lt 1 ]; then
    
      # Try this command 3 times just in case, stolen from https://stackoverflow.com/a/33354419
      if ! (r=3; while ! /opt/mgmt/bin/clusterctl init \
        --core "cluster-api:v${METAL3_CAPICOREVERSION}"\
        --infrastructure "metal3:v${METAL3_CAPIMETAL3VERSION}"\
        --bootstrap "${METAL3_CAPIPROVIDER}:v${METAL3_CAPIRKE2VERSION}"\
        --control-plane "${METAL3_CAPIPROVIDER}:v${METAL3_CAPIRKE2VERSION}"\
        --config /root/cluster-api/clusterctl.yaml ; do
                ((--r))||exit
                echo "Something went wrong, let's wait 10 seconds and retry"
                sleep 10;done) ; then
          echo "clusterctl failed"
          exit 1
      fi
    
      # Wait for capi-controller-manager
      while ! ${KUBECTL} wait --for condition=ready -n ${METAL3_CAPISYSTEMNAMESPACE} $(${KUBECTL} get pods -n ${METAL3_CAPISYSTEMNAMESPACE} -l cluster.x-k8s.io/provider=cluster-api -o name) --timeout=10s; do sleep 2 ; done
    
      # Wait for capm3-controller-manager, there are two pods, the ipam and the capm3 one, just wait for the first one
      while ! ${KUBECTL} wait --for condition=ready -n ${METAL3_CAPM3NAMESPACE} $(${KUBECTL} get pods -n ${METAL3_CAPM3NAMESPACE} -l cluster.x-k8s.io/provider=infrastructure-metal3 -o name | head -n1 ) --timeout=10s; do sleep 2 ; done
    
      # Wait for rke2-bootstrap-controller-manager
      while ! ${KUBECTL} wait --for condition=ready -n ${METAL3_RKE2BOOTSTRAPNAMESPACE} $(${KUBECTL} get pods -n ${METAL3_RKE2BOOTSTRAPNAMESPACE} -l cluster.x-k8s.io/provider=bootstrap-rke2 -o name) --timeout=10s; do sleep 2 ; done
    
      # Wait for rke2-control-plane-controller-manager
      while ! ${KUBECTL} wait --for condition=ready -n ${METAL3_RKE2CONTROLPLANENAMESPACE} $(${KUBECTL} get pods -n ${METAL3_RKE2CONTROLPLANENAMESPACE} -l cluster.x-k8s.io/provider=control-plane-rke2 -o name) --timeout=10s; do sleep 2 ; done
    
    fi
    
    # Clean up the lock cm
    
    ${KUBECTL} delete configmap ${METAL3LOCKCMNAME} -n ${METAL3LOCKNAMESPACE}
  • custom/files/airgap-resources.tar.gzファイルを変更し、管理クラスタをエアギャップ環境で実行するために必要なすべてのリソースとともにcustom/filesフォルダに含める必要があります。このファイルを準備するには、すべてのリソースを手動でダウンロードして1つのファイルに圧縮する必要があります。airgap-resources.tar.gzファイルには次のリソースが含まれます。

    |-- clusterctl
    |-- clusterctl.yaml
    |-- overrides
        |-- bootstrap-rke2
        |   |-- v0.2.6
        |       |-- bootstrap-components.yaml
        |       |-- metadata.yaml
        |-- cluster-api
        |   |-- v1.6.2
        |       |-- core-components.yaml
        |       |-- metadata.yaml
        |-- control-plane-rke2
        |   |-- v0.2.6
        |       |-- control-plane-components.yaml
        |       |-- metadata.yaml
        |-- infrastructure-metal3
            |-- v1.6.0
                |-- cluster-template.yaml
                |-- infrastructure-components.yaml
                |-- metadata.yaml

clusterctl.yamlファイルには、イメージの場所、およびclusterctlツールで利用する上書き設定が含まれます。overridesフォルダには、インターネットからダウンロードする代わりに使用するyamlファイルマニフェストが含まれます。

providers:
  # override a pre-defined provider
  - name: "cluster-api"
    url: "/root/cluster-api/overrides/cluster-api/v1.6.2/core-components.yaml"
    type: "CoreProvider"
  - name: "metal3"
    url: "/root/cluster-api/overrides/infrastructure-metal3/v1.6.0/infrastructure-components.yaml"
    type: "InfrastructureProvider"
  - name: "rke2"
    url: "/root/cluster-api/overrides/bootstrap-rke2/v0.2.6/bootstrap-components.yaml"
    type: "BootstrapProvider"
  - name: "rke2"
    url: "/root/cluster-api/overrides/control-plane-rke2/v0.2.6/control-plane-components.yaml"
    type: "ControlPlaneProvider"
images:
  all:
    repository: registry.suse.com/edge

overridesフォルダに含まれるclusterctlと残りのファイル は、次のcurlsコマンドを使用してダウンロードできます。

# clusterctl binary
curl -L https://github.com/kubernetes-sigs/cluster-api/releases/download/1.6.2/clusterctl-linux-${GOARCH} -o /usr/local/bin/clusterct

# boostrap-components (boostrap-rke2)
curl -L https://github.com/rancher-sandbox/cluster-api-provider-rke2/releases/download/v0.2.6/bootstrap-components.yaml
curl -L https://github.com/rancher-sandbox/cluster-api-provider-rke2/releases/download/v0.2.6/metadata.yaml

# control-plane-components (control-plane-rke2)
curl -L https://github.com/rancher-sandbox/cluster-api-provider-rke2/releases/download/v0.2.6/control-plane-components.yaml
curl -L https://github.com/rancher-sandbox/cluster-api-provider-rke2/releases/download/v0.2.6/metadata.yaml

# cluster-api components
curl -L https://github.com/kubernetes-sigs/cluster-api/releases/download/v1.6.2/core-components.yaml
curl -L https://github.com/kubernetes-sigs/cluster-api/releases/download/v1.6.2/metadata.yaml

# infrastructure-components (infrastructure-metal3)
curl -L https://github.com/metal3-io/cluster-api-provider-metal3/releases/download/v1.6.0/infrastructure-components.yaml
curl -L https://github.com/metal3-io/cluster-api-provider-metal3/releases/download/v1.6.0/metadata.yaml
注記
注記

異なるバージョンのコンポーネントを使用する場合、URL内のバージョンを変更すると、特定のバージョンのコンポーネントをダウンロードできます。

以前のリソースをダウンロード済みの場合、次のコマンドを使用してそれらを1つのファイルに圧縮できます。

tar -czvf airgap-resources.tar.gz clusterctl clusterctl.yaml overrides

29.5 イメージの作成

前の各セクションに従ってディレクトリ構造を準備したら(接続シナリオとエアギャップシナリオの両方が対象です)、次のコマンドを実行してイメージを構築します。

podman run --rm --privileged -it -v $PWD:/eib \
 registry.suse.com/edge/edge-image-builder:1.0.2 \
 build --definition-file mgmt-cluster.yaml

ISO出力イメージファイルが作成されます。ここでは、上記のイメージ定義に基づくeib-mgmt-cluster-image.isoという名前のファイルです。

29.6 管理クラスタのプロビジョニング

前のイメージには、上述のコンポーネントがすべて含まれています。このイメージを使って、仮想マシンまたはベアメタルサーバを使用して(仮想メディア機能を使用して)管理クラスタをプロビジョニングできます。

30 通信機能の設定

このセクションでは、ATIPがデプロイされたクラスタの通信事業者固有の機能について記述および説明します。

ダイレクトネットワークプロビジョニングのデプロイメント方法を使用します。この方法については、ATIPの自動プロビジョニング(第31章 「完全に自動化されたダイレクトネットワークプロビジョニング)に関するセクションで説明しています。

このセクションでは、次のトピックについて説明します。

30.1 リアルタイム用のカーネルイメージ

リアルタイムカーネルイメージは必ずしも標準カーネルより優れているとは限りません。リアルタイムカーネルは、特定のユースケース用に調整された別のカーネルです。低レイテンシを実現するために調整されていますが、その結果、スループットが犠牲になります。リアルタイムカーネルは一般的な用途には推奨されませんが、ここでは低レイテンシが重要な要因である通信ワークロード用のカーネルとして推奨されています。

主に4つの機能があります。

  • 決定論的実行:

    予測可能性の向上 — 高負荷状態でも重要なビジネスプロセスが期限内に確実に完了し、常に高品質なサービスを提供します。高優先度プロセスのために重要なシステムリソースを保護することで、時間に依存するアプリケーションの予測可能性を向上できます。

  • 低ジッタ:

    高度に決定論的な技術に基づいてジッタが低く抑えられているため、アプリケーションと実世界との同期を維持できます。これは、継続的に繰り返し計算を行う必要があるサービスで役立ちます。

  • 優先度の継承:

    優先度の継承とは、優先度の高いプロセスがある状況において、そのプロセスがタスクを完了するためには優先度の低いプロセスが完了するのを待つ必要がある場合に、優先度の低いプロセスが高優先度を一時的に引き受ける機能です。SUSE Linux Enterprise Real Timeは、ミッションクリティカルなプロセスにおけるこのような優先度の逆転の問題を解決します。

  • スレッドの割り込み:

    一般的なオペレーティングシステムでは、割り込みモードで実行中のプロセスはプリエンプト可能ではありません。SUSE Linux Enterprise Real Timeでは、このような割り込みをカーネルスレッドでカプセル化して割り込み可能にし、ユーザが定義した高優先度プロセスでハード割り込みとソフト割り込みをプリエンプトできます。

    ここでは、SLE Micro RTのようなリアルタイムイメージをインストール済みの場合、カーネルリアルタイムはすでにインストールされています。リアルタイムカーネルイメージはSUSE Customer Centerからダウンロードできます。

    注記
    注記

    リアルタイムカーネルの詳細については、SUSE Real Timeを参照してください。

30.2 CPU調整設定

CPU調整設定を使用すると、リアルタイムカーネルが使用するCPUコアを分離できます。OSがリアルタイムカーネルと同じコアを使用しないようにすることが重要です。OSがそのコアを使用すると、リアルタイムカーネルの遅延が増加するためです。

この機能を有効にして設定するには、まず、分離するCPUコアのプロファイルを作成します。ここでは、コア1-30および33-62を分離しています。

$ echo "export tuned_params" >> /etc/grub.d/00_tuned

$ echo "isolated_cores=1-30,33-62" >> /etc/tuned/cpu-partitioning-variables.conf

$ tuned-adm profile cpu-partitioning
Tuned (re)started, changes applied.

次に、GRUBオプションを変更して、CPUコアと、CPUの使用法に関するその他の重要なパラメータを分離する必要があります。現在のハードウェア仕様で次のオプションをカスタマイズすることが重要です。

パラメータ説明

isolcpus

1-30、33-62

コア1-30および33-62を分離します。

skew_tick

1

このオプションを使用すると、カーネルは分離されたCPU全体でタイマー割り込みをずらすことができます。

nohz

on

このオプションを使用すると、カーネルはシステムがアイドル状態のときに1つのCPU上でタイマーティックを実行できます。

nohz_full

1-30、33-62

カーネルブートパラメータは、完全なdynticksとCPU分離の設定を行うための現在の主要インタフェースです。

rcu_nocbs

1-30、33-62

このオプションを使用すると、カーネルはシステムがアイドル状態のときに1つのCPU上でRCUコールバックを実行できます。

kthread_cpus

0、31、32、63

このオプションを使用すると、システムがアイドル状態のときに1つのCPU上でkthreadsを実行できます。

irqaffinity

0、31、32、63

このオプションを使用すると、システムがアイドル状態のときに1つのCPU上で割り込みを実行できます。

processor.max_cstate

1

このオプションを使用すると、アイドル状態のときにCPUがスリープ状態になるのを防ぎます。

intel_idle.max_cstate

0

このオプションを使用すると、intel_idleドライバが無効になり、acpi_idleを使用できるようになります。

上記の値を使用することで、60個のコアを分離し、4個のコアをOSに使用します。

次のコマンドでGRUB設定を変更し、上記の変更を次回ブート時に適用します。

/etc/default/grubファイルを編集し、上記のパラメータを追加します。

GRUB_CMDLINE_LINUX="intel_iommu=on intel_pstate=passive processor.max_cstate=1 intel_idle.max_cstate=0 iommu=pt usbcore.autosuspend=-1 selinux=0 enforcing=0 nmi_watchdog=0 crashkernel=auto softlockup_panic=0 audit=0 mce=off hugepagesz=1G hugepages=40 hugepagesz=2M hugepages=0 default_hugepagesz=1G kthread_cpus=0,31,32,63 irqaffinity=0,31,32,63 isolcpus=1-30,33-62 skew_tick=1 nohz_full=1-30,33-62 rcu_nocbs=1-30,33-62 rcu_nocb_poll"

GRUB設定を更新します。

$ transactional-update grub.cfg
$ reboot

再起動後にパラメータが適用されていることを検証するには、次のコマンドを使用してカーネルコマンドラインを確認できます。

$ cat /proc/cmdline

30.3 CNI設定

30.3.1 Cilium

CiliumはATIPのデフォルトのCNIプラグインです。RKE2クラスタでCiliumをデフォルトのプラグインとして有効にするには、/etc/rancher/rke2/config.yamlファイルに次の設定が必要です。

cni:
- cilium

これはコマンドライン引数でも指定できます。具体的には、/etc/systemd/system/rke2-serverファイルのサーバの行に--cni=ciliumを追加します。

次のセクション(30.4項 「SR-IOV」)で説明するSR-IOV Network Operatorを使用するには、Multusとともに、CiliumCalicoなどの別のCNIプラグインをセカンダリプラグインとして使用します。

cni:
- multus
- cilium
注記
注記

CNIプラグインの詳細については、「Network Options (ネットワークオプション)」を参照してください。

30.4 SR-IOV

SR-IOVを使用すると、ネットワークアダプタなどのデバイスで、そのリソースへのアクセスをさまざまなPCIeハードウェア機能の間で分離することができます。SR-IOVをデプロイするにはさまざまな方法がありますが、ここでは2つの方法を示します。

  • オプション1: SR-IOV CNIデバイスプラグインと設定マップを使用して適切に設定する。

  • オプション2 (推奨): Rancher PrimeからSR-IOV Helmチャートを使用してこのデプロイメントを簡単に行えるようにする。

オプション1 - SR-IOV CNIデバイスプラグインと設定マップをインストールして適切に設定する

  • デバイスプラグインの設定マップを準備する

設定マップに入力する情報をlspciコマンドから取得します。

$ lspci | grep -i acc
8a:00.0 Processing accelerators: Intel Corporation Device 0d5c

$ lspci | grep -i net
19:00.0 Ethernet controller: Broadcom Inc. and subsidiaries BCM57504 NetXtreme-E 10Gb/25Gb/40Gb/50Gb/100Gb/200Gb Ethernet (rev 11)
19:00.1 Ethernet controller: Broadcom Inc. and subsidiaries BCM57504 NetXtreme-E 10Gb/25Gb/40Gb/50Gb/100Gb/200Gb Ethernet (rev 11)
19:00.2 Ethernet controller: Broadcom Inc. and subsidiaries BCM57504 NetXtreme-E 10Gb/25Gb/40Gb/50Gb/100Gb/200Gb Ethernet (rev 11)
19:00.3 Ethernet controller: Broadcom Inc. and subsidiaries BCM57504 NetXtreme-E 10Gb/25Gb/40Gb/50Gb/100Gb/200Gb Ethernet (rev 11)
51:00.0 Ethernet controller: Intel Corporation Ethernet Controller E810-C for QSFP (rev 02)
51:00.1 Ethernet controller: Intel Corporation Ethernet Controller E810-C for QSFP (rev 02)
51:01.0 Ethernet controller: Intel Corporation Ethernet Adaptive Virtual Function (rev 02)
51:01.1 Ethernet controller: Intel Corporation Ethernet Adaptive Virtual Function (rev 02)
51:01.2 Ethernet controller: Intel Corporation Ethernet Adaptive Virtual Function (rev 02)
51:01.3 Ethernet controller: Intel Corporation Ethernet Adaptive Virtual Function (rev 02)
51:11.0 Ethernet controller: Intel Corporation Ethernet Adaptive Virtual Function (rev 02)
51:11.1 Ethernet controller: Intel Corporation Ethernet Adaptive Virtual Function (rev 02)
51:11.2 Ethernet controller: Intel Corporation Ethernet Adaptive Virtual Function (rev 02)
51:11.3 Ethernet controller: Intel Corporation Ethernet Adaptive Virtual Function (rev 02)

設定マップはJSONファイルで構成され、このファイルで、フィルタを使用して検出を行うデバイスを記述し、インタフェースのグループを作成します。フィルタとグループを理解することが重要です。フィルタはデバイスを検出するために使用され、グループはインタフェースを作成するために使用されます。

フィルタを設定することもできます。

  • vendorID: 8086 (Intel)

  • deviceID: 0d5c (アクセラレータカード)

  • driver: vfio-pci (ドライバ)

  • pfNames: p2p1 (物理インタフェース名)

フィルタを設定して、より複雑なインタフェース構文に一致させることもできます。次に例を示します。

  • pfNames: ["eth1#1,2,3,4,5,6"]または[eth1#1-6] (物理インタフェース名)

グループに関連して、FECカード用のグループを1つと、Intelカード用のグループを1つ作成し、さらに、ユースケースに応じてプレフィックスを作成することもできます。

  • resourceName: pci_sriov_net_bh_dpdk

  • resourcePrefix: Rancher.io

リソースグループを検出して作成し、一部のVFをPodに割り当てる組み合わせは多数あります。

注記
注記

フィルタとグループの詳細については、「sriov-network-device-plugin (sr-iovネットワークデバイスプラグイン)」を参照してください。

フィルタとグループを設定して、ハードウェアとユースケースに応じたインタフェースに一致させると、使用する例が次の設定マップに表示されます。

apiVersion: v1
kind: ConfigMap
metadata:
  name: sriovdp-config
  namespace: kube-system
data:
  config.json: |
    {
        "resourceList": [
            {
                "resourceName": "intel_fec_5g",
                "devicetype": "accelerator",
                "selectors": {
                    "vendors": ["8086"],
                    "devices": ["0d5d"]
                }
            },
            {
                "resourceName": "intel_sriov_odu",
                "selectors": {
                    "vendors": ["8086"],
                    "devices": ["1889"],
                    "drivers": ["vfio-pci"],
                    "pfNames": ["p2p1"]
                }
            },
            {
                "resourceName": "intel_sriov_oru",
                "selectors": {
                    "vendors": ["8086"],
                    "devices": ["1889"],
                    "drivers": ["vfio-pci"],
                    "pfNames": ["p2p2"]
                }
            }
        ]
    }
  • daemonsetファイルを準備して、デバイスプラグインをデプロイします。

このデバイスプラグインは、複数のアーキテクチャ(armamdppc64le)をサポートしています。したがって、同じファイルを異なるアーキテクチャに使用して、各アーキテクチャに複数のdaemonsetをデプロイできます。

apiVersion: v1
kind: ServiceAccount
metadata:
  name: sriov-device-plugin
  namespace: kube-system
---
apiVersion: apps/v1
kind: DaemonSet
metadata:
  name: kube-sriov-device-plugin-amd64
  namespace: kube-system
  labels:
    tier: node
    app: sriovdp
spec:
  selector:
    matchLabels:
      name: sriov-device-plugin
  template:
    metadata:
      labels:
        name: sriov-device-plugin
        tier: node
        app: sriovdp
    spec:
      hostNetwork: true
      nodeSelector:
        kubernetes.io/arch: amd64
      tolerations:
      - key: node-role.kubernetes.io/master
        operator: Exists
        effect: NoSchedule
      serviceAccountName: sriov-device-plugin
      containers:
      - name: kube-sriovdp
        image: rancher/hardened-sriov-network-device-plugin:v3.5.1-build20231009-amd64
        imagePullPolicy: IfNotPresent
        args:
        - --log-dir=sriovdp
        - --log-level=10
        securityContext:
          privileged: true
        resources:
          requests:
            cpu: "250m"
            memory: "40Mi"
          limits:
            cpu: 1
            memory: "200Mi"
        volumeMounts:
        - name: devicesock
          mountPath: /var/lib/kubelet/
          readOnly: false
        - name: log
          mountPath: /var/log
        - name: config-volume
          mountPath: /etc/pcidp
        - name: device-info
          mountPath: /var/run/k8s.cni.cncf.io/devinfo/dp
      volumes:
        - name: devicesock
          hostPath:
            path: /var/lib/kubelet/
        - name: log
          hostPath:
            path: /var/log
        - name: device-info
          hostPath:
            path: /var/run/k8s.cni.cncf.io/devinfo/dp
            type: DirectoryOrCreate
        - name: config-volume
          configMap:
            name: sriovdp-config
            items:
            - key: config.json
              path: config.json
  • 設定マップとdaemonsetを適用すると、デバイスプラグインがデプロイされ、インタフェースが検出されてPodで使用できるようになります。

    $ kubectl get pods -n kube-system | grep sriov
    kube-system  kube-sriov-device-plugin-amd64-twjfl  1/1  Running  0  2m
  • Podで使用するノードでインタフェースが検出されて利用可能であることを確認します。

    $ kubectl get $(kubectl get nodes -oname) -o jsonpath='{.status.allocatable}' | jq
    {
      "cpu": "64",
      "ephemeral-storage": "256196109726",
      "hugepages-1Gi": "40Gi",
      "hugepages-2Mi": "0",
      "intel.com/intel_fec_5g": "1",
      "intel.com/intel_sriov_odu": "4",
      "intel.com/intel_sriov_oru": "4",
      "memory": "221396384Ki",
      "pods": "110"
    }
  • FECintel.com/intel_fec_5gで、値は1です。

  • Helmチャートを使用せずに、デバイスプラグインと設定マップを使用してデプロイした場合、VFは、intel.com/intel_sriov_oduまたはintel.com/intel_sriov_oruです。

重要
重要

ここにインタフェースがない場合、そのインタフェースをPodで使用することはできないため、続行しても意味がありません。まず、設定マップとフィルタを確認して問題を解決してください。

オプション2 (推奨) - Rancherを使用し、SR-IOV CNIおよびデバイスプラグイン用のHelmチャートを使用したインストール

  • Helmがない場合は入手します。

$ curl https://raw.githubusercontent.com/helm/helm/main/scripts/get-helm-3 | bash
  • SR-IOVをインストールします。

この部分は2つの方法で実行できます。CLIを使用する方法と、Rancher UIを使用する方法です。

CLIからのオペレータのインストール
helm repo add suse-edge https://suse-edge.github.io/charts
helm install sriov-crd suse-edge/sriov-crd -n sriov-network-operator
helm install install sriov-network-operator suse-edge/sriov-network-operator -n sriov-network-operator
Rancher UIからのオペレータのインストール

クラスタがインストールされたら、Rancher UIにアクセスできるようになり、[Apps (アプリ)]タブでRancher UIからSR-IOVオペレータをインストールできます。

注記
注記

必ず、正しいネームスペースを選択してオペレータをインストールしてください(例: sriov-network-operator)。

+ image::features_sriov.png[sriov.png]

  • デプロイしたリソースのcrdとPodを確認します。

$ kubectl get crd
$ kubectl -n sriov-network-operator get pods
  • ノードのラベルを確認します。

すべてのリソースが実行されていると、ラベルがノードに自動的に表示されます。

$ kubectl get nodes -oyaml | grep feature.node.kubernetes.io/network-sriov.capable

feature.node.kubernetes.io/network-sriov.capable: "true"
  • daemonsetを確認し、新しいsriov-network-config-daemonおよびsriov-rancher-nfd-workerがアクティブで準備できていることを確認します。

$ kubectl get daemonset -A
NAMESPACE             NAME                            DESIRED   CURRENT   READY   UP-TO-DATE   AVAILABLE   NODE SELECTOR                                           AGE
calico-system            calico-node                     1         1         1       1            1           kubernetes.io/os=linux                                  15h
sriov-network-operator   sriov-network-config-daemon     1         1         1       1            1           feature.node.kubernetes.io/network-sriov.capable=true   45m
sriov-network-operator   sriov-rancher-nfd-worker        1         1         1       1            1           <none>                                                  45m
kube-system              rke2-ingress-nginx-controller   1         1         1       1            1           kubernetes.io/os=linux                                  15h
kube-system              rke2-multus-ds                  1         1         1       1            1           kubernetes.io/arch=amd64,kubernetes.io/os=linux         15h

数分後(更新に最大で10分かかる可能性があります)、ノードが検出されて、SR-IOVの機能が設定されます。

$ kubectl get sriovnetworknodestates.sriovnetwork.openshift.io -A
NAMESPACE             NAME     AGE
sriov-network-operator   xr11-2   83s
  • 検出されたインタフェースを確認します。

検出されたインタフェースはネットワークデバイスのPCIアドレスである必要があります。この情報は、ホストでlspciコマンドを使用して確認します。

$ kubectl get sriovnetworknodestates.sriovnetwork.openshift.io -n kube-system -oyaml
apiVersion: v1
items:
- apiVersion: sriovnetwork.openshift.io/v1
  kind: SriovNetworkNodeState
  metadata:
    creationTimestamp: "2023-06-07T09:52:37Z"
    generation: 1
    name: xr11-2
    namespace: sriov-network-operator
    ownerReferences:
    - apiVersion: sriovnetwork.openshift.io/v1
      blockOwnerDeletion: true
      controller: true
      kind: SriovNetworkNodePolicy
      name: default
      uid: 80b72499-e26b-4072-a75c-f9a6218ec357
    resourceVersion: "356603"
    uid: e1f1654b-92b3-44d9-9f87-2571792cc1ad
  spec:
    dpConfigVersion: "356507"
  status:
    interfaces:
    - deviceID: "1592"
      driver: ice
      eSwitchMode: legacy
      linkType: ETH
      mac: 40:a6:b7:9b:35:f0
      mtu: 1500
      name: p2p1
      pciAddress: "0000:51:00.0"
      totalvfs: 128
      vendor: "8086"
    - deviceID: "1592"
      driver: ice
      eSwitchMode: legacy
      linkType: ETH
      mac: 40:a6:b7:9b:35:f1
      mtu: 1500
      name: p2p2
      pciAddress: "0000:51:00.1"
      totalvfs: 128
      vendor: "8086"
    syncStatus: Succeeded
kind: List
metadata:
  resourceVersion: ""
注記
注記

ここでインタフェースが検出されていない場合は、インタフェースが次の設定マップに存在することを確認してください。

$ kubectl get cm supported-nic-ids -oyaml -n sriov-network-operator

ここにデバイスがない場合は、設定マップを編集して、検出すべき適切な値を追加します(sriov-network-config-daemonデーモンセットの再起動が必要になります)。

  • NetworkNodeポリシーを作成してVFを設定します。

VF (numVfs)がデバイス(rootDevices)から作成され、ドライバdeviceTypeMTUが設定されます。

注記
注記

resourceNameフィールドには特殊文字を含めないでください。また、このフィールドはクラスタ全体で一意である必要があります。この例では、dpdksr-iovと組み合わせて使用するため、deviceType: vfio-pciを使用しています。dpdkを使用しない場合は、deviceTypeをdeviceType: netdevice (デフォルト値)にする必要があります。

apiVersion: sriovnetwork.openshift.io/v1
kind: SriovNetworkNodePolicy
metadata:
  name: policy-dpdk
  namespace: sriov-network-operator
spec:
  nodeSelector:
    feature.node.kubernetes.io/network-sriov.capable: "true"
  resourceName: intelnicsDpdk
  deviceType: vfio-pci
  numVfs: 8
  mtu: 1500
  nicSelector:
    deviceID: "1592"
    vendor: "8086"
    rootDevices:
    - 0000:51:00.0
  • 設定を検証します。

$ kubectl get $(kubectl get nodes -oname) -o jsonpath='{.status.allocatable}' | jq
{
  "cpu": "64",
  "ephemeral-storage": "256196109726",
  "hugepages-1Gi": "60Gi",
  "hugepages-2Mi": "0",
  "intel.com/intel_fec_5g": "1",
  "memory": "200424836Ki",
  "pods": "110",
  "rancher.io/intelnicsDpdk": "8"
}
  • sr-iovネットワークを作成します(別のネットワークが必要な場合のオプション)。

apiVersion: sriovnetwork.openshift.io/v1
kind: SriovNetwork
metadata:
  name: network-dpdk
  namespace: sriov-network-operator
spec:
  ipam: |
    {
      "type": "host-local",
      "subnet": "192.168.0.0/24",
      "rangeStart": "192.168.0.20",
      "rangeEnd": "192.168.0.60",
      "routes": [{
        "dst": "0.0.0.0/0"
      }],
      "gateway": "192.168.0.1"
    }
  vlan: 500
  resourceName: intelnicsDpdk
  • 作成されたネットワークを確認します。

$ kubectl get network-attachment-definitions.k8s.cni.cncf.io -A -oyaml

apiVersion: v1
items:
- apiVersion: k8s.cni.cncf.io/v1
  kind: NetworkAttachmentDefinition
  metadata:
    annotations:
      k8s.v1.cni.cncf.io/resourceName: rancher.io/intelnicsDpdk
    creationTimestamp: "2023-06-08T11:22:27Z"
    generation: 1
    name: network-dpdk
    namespace: sriov-network-operator
    resourceVersion: "13124"
    uid: df7c89f5-177c-4f30-ae72-7aef3294fb15
  spec:
    config: '{ "cniVersion":"0.3.1", "name":"network-dpdk","type":"sriov","vlan":500,"vlanQoS":0,"ipam":{"type":"host-local","subnet":"192.168.0.0/24","rangeStart":"192.168.0.10","rangeEnd":"192.168.0.60","routes":[{"dst":"0.0.0.0/0"}],"gateway":"192.168.0.1"}
      }'
kind: List
metadata:
  resourceVersion: ""

30.5 DPDK

DPDK (データプレーン開発キット)は、パケットの高速処理用の一連のライブラリとドライバです。DPDKは、広範なCPUアーキテクチャ上で実行されるパケット処理ワークロードを高速化するために使用されます。DPDKには、データプレーンライブラリと、以下のために最適化されたネットワークインタフェースコントローラ(NIC)ドライバが含まれています。

  1. キューマネージャはロックなしのキューを実装します。

  2. バッファマネージャは固定サイズのバッファを事前割り当てします。

  3. メモリマネージャは、メモリ内にオブジェクトのプールを割り当て、リングを使用してフリーオブジェクトを格納します。オブジェクトがすべてのDRAMチャンネルに均等に分散されるようにします。

  4. ポールモードドライバ(PMD)は、非同期通知なしで動作するように設計されているため、オーバーヘッドが軽減されます。

  5. パケット処理を開発するためのヘルパである一連のライブラリとしてのパケットフレームワーク。

次の手順では、DPDKを有効にする方法と、DPDKインタフェースが使用するNICからVFを作成する方法を示します。

  • DPDKパッケージをインストールします。

$ transactional-update pkg install dpdk22 dpdk22-tools libdpdk-23
$ reboot
  • カーネルパラメータ:

DPDKを使用するには、ドライバをいくつか使用して、カーネルの特定のパラメータを有効にします。

パラメータ説明

iommu

pt

このオプションを使用すると、DPDKインタフェースにvfioドライバを使用できます。

intel_iommu

on

このオプションを使用すると、VFvfioを使用できます。

これらのパラメータを有効にするには、各パラメータを/etc/default/grubファイルに追加します。

GRUB_CMDLINE_LINUX="intel_iommu=on intel_pstate=passive processor.max_cstate=1 intel_idle.max_cstate=0 iommu=pt usbcore.autosuspend=-1 selinux=0 enforcing=0 nmi_watchdog=0 crashkernel=auto softlockup_panic=0 audit=0 mce=off hugepagesz=1G hugepages=40 hugepagesz=2M hugepages=0 default_hugepagesz=1G kthread_cpus=0,31,32,63 irqaffinity=0,31,32,63 isolcpus=1-30,33-62 skew_tick=1 nohz_full=1-30,33-62 rcu_nocbs=1-30,33-62 rcu_nocb_poll"

GRUBの設定を更新し、システムを再起動して変更を適用します。

$ transactional-update grub.cfg
$ reboot
  • vfio-pciカーネルモジュールを読み込み、NICSR-IOVを有効にします。

$ modprobe vfio-pci enable_sriov=1 disable_idle_d3=1
  • NICから仮想機能(VF)をいくつか作成します。

たとえば、2つの異なるNICに対してVFを作成するには、次のコマンドが必要です。

$ echo 4 > /sys/bus/pci/devices/0000:51:00.0/sriov_numvfs
$ echo 4 > /sys/bus/pci/devices/0000:51:00.1/sriov_numvfs
  • 新しいVFをvfio-pciドライバにバインドします。

$ dpdk-devbind.py -b vfio-pci 0000:51:01.0 0000:51:01.1 0000:51:01.2 0000:51:01.3 \
                              0000:51:11.0 0000:51:11.1 0000:51:11.2 0000:51:11.3
  • 設定が正しく適用されたことを確認します。

$ dpdk-devbind.py -s

Network devices using DPDK-compatible driver
============================================
0000:51:01.0 'Ethernet Adaptive Virtual Function 1889' drv=vfio-pci unused=iavf,igb_uio
0000:51:01.1 'Ethernet Adaptive Virtual Function 1889' drv=vfio-pci unused=iavf,igb_uio
0000:51:01.2 'Ethernet Adaptive Virtual Function 1889' drv=vfio-pci unused=iavf,igb_uio
0000:51:01.3 'Ethernet Adaptive Virtual Function 1889' drv=vfio-pci unused=iavf,igb_uio
0000:51:01.0 'Ethernet Adaptive Virtual Function 1889' drv=vfio-pci unused=iavf,igb_uio
0000:51:11.1 'Ethernet Adaptive Virtual Function 1889' drv=vfio-pci unused=iavf,igb_uio
0000:51:21.2 'Ethernet Adaptive Virtual Function 1889' drv=vfio-pci unused=iavf,igb_uio
0000:51:31.3 'Ethernet Adaptive Virtual Function 1889' drv=vfio-pci unused=iavf,igb_uio

Network devices using kernel driver
===================================
0000:19:00.0 'BCM57504 NetXtreme-E 10Gb/25Gb/40Gb/50Gb/100Gb/200Gb Ethernet 1751' if=em1 drv=bnxt_en unused=igb_uio,vfio-pci *Active*
0000:19:00.1 'BCM57504 NetXtreme-E 10Gb/25Gb/40Gb/50Gb/100Gb/200Gb Ethernet 1751' if=em2 drv=bnxt_en unused=igb_uio,vfio-pci
0000:19:00.2 'BCM57504 NetXtreme-E 10Gb/25Gb/40Gb/50Gb/100Gb/200Gb Ethernet 1751' if=em3 drv=bnxt_en unused=igb_uio,vfio-pci
0000:19:00.3 'BCM57504 NetXtreme-E 10Gb/25Gb/40Gb/50Gb/100Gb/200Gb Ethernet 1751' if=em4 drv=bnxt_en unused=igb_uio,vfio-pci
0000:51:00.0 'Ethernet Controller E810-C for QSFP 1592' if=eth13 drv=ice unused=igb_uio,vfio-pci
0000:51:00.1 'Ethernet Controller E810-C for QSFP 1592' if=rename8 drv=ice unused=igb_uio,vfio-pci

30.6 vRANアクセラレーション(Intel ACC100/ACC200)

4Gから5Gネットワークへの移行に伴い、多くの通信サービスプロバイダが仮想化無線アクセスネットワーク(vRAN)アーキテクチャを採用して、チャンネル容量を増やし、エッジベースのサービスとアプリケーションのデプロイメントを容易にしようとしています。vRANソリューションは、ネットワーク上のリアルタイムのトラフィックと需要の量に応じて容量を柔軟に増減できるため、低レイテンシのサービスを提供するのに理想的です。

4Gおよび5Gで最も計算負荷が高いワークロードの1つがRANレイヤ1 (L1)のFECです。これは、信頼性の低い通信チャンネルやノイズの多い通信チャンネルでのデータ伝送エラーを解消するものです。FEC技術は、4Gまたは5Gデータの一定数のエラーを検出して訂正することで、再送信の必要性を解消します。FECアクセラレーショントランザクションにはセルの状態情報が含まれないため、簡単に仮想化でき、プールするメリットとセルの容易な移行が実現します。

  • カーネルパラメータ

vRANアクセラレーションを有効にするには、次のカーネルパラメータを有効にする必要があります(まだ存在しない場合)。

パラメータ説明

iommu

pt

このオプションを使用すると、DPDKインタフェースにvfioを使用できます。

intel_iommu

on

このオプションを使用すると、VFにvfioを使用できます。

GRUBファイル/etc/default/grubを変更して、これらのパラメータをカーネルコマンドラインに追加します。

GRUB_CMDLINE_LINUX="intel_iommu=on intel_pstate=passive processor.max_cstate=1 intel_idle.max_cstate=0 iommu=pt usbcore.autosuspend=-1 selinux=0 enforcing=0 nmi_watchdog=0 crashkernel=auto softlockup_panic=0 audit=0 mce=off hugepagesz=1G hugepages=40 hugepagesz=2M hugepages=0 default_hugepagesz=1G kthread_cpus=0,31,32,63 irqaffinity=0,31,32,63 isolcpus=1-30,33-62 skew_tick=1 nohz_full=1-30,33-62 rcu_nocbs=1-30,33-62 rcu_nocb_poll"

GRUBの設定を更新し、システムを再起動して変更を適用します。

$ transactional-update grub.cfg
$ reboot

再起動後にパラメータが適用されていることを確認するには、コマンドラインを確認します。

$ cat /proc/cmdline
  • vfio-pciカーネルモジュールを読み込み、vRANアクセラレーションを有効にします。

$ modprobe vfio-pci enable_sriov=1 disable_idle_d3=1
  • インタフェース情報Acc100を取得します。

$ lspci | grep -i acc
8a:00.0 Processing accelerators: Intel Corporation Device 0d5c
  • 物理インタフェース(PF)をvfio-pciドライバにバインドします。

$ dpdk-devbind.py -b vfio-pci 0000:8a:00.0
  • 仮想機能(VF)を物理インタフェース(PF)から作成します。

2つのVFPFから作成し、次の手順に従ってvfio-pciにバインドします。

$ echo 2 > /sys/bus/pci/devices/0000:8a:00.0/sriov_numvfs
$ dpdk-devbind.py -b vfio-pci 0000:8b:00.0
  • 提案された設定ファイルを使用してacc100を設定します。

$ pf_bb_config ACC100 -c /opt/pf-bb-config/acc100_config_vf_5g.cfg
Tue Jun  6 10:49:20 2023:INFO:Queue Groups: 2 5GUL, 2 5GDL, 2 4GUL, 2 4GDL
Tue Jun  6 10:49:20 2023:INFO:Configuration in VF mode
Tue Jun  6 10:49:21 2023:INFO: ROM version MM 99AD92
Tue Jun  6 10:49:21 2023:WARN:* Note: Not on DDR PRQ version  1302020 != 10092020
Tue Jun  6 10:49:21 2023:INFO:PF ACC100 configuration complete
Tue Jun  6 10:49:21 2023:INFO:ACC100 PF [0000:8a:00.0] configuration complete!
  • FEC PFから作成した新しいVFを確認します。

$ dpdk-devbind.py -s
Baseband devices using DPDK-compatible driver
=============================================
0000:8a:00.0 'Device 0d5c' drv=vfio-pci unused=
0000:8b:00.0 'Device 0d5d' drv=vfio-pci unused=

Other Baseband devices
======================
0000:8b:00.1 'Device 0d5d' unused=

30.7 Huge Page

プロセスがRAMを使用すると、CPUはそのメモリ領域をプロセスが使用中であるとマークします。効率を高めるために、CPURAMをチャンクで割り当てます。多くのプラットフォームでは4Kバイトがチャンクのデフォルト値です。これらのチャンクをページと呼び、ディスクなどにスワップできます。

プロセスのアドレススペースは仮想であるため、CPUとオペレーティングシステムは、どのページがどのプロセスに属していて、各ページがどこに保管されているかを覚えておく必要があります。ページ数が多いほど、メモリマッピングの検索に時間がかかります。プロセスが1GBのメモリを使用する場合、検索するエントリは262,144個になります(1GB / 4K)。1つのページテーブルエントリが8バイトを消費する場合、2MB (262,144 * 8)を検索することになります。

最新のCPUアーキテクチャはデフォルトより大きいページをサポートしているので、CPU/OSが検索するエントリが減少します。

  • カーネルパラメータ

Huge Pageを有効にするには、次のカーネルパラメータを追加する必要があります。

パラメータ説明

hugepagesz

1G

このオプションを使用すると、Huge Pageを1Gに設定できます

hugepages

40

前に定義したHuge Pageの数です

default_hugepagesz

1G

Huge Pageを取得するためのデフォルト値です

GRUBファイル/etc/default/grubを変更して、これらのパラメータをカーネルコマンドラインに追加します。

GRUB_CMDLINE_LINUX="intel_iommu=on intel_pstate=passive processor.max_cstate=1 intel_idle.max_cstate=0 iommu=pt usbcore.autosuspend=-1 selinux=0 enforcing=0 nmi_watchdog=0 crashkernel=auto softlockup_panic=0 audit=0 mce=off hugepagesz=1G hugepages=40 hugepagesz=2M hugepages=0 default_hugepagesz=1G kthread_cpus=0,31,32,63 irqaffinity=0,31,32,63 isolcpus=1-30,33-62 skew_tick=1 nohz_full=1-30,33-62 rcu_nocbs=1-30,33-62 rcu_nocb_poll"

GRUBの設定を更新し、システムを再起動して変更を適用します。

$ transactional-update grub.cfg
$ reboot

再起動後にパラメータが適用されていることを検証するには、次のコマンドラインを確認できます。

$ cat /proc/cmdline
  • Huge Pageの使用

Huge Pageを使用するには、Huge Pageをマウントする必要があります。

$ mkdir -p /hugepages
$ mount -t hugetlbfs nodev /hugepages

Kubernetesワークロードをデプロイし、リソースとボリュームを作成します。

...
 resources:
   requests:
     memory: "24Gi"
     hugepages-1Gi: 16Gi
     intel.com/intel_sriov_oru: '4'
   limits:
     memory: "24Gi"
     hugepages-1Gi: 16Gi
     intel.com/intel_sriov_oru: '4'
...
...
volumeMounts:
  - name: hugepage
    mountPath: /hugepages
...
volumes:
  - name: hugepage
    emptyDir:
      medium: HugePages
...

30.8 CPUピニング設定

  • 要件

    1. こちらのセクション(30.2項 「CPU調整設定」)で説明したパフォーマンスプロファイルに合わせてCPUが調整されていること。

    2. 次のブロック(例)を/etc/rancher/rke2/config.yamlファイルに追加して、RKE2クラスタのkubeletにCPU管理の引数が設定されていること。

kubelet-arg:
- "cpu-manager=true"
- "cpu-manager-policy=static"
- "cpu-manager-policy-options=full-pcpus-only=true"
- "cpu-manager-reconcile-period=0s"
- "kubelet-reserved=cpu=1"
- "system-reserved=cpu=1"
  • KubernetesでのCPUピニングの使用

kubeletで定義された静的ポリシーを使ってCPUピニング機能を使用する方法は、ワークロードに対して定義した要求と制限に応じて3つあります。

  1. BestEffort QoSクラス: CPUに対して要求または制限を定義していない場合、Podはシステムで使用できる最初のCPUでスケジュールされます。

    BestEffort QoSクラスを使用する例を次に示します。

    spec:
      containers:
      - name: nginx
        image: nginx
  2. Burstable QoSクラス: CPUに対して要求を定義し、その要求が制限と同じではない場合、またはCPUの要求がない場合。

    Burstable QoSクラスを使用する例を次に示します。

    spec:
      containers:
      - name: nginx
        image: nginx
        resources:
          limits:
            memory: "200Mi"
          requests:
            memory: "100Mi"

    または

    spec:
      containers:
      - name: nginx
        image: nginx
        resources:
          limits:
            memory: "200Mi"
            cpu: "2"
          requests:
            memory: "100Mi"
            cpu: "1"
  3. Guaranteed QoSクラス: CPUに対して要求を定義し、その要求が制限と同じである場合。

    Guaranteed QoSクラスを使用する例を次に示します。

    spec:
      containers:
        - name: nginx
          image: nginx
          resources:
            limits:
              memory: "200Mi"
              cpu: "2"
            requests:
              memory: "200Mi"
              cpu: "2"

30.9 NUMA対応のスケジューリング

Non-Uniform Memory AccessまたはNon-Uniform Memory Architecture (NUMA)は、SMP (マルチプロセッサ)アーキテクチャにおいて使用される物理メモリ設計であり、メモリアクセス時間がプロセッサからのメモリの相対的な位置によって異なります。NUMAでは、プロセッサは専用のローカルメモリに、非ローカルメモリ、つまり別のプロセッサにローカルなメモリや複数のプロセッサで共有されているメモリよりも高速にアクセスできます。

30.9.1 NUMAノードの特定

NUMAノードを特定するには、システムで次のコマンドを使用します。

$ lscpu | grep NUMA
NUMA node(s):                       1
NUMA node0 CPU(s):                  0-63
注記
注記

この例では、NUMAノードが1つだけあり、64個のCPUが表示されています。

NUMABIOSで有効にする必要があります。dmesgにブート時のNUMA初期化レコードがない場合、カーネルリングバッファ内のNUMA関連のメッセージが上書きされた可能性があります。

30.10 MetalLB

MetalLBは、ベアメタルKubernetesクラスタ用のロードバランサの実装であり、L2BGPなどの標準ルーティングプロトコルをアドバタイズプロトコルとして使用します。ベアメタル環境ではKubernetesサービスタイプLoadBalancerを使用する必要があるため、Kubernetesクラスタ内のサービスを外部に公開するために使用できるのは、ネットワークロードバランサです。

RKE2クラスタでMetalLBを有効にするには、次の手順を実行する必要があります。

  • 次のコマンドを使用してMetalLBをインストールします。

$ kubectl apply <<EOF -f
apiVersion: helm.cattle.io/v1
kind: HelmChart
metadata:
  name: metallb
  namespace: kube-system
spec:
  repo: https://metallb.github.io/metallb/
  chart: metallb
  targetNamespace: metallb-system
---
apiVersion: helm.cattle.io/v1
kind: HelmChart
metadata:
  name: endpoint-copier-operator
  namespace: kube-system
spec:
  repo: https://suse-edge.github.io/endpoint-copier-operator
  chart: endpoint-copier-operator
  targetNamespace: endpoint-copier-operator
EOF
  • IpAddressPoolおよびL2advertisementの設定を作成します。

apiVersion: metallb.io/v1beta1
kind: IPAddressPool
metadata:
  name: kubernetes-vip-ip-pool
  namespace: metallb-system
spec:
  addresses:
    - 10.168.200.98/32
  serviceAllocation:
    priority: 100
    namespaces:
      - default
---
apiVersion: metallb.io/v1beta1
kind: L2Advertisement
metadata:
  name: ip-pool-l2-adv
  namespace: metallb-system
spec:
  ipAddressPools:
    - kubernetes-vip-ip-pool
  • VIPを公開するためのエンドポイントサービスを作成します。

apiVersion: v1
kind: Service
metadata:
  name: kubernetes-vip
  namespace: default
spec:
  internalTrafficPolicy: Cluster
  ipFamilies:
  - IPv4
  ipFamilyPolicy: SingleStack
  ports:
  - name: rke2-api
    port: 9345
    protocol: TCP
    targetPort: 9345
  - name: k8s-api
    port: 6443
    protocol: TCP
    targetPort: 6443
  sessionAffinity: None
  type: LoadBalancer
  • VIPが作成され、MetalLBのPodが実行中であることを確認します。

$ kubectl get svc -n default
$ kubectl get pods -n default

30.11 プライベートレジストリ設定

Containerdをプライベートレジストリに接続するように設定し、そのプライベートレジストリを使用して各ノードにプライベートイメージをプルできます。

起動時に、RKE2は、registries.yamlファイルが/etc/rancher/rke2/に存在するかどうかを確認し、このファイルで定義されたレジストリを使用するようにcontainerdに指示します。プライベートレジストリを使用するには、このファイルを、レジストリを使用する各ノードにルートとして作成します。

プライベートレジストリを追加するには、ファイル/etc/rancher/rke2/registries.yamlを作成して次の内容を設定します。

mirrors:
  docker.io:
    endpoint:
      - "https://registry.example.com:5000"
configs:
  "registry.example.com:5000":
    auth:
      username: xxxxxx # this is the registry username
      password: xxxxxx # this is the registry password
    tls:
      cert_file:            # path to the cert file used to authenticate to the registry
      key_file:             # path to the key file for the certificate used to authenticate to the registry
      ca_file:              # path to the ca file used to verify the registry's certificate
      insecure_skip_verify: # may be set to true to skip verifying the registry's certificate

または、認証を使用しない場合は次のように設定します。

mirrors:
  docker.io:
    endpoint:
      - "https://registry.example.com:5000"
configs:
  "registry.example.com:5000":
    tls:
      cert_file:            # path to the cert file used to authenticate to the registry
      key_file:             # path to the key file for the certificate used to authenticate to the registry
      ca_file:              # path to the ca file used to verify the registry's certificate
      insecure_skip_verify: # may be set to true to skip verifying the registry's certificate

レジストリの変更を有効にするには、ノード上でRKE2を起動する前にこのファイルを設定するか、または設定した各ノードでRKE2を再起動します。

注記
注記

詳細については、「Containerd Registry Configuration | RKE2 (Containerdのレジストリ設定 | RKE2)」を確認してください。

31 完全に自動化されたダイレクトネットワークプロビジョニング

31.1 はじめに

ダイレクトネットワークプロビジョニングは、ダウンストリームクラスタのプロビジョニングを自動化できる機能です。この機能は、プロビジョニングするダウンストリームクラスタが多数あり、そのプロセスを自動化したい場合に便利です。

管理クラスタ(第29章 「管理クラスタの設定)は、次のコンポーネントのデプロイメントを自動化します。

  • SUSE Linux Enterprise Micro RT (OS)。ユースケースに応じて、ネットワーキング、ストレージ、ユーザ、カーネル引数などの設定をカスタマイズできます。

  • RKE2 (Kubernetesクラスタ)。デフォルトのCNIプラグインはCiliumです。ユースケースに応じて、特定のCNIプラグイン(Cilium+Multusなど)を使用できます。

  • Longhorn (ストレージソリューション)。

  • NeuVector (セキュリティソリューション)。

  • MetalLB。高可用性マルチノードクラスタのロードバランサとして使用できます。

注記
注記

SUSE Linux Enterprise Microの詳細については第7章 「SLE Microを、RKE2の詳細については第14章 「RKE2を、Longhornの詳細については第15章 「Longhornを、NeuVectorの詳細については第16章 「NeuVectorをそれぞれ参照してください。

以降のセクションでは、さまざまなダイレクトネットワークプロビジョニングワークフローと、プロビジョニングプロセスに追加できる機能について説明します。

31.2 接続シナリオのダウンストリームクラスタイメージの準備

Edge Image Builder (第9章 「Edge Image Builder)を使用して、ダウンストリームクラスタホスト上にプロビジョニングされる、変更されたSLEMicroベースイメージを準備します。

ほとんどの設定はEdge Image Builderを使用して行うことができますが、このガイドではダウンストリームクラスタをセットアップするために必要な最小限の設定について説明します。

31.2.1 接続シナリオの前提条件

31.2.2 接続シナリオのイメージの設定

Edge Image Builderを実行すると、そのホストからディレクトリがマウントされるため、ターゲットイメージの定義に使用する設定ファイルを保存するディレクトリ構造を作成する必要があります。

  • downstream-cluster-config.yamlはイメージ定義ファイルです。詳細については、第3章 「Edge Image Builderを使用したスタンドアロンクラスタを参照してください。

  • ダウンロードされたベースイメージはxzで圧縮されているので、unxzで展開し、base-imagesフォルダの下にコピー/移動する必要があります。

  • networkフォルダはオプションです。詳細については、31.2.2.4項 「高度なネットワーク設定のための追加スクリプト」を参照してください。

  • custom/scriptsディレクトリには、初回ブート時に実行するスクリプトが含まれます。現在、デプロイメントのOSルートパーティションのサイズを変更するには、01-fix-growfs.shスクリプトが必要です。

├── downstream-cluster-config.yaml
├── base-images/
│   └ SLE-Micro.x86_64-5.5.0-Default-RT-GM.raw
├── network/
|   └ configure-network.sh
└── custom/
    └ scripts/
        └ 01-fix-growfs.sh

31.2.2.1 ダウンストリームクラスタイメージ定義ファイル

downstream-cluster-config.yamlファイルは、ダウンストリームクラスタイメージの主要な設定ファイルです。次に、Metal3を介したデプロイメントの最小例を示します。

apiVersion: 1.0
image:
  imageType: RAW
  arch: x86_64
  baseImage: SLE-Micro.x86_64-5.5.0-Default-RT-GM.raw
  outputImageName: eibimage-slemicro55rt-telco.raw
operatingSystem:
  kernelArgs:
    - ignition.platform.id=openstack
    - net.ifnames=1
  systemd:
    disable:
      - rebootmgr
  users:
    - username: root
      encryptedPassword: ${ROOT_PASSWORD}
      sshKeys:
      - ${USERKEY1}

${ROOT_PASSWORD}はルートユーザの暗号化パスワードで、テスト/デバッグに役立ちます。このパスワードは、openssl passwd -6 PASSWORDコマンドで生成できます。

運用環境では、${USERKEY1}を実際のSSHキーに置き換えて、usersブロックに追加できるSSHキーを使用することをお勧めします。

注記
注記

net.ifnames=1は、Predictable Network Interface Namingを有効にします。

これはmetal3チャートのデフォルト設定と一致しますが、この設定は、設定されたチャートのpredictableNicNamesの値と一致する必要があります。

また、ignition.platform.id=openstackは必須であり、この引数がないと、Metal3の自動化フローでIgnitionによるSLEMicroの設定が失敗することにも注意してください。

31.2.2.2 Growfsスクリプト

現在、プロビジョニング後の初回ブート時にディスクサイズに合わせてファイルシステムを拡張するには、カスタムスクリプトcustom/scripts/01-fix-growfs.shが必要です。01-fix-growfs.shスクリプトには次の情報が含まれます。

#!/bin/bash
growfs() {
  mnt="$1"
  dev="$(findmnt --fstab --target ${mnt} --evaluate --real --output SOURCE --noheadings)"
  # /dev/sda3 -> /dev/sda, /dev/nvme0n1p3 -> /dev/nvme0n1
  parent_dev="/dev/$(lsblk --nodeps -rno PKNAME "${dev}")"
  # Last number in the device name: /dev/nvme0n1p42 -> 42
  partnum="$(echo "${dev}" | sed 's/^.*[^0-9]\([0-9]\+\)$/\1/')"
  ret=0
  growpart "$parent_dev" "$partnum" || ret=$?
  [ $ret -eq 0 ] || [ $ret -eq 1 ] || exit 1
  /usr/lib/systemd/systemd-growfs "$mnt"
}
growfs /
注記
注記

同じアプローチを使用して、プロビジョニングプロセス中に実行する独自のカスタムスクリプトを追加します。詳細については、第3章 「Edge Image Builderを使用したスタンドアロンクラスタを参照してください。

この回避策に関連するバグは、https://bugzilla.suse.com/show_bug.cgi?id=1217430です。

31.2.2.3 通信ワークロードの追加設定

dpdksr-iovFECなどの通信機能を有効にするには、次の例に示すように追加のパッケージが必要な場合があります。

apiVersion: 1.0
image:
  imageType: RAW
  arch: x86_64
  baseImage: SLE-Micro.x86_64-5.5.0-Default-RT-GM.raw
  outputImageName: eibimage-slemicro55rt-telco.raw
operatingSystem:
  kernelArgs:
    - ignition.platform.id=openstack
    - net.ifnames=1
  systemd:
    disable:
      - rebootmgr
  users:
    - username: root
      encryptedPassword: ${ROOT_PASSWORD}
      sshKeys:
      - ${user1Key1}
  packages:
    packageList:
      - jq
      - dpdk22
      - dpdk22-tools
      - libdpdk-23
      - pf-bb-config
    additionalRepos:
      - url: https://download.opensuse.org/repositories/isv:/SUSE:/Edge:/Telco/SLEMicro5.5/
    sccRegistrationCode: ${SCC_REGISTRATION_CODE}

ここで、${SCC_REGISTRATION_CODE}SUSE Customer Centerからコピーした登録コードです。また、パッケージリストには通信事業者プロファイル用の最小限のパッケージが含まれています。pf-bb-configパッケージを使用するには(FEC機能とドライバへのバインドを有効にするには)、additionalReposブロックを含めてSUSE Edge Telcoリポジトリを追加する必要があります。

31.2.2.4 高度なネットワーク設定のための追加スクリプト

31.6項 「高度なネットワーク設定」で説明されている静的IPや、より高度なネットワーキングシナリオを設定する必要がある場合、次の追加設定が必要です。

networkフォルダに、次のconfigure-network.shファイルを作成します。 このファイルは、初回ブート時に設定ドライブデータを使用し、NM Configuratorツールを使用してホストネットワーキングを設定します。

#!/bin/bash

set -eux

# Attempt to statically configure a NIC in the case where we find a network_data.json
# In a configuration drive

CONFIG_DRIVE=$(blkid --label config-2 || true)
if [ -z "${CONFIG_DRIVE}" ]; then
  echo "No config-2 device found, skipping network configuration"
  exit 0
fi

mount -o ro $CONFIG_DRIVE /mnt

NETWORK_DATA_FILE="/mnt/openstack/latest/network_data.json"

if [ ! -f "${NETWORK_DATA_FILE}" ]; then
  umount /mnt
  echo "No network_data.json found, skipping network configuration"
  exit 0
fi

DESIRED_HOSTNAME=$(cat /mnt/openstack/latest/meta_data.json | tr ',{}' '\n' | grep '\"metal3-name\"' | sed 's/.*\"metal3-name\": \"\(.*\)\"/\1/')

mkdir -p /tmp/nmc/{desired,generated}
cp ${NETWORK_DATA_FILE} /tmp/nmc/desired/${DESIRED_HOSTNAME}.yaml
umount /mnt

./nmc generate --config-dir /tmp/nmc/desired --output-dir /tmp/nmc/generated
./nmc apply --config-dir /tmp/nmc/generated

31.2.3 イメージの作成

これまでのセクションに従ってディレクトリ構造を準備したら、次のコマンドを実行してイメージを構築します。

podman run --rm --privileged -it -v $PWD:/eib \
 registry.suse.com/edge/edge-image-builder:1.0.2 \
 build --definition-file downstream-cluster-config.yaml

これにより、上記の定義に基づいてeibimage-slemicro55rt-telco.rawという名前の出力ISOイメージファイルが作成されます。

その後、この出力イメージをWebサーバ経由で利用できるようにする必要があります。その際、管理クラスタのドキュメントを使用して有効にしたメディアサーバコンテナ(注記)か、ローカルにアクセス可能な他のサーバのいずれかを使用します。以下の例では、このサーバをimagecache.local:8080と呼びます。

31.3 エアギャップシナリオ用のダウンストリームクラスタイメージの準備

Edge Image Builder (第9章 「Edge Image Builder)を使用して、ダウンストリームクラスタホスト上にプロビジョニングされる、変更されたSLEMicroベースイメージを準備します。

設定の多くはEdge Image Builderを使用して行うことができますが、このガイドではエアギャップシナリオ用のダウンストリームクラスタの設定に必要な最小限の設定について説明します。

31.3.1 エアギャップシナリオの前提条件

  • Edge Image Builderを実行するには、PodmanRancher Desktopなどのコンテナランタイムが必要です。

  • ゴールデンイメージSLE-Micro.x86_64-5.5.0-Default-RT-GM.rawSUSE Customer CenterまたはSUSEダウンロードページからダウンロードする必要があります。

  • コンテナイメージが必要なSR-IOVなどのワークロードを使用する場合、ローカルのプライベートレジストリをデプロイして設定済みである必要があります(TLSまたは認証、あるいはその両方を使用/不使用)。このレジストリを使用して、イメージとHelmチャートOCIイメージを保存します。

31.3.2 エアギャップシナリオのイメージの設定

Edge Image Builderを実行すると、そのホストからディレクトリがマウントされるため、ターゲットイメージの定義に使用する設定ファイルを保存するディレクトリ構造を作成する必要があります。

  • downstream-cluster-airgap-config.yamlはイメージ定義ファイルです。詳細については、第3章 「Edge Image Builderを使用したスタンドアロンクラスタを参照してください。

  • ダウンロードされたベースイメージはxzで圧縮されているので、unxzで展開し、base-imagesフォルダの下にコピー/移動する必要があります。

  • networkフォルダはオプションです。詳細については、31.2.2.4項 「高度なネットワーク設定のための追加スクリプト」を参照してください。

  • custom/scriptsディレクトリには、初回ブート時に実行するスクリプトが含まれています。現在は、デプロイメントのOSルートパーティションのサイズを変更するために、スクリプト01-fix-growfs.shが必要です。エアギャップシナリオでは、イメージ作成プロセス中にイメージを正しい場所にコピーするために、スクリプト02-airgap.shが必要です。

  • custom/filesディレクトリには、イメージ作成プロセス中にそのイメージにコピーするrke2イメージとcniイメージが含まれています。

├── downstream-cluster-airgap-config.yaml
├── base-images/
│   └ SLE-Micro.x86_64-5.5.0-Default-RT-GM.raw
├── network/
|   └ configure-network.sh
└── custom/
    └ files/
    |   └ install.sh
    |   └ rke2-images-cilium.linux-amd64.tar.zst
    |   └ rke2-images-core.linux-amd64.tar.zst
    |   └ rke2-images-multus.linux-amd64.tar.zst
    |   └ rke2-images.linux-amd64.tar.zst
    |   └ rke2.linux-amd64.tar.zst
    |   └ sha256sum-amd64.txt
    └ scripts/
        └ 01-fix-growfs.sh
        └ 02-airgap.sh

31.3.2.1 ダウンストリームクラスタイメージ定義ファイル

downstream-cluster-airgap-config.yamlファイルは、ダウンストリームクラスタ用のメイン設定ファイルです。その内容については、前のセクション(31.2.2.3項 「通信ワークロードの追加設定」)で説明されています。

31.3.2.2 Growfsスクリプト

現在、プロビジョニング後の初回ブート時にディスクサイズに合わせてファイルシステムを拡張するには、カスタムスクリプトcustom/scripts/01-fix-growfs.shが必要です。01-fix-growfs.shスクリプトには次の情報が含まれます。

#!/bin/bash
growfs() {
  mnt="$1"
  dev="$(findmnt --fstab --target ${mnt} --evaluate --real --output SOURCE --noheadings)"
  # /dev/sda3 -> /dev/sda, /dev/nvme0n1p3 -> /dev/nvme0n1
  parent_dev="/dev/$(lsblk --nodeps -rno PKNAME "${dev}")"
  # Last number in the device name: /dev/nvme0n1p42 -> 42
  partnum="$(echo "${dev}" | sed 's/^.*[^0-9]\([0-9]\+\)$/\1/')"
  ret=0
  growpart "$parent_dev" "$partnum" || ret=$?
  [ $ret -eq 0 ] || [ $ret -eq 1 ] || exit 1
  /usr/lib/systemd/systemd-growfs "$mnt"
}
growfs /

31.3.2.3 エアギャップスクリプト

イメージ作成プロセス中にイメージを正しい場所にコピーするために、次のスクリプトcustom/scripts/02-airgap.shが必要です。

#!/bin/bash

# create the folder to extract the artifacts there
mkdir -p /opt/rke2-artifacts
mkdir -p /var/lib/rancher/rke2/agent/images

# copy the artifacts
cp install.sh /opt/
cp rke2-images*.tar.zst rke2.linux-amd64.tar.gz sha256sum-amd64.txt /opt/rke2-artifacts/

31.3.2.4 エアギャップシナリオのカスタムファイル

custom/filesディレクトリには、イメージ作成プロセス中にそのイメージにコピーするrke2イメージとcniイメージが含まれています。イメージを簡単に生成するには、次のスクリプトと、こちらにあるイメージのリストを使用してローカルでイメージを準備し、custom/filesに含める必要があるアーティファクトを生成します。また、最新のrke2-installスクリプトをこちらからダウンロードすることもできます。

$ ./edge-save-rke2-images.sh -o custom/files -l ~/edge-release-rke2-images.txt

イメージをダウンロードした後、ディレクトリ構造は次のようになるはずです。

└── custom/
    └ files/
        └ install.sh
        └ rke2-images-cilium.linux-amd64.tar.zst
        └ rke2-images-core.linux-amd64.tar.zst
        └ rke2-images-multus.linux-amd64.tar.zst
        └ rke2-images.linux-amd64.tar.zst
        └ rke2.linux-amd64.tar.zst
        └ sha256sum-amd64.txt

31.3.2.5 エアギャップシナリオおよびSR-IOV (オプション)に必要なイメージのプライベートレジストリへのプリロード

エアギャップシナリオまたはその他のワークロードイメージでSR-IOVを使用する場合、次の各手順に従って、ローカルのプライベートレジストリにイメージをプリロードする必要があります。

  • HelmチャートOCIイメージをダウンロードして抽出し、プライベートレジストリにプッシュする

  • 必要な残りのイメージをダウンロードして抽出し、プライベートレジストリにプッシュする

次のスクリプトを使用して、イメージをダウンロードして抽出し、プライベートレジストリにプッシュできます。これからSR-IOVイメージをプリロードする例を示しますが、その他のカスタムイメージも同じ方法でプリロードすることができます。

  1. SR-IOVのHelmチャートOCIイメージのプリロード:

    1. 必要なHelmチャートOCIイメージが含まれるリストを作成する必要があります。

      $ cat > edge-release-helm-oci-artifacts.txt <<EOF
      edge/sriov-network-operator-chart:1.2.2
      edge/sriov-crd-chart:1.2.2
      EOF
    2. 次のスクリプトと前の手順で作成したリストを使用して、ローカルのtarballファイルを生成します。

      $ ./edge-save-oci-artefacts.sh -al ./edge-release-helm-oci-artifacts.txt -s registry.suse.com
      Pulled: registry.suse.com/edge/sriov-network-operator-chart:1.2.2
      Pulled: registry.suse.com/edge/sriov-crd-chart:1.2.2
      a edge-release-oci-tgz-20240705
      a edge-release-oci-tgz-20240705/sriov-network-operator-chart-1.2.2.tgz
      a edge-release-oci-tgz-20240705/sriov-crd-chart-1.2.2.tgz
    3. 次のスクリプトを使用してtarballファイルをプライベートレジストリ(例: myregistry:5000)にアップロードし、前の手順でダウンロードしたHelmチャートOCIイメージをレジストリにプリロードします。

      $ tar zxvf edge-release-oci-tgz-20240705.tgz
      $ ./edge-load-oci-artefacts.sh -ad edge-release-oci-tgz-20240705 -r myregistry:5000
  2. SR-IOVに必要な残りのイメージをプリロードします。

    1. ここでは、通信ワークロードのために「sr-iov」コンテナイメージを含める必要があります(例: 参考として、これはhelmチャート値から取得できます)。

      $ cat > edge-release-images.txt <<EOF
      rancher/hardened-sriov-network-operator:v1.2.0-build20240327
      rancher/rancher/hardened-sriov-network-config-daemon:v1.2.0-build20240327
      rancher/hardened-sriov-cni:v1.2.0-build20240327
      rancher/hardened-ib-sriov-cni:v1.2.0-build20240327
      rancher/hardened-sriov-network-device-plugin:v1.2.0-build20240327
      rancher/hardened-sriov-network-resources-injector:v1.2.0-build20240327
      rancher/hardened-sriov-network-webhook:v1.2.0-build20240327
      EOF
    2. 次のスクリプトと前の手順で作成したリストを使用し、必要なイメージが含まれるtarballファイルをローカルで生成する必要があります。

      $ ./edge-save-images.sh -al ./edge-release-images.txt -s registry.suse.com
      Pulled: registry.suse.com/rancher/hardened-sriov-network-operator:v1.2.0-build20240327
      Pulled: registry.suse.com/rancher/rancher/hardened-sriov-network-config-daemon:v1.2.0-build20240327
      Pulled: registry.suse.com/rancher/hardened-sriov-cni:v1.2.0-build20240327
      Pulled: registry.suse.com/rancher/hardened-ib-sriov-cni:v1.2.0-build20240327
      Pulled: registry.suse.com/rancher/hardened-sriov-network-device-plugin:v1.2.0-build20240327
      Pulled: registry.suse.com/rancher/hardened-sriov-network-resources-injector:v1.2.0-build20240327
      Pulled: registry.suse.com/rancher/hardened-sriov-network-webhook:v1.2.0-build20240327
      a edge-release-images-tgz-20240705
      a edge-release-images-tgz-20240705/hardened-sriov-network-operator-v1.2.0-build20240327.tar.gz
      a edge-release-images-tgz-20240705/hardened-sriov-network-config-daemon-v1.2.0-build20240327.tar.gz
      a edge-release-images-tgz-20240705/hardened-sriov-cni-v1.2.0-build20240327.tar.gz
      a edge-release-images-tgz-20240705/hardened-ib-sriov-cni-v1.2.0-build20240327.tar.gz
      a edge-release-images-tgz-20240705/hardened-sriov-network-device-plugin-v1.2.0-build20240327.tar.gz
      a edge-release-images-tgz-20240705/hardened-sriov-network-resources-injector-v1.2.0-build20240327.tar.gz
      a edge-release-images-tgz-20240705/hardened-sriov-network-webhook-v1.2.0-build20240327.tar.gz
    3. 次のスクリプトを使用してtarballファイルをプライベートレジストリ(例: myregistry:5000)にアップロードし、前の手順でダウンロードしたイメージをプライベートレジストリにプリロードします。

      $ tar zxvf edge-release-images-tgz-20240705.tgz
      $ ./edge-load-images.sh -ad edge-release-images-tgz-20240705 -r myregistry:5000

31.3.3 エアギャップシナリオのイメージの作成

これまでのセクションに従ってディレクトリ構造を準備したら、次のコマンドを実行してイメージを構築します。

podman run --rm --privileged -it -v $PWD:/eib \
 registry.suse.com/edge/edge-image-builder:1.0.2 \
 build --definition-file downstream-cluster-airgap-config.yaml

これにより、上記の定義に基づいてeibimage-slemicro55rt-telco.rawという名前の出力ISOイメージファイルが作成されます。

その後、この出力イメージをWebサーバ経由で利用できるようにする必要があります。その際、管理クラスタドキュメントを使用して有効にしたメディアサーバコンテナ(注記)か、ローカルにアクセス可能な他のサーバのいずれかを使用します。以下の例では、このサーバをimagecache.local:8080として参照します。

31.4 ダイレクトネットワークプロビジョニングを使用したダウンストリームクラスタのプロビジョニング(シングルノード)

このセクションでは、ダイレクトネットワークプロビジョニングを使用してシングルノードのダウンストリームクラスタのプロビジョニングを自動化するために用いるワークフローについて説明します。これは、ダウンストリームクラスタのプロビジョニングを自動化する最もシンプルな方法です。

要件

ワークフロー

次の図は、ダイレクトネットワークプロビジョニングを使用してシングルノードのダウンストリームクラスタのプロビジョニングを自動化するために用いるワークフローを示しています。

atip自動化シングルノード1

ダイレクトネットワークプロビジョニングを使用してシングルノードのダウンストリームクラスタのプロビジョニングを自動化する手順は2種類です。

  1. ベアメタルホストを登録して、プロビジョニングプロセスで使用できるようにする。

  2. ベアメタルホストをプロビジョニングして、オペレーティングシステムとKubernetesクラスタをインストールして設定する。

ベアメタルホストの登録

最初の手順では、新しいベアメタルホストを管理クラスタに登録してプロビジョニングできるようにします。そのためには、次のファイル(bmh-example.yaml)を管理クラスタ内に作成して、使用するBMC資格情報と登録するBaremetalHostオブジェクトを指定する必要があります。

apiVersion: v1
kind: Secret
metadata:
  name: example-demo-credentials
type: Opaque
data:
  username: ${BMC_USERNAME}
  password: ${BMC_PASSWORD}
---
apiVersion: metal3.io/v1alpha1
kind: BareMetalHost
metadata:
  name: flexran-demo
  labels:
    cluster-role: control-plane
spec:
  online: true
  bootMACAddress: ${BMC_MAC}
  rootDeviceHints:
    deviceName: /dev/nvme0n1
  bmc:
    address: ${BMC_ADDRESS}
    disableCertificateVerification: true
    credentialsName: example-demo-credentials

各項目の内容は次のとおりです。

  • ${BMC_USERNAME} — 新しいベアメタルホストのBMCのユーザ名。

  • ${BMC_PASSWORD} — 新しいベアメタルホストのBMCのパスワード。

  • ${BMC_MAC} — 使用する新しいベアメタルホストのMACアドレス。

  • ${BMC_ADDRESS} — ベアメタルホストのBMCURL (例: redfish-virtualmedia://192.168.200.75/redfish/v1/Systems/1/)。ハードウェアプロバイダに応じて使用できる各種のオプションの詳細については、こちらのリンクを確認してください。

ファイルを作成したら、管理クラスタで次のコマンドを実行し、管理クラスタで新しいベアメタルホストの登録を開始する必要があります。

$ kubectl apply -f bmh-example.yaml

新しいベアメタルホストオブジェクトが登録され、その状態が「Registering (登録中)」から「Inspecting (検査中)」に変わり、「Available (使用可能)」になります。この変更は次のコマンドを使用して確認できます。

$ kubectl get bmh
注記
注記

BaremetalHostオブジェクトは、BMCの資格情報が検証されるまでは「Registering (登録中)」の状態です。資格情報の検証が完了すると、BaremetalHostオブジェクトの状態が「Inspecting (検査中)」に変わります。この手順はハードウェアによっては多少時間がかかる可能性があります(最大で20分)。「Inspecting (検査中)」のフェーズ中に、ハードウェア情報が取得されてKubernetesオブジェクトが更新されます。kubectl get bmh -o yamlコマンドを使用して情報を確認してください。

プロビジョニング手順

ベアメタルホストが登録されて使用可能になったら、次に、ベアメタルホストをプロビジョニングしてオペレーティングシステムとKubernetesクラスタをインストールして設定します。そのためには、次の情報を使用して管理クラスタで以下のファイルcapi-provisioning-example.yamlを作成する必要があります(capi-provisioning-example.yamlは、以下のブロックを結合して生成できます)。

注記
注記

実際の値に置き換える必要があるのは、$\{…​\}の中の値だけです。

次のブロックはクラスタ定義です。ここで、podsブロックとservicesブロックを使用してネットワーキングを設定できます。また、ここにはコントロールプレーンオブジェクトと、使用するインフラストラクチャ(Metal3プロバイダを使用)オブジェクトへの参照も含まれています。

apiVersion: cluster.x-k8s.io/v1beta1
kind: Cluster
metadata:
  name: single-node-cluster
  namespace: default
spec:
  clusterNetwork:
    pods:
      cidrBlocks:
        - 192.168.0.0/18
    services:
      cidrBlocks:
        - 10.96.0.0/12
  controlPlaneRef:
    apiVersion: controlplane.cluster.x-k8s.io/v1alpha1
    kind: RKE2ControlPlane
    name: single-node-cluster
  infrastructureRef:
    apiVersion: infrastructure.cluster.x-k8s.io/v1beta1
    kind: Metal3Cluster
    name: single-node-cluster

Metal3Clusterオブジェクトには、設定するコントロールプレーンのエンドポイント(${DOWNSTREAM_CONTROL_PLANE_IP}を置き換える)と、noCloudProvider(ベアメタルノードを使用しているため)を指定します。

apiVersion: infrastructure.cluster.x-k8s.io/v1beta1
kind: Metal3Cluster
metadata:
  name: single-node-cluster
  namespace: default
spec:
  controlPlaneEndpoint:
    host: ${DOWNSTREAM_CONTROL_PLANE_IP}
    port: 6443
  noCloudProvider: true

RKE2ControlPlaneオブジェクトには、使用するコントロールプレーンの設定を指定し、Metal3MachineTemplateオブジェクトには、使用するコントロールプレーンのイメージを指定します。また、ここには使用するレプリカの数(ここでは1)と、使用するCNIプラグイン(ここではCilium)に関する情報が含まれています。agentConfigブロックには、使用するIgnitionの形式と、使用するadditionalUserDataが含まれます。これを使用して、RKE2ノードにrke2-preinstall.serviceという名前のsystemdサービスを設定し、プロビジョニングプロセス中にIronicの情報を使用してBAREMETALHOST_UUIDnode-nameを自動的に置き換えます。最後の情報ブロックには、使用するKubernetesバージョンが含まれています。${RKE2_VERSION}は使用するRKE2のバージョンであり、この値は置き換えます(例: v1.28.9+rke2r1)。

apiVersion: controlplane.cluster.x-k8s.io/v1alpha1
kind: RKE2ControlPlane
metadata:
  name: single-node-cluster
  namespace: default
spec:
  infrastructureRef:
    apiVersion: infrastructure.cluster.x-k8s.io/v1beta1
    kind: Metal3MachineTemplate
    name: single-node-cluster-controlplane
  replicas: 1
  serverConfig:
    cni: cilium
  agentConfig:
    format: ignition
    additionalUserData:
      config: |
        variant: fcos
        version: 1.4.0
        systemd:
          units:
            - name: rke2-preinstall.service
              enabled: true
              contents: |
                [Unit]
                Description=rke2-preinstall
                Wants=network-online.target
                Before=rke2-install.service
                ConditionPathExists=!/run/cluster-api/bootstrap-success.complete
                [Service]
                Type=oneshot
                User=root
                ExecStartPre=/bin/sh -c "mount -L config-2 /mnt"
                ExecStart=/bin/sh -c "sed -i \"s/BAREMETALHOST_UUID/$(jq -r .uuid /mnt/openstack/latest/meta_data.json)/\" /etc/rancher/rke2/config.yaml"
                ExecStart=/bin/sh -c "echo \"node-name: $(jq -r .name /mnt/openstack/latest/meta_data.json)\" >> /etc/rancher/rke2/config.yaml"
                ExecStartPost=/bin/sh -c "umount /mnt"
                [Install]
                WantedBy=multi-user.target
    kubelet:
      extraArgs:
        - provider-id=metal3://BAREMETALHOST_UUID
    version: ${RKE2_VERSION}
    nodeName: "localhost.localdomain"

Metal3MachineTemplateオブジェクトには次の情報を指定します。

apiVersion: infrastructure.cluster.x-k8s.io/v1beta1
kind: Metal3MachineTemplate
metadata:
  name: single-node-cluster-controlplane
  namespace: default
spec:
  template:
    spec:
      dataTemplate:
        name: single-node-cluster-controlplane-template
      hostSelector:
        matchLabels:
          cluster-role: control-plane
      image:
        checksum: http://imagecache.local:8080/eibimage-slemicro55rt-telco.raw.sha256
        checksumType: sha256
        format: raw
        url: http://imagecache.local:8080/eibimage-slemicro55rt-telco.raw

Metal3DataTemplateオブジェクトには、ダウンストリームクラスタのmetaDataを指定します。

apiVersion: infrastructure.cluster.x-k8s.io/v1beta1
kind: Metal3DataTemplate
metadata:
  name: single-node-cluster-controlplane-template
  namespace: default
spec:
  clusterName: single-node-cluster
  metaData:
    objectNames:
      - key: name
        object: machine
      - key: local-hostname
        object: machine
      - key: local_hostname
        object: machine

前のブロックを結合してファイルを作成したら、管理クラスタで次のコマンドを実行して、新しいベアメタルホストのプロビジョニングを開始する必要があります。

$ kubectl apply -f capi-provisioning-example.yaml

31.5 ダイレクトネットワークプロビジョニングを使用したダウンストリームクラスタのプロビジョニング(マルチノード)

このセクションでは、ダイレクトネットワークプロビジョニングとMetalLBをロードバランサ戦略として使用して、マルチノードのダウンストリームクラスタのプロビジョニングを自動化するために使用するワークフローについて説明します。これはダウンストリームクラスタのプロビジョニングを自動化する最もシンプルな方法です。次の図は、ダイレクトネットワークプロビジョニングとMetalLBを使用してマルチノードのダウンストリームクラスタのプロビジョニングを自動化するためのワークフローを示しています。

要件

ワークフロー

次の図は、ダイレクトネットワークプロビジョニングを使用してマルチノードのダウンストリームクラスタのプロビジョニングを自動化するために使用するワークフローを示しています。

atip自動化マルチノード1
  1. 3つのベアメタルホストを登録し、プロビジョニングプロセスで使用できるようにする。

  2. 3つのベアメタルホストをプロビジョニングし、オペレーティングシステムと、MetalLBを使用するKubernetesクラスタをインストールして設定する。

ベアメタルホストの登録

最初の手順では、管理クラスタに3つのベアメタルホストを登録してプロビジョニングできるようにします。そのためには、管理クラスタにファイルbmh-example-node1.yamlbmh-example-node2.yaml、およびbmh-example-node3.yamlを作成して、使用するBMC資格情報と、管理クラスタに登録するBaremetalHostオブジェクトを指定する必要があります。

注記
注記
  • 実際の値に置き換える必要があるのは、$\{…​\}の中の値だけです。

  • 1つのホストのプロセスについてのみ説明します。他の2つのノードにも同じ手順が適用されます。

apiVersion: v1
kind: Secret
metadata:
  name: node1-example-credentials
type: Opaque
data:
  username: ${BMC_NODE1_USERNAME}
  password: ${BMC_NODE1_PASSWORD}
---
apiVersion: metal3.io/v1alpha1
kind: BareMetalHost
metadata:
  name: node1-example
  labels:
    cluster-role: control-plane
spec:
  online: true
  bootMACAddress: ${BMC_NODE1_MAC}
  bmc:
    address: ${BMC_NODE1_ADDRESS}
    disableCertificateVerification: true
    credentialsName: node1-example-credentials

各項目の内容は次のとおりです。

  • ${BMC_NODE1_USERNAME} — 最初のベアメタルホストのBMCのユーザ名。

  • ${BMC_NODE1_PASSWORD} — 最初のベアメタルホストのBMCのパスワード。

  • ${BMC_NODE1_MAC} — 使用する最初のベアメタルホストのMACアドレス。

  • ${BMC_NODE1_ADDRESS} — 最初のベアメタルホストのBMCのURL (例: redfish-virtualmedia://192.168.200.75/redfish/v1/Systems/1/)。ハードウェアプロバイダに応じて使用できる各種のオプションの詳細については、こちらのリンクを確認してください。

ファイルを作成したら、管理クラスタで次のコマンドを実行して、管理クラスタへのベアメタルホストの登録を開始する必要があります。

$ kubectl apply -f bmh-example-node1.yaml
$ kubectl apply -f bmh-example-node2.yaml
$ kubectl apply -f bmh-example-node3.yaml

新しいベアメタルホストオブジェクトが登録され、その状態が「Registering (登録中)」から「Inspecting (検査中)」に変わり、「Available (使用可能)」になります。この変更は次のコマンドを使用して確認できます。

$ kubectl get bmh -o wide
注記
注記

BaremetalHostオブジェクトは、BMCの資格情報が検証されるまでは「Registering (登録中)」の状態です。資格情報の検証が完了すると、BaremetalHostオブジェクトの状態が「Inspecting (検査中)」に変わります。この手順はハードウェアによっては多少時間がかかる可能性があります(最大で20分)。「Inspecting (検査中)」のフェーズ中に、ハードウェア情報が取得されてKubernetesオブジェクトが更新されます。kubectl get bmh -o yamlコマンドを使用して情報を確認してください。

プロビジョニング手順

3つのベアメタルホストが登録されて使用可能になったら、次の手順は、ベアメタルホストをプロビジョニングしてオペレーティングシステムとKubernetesクラスタをインストールして設定し、ロードバランサを作成して3つのベアメタルホストを管理することです。そのためには、次の情報を使用して管理クラスタにファイルcapi-provisioning-example.yamlを作成する必要があります(capi-provisioning-example.yamlは、次のブロックを結合して生成できます)。

注記
注記
  • 実際の値に置き換える必要があるのは、$\{…​\}の中の値だけです。

  • VIPアドレスは、どのノードにも割り当てられていない予約済みのIPアドレスであり、ロードバランサを設定するために使用されます。

以下はクラスタ定義です。ここで、podsブロックとservicesブロックを使用してクラスタのネットワークを設定できます。また、ここにはコントロールプレーンと、使用するインフラストラクチャ(Metal3プロバイダを使用)のオブジェクトへの参照も含まれています。

apiVersion: cluster.x-k8s.io/v1beta1
kind: Cluster
metadata:
  name: multinode-cluster
  namespace: default
spec:
  clusterNetwork:
    pods:
      cidrBlocks:
        - 192.168.0.0/18
    services:
      cidrBlocks:
        - 10.96.0.0/12
  controlPlaneRef:
    apiVersion: controlplane.cluster.x-k8s.io/v1alpha1
    kind: RKE2ControlPlane
    name: multinode-cluster
  infrastructureRef:
    apiVersion: infrastructure.cluster.x-k8s.io/v1beta1
    kind: Metal3Cluster
    name: multinode-cluster

Metal3Clusterオブジェクトには、予約済みのVIPアドレス(${DOWNSTREAM_VIP_ADDRESS}を置き換え)を使用して設定するコントロールプレーンのエンドポイントと、noCloudProvider (3つのベアメタルノードを使用しているため)を指定しています。

apiVersion: infrastructure.cluster.x-k8s.io/v1beta1
kind: Metal3Cluster
metadata:
  name: multinode-cluster
  namespace: default
spec:
  controlPlaneEndpoint:
    host: ${EDGE_VIP_ADDRESS}
    port: 6443
  noCloudProvider: true

RKE2ControlPlaneオブジェクトには、使用するコントロールプレーンの設定を指定し、Metal3MachineTemplateオブジェクトには、使用するコントロールプレーンのイメージを指定します。

  • 使用するレプリカの数(ここでは3)。

  • ロードバランサで使用するアドバタイズモード(addressではL2実装を使用)、および使用するアドレス(${EDGE_VIP_ADDRESS}VIPアドレスに置き換え)。

  • 使用するCNIプラグイン(ここではCilium)と、VIPアドレスの設定に使用するtlsSanが含まれるserverConfig

  • agentConfigブロックには、使用するIgnitionの形式と、RKE2ノードに次のような情報を設定するために使用するadditionalUserDataが含まれています。

    • プロビジョニングプロセス中にIronicの情報を使用してBAREMETALHOST_UUIDnode-nameを自動的に置き換える、rke2-preinstall.serviceという名前のsystemdサービス。

    • MetalLBendpoint-copier-operatorのインストールに使用するHelmチャートが含まれているstorageブロック。

    • 使用するIPaddressPoolL2Advertisementが含まれているmetalLBカスタムリソースファイル(${EDGE_VIP_ADDRESS}VIPアドレスに置き換え)。

    • MetalLBVIPアドレスを管理するために使用するkubernetes-vipサービスの設定に使用するendpoint-svc.yamlファイル。

  • 最後の情報ブロックには、使用するKubernetesバージョンが含まれています。${RKE2_VERSION}は、使用するRKE2のバージョンであり、この値は置き換えます(例: v1.28.9+rke2r1)。

apiVersion: controlplane.cluster.x-k8s.io/v1alpha1
kind: RKE2ControlPlane
metadata:
  name: multinode-cluster
  namespace: default
spec:
  infrastructureRef:
    apiVersion: infrastructure.cluster.x-k8s.io/v1beta1
    kind: Metal3MachineTemplate
    name: multinode-cluster-controlplane
  replicas: 3
  registrationMethod: "address"
  registrationAddress: ${EDGE_VIP_ADDRESS}
  serverConfig:
    cni: cilium
    tlsSan:
      - ${EDGE_VIP_ADDRESS}
      - https://${EDGE_VIP_ADDRESS}.sslip.io
  agentConfig:
    format: ignition
    additionalUserData:
      config: |
        variant: fcos
        version: 1.4.0
        systemd:
          units:
            - name: rke2-preinstall.service
              enabled: true
              contents: |
                [Unit]
                Description=rke2-preinstall
                Wants=network-online.target
                Before=rke2-install.service
                ConditionPathExists=!/run/cluster-api/bootstrap-success.complete
                [Service]
                Type=oneshot
                User=root
                ExecStartPre=/bin/sh -c "mount -L config-2 /mnt"
                ExecStart=/bin/sh -c "sed -i \"s/BAREMETALHOST_UUID/$(jq -r .uuid /mnt/openstack/latest/meta_data.json)/\" /etc/rancher/rke2/config.yaml"
                ExecStart=/bin/sh -c "echo \"node-name: $(jq -r .name /mnt/openstack/latest/meta_data.json)\" >> /etc/rancher/rke2/config.yaml"
                ExecStartPost=/bin/sh -c "umount /mnt"
                [Install]
                WantedBy=multi-user.target
        storage:
          files:
            - path: /var/lib/rancher/rke2/server/manifests/endpoint-copier-operator.yaml
              overwrite: true
              contents:
                inline: |
                  apiVersion: helm.cattle.io/v1
                  kind: HelmChart
                  metadata:
                    name: endpoint-copier-operator
                    namespace: kube-system
                  spec:
                    chart: oci://registry.suse.com/edge/endpoint-copier-operator-chart
                    targetNamespace: endpoint-copier-operator
                    version: 0.2.0
                    createNamespace: true
            - path: /var/lib/rancher/rke2/server/manifests/metallb.yaml
              overwrite: true
              contents:
                inline: |
                  apiVersion: helm.cattle.io/v1
                  kind: HelmChart
                  metadata:
                    name: metallb
                    namespace: kube-system
                  spec:
                    chart: oci://registry.suse.com/edge/metallb-chart
                    targetNamespace: metallb-system
                    version: 0.14.3
                    createNamespace: true

            - path: /var/lib/rancher/rke2/server/manifests/metallb-cr.yaml
              overwrite: true
              contents:
                inline: |
                  apiVersion: metallb.io/v1beta1
                  kind: IPAddressPool
                  metadata:
                    name: kubernetes-vip-ip-pool
                    namespace: metallb-system
                  spec:
                    addresses:
                      - ${EDGE_VIP_ADDRESS}/32
                    serviceAllocation:
                      priority: 100
                      namespaces:
                        - default
                      serviceSelectors:
                        - matchExpressions:
                          - {key: "serviceType", operator: In, values: [kubernetes-vip]}
                  ---
                  apiVersion: metallb.io/v1beta1
                  kind: L2Advertisement
                  metadata:
                    name: ip-pool-l2-adv
                    namespace: metallb-system
                  spec:
                    ipAddressPools:
                      - kubernetes-vip-ip-pool
            - path: /var/lib/rancher/rke2/server/manifests/endpoint-svc.yaml
              overwrite: true
              contents:
                inline: |
                  apiVersion: v1
                  kind: Service
                  metadata:
                    name: kubernetes-vip
                    namespace: default
                    labels:
                      serviceType: kubernetes-vip
                  spec:
                    ports:
                    - name: rke2-api
                      port: 9345
                      protocol: TCP
                      targetPort: 9345
                    - name: k8s-api
                      port: 6443
                      protocol: TCP
                      targetPort: 6443
                    type: LoadBalancer
    kubelet:
      extraArgs:
        - provider-id=metal3://BAREMETALHOST_UUID
    version: ${RKE2_VERSION}
    nodeName: "Node-multinode-cluster"

Metal3MachineTemplateオブジェクトには次の情報を指定します。

apiVersion: infrastructure.cluster.x-k8s.io/v1beta1
kind: Metal3MachineTemplate
metadata:
  name: multinode-cluster-controlplane
  namespace: default
spec:
  template:
    spec:
      dataTemplate:
        name: multinode-cluster-controlplane-template
      hostSelector:
        matchLabels:
          cluster-role: control-plane
      image:
        checksum: http://imagecache.local:8080/eibimage-slemicro55rt-telco.raw.sha256
        checksumType: sha256
        format: raw
        url: http://imagecache.local:8080/eibimage-slemicro55rt-telco.raw

Metal3DataTemplateオブジェクトには、ダウンストリームクラスタのmetaDataを指定します。

apiVersion: infrastructure.cluster.x-k8s.io/v1beta1
kind: Metal3DataTemplate
metadata:
  name: single-node-cluster-controlplane-template
  namespace: default
spec:
  clusterName: single-node-cluster
  metaData:
    objectNames:
      - key: name
        object: machine
      - key: local-hostname
        object: machine
      - key: local_hostname
        object: machine

前のブロックを結合してファイルを作成したら、管理クラスタで次のコマンドを実行して、新しい3つのベアメタルホストのプロビジョニングを開始する必要があります。

$ kubectl apply -f capi-provisioning-example.yaml

31.6 高度なネットワーク設定

ダイレクトネットワークプロビジョニングのワークフローでは、静的IP、ボンディング、VLANなどのダウンストリームクラスタのネットワーク設定を行うことができます。

次の各セクションでは、高度なネットワーク設定を使用してダウンストリームクラスタをプロビジョニングできるようにするために必要な追加手順について説明します。

要件

設定

次の2つのセクションをベースとして使用し、ホストを登録してプロビジョニングします。

高度なネットワーク設定を有効にするために必要な変更は次のとおりです。

  • 登録手順: 設定に使用するnetworkDataに関する情報(例: ダウンストリームクラスタの静的IPVLAN)を格納したシークレットが含まれる新しいサンプルファイル

apiVersion: v1
kind: Secret
metadata:
  name: controlplane-0-networkdata
type: Opaque
stringData:
  networkData: |
    interfaces:
    - name: ${CONTROLPLANE_INTERFACE}
      type: ethernet
      state: up
      mtu: 1500
      mac-address: "${CONTROLPLANE_MAC}"
      ipv4:
        address:
        - ip:  "${CONTROLPLANE_IP}"
          prefix-length: "${CONTROLPLANE_PREFIX}"
        enabled: true
        dhcp: false
    - name: floating
      type: vlan
      state: up
      vlan:
        base-iface: ${CONTROLPLANE_INTERFACE}
        id: ${VLAN_ID}
    dns-resolver:
      config:
        server:
        - "${DNS_SERVER}"
    routes:
      config:
      - destination: 0.0.0.0/0
        next-hop-address: "${CONTROLPLANE_GATEWAY}"
        next-hop-interface: ${CONTROLPLANE_INTERFACE}

このファイルには、ダウンストリームクラスタに高度なネットワーク設定(例: 静的IPVLAN)を行う場合に使用するnmstate形式のnetworkDataが含まれています。ご覧のとおり、この例は、静的IPを使用してインタフェースを有効にするための設定と、ベースインタフェースを使用してVLANを有効にするための設定を示しています。その他のnmstateの例を定義して、ダウンストリームクラスタのネットワークを特定の要件に適合するように設定できます。ここでは、次の変数を実際の値に置き換える必要があります。

  • ${CONTROLPLANE1_INTERFACE} — エッジクラスタに使用するコントロールプレーンインタフェース(例: eth0)。

  • ${CONTROLPLANE1_IP} — エッジクラスタのエンドポイントとして使用するIPアドレス(kubeapiサーバのエンドポイントと一致する必要があります)。

  • ${CONTROLPLANE1_PREFIX} — エッジクラスタに使用するCIDR (例: /24または255.255.255.0を使用する場合には24)。

  • ${CONTROLPLANE1_GATEWAY} — エッジクラスタに使用するゲートウェイ(例: 192.168.100.1)。

  • ${CONTROLPLANE1_MAC} — コントロールプレーンインタフェースに使用するMACアドレス(例: 00:0c:29:3e:3e:3e)。

  • ${DNS_SERVER} — エッジクラスタに使用するDNS (例: 192.168.100.2)。

  • ${VLAN_ID} — エッジクラスタに使用するVLAN ID (例: 100)。

また、管理クラスタに登録するには、ファイルの末尾にあるBaremetalHostオブジェクトに、preprovisioningNetworkDataNameを使用するシークレットへの参照が必要です。

apiVersion: v1
kind: Secret
metadata:
  name: example-demo-credentials
type: Opaque
data:
  username: ${BMC_USERNAME}
  password: ${BMC_PASSWORD}
---
apiVersion: metal3.io/v1alpha1
kind: BareMetalHost
metadata:
  name: flexran-demo
  labels:
    cluster-role: control-plane
spec:
  online: true
  bootMACAddress: ${BMC_MAC}
  rootDeviceHints:
    deviceName: /dev/nvme0n1
  bmc:
    address: ${BMC_ADDRESS}
    disableCertificateVerification: true
    credentialsName: example-demo-credentials
  preprovisioningNetworkDataName: controlplane-0-networkdata
注記
注記

マルチノードクラスタをデプロイする必要がある場合は、同じプロセスをその他のノードに対して実行する必要があります。

  • プロビジョニング手順: ネットワークデータに関連する情報のブロックを削除する必要があります。その理由は、ネットワークデータの設定は、プラットフォームによってシークレットcontrolplane-0-networkdataに組み込まれるためです。

apiVersion: infrastructure.cluster.x-k8s.io/v1beta1
kind: Metal3DataTemplate
metadata:
  name: multinode-cluster-controlplane-template
  namespace: default
spec:
  clusterName: multinode-cluster
  metaData:
    objectNames:
      - key: name
        object: machine
      - key: local-hostname
        object: machine
      - key: local_hostname
        object: machine
注記
注記

Metal3DataTemplatenetworkData、およびMetal3 IPAMは現在サポートされていません。静的シークレットを介した設定のみが完全にサポートされています。

31.7 通信機能(DPDK、SR-IOV、CPUの分離、Huge Page、NUMAなど)

ダイレクトネットワークプロビジョニングのワークフローでは、ダウンストリームクラスタで使用する通信機能を自動化して、そのサーバ上で通信ワークロードを実行できます。

要件

設定

次の2つのセクションをベースとして使用し、ホストを登録してプロビジョニングします。

このセクションで説明する通信機能を次に示します。

  • DPDKとVFの作成

  • ワークロードで使用されるSR-IOVとVFの割り当て

  • CPUの分離とパフォーマンスの調整

  • Huge Pageの設定

  • カーネルパラメータの調整

注記
注記

通信機能の詳細については、第30章 「通信機能の設定を参照してください。

上記の通信機能を有効にするために必要な変更はすべて、プロビジョニングファイルcapi-provisioning-example.yamlRKE2ControlPlaneブロック内にあります。ファイルcapi-provisioning-example.yaml内の残りの情報は、プロビジョニングに関するセクション(31.4項 「ダイレクトネットワークプロビジョニングを使用したダウンストリームクラスタのプロビジョニング(シングルノード)」)で指定した情報と同じです。

このプロセスを明確にするために、通信機能を有効にするためにそのブロック(RKE2ControlPlane)で必要な変更を次に示します。

  • RKE2インストールプロセスの前にコマンドを実行するために使用するpreRKE2Commands。ここでは、modprobeコマンドを使用して、vfio-pciSR-IOVのカーネルモジュールを有効にします。

  • 作成してワークロードに公開するインタフェース、ドライバ、およびVFsの数を定義するために使用するIgnitionファイル/var/lib/rancher/rke2/server/manifests/configmap-sriov-custom-auto.yaml

    • 実際の値に置き換える値は、設定マップsriov-custom-auto-config内の値のみです。

      • ${RESOURCE_NAME1} — 最初のPFインタフェースに使用するリソース名(例: sriov-resource-du1)。このリソース名はプレフィックスrancher.ioに追加されてラベルとして使用され、ワークロードで使用されます(例: rancher.io/sriov-resource-du1)。

      • ${SRIOV-NIC-NAME1} — 使用する最初のPFインタフェースの名前(例: eth0)。

      • ${PF_NAME1} — 使用する最初の物理機能PFの名前。これを使用して、より複雑なフィルタを生成します(例: eth0#2-5)。

      • ${DRIVER_NAME1} — 最初のVFインタフェースに使用するドライバ名(例: vfio-pci)。

      • ${NUM_VFS1} — 最初のPFインタフェース用に作成するVFの数(例: 8)。

  • /var/sriov-auto-filler.shは、高レベルの設定マップsriov-custom-auto-configと、低レベルのハードウェア情報を含むsriovnetworknodepolicyとの間で情報を変換するために使用されます。このスクリプトは、ユーザがハードウェア情報を事前に把握する手間をなくすために作成されています。このファイルを変更する必要はありませんが、sr-iovを有効にしてVFを作成する必要がある場合は、このファイルが存在する必要があります。

  • 次の機能を有効にするために使用するカーネル引数:

パラメータ

説明

isolcpus

1-30、33-62

コア1-30および33-62を分離します。

skew_tick

1

分離されたCPU間でカーネルがタイマー割り込みをずらすことができるようにします。

nohz

on

システムがアイドル状態のときにカーネルが1つのCPUでタイマーティックを実行できるようにします。

nohz_full

1-30、33-62

カーネルブートパラメータは、完全なdynticksとCPU分離の設定を行うための現在の主要インタフェースです。

rcu_nocbs

1-30、33-62

システムがアイドル状態のときにカーネルが1つのCPUでRCUコールバックを実行できるようにします。

kthread_cpus

0、31、32、63

システムがアイドル状態のときにカーネルが1つのCPUでkthreadsを実行できるようにします。

irqaffinity

0、31、32、63

システムがアイドル状態のときにカーネルが1つのCPUで割り込みを実行できるようにします。

processor.max_cstate

1

アイドル状態のときにCPUがスリープ状態にならないようにします。

intel_idle.max_cstate

0

intel_idleドライバを無効にし、acpi_idleを使用できるようにします。

iommu

pt

vfioをdpdkインタフェースに使用できるようにします。

intel_iommu

on

vfioをVFに使用できるようにします。

hugepagesz

1G

Huge Pageのサイズを1Gに設定できるようにします。

hugepages

40

前に定義したHuge Pageの数。

default_hugepagesz

1G

Huge Pageを有効にする場合のデフォルト値。

  • 次のsystemdサービスは、以下のサービスを有効にするために使用します。

    • rke2-preinstall.service - プロビジョニングプロセス中にIronicの情報を利用してBAREMETALHOST_UUIDnode-nameを自動的に置き換えます。

    • cpu-performance.service - CPUパフォーマンスの調整を有効にします。${CPU_FREQUENCY}は実際の値に置き換える必要があります(例: CPUの周波数を2.5GHzに設定する場合、2500000)。

    • cpu-partitioning.service - CPUの分離コアを有効にします(例: 1-30,33-62)。

    • sriov-custom-auto-vfs.service - sriov Helmチャートをインストールし、カスタムリソースが作成されるまで待機し、/var/sriov-auto-filler.shを実行して設定マップsriov-custom-auto-configの値を置き換えてワークロードが使用するsriovnetworknodepolicyを作成します。

  • ${RKE2_VERSION}は、この値の置き換えに使用するRKE2のバージョンです(例: v1.28.9+rke2r1)。

これらの変更をすべて行うと、capi-provisioning-example.yamlRKE2ControlPlaneブロックは次のようになります。

apiVersion: controlplane.cluster.x-k8s.io/v1alpha1
kind: RKE2ControlPlane
metadata:
  name: single-node-cluster
  namespace: default
spec:
  infrastructureRef:
    apiVersion: infrastructure.cluster.x-k8s.io/v1beta1
    kind: Metal3MachineTemplate
    name: single-node-cluster-controlplane
  replicas: 1
  serverConfig:
    cni: cilium
    cniMultusEnable: true
  preRKE2Commands:
    - modprobe vfio-pci enable_sriov=1 disable_idle_d3=1
  agentConfig:
    format: ignition
    additionalUserData:
      config: |
        variant: fcos
        version: 1.4.0
        storage:
          files:
            - path: /var/lib/rancher/rke2/server/manifests/configmap-sriov-custom-auto.yaml
              overwrite: true
              contents:
                inline: |
                  apiVersion: v1
                  kind: ConfigMap
                  metadata:
                    name: sriov-custom-auto-config
                    namespace: kube-system
                  data:
                    config.json: |
                      [
                         {
                           "resourceName": "${RESOURCE_NAME1}",
                           "interface": "${SRIOV-NIC-NAME1}",
                           "pfname": "${PF_NAME1}",
                           "driver": "${DRIVER_NAME1}",
                           "numVFsToCreate": ${NUM_VFS1}
                         },
                         {
                           "resourceName": "${RESOURCE_NAME2}",
                           "interface": "${SRIOV-NIC-NAME2}",
                           "pfname": "${PF_NAME2}",
                           "driver": "${DRIVER_NAME2}",
                           "numVFsToCreate": ${NUM_VFS2}
                         }
                      ]
              mode: 0644
              user:
                name: root
              group:
                name: root
            - path: /var/lib/rancher/rke2/server/manifests/sriov-crd.yaml
              overwrite: true
              contents:
                inline: |
                  apiVersion: helm.cattle.io/v1
                  kind: HelmChart
                  metadata:
                    name: sriov-crd
                    namespace: kube-system
                  spec:
                    chart: oci://registry.suse.com/edge/sriov-crd-chart
                    targetNamespace: sriov-network-operator
                    version: 1.2.2
                    createNamespace: true
            - path: /var/lib/rancher/rke2/server/manifests/sriov-network-operator.yaml
              overwrite: true
              contents:
                inline: |
                  apiVersion: helm.cattle.io/v1
                  kind: HelmChart
                  metadata:
                    name: sriov-network-operator
                    namespace: kube-system
                  spec:
                    chart: oci://registry.suse.com/edge/sriov-network-operator-chart
                    targetNamespace: sriov-network-operator
                    version: 1.2.2
                    createNamespace: true
            - path: /var/sriov-auto-filler.sh
              overwrite: true
              contents:
                inline: |
                  #!/bin/bash
                  cat <<- EOF > /var/sriov-networkpolicy-template.yaml
                  apiVersion: sriovnetwork.openshift.io/v1
                  kind: SriovNetworkNodePolicy
                  metadata:
                    name: atip-RESOURCENAME
                    namespace: sriov-network-operator
                  spec:
                    nodeSelector:
                      feature.node.kubernetes.io/network-sriov.capable: "true"
                    resourceName: RESOURCENAME
                    deviceType: DRIVER
                    numVfs: NUMVF
                    mtu: 1500
                    nicSelector:
                      pfNames: ["PFNAMES"]
                      deviceID: "DEVICEID"
                      vendor: "VENDOR"
                      rootDevices:
                        - PCIADDRESS
                  EOF

                  export KUBECONFIG=/etc/rancher/rke2/rke2.yaml; export KUBECTL=/var/lib/rancher/rke2/bin/kubectl
                  while [ $(${KUBECTL} --kubeconfig=${KUBECONFIG} get sriovnetworknodestates.sriovnetwork.openshift.io -n sriov-network-operator -ojson | jq -r '.items[].status.syncStatus') != "Succeeded" ]; do sleep 1; done
                  input=$(${KUBECTL} --kubeconfig=${KUBECONFIG} get cm sriov-custom-auto-config -n kube-system -ojson | jq -r '.data."config.json"')
                  jq -c '.[]' <<< $input | while read i; do
                    interface=$(echo $i | jq -r '.interface')
                    pfname=$(echo $i | jq -r '.pfname')
                    pciaddress=$(${KUBECTL} --kubeconfig=${KUBECONFIG} get sriovnetworknodestates.sriovnetwork.openshift.io -n sriov-network-operator -ojson | jq -r ".items[].status.interfaces[]|select(.name==\"$interface\")|.pciAddress")
                    vendor=$(${KUBECTL} --kubeconfig=${KUBECONFIG} get sriovnetworknodestates.sriovnetwork.openshift.io -n sriov-network-operator -ojson | jq -r ".items[].status.interfaces[]|select(.name==\"$interface\")|.vendor")
                    deviceid=$(${KUBECTL} --kubeconfig=${KUBECONFIG} get sriovnetworknodestates.sriovnetwork.openshift.io -n sriov-network-operator -ojson | jq -r ".items[].status.interfaces[]|select(.name==\"$interface\")|.deviceID")
                    resourceName=$(echo $i | jq -r '.resourceName')
                    driver=$(echo $i | jq -r '.driver')
                    sed -e "s/RESOURCENAME/$resourceName/g" \
                        -e "s/DRIVER/$driver/g" \
                        -e "s/PFNAMES/$pfname/g" \
                        -e "s/VENDOR/$vendor/g" \
                        -e "s/DEVICEID/$deviceid/g" \
                        -e "s/PCIADDRESS/$pciaddress/g" \
                        -e "s/NUMVF/$(echo $i | jq -r '.numVFsToCreate')/g" /var/sriov-networkpolicy-template.yaml > /var/lib/rancher/rke2/server/manifests/$resourceName.yaml
                  done
              mode: 0755
              user:
                name: root
              group:
                name: root
        kernel_arguments:
          should_exist:
            - intel_iommu=on
            - intel_pstate=passive
            - processor.max_cstate=1
            - intel_idle.max_cstate=0
            - iommu=pt
            - mce=off
            - hugepagesz=1G hugepages=40
            - hugepagesz=2M hugepages=0
            - default_hugepagesz=1G
            - kthread_cpus=${NON-ISOLATED_CPU_CORES}
            - irqaffinity=${NON-ISOLATED_CPU_CORES}
            - isolcpus=${ISOLATED_CPU_CORES}
            - nohz_full=${ISOLATED_CPU_CORES}
            - rcu_nocbs=${ISOLATED_CPU_CORES}
            - rcu_nocb_poll
            - nosoftlockup
            - nohz=on
        systemd:
          units:
            - name: rke2-preinstall.service
              enabled: true
              contents: |
                [Unit]
                Description=rke2-preinstall
                Wants=network-online.target
                Before=rke2-install.service
                ConditionPathExists=!/run/cluster-api/bootstrap-success.complete
                [Service]
                Type=oneshot
                User=root
                ExecStartPre=/bin/sh -c "mount -L config-2 /mnt"
                ExecStart=/bin/sh -c "sed -i \"s/BAREMETALHOST_UUID/$(jq -r .uuid /mnt/openstack/latest/meta_data.json)/\" /etc/rancher/rke2/config.yaml"
                ExecStart=/bin/sh -c "echo \"node-name: $(jq -r .name /mnt/openstack/latest/meta_data.json)\" >> /etc/rancher/rke2/config.yaml"
                ExecStartPost=/bin/sh -c "umount /mnt"
                [Install]
                WantedBy=multi-user.target
            - name: cpu-performance.service
              enabled: true
              contents: |
                [Unit]
                Description=CPU perfomance
                Wants=network-online.target
                After=network.target network-online.target
                [Service]
                User=root
                Type=forking
                TimeoutStartSec=900
                ExecStart=/bin/sh -c "cpupower frequency-set -g performance; cpupower frequency-set -u ${CPU_FREQUENCY}; cpupower frequency-set -d ${CPU_FREQUENCY}"
                RemainAfterExit=yes
                KillMode=process
                [Install]
                WantedBy=multi-user.target
            - name: cpu-partitioning.service
              enabled: true
              contents: |
                [Unit]
                Description=cpu-partitioning
                Wants=network-online.target
                After=network.target network-online.target
                [Service]
                Type=oneshot
                User=root
                ExecStart=/bin/sh -c "echo isolated_cores=${ISOLATED_CPU_CORES} > /etc/tuned/cpu-partitioning-variables.conf"
                ExecStartPost=/bin/sh -c "tuned-adm profile cpu-partitioning"
                ExecStartPost=/bin/sh -c "systemctl enable tuned.service"
                [Install]
                WantedBy=multi-user.target
            - name: sriov-custom-auto-vfs.service
              enabled: true
              contents: |
                [Unit]
                Description=SRIOV Custom Auto VF Creation
                Wants=network-online.target  rke2-server.target
                After=network.target network-online.target rke2-server.target
                [Service]
                User=root
                Type=forking
                TimeoutStartSec=900
                ExecStart=/bin/sh -c "while ! /var/lib/rancher/rke2/bin/kubectl --kubeconfig=/etc/rancher/rke2/rke2.yaml wait --for condition=ready nodes --all ; do sleep 2 ; done"
                ExecStartPost=/bin/sh -c "while [ $(/var/lib/rancher/rke2/bin/kubectl --kubeconfig=/etc/rancher/rke2/rke2.yaml get sriovnetworknodestates.sriovnetwork.openshift.io --ignore-not-found --no-headers -A | wc -l) -eq 0 ]; do sleep 1; done"
                ExecStartPost=/bin/sh -c "/var/sriov-auto-filler.sh"
                RemainAfterExit=yes
                KillMode=process
                [Install]
                WantedBy=multi-user.target
    kubelet:
      extraArgs:
        - provider-id=metal3://BAREMETALHOST_UUID
    version: ${RKE2_VERSION}
    nodeName: "localhost.localdomain"

前の各ブロックを結合してファイルを作成したら、管理クラスタで次のコマンドを実行し、通信機能を使用する新しいダウンストリームクラスタのプロビジョニングを開始する必要があります。

$ kubectl apply -f capi-provisioning-example.yaml

31.8 プライベートレジストリ

ワークロードで使用するイメージのミラーとしてプライベートレジストリを設定できます。

そのために、ダウンストリームクラスタで使用するプライベートレジストリに関する情報を含むシークレットを作成します。

apiVersion: v1
kind: Secret
metadata:
  name: private-registry-cert
  namespace: default
data:
  tls.crt: ${TLS_CERTIFICATE}
  tls.key: ${TLS_KEY}
  ca.crt: ${CA_CERTIFICATE}
type: kubernetes.io/tls
---
apiVersion: v1
kind: Secret
metadata:
  name: private-registry-auth
  namespace: default
data:
  username: ${REGISTRY_USERNAME}
  password: ${REGISTRY_PASSWORD}

tls.crttls.key、およびca.crtは、プライベートレジストリを認証するために使用する証明書です。usernameおよびpasswordは、プライベートレジストリを認証するために使用する資格情報です。

注記
注記

tls.crttls.keyca.crtusername、およびpasswordは、シークレットで使用する前にbase64形式でエンコードする必要があります。

これらの変更をすべて行うと、capi-provisioning-example.yamlRKE2ControlPlaneブロックは次のようになります。

apiVersion: controlplane.cluster.x-k8s.io/v1alpha1
kind: RKE2ControlPlane
metadata:
  name: single-node-cluster
  namespace: default
spec:
  infrastructureRef:
    apiVersion: infrastructure.cluster.x-k8s.io/v1beta1
    kind: Metal3MachineTemplate
    name: single-node-cluster-controlplane
  replicas: 1
  privateRegistriesConfig:
    mirrors:
      "registry.example.com":
        endpoint:
          - "https://registry.example.com:5000"
    configs:
      "registry.example.com":
        authSecret:
          apiVersion: v1
          kind: Secret
          namespace: default
          name: private-registry-auth
        tls:
          tlsConfigSecret:
            apiVersion: v1
            kind: Secret
            namespace: default
            name: private-registry-cert
  serverConfig:
    cni: cilium
  agentConfig:
    format: ignition
    additionalUserData:
      config: |
        variant: fcos
        version: 1.4.0
        systemd:
          units:
            - name: rke2-preinstall.service
              enabled: true
              contents: |
                [Unit]
                Description=rke2-preinstall
                Wants=network-online.target
                Before=rke2-install.service
                ConditionPathExists=!/run/cluster-api/bootstrap-success.complete
                [Service]
                Type=oneshot
                User=root
                ExecStartPre=/bin/sh -c "mount -L config-2 /mnt"
                ExecStart=/bin/sh -c "sed -i \"s/BAREMETALHOST_UUID/$(jq -r .uuid /mnt/openstack/latest/meta_data.json)/\" /etc/rancher/rke2/config.yaml"
                ExecStart=/bin/sh -c "echo \"node-name: $(jq -r .name /mnt/openstack/latest/meta_data.json)\" >> /etc/rancher/rke2/config.yaml"
                ExecStartPost=/bin/sh -c "umount /mnt"
                [Install]
                WantedBy=multi-user.target
    kubelet:
      extraArgs:
        - provider-id=metal3://BAREMETALHOST_UUID
    version: ${RKE2_VERSION}
    nodeName: "localhost.localdomain"

ここで、registry.example.comは、ダウンストリームクラスタで使用するプライベートレジストリの名前の例です。これは実際の値に置き換える必要があります。

31.9 エアギャップシナリオでのダウンストリームクラスタのプロビジョニング

ダイレクトネットワークプロビジョニングワークフローでは、エアギャップシナリオでのダウンストリームクラスタのプロビジョニングを自動化できます。

31.9.1 エアギャップシナリオの要件

  1. EIBを使用して生成されたのイメージには、エアギャップシナリオでダウンストリームクラスタを実行するために必要な特定のコンテナイメージ(HelmチャートOCIイメージとコンテナイメージ)を含める必要があります。詳細については、こちらのセクション(31.3項 「エアギャップシナリオ用のダウンストリームクラスタイメージの準備」)を参照してください。

  2. SR-IOVまたはその他のカスタムワークロードを使用する場合、プライベートレジストリへのプリロードに関するセクション(31.3.2.5項 「エアギャップシナリオおよびSR-IOV (オプション)に必要なイメージのプライベートレジストリへのプリロード」)に従って、ワークロードを実行するために必要なイメージをプライベートレジストリにプリロードする必要があります。

31.9.2 エアギャップシナリオでのベアメタルホストの登録

管理クラスタにベアメタルホストを登録するプロセスは、前のセクション(31.4項 「ダイレクトネットワークプロビジョニングを使用したダウンストリームクラスタのプロビジョニング(シングルノード)」)で説明したプロセスと同じです。

31.9.3 エアギャップシナリオでのダウンストリームクラスタのプロビジョニング

エアギャップシナリオでダウンストリームクラスタをプロビジョニングするために必要となる重要な変更がいくつかあります。

  1. capi-provisioning-example.yamlファイルのRKE2ControlPlaneブロックにspec.agentConfig.airGapped: trueディレクティブを含める必要があります。

  2. プライベートレジストリに関するセクション(31.8項 「プライベートレジストリ」)に従って、プライベートレジストリの設定をcapi-provisioning-airgap-example.yamlファイルのRKE2ControlPlaneブロックに含める必要があります。

  3. SR-IOV、またはHelmチャートをインストールする必要があるその他のAdditionalUserData設定(combustionスクリプト)を使用している場合、内容を変更して、パブリックレジストリを使用するのではなくプライベートレジストリを参照する必要があります。

次の例は、プライベートレジストリを参照するために必要な変更を行った、capi-provisioning-airgap-example.yamlファイルのAdditionalUserDataブロックのSR-IOVの設定を示しています。

  • プライベートレジストリのシークレットの参照

  • パブリックOCIイメージではなくプライベートレジストリを使用するHelmチャートの定義

# secret to include the private registry certificates
apiVersion: v1
kind: Secret
metadata:
  name: private-registry-cert
  namespace: default
data:
  tls.crt: ${TLS_BASE64_CERT}
  tls.key: ${TLS_BASE64_KEY}
  ca.crt: ${CA_BASE64_CERT}
type: kubernetes.io/tls
---
# secret to include the private registry auth credentials
apiVersion: v1
kind: Secret
metadata:
  name: private-registry-auth
  namespace: default
data:
  username: ${REGISTRY_USERNAME}
  password: ${REGISTRY_PASSWORD}
---
apiVersion: controlplane.cluster.x-k8s.io/v1alpha1
kind: RKE2ControlPlane
metadata:
  name: single-node-cluster
  namespace: default
spec:
  infrastructureRef:
    apiVersion: infrastructure.cluster.x-k8s.io/v1beta1
    kind: Metal3MachineTemplate
    name: single-node-cluster-controlplane
  replicas: 1
  privateRegistriesConfig:       # Private registry configuration to add your own mirror and credentials
    mirrors:
      docker.io:
        endpoint:
          - "https://$(PRIVATE_REGISTRY_URL)"
    configs:
      "192.168.100.22:5000":
        authSecret:
          apiVersion: v1
          kind: Secret
          namespace: default
          name: private-registry-auth
        tls:
          tlsConfigSecret:
            apiVersion: v1
            kind: Secret
            namespace: default
            name: private-registry-cert
          insecureSkipVerify: false
  serverConfig:
    cni: cilium
    cniMultusEnable: true
  preRKE2Commands:
    - modprobe vfio-pci enable_sriov=1 disable_idle_d3=1
  agentConfig:
    airGapped: true       # Airgap true to enable airgap mode
    format: ignition
    additionalUserData:
      config: |
        variant: fcos
        version: 1.4.0
        storage:
          files:
            - path: /var/lib/rancher/rke2/server/manifests/configmap-sriov-custom-auto.yaml
              overwrite: true
              contents:
                inline: |
                  apiVersion: v1
                  kind: ConfigMap
                  metadata:
                    name: sriov-custom-auto-config
                    namespace: sriov-network-operator
                  data:
                    config.json: |
                      [
                         {
                           "resourceName": "${RESOURCE_NAME1}",
                           "interface": "${SRIOV-NIC-NAME1}",
                           "pfname": "${PF_NAME1}",
                           "driver": "${DRIVER_NAME1}",
                           "numVFsToCreate": ${NUM_VFS1}
                         },
                         {
                           "resourceName": "${RESOURCE_NAME2}",
                           "interface": "${SRIOV-NIC-NAME2}",
                           "pfname": "${PF_NAME2}",
                           "driver": "${DRIVER_NAME2}",
                           "numVFsToCreate": ${NUM_VFS2}
                         }
                      ]
              mode: 0644
              user:
                name: root
              group:
                name: root
            - path: /var/lib/rancher/rke2/server/manifests/sriov.yaml
              overwrite: true
              contents:
                inline: |
                  apiVersion: v1
                  data:
                    .dockerconfigjson: ${REGISTRY_AUTH_DOCKERCONFIGJSON}
                  kind: Secret
                  metadata:
                    name: privregauth
                    namespace: kube-system
                  type: kubernetes.io/dockerconfigjson
                  ---
                  apiVersion: v1
                  kind: ConfigMap
                  metadata:
                    namespace: kube-system
                    name: example-repo-ca
                  data:
                    ca.crt: |-
                      -----BEGIN CERTIFICATE-----
                      ${CA_BASE64_CERT}
                      -----END CERTIFICATE-----
                  ---
                  apiVersion: helm.cattle.io/v1
                  kind: HelmChart
                  metadata:
                    name: sriov-crd
                    namespace: kube-system
                  spec:
                    chart: oci://${PRIVATE_REGISTRY_URL}/sriov-crd
                    dockerRegistrySecret:
                      name: privregauth
                    repoCAConfigMap:
                      name: example-repo-ca
                    createNamespace: true
                    set:
                      global.clusterCIDR: 192.168.0.0/18
                      global.clusterCIDRv4: 192.168.0.0/18
                      global.clusterDNS: 10.96.0.10
                      global.clusterDomain: cluster.local
                      global.rke2DataDir: /var/lib/rancher/rke2
                      global.serviceCIDR: 10.96.0.0/12
                    targetNamespace: sriov-network-operator
                    version: ${SRIOV_CRD_VERSION}
                  ---
                  apiVersion: helm.cattle.io/v1
                  kind: HelmChart
                  metadata:
                    name: sriov-network-operator
                    namespace: kube-system
                  spec:
                    chart: oci://${PRIVATE_REGISTRY_URL}/sriov-network-operator
                    dockerRegistrySecret:
                      name: privregauth
                    repoCAConfigMap:
                      name: example-repo-ca
                    createNamespace: true
                    set:
                      global.clusterCIDR: 192.168.0.0/18
                      global.clusterCIDRv4: 192.168.0.0/18
                      global.clusterDNS: 10.96.0.10
                      global.clusterDomain: cluster.local
                      global.rke2DataDir: /var/lib/rancher/rke2
                      global.serviceCIDR: 10.96.0.0/12
                    targetNamespace: sriov-network-operator
                    version: ${SRIOV_OPERATOR_VERSION}
              mode: 0644
              user:
                name: root
              group:
                name: root
            - path: /var/sriov-auto-filler.sh
              overwrite: true
              contents:
                inline: |
                  #!/bin/bash
                  cat <<- EOF > /var/sriov-networkpolicy-template.yaml
                  apiVersion: sriovnetwork.openshift.io/v1
                  kind: SriovNetworkNodePolicy
                  metadata:
                    name: atip-RESOURCENAME
                    namespace: sriov-network-operator
                  spec:
                    nodeSelector:
                      feature.node.kubernetes.io/network-sriov.capable: "true"
                    resourceName: RESOURCENAME
                    deviceType: DRIVER
                    numVfs: NUMVF
                    mtu: 1500
                    nicSelector:
                      pfNames: ["PFNAMES"]
                      deviceID: "DEVICEID"
                      vendor: "VENDOR"
                      rootDevices:
                        - PCIADDRESS
                  EOF

                  export KUBECONFIG=/etc/rancher/rke2/rke2.yaml; export KUBECTL=/var/lib/rancher/rke2/bin/kubectl
                  while [ $(${KUBECTL} --kubeconfig=${KUBECONFIG} get sriovnetworknodestates.sriovnetwork.openshift.io -n sriov-network-operator -ojson | jq -r '.items[].status.syncStatus') != "Succeeded" ]; do sleep 1; done
                  input=$(${KUBECTL} --kubeconfig=${KUBECONFIG} get cm sriov-custom-auto-config -n sriov-network-operator -ojson | jq -r '.data."config.json"')
                  jq -c '.[]' <<< $input | while read i; do
                    interface=$(echo $i | jq -r '.interface')
                    pfname=$(echo $i | jq -r '.pfname')
                    pciaddress=$(${KUBECTL} --kubeconfig=${KUBECONFIG} get sriovnetworknodestates.sriovnetwork.openshift.io -n sriov-network-operator -ojson | jq -r ".items[].status.interfaces[]|select(.name==\"$interface\")|.pciAddress")
                    vendor=$(${KUBECTL} --kubeconfig=${KUBECONFIG} get sriovnetworknodestates.sriovnetwork.openshift.io -n sriov-network-operator -ojson | jq -r ".items[].status.interfaces[]|select(.name==\"$interface\")|.vendor")
                    deviceid=$(${KUBECTL} --kubeconfig=${KUBECONFIG} get sriovnetworknodestates.sriovnetwork.openshift.io -n sriov-network-operator -ojson | jq -r ".items[].status.interfaces[]|select(.name==\"$interface\")|.deviceID")
                    resourceName=$(echo $i | jq -r '.resourceName')
                    driver=$(echo $i | jq -r '.driver')
                    sed -e "s/RESOURCENAME/$resourceName/g" \
                        -e "s/DRIVER/$driver/g" \
                        -e "s/PFNAMES/$pfname/g" \
                        -e "s/VENDOR/$vendor/g" \
                        -e "s/DEVICEID/$deviceid/g" \
                        -e "s/PCIADDRESS/$pciaddress/g" \
                        -e "s/NUMVF/$(echo $i | jq -r '.numVFsToCreate')/g" /var/sriov-networkpolicy-template.yaml > /var/lib/rancher/rke2/server/manifests/$resourceName.yaml
                  done
              mode: 0755
              user:
                name: root
              group:
                name: root
        kernel_arguments:
          should_exist:
            - intel_iommu=on
            - intel_pstate=passive
            - processor.max_cstate=1
            - intel_idle.max_cstate=0
            - iommu=pt
            - mce=off
            - hugepagesz=1G hugepages=40
            - hugepagesz=2M hugepages=0
            - default_hugepagesz=1G
            - kthread_cpus=${NON-ISOLATED_CPU_CORES}
            - irqaffinity=${NON-ISOLATED_CPU_CORES}
            - isolcpus=${ISOLATED_CPU_CORES}
            - nohz_full=${ISOLATED_CPU_CORES}
            - rcu_nocbs=${ISOLATED_CPU_CORES}
            - rcu_nocb_poll
            - nosoftlockup
            - nohz=on
        systemd:
          units:
            - name: rke2-preinstall.service
              enabled: true
              contents: |
                [Unit]
                Description=rke2-preinstall
                Wants=network-online.target
                Before=rke2-install.service
                ConditionPathExists=!/run/cluster-api/bootstrap-success.complete
                [Service]
                Type=oneshot
                User=root
                ExecStartPre=/bin/sh -c "mount -L config-2 /mnt"
                ExecStart=/bin/sh -c "sed -i \"s/BAREMETALHOST_UUID/$(jq -r .uuid /mnt/openstack/latest/meta_data.json)/\" /etc/rancher/rke2/config.yaml"
                ExecStart=/bin/sh -c "echo \"node-name: $(jq -r .name /mnt/openstack/latest/meta_data.json)\" >> /etc/rancher/rke2/config.yaml"
                ExecStartPost=/bin/sh -c "umount /mnt"
                [Install]
                WantedBy=multi-user.target
            - name: cpu-partitioning.service
              enabled: true
              contents: |
                [Unit]
                Description=cpu-partitioning
                Wants=network-online.target
                After=network.target network-online.target
                [Service]
                Type=oneshot
                User=root
                ExecStart=/bin/sh -c "echo isolated_cores=${ISOLATED_CPU_CORES} > /etc/tuned/cpu-partitioning-variables.conf"
                ExecStartPost=/bin/sh -c "tuned-adm profile cpu-partitioning"
                ExecStartPost=/bin/sh -c "systemctl enable tuned.service"
                [Install]
                WantedBy=multi-user.target
            - name: sriov-custom-auto-vfs.service
              enabled: true
              contents: |
                [Unit]
                Description=SRIOV Custom Auto VF Creation
                Wants=network-online.target  rke2-server.target
                After=network.target network-online.target rke2-server.target
                [Service]
                User=root
                Type=forking
                TimeoutStartSec=900
                ExecStart=/bin/sh -c "while ! /var/lib/rancher/rke2/bin/kubectl --kubeconfig=/etc/rancher/rke2/rke2.yaml wait --for condition=ready nodes --all ; do sleep 2 ; done"
                ExecStartPost=/bin/sh -c "while [ $(/var/lib/rancher/rke2/bin/kubectl --kubeconfig=/etc/rancher/rke2/rke2.yaml get sriovnetworknodestates.sriovnetwork.openshift.io --ignore-not-found --no-headers -A | wc -l) -eq 0 ]; do sleep 1; done"
                ExecStartPost=/bin/sh -c "/var/sriov-auto-filler.sh"
                RemainAfterExit=yes
                KillMode=process
                [Install]
                WantedBy=multi-user.target
    kubelet:
      extraArgs:
        - provider-id=metal3://BAREMETALHOST_UUID
    version: ${RKE2_VERSION}
    nodeName: "localhost.localdomain"

32 ライフサイクルのアクション

このセクションでは、デプロイしたATIPクラスタのライフサイクル管理アクションについて説明します。

32.1 管理クラスタのアップグレード

管理クラスタのアップグレードには複数のコンポーネントが関係します。アップグレードする必要がある一般的なコンポーネントのリストについては、Day 2管理クラスタ(第24章 「管理クラスタ)のドキュメントを参照してください。

このセットアップに固有のコンポーネントをアップグレードする手順を以下に示します。

Metal3のアップグレード

Metal3をアップグレードするには、次のコマンドを使用してHelmリポジトリキャッシュを更新し、最新のチャートをフェッチしてHelmチャートリポジトリからMetal3をインストールします。

helm repo update
helm fetch suse-edge/metal3

その後、現在の設定をファイルにエクスポートしてから、その前のファイルを使用してMetal3のバージョンをアップグレードすると、簡単にアップグレードできます。新しいバージョンで何らかの変更が必要な場合、アップグレードの前にそのファイルを編集できます。

helm get values metal3 -n metal3-system -o yaml > metal3-values.yaml
helm upgrade metal3 suse-edge/metal3 \
  --namespace metal3-system \
  -f metal3-values.yaml \
  --version=0.7.1

32.2 ダウンストリームクラスタのアップグレード

ダウンストリームクラスタをアップグレードするには、複数のコンポーネントを更新する必要があります。次の各セクションでは、各コンポーネントのアップグレードプロセスについて説明します。

オペレーティングシステムのアップグレード

このプロセスでは、次の参照資料を確認して、新しいオペレーティングシステムバージョンで新しいイメージを構築します。EIBで生成されたこの新しいイメージにより、次のプロビジョニングフェーズでは、指定した新しいオペレーティングシステムバージョンが使用されます。次の手順では、この新しいイメージを使用してノードをアップグレードします。

RKE2クラスタのアップグレード

自動化されたワークフローを使用してRKE2クラスタをアップグレードするために必要な変更は次のとおりです。

  • 次のセクションに示すcapi-provisioning-example.yamlのブロックRKE2ControlPlaneを次のように変更します。

    • 仕様ファイルにロールアウト戦略を追加します。

    • ${RKE2_NEW_VERSION}を置き換えて、RKE2クラスタのバージョンを新しいバージョンに変更します。

apiVersion: controlplane.cluster.x-k8s.io/v1alpha1
kind: RKE2ControlPlane
metadata:
  name: single-node-cluster
  namespace: default
spec:
  infrastructureRef:
    apiVersion: infrastructure.cluster.x-k8s.io/v1beta1
    kind: Metal3MachineTemplate
    name: single-node-cluster-controlplane
  replicas: 1
  serverConfig:
    cni: cilium
  rolloutStrategy:
    rollingUpdate:
      maxSurge: 0
  agentConfig:
    format: ignition
    additionalUserData:
      config: |
        variant: fcos
        version: 1.4.0
        systemd:
          units:
            - name: rke2-preinstall.service
              enabled: true
              contents: |
                [Unit]
                Description=rke2-preinstall
                Wants=network-online.target
                Before=rke2-install.service
                ConditionPathExists=!/run/cluster-api/bootstrap-success.complete
                [Service]
                Type=oneshot
                User=root
                ExecStartPre=/bin/sh -c "mount -L config-2 /mnt"
                ExecStart=/bin/sh -c "sed -i \"s/BAREMETALHOST_UUID/$(jq -r .uuid /mnt/openstack/latest/meta_data.json)/\" /etc/rancher/rke2/config.yaml"
                ExecStart=/bin/sh -c "echo \"node-name: $(jq -r .name /mnt/openstack/latest/meta_data.json)\" >> /etc/rancher/rke2/config.yaml"
                ExecStartPost=/bin/sh -c "umount /mnt"
                [Install]
                WantedBy=multi-user.target
    kubelet:
      extraArgs:
        - provider-id=metal3://BAREMETALHOST_UUID
    version: ${RKE2_NEW_VERSION}
    nodeName: "localhost.localdomain"
  • 次のセクションに示すcapi-provisioning-example.yamlのブロックMetal3MachineTemplateを次のように変更します。

    • イメージ名およびチェックサムを、前の手順で生成した新しいバージョンに変更します。

    • ディレクティブnodeReuseを追加してtrueに設定し、新しいノードが作成されないようにします。

    • ディレクティブautomatedCleaningModeを追加してmetadataに設定し、ノードの自動クリーニングを有効にします。

apiVersion: infrastructure.cluster.x-k8s.io/v1beta1
kind: Metal3MachineTemplate
metadata:
  name: single-node-cluster-controlplane
  namespace: default
spec:
  nodeReuse: True
  template:
    spec:
      automatedCleaningMode: metadata
      dataTemplate:
        name: single-node-cluster-controlplane-template
      hostSelector:
        matchLabels:
          cluster-role: control-plane
      image:
        checksum: http://imagecache.local:8080/${NEW_IMAGE_GENERATED}.sha256
        checksumType: sha256
        format: raw
        url: http://imagecache.local:8080/${NEW_IMAGE_GENERATED}.raw

これらの変更を行った後、次にコマンドを使用してcapi-provisioning-example.yamlファイルをクラスタに適用できます。

kubectl apply -f capi-provisioning-example.yaml

パート VII 付録

  • 33 リリースノート
  • SUSE Edge 3.0は、インフラストラクチャとクラウドネイティブなアプリケーションをエッジにデプロイするという他に例を見ない課題に対処することを目的とした、緊密に統合されて包括的に検証されたエンドツーエンドのソリューションです。SUSE Edgeが重点を置いているのは、独創的でありながら高い柔軟性とスケーラビリティを持つセキュアなプラットフォームを提供し、初期デプロイメントイメージの構築からノードのプロビジョニングとオンボーディング、アプリケーションのデプロイメント、可観測性、ライフサイクル管理にまで対応することです。

33 リリースノート

33.1 要約

SUSE Edge 3.0は、インフラストラクチャとクラウドネイティブなアプリケーションをエッジにデプロイするという他に例を見ない課題に対処することを目的とした、緊密に統合されて包括的に検証されたエンドツーエンドのソリューションです。SUSE Edgeが重点を置いているのは、独創的でありながら高い柔軟性とスケーラビリティを持つセキュアなプラットフォームを提供し、初期デプロイメントイメージの構築からノードのプロビジョニングとオンボーディング、アプリケーションのデプロイメント、可観測性、ライフサイクル管理にまで対応することです。

このソリューションは、顧客の要件や期待はさまざまであるため「万能」なエッジプラットフォームは存在しないという考え方に基づいて設計されています。エッジデプロイメントにより、実に困難な問題を解決し、継続的に進化させることが要求されます。たとえば、大規模なスケーラビリティ、ネットワークの可用性の制限、物理的なスペースの制約、新たなセキュリティの脅威と攻撃ベクトル、ハードウェアアーキテクチャとシステムリソースのバリエーション、レガシインフラストラクチャやレガシアプリケーションのデプロイとインタフェースの要件、耐用年数を延長している顧客ソリューションといった課題があります。

SUSE Edgeは、最良のオープンソースソフトウェアに基づいてゼロから構築されており、SUSEが持つ、30年にわたってセキュアで安定した定評あるSUSE Linuxプラットフォームを提供してきた歴史と、Rancherポートフォリオによって拡張性に優れ機能豊富なKubernetes管理を提供してきた経験の両方に合致するものです。SUSE Edgeは、これらの機能の上に構築されており、小売、医療、輸送、物流、通信、スマート製造、産業用IoTなど、さまざまな市場セグメントに対応できる機能を提供します。

注記
注記

SUSE Adaptive Telco Infrastructure Platform (ATIP)はSUSE Edgeの派生製品(ダウンストリーム製品)にあたり、このプラットフォームを通信事業者の要件に対処可能にするための最適化とコンポーネントが追加されています。明記されていない限り、すべてのリリースノートはSUSE Edge 3.0とSUSE ATIP 3.0の両方に適用されます。

33.2 概要

これらのリリースノートは、明示的に指定および説明されていない限り、すべてのアーキテクチャで同一です。また、最新バージョンは、その他すべてのSUSE製品のリリースノートとともに、常にhttps://www.suse.com/releasenotesでオンラインで参照できます。

エントリが記載されるのは1回だけですが、そのエントリが重要で複数のセクションに属している場合は複数の場所で参照できます。リリースノートには通常、連続する2つのリリース間の変更のみが記載されます。特定の重要なエントリは、以前の製品バージョンのリリースノートから繰り返し記載される場合があります。このようなエントリを特定しやすくするために、該当するエントリにはその旨を示すメモが含まれています。

ただし、繰り返し記載されているエントリは厚意としてのみ提供されています。したがって、リリースを1つ以上スキップする場合は、スキップしたリリースのリリースノートも確認してください。現行リリースのリリースノートしか確認しないと、システムの動作に影響する可能性がある重要な変更を見逃す可能性があります。

33.3 リリース3.0.0

公開日: 2024年4月26日

概要: SUSE Edge 3.0.0は、SUSE Edge 3.0ポートフォリオの最初のリリースです。

33.3.1 新機能

  • 該当なし - これは3.0.zの最初のリリースです。

33.3.2 バグおよびセキュリティの修正

  • 該当なし - これは3.0.zの最初のリリースです。

33.3.3 コンポーネントバージョン

次の表に、3.0.0リリースを構成する個々のコンポーネントを示します。ここには、バージョン、Helmチャートバージョン(該当する場合)、およびリリースされたアーティファクトをバイナリ形式でプル可能な場所も記載されています。使用法とデプロイメントの例については、関連するドキュメントに従ってください。

名前

バージョン

Helmチャートバージョン

アーティファクトの場所(URL/イメージ)

SLE Micro

5.5 (最新)

該当なし

SLE Microダウンロードページ
SLE-Micro.x86_64-5.5.0-Default-SelfInstall-GM2.install.iso (sha256 4f672a4a0f8ec421e7c25797def05598037c56b7f306283566a9f921bdce904a)
SLE-Micro.x86_64-5.5.0-Default-RT-SelfInstall-GM2.install.iso (sha256 527a5a7cdbf11e3e6238e386533755257676ad8b4c80be3b159d0904cb637678)
SLE-Micro.x86_64-5.5.0-Default-GM.raw.xz (sha256 13243a737ca219bad6a7aa41fa747c06e8b825fef10a756cf4d575f4493ed68b)
SLE-Micro.x86_64-5.5.0-Default-RT-GM.raw.xz (sha256 6c2af94e7ac785c8f6a276032c8e6a4b493c294e6cd72809c75089522f01bc93)

SUSE Manager

4.3.11

該当なし

SUSE Managerダウンロードページ

K3s

1.28.8

該当なし

アップストリームのK3sリリース

RKE2

1.28.8

該当なし

アップストリームのRKE2リリース

Rancher Prime

2.8.3

2.8.3

Rancher 2.8.3 Images
Rancher Prime Helmリポジトリ

Longhorn

1.6.1

103.3.0

Longhorn 1.6.1イメージ
Longhorn Helmリポジトリ

NM Configurator

0.2.3

該当なし

NMConfiguratorアップストリームリリース

NeuVector

5.3.0

103.0.3

registry.suse.com/rancher/mirrored-neuvector-controller:5.3.0
registry.suse.com/rancher/mirrored-neuvector-enforcer:5.3.0
registry.suse.com/rancher/mirrored-neuvector-manager:5.3.0
registry.suse.com/rancher/mirrored-neuvector-prometheus-exporter:5.3.0
registry.suse.com/rancher mirrored-neuvector-registry-adapter:0.1.1-s1
registry.suse.com/rancher/mirrored-neuvector-scanner:latest
registry.suse.com/rancher/mirrored-neuvector-updater:latest

Cluster API (CAPI)

1.6.2

該当なし

registry.suse.com/edge/cluster-api-controller:1.6.2
registry.suse.com/edge/cluster-api-provider-metal3:1.6.0
registry.suse.com/edge/cluster-api-provider-rke2-bootstrap:0.2.6

Metal3

1.16.0

0.6.5

registry.suse.com/edge/metal3-chart:0.6.5
registry.suse.com/edge/baremetal-operator:0.5.1
registry.suse.com/edge/cluster-api-provider-rke2-controlplane:0.2.6
registry.suse.com/edge/ip-address-manager:1.6.0
registry.suse.com/edge/ironic:23.0.1.2
registry.suse.com/edge/ironic-ipa-downloader:1.3.1
registry.suse.com/edge/kube-rbac-proxy:v0.14.2
registry.suse.com/edge/mariadb:10.6.15.1

MetalLB

0.14.3

0.14.3

registry.suse.com/edge/metallb-chart:0.14.3
registry.suse.com/edge/metallb-controller:v0.14.3
registry.suse.com/edge/metallb-speaker:v0.14.3
registry.suse.com/edge/frr:8.4
registry.suse.com/edge/frr-k8s:v0.0.8

Elemental

1.4.3

103.1.0

registry.suse.com/rancher/elemental-operator-chart:1.4.3
registry.suse.com/rancher/elemental-operator-crds-chart:1.4.3
registry.suse.com/rancher/elemental-operator:1.4.3

Edge Image Builder

1.0.1

該当なし

registry.suse.com/edge/edge-image-builder:1.0.1

KubeVirt

1.1.1

0.2.4

registry.suse.com/edge/kubevirt-chart:0.2.4
registry.suse.com/suse/sles/15.5/virt-operator:1.1.1
registry.suse.com/suse/sles/15.5/virt-api:1.1.1
registry.suse.com/suse/sles/15.5/virt-controller:1.1.1
registry.suse.com/suse/sles/15.5/virt-exportproxy:1.1.1
registry.suse.com/suse/sles/15.5/virt-exportserver:1.1.1
registry.suse.com/suse/sles/15.5/virt-handler:1.1.1
registry.suse.com/suse/sles/15.5/virt-launcher:1.1.1

KubeVirtダッシュボード拡張機能

1.0.0

1.0.0

registry.suse.com/edge/kubevirt-dashboard-extension-chart:1.0.0

Containerized Data Importer

1.58.0

0.2.3

registry.suse.com/edge/cdi-chart:0.2.3
registry.suse.com/suse/sles/15.5/cdi-operator:1.58.0
registry.suse.com/suse/sles/15.5/cdi-controller:1.58.0
registry.suse.com/suse/sles/15.5/cdi-importer:1.58.0
registry.suse.com/suse/sles/15.5/cdi-cloner:1.58.0
registry.suse.com/suse/sles/15.5/cdi-apiserver:1.58.0
registry.suse.com/suse/sles/15.5/cdi-uploadserver:1.58.0
registry.suse.com/suse/sles/15.5/cdi-uploadproxy:1.58.0

Endpoint Copier Operator

0.2.0

0.2.0

registry.suse.com/edge/endpoint-copier-operator:v0.2.0
registry.suse.com/edge/endpoint-copier-operator-chart:0.2.0

Akri (技術プレビュー)

0.12.20

0.12.20

registry.suse.com/edge/akri-chart:0.12.20
registry.suse.com/edge/akri-dashboard-extension-chart:1.0.0
registry.suse.com/edge/akri-agent:v0.12.20
registry.suse.com/edge/akri-controller:v0.12.20
registry.suse.com/edge/akri-debug-echo-discovery-handler:v0.12.20
registry.suse.com/edge/akri-onvif-discovery-handler:v0.12.20
registry.suse.com/edge/akri-opcua-discovery-handler:v0.12.20
registry.suse.com/edge/akri-udev-discovery-handler:v0.12.20
registry.suse.com/edge/akri-webhook-configuration:v0.12.20

注記
注記

SUSE Edge zストリームリリースは、バージョン管理されたスタックとして緊密に統合されていて、綿密にテストされています。個々のコンポーネントを上記のバージョンとは異なるバージョンにアップグレードすると、システムのダウンタイムが発生する可能性が高くなります。テストされていない設定でEdgeクラスタを実行することは可能ですが、推奨されません。また、サポートチャンネルを通じて解決策を提供するのに時間がかかる場合があります。

33.4 リリース3.0.1

公開日: 2024年6月14日

概要: SUSE Edge 3.0.1は、SUSE Edge 3.0ポートフォリオの最初のzストリームリリースです。

33.4.1 新機能

  • ElementalとEIBで、管理対象外のホストのノードリセットがサポートされました

  • SR-IOV Network Operatorチャートを組み込みました

  • Metal3チャートで、信頼できるCA証明書を追加で提供できるようになりました

  • NM Configuratorで、MACを指定せずに統合設定を適用できるようになりました

  • EIBにversionサブコマンドが追加され、EIBによって構築された各イメージにバージョンも自動的に含まれるようになりました

33.4.2 バグおよびセキュリティの修正

  • EIBで、カスタムスクリプトに実行ビットが自動的に設定されるようになりました: SUSE Edge issue #429

  • EIBで、512バイトを超えるセクタサイズのディスクがサポートされるようになりました: SUSE Edge issue #447

  • Helmチャート内のコンテナイメージを検出するEIBの機能を強化しました: SUSE Edge issue #442

33.4.3 コンポーネントバージョン

次の表に、3.0.1リリースを構成する個々のコンポーネントを示します。ここには、バージョン、Helmチャートバージョン(該当する場合)、およびリリースされたアーティファクトをバイナリ形式でプル可能な場所も記載されています。使用法とデプロイメントの例については、関連するマニュアルに従ってください。

名前

バージョン

Helmチャートバージョン

アーティファクトの場所(URL/イメージ)

SLE Micro

5.5 (最新)

該当なし

SLE Microダウンロードページ
SLE-Micro.x86_64-5.5.0-Default-SelfInstall-GM2.install.iso (sha256 4f672a4a0f8ec421e7c25797def05598037c56b7f306283566a9f921bdce904a)
SLE-Micro.x86_64-5.5.0-Default-RT-SelfInstall-GM2.install.iso (sha256 527a5a7cdbf11e3e6238e386533755257676ad8b4c80be3b159d0904cb637678)
SLE-Micro.x86_64-5.5.0-Default-GM.raw.xz (sha256 13243a737ca219bad6a7aa41fa747c06e8b825fef10a756cf4d575f4493ed68b)
SLE-Micro.x86_64-5.5.0-Default-RT-GM.raw.xz (sha256 6c2af94e7ac785c8f6a276032c8e6a4b493c294e6cd72809c75089522f01bc93)

SUSE Manager

4.3.11

該当なし

SUSE Managerダウンロードページ

K3s

1.28.9

該当なし

アップストリームのK3sリリース

RKE2

1.28.9

該当なし

アップストリームのRKE2リリース

Rancher Prime

2.8.4

2.8.4

Rancher 2.8.4イメージ
Rancher Prime Helmリポジトリ

Longhorn

1.6.1

103.3.0

Longhorn 1.6.1イメージ
Longhorn Helmリポジトリ

NM Configurator

0.3.0

該当なし

NMConfiguratorアップストリームリリース

NeuVector

5.3.0

103.0.3

registry.suse.com/rancher/mirrored-neuvector-controller:5.3.0
registry.suse.com/rancher/mirrored-neuvector-enforcer:5.3.0
registry.suse.com/rancher/mirrored-neuvector-manager:5.3.0
registry.suse.com/rancher/mirrored-neuvector-prometheus-exporter:5.3.0
registry.suse.com/rancher mirrored-neuvector-registry-adapter:0.1.1-s1
registry.suse.com/rancher/mirrored-neuvector-scanner:latest
registry.suse.com/rancher/mirrored-neuvector-updater:latest

Cluster API (CAPI)

1.6.2

該当なし

registry.suse.com/edge/cluster-api-controller:1.6.2
registry.suse.com/edge/cluster-api-provider-metal3:1.6.0
registry.suse.com/edge/cluster-api-provider-rke2-bootstrap:0.2.6

Metal3

1.16.0

0.7.1

registry.suse.com/edge/metal3-chart:0.7.1
registry.suse.com/edge/baremetal-operator:0.5.1
registry.suse.com/edge/cluster-api-provider-rke2-controlplane:0.2.6
registry.suse.com/edge/ip-address-manager:1.6.0
registry.suse.com/edge/ironic:23.0.2.1
registry.suse.com/edge/ironic-ipa-downloader:1.3.2
registry.suse.com/edge/kube-rbac-proxy:v0.14.2 +.1 registry.suse.com/edge/mariadb:10.6.15.1

MetalLB

0.14.3

0.14.3

registry.suse.com/edge/metallb-chart:0.14.3
registry.suse.com/edge/metallb-controller:v0.14.3
registry.suse.com/edge/metallb-speaker:v0.14.3
registry.suse.com/edge/frr:8.4
registry.suse.com/edge/frr-k8s:v0.0.8

Elemental

1.4.4

103.1.0

registry.suse.com/rancher/elemental-operator-chart:1.4.4
registry.suse.com/rancher/elemental-operator-crds-chart:1.4.4
registry.suse.com/rancher/elemental-operator:1.4.4

Edge Image Builder

1.0.2

該当なし

registry.suse.com/edge/edge-image-builder:1.0.2

KubeVirt

1.1.1

0.2.4

registry.suse.com/edge/kubevirt-chart:0.2.4
registry.suse.com/suse/sles/15.5/virt-operator:1.1.1
registry.suse.com/suse/sles/15.5/virt-api:1.1.1
registry.suse.com/suse/sles/15.5/virt-controller:1.1.1
registry.suse.com/suse/sles/15.5/virt-exportproxy:1.1.1
registry.suse.com/suse/sles/15.5/virt-exportserver:1.1.1
registry.suse.com/suse/sles/15.5/virt-handler:1.1.1
registry.suse.com/suse/sles/15.5/virt-launcher:1.1.1

KubeVirtダッシュボード拡張機能

1.0.0

1.0.0

registry.suse.com/edge/kubevirt-dashboard-extension-chart:1.0.0

Containerized Data Importer

1.58.0

0.2.3

registry.suse.com/edge/cdi-chart:0.2.3
registry.suse.com/suse/sles/15.5/cdi-operator:1.58.0
registry.suse.com/suse/sles/15.5/cdi-controller:1.58.0
registry.suse.com/suse/sles/15.5/cdi-importer:1.58.0
registry.suse.com/suse/sles/15.5/cdi-cloner:1.58.0
registry.suse.com/suse/sles/15.5/cdi-apiserver:1.58.0
registry.suse.com/suse/sles/15.5/cdi-uploadserver:1.58.0
registry.suse.com/suse/sles/15.5/cdi-uploadproxy:1.58.0

Endpoint Copier Operator

0.2.0

0.2.0

registry.suse.com/edge/endpoint-copier-operator:v0.2.0
registry.suse.com/edge/endpoint-copier-operator-chart:0.2.0

Akri (技術プレビュー)

0.12.20

0.12.20

registry.suse.com/edge/akri-chart:0.12.20
registry.suse.com/edge/akri-dashboard-extension-chart:1.0.0
registry.suse.com/edge/akri-agent:v0.12.20
registry.suse.com/edge/akri-controller:v0.12.20
registry.suse.com/edge/akri-debug-echo-discovery-handler:v0.12.20
registry.suse.com/edge/akri-onvif-discovery-handler:v0.12.20
registry.suse.com/edge/akri-opcua-discovery-handler:v0.12.20
registry.suse.com/edge/akri-udev-discovery-handler:v0.12.20
registry.suse.com/edge/akri-webhook-configuration:v0.12.20

SR-IOV Network Operator

1.2.2

1.2.2+up0.1.0

registry.suse.com/edge/sriov-network-operator-chart:1.2.2
registry.suse.com/edge/sriov-crd-chart:1.2.2

33.5 コンポーネントの検証

上記のコンポーネントはSoftware Bill Of Materials (SBOM)のデータを使用して検証できます。たとえば、以下に説明するようにcosignを使用します。

SUSE署名キーのソースからSUSE Edge Containerの公開鍵をダウンロードします。

> cat key.pem
-----BEGIN PUBLIC KEY-----
MIICIjANBgkqhkiG9w0BAQEFAAOCAg8AMIICCgKCAgEA7N0S2d8LFKW4WU43bq7Z
IZT537xlKe17OQEpYjNrdtqnSwA0/jLtK83m7bTzfYRK4wty/so0g3BGo+x6yDFt
SVXTPBqnYvabU/j7UKaybJtX3jc4SjaezeBqdi96h6yEslvg4VTZDpy6TFP5ZHxZ
A0fX6m5kU2/RYhGXItoeUmL5hZ+APYgYG4/455NBaZT2yOywJ6+1zRgpR0cRAekI
OZXl51k0ebsGV6ui/NGECO6MB5e3arAhszf8eHDE02FeNJw5cimXkgDh/1Lg3KpO
dvUNm0EPWvnkNYeMCKR+687QG0bXqSVyCbY6+HG/HLkeBWkv6Hn41oeTSLrjYVGa
T3zxPVQM726sami6pgZ5vULyOleQuKBZrlFhFLbFyXqv1/DokUqEppm2Y3xZQv77
fMNogapp0qYz+nE3wSK4UHPd9z+2bq5WEkQSalYxadyuqOzxqZgSoCNoX5iIuWte
Zf1RmHjiEndg/2UgxKUysVnyCpiWoGbalM4dnWE24102050Gj6M4B5fe73hbaRlf
NBqP+97uznnRlSl8FizhXzdzJiVPcRav1tDdRUyDE2XkNRXmGfD3aCmILhB27SOA
Lppkouw849PWBt9kDMvzelUYLpINYpHRi2+/eyhHNlufeyJ7e7d6N9VcvjR/6qWG
64iSkcF2DTW61CN5TrCe0k0CAwEAAQ==
-----END PUBLIC KEY-----

コンテナイメージのハッシュを検証します。たとえば、craneを使用します。

> crane digest registry.suse.com/edge/baremetal-operator:0.5.1
sha256:13e8b2c59aeb503f8adaac095495007071559c9d6d8ef5a7cb1ce6fd1430c782

cosignを使用して検証します。

> cosign verify-attestation --type spdxjson --key key.pem registry.suse.com/edge/baremetal-operator@sha256:13e8b2c59aeb503f8adaac095495007071559c9d6d8ef5a7cb1ce6fd1430c782 > /dev/null
#
Verification for registry.suse.com/edge/baremetal-operator@sha256:13e8b2c59aeb503f8adaac095495007071559c9d6d8ef5a7cb1ce6fd1430c782 --
The following checks were performed on each of these signatures:
  - The cosign claims were validated
  - The claims were present in the transparency log
  - The signatures were integrated into the transparency log when the certificate was valid
  - The signatures were verified against the specified public key

アップストリームドキュメントの説明に従ってSBOMデータを抽出します。

> cosign verify-attestation --type spdxjson --key key.pem registry.suse.com/edge/baremetal-operator@sha256:13e8b2c59aeb503f8adaac095495007071559c9d6d8ef5a7cb1ce6fd1430c782 | jq '.payload | @base64d | fromjson | .predicate'

33.6 アップグレード手順

新しいzストリームリリースへのアップグレード方法の詳細については、Day 2のドキュメントを参照してください。

33.7 既知の制限事項

別途記載されていない限り、これらは3.0.0リリースと後続のすべてのzストリームバージョンに適用されます。

  • Akriは初めて技術プレビュー製品としてリリースされるため、標準のサポート範囲に含まれません。

  • SUSE Edgeで使用されるRancher UI拡張機能は現在、Rancher Marketplace経由ではデプロイできません。手動でデプロイする必要があります。Rancher issue #29105

  • NVIDIA GPUを使用している場合、SELinuxポリシーがないため、SELinuxをcontainerd階層で有効にすることはできません。Bugzilla #1222725

  • Metal3とCluster API (CAPI)を使用してデプロイする場合、クラスタはインストール後に自動的にRancherにインポートされません。この問題は今後のリリースで対処予定です。

33.8 製品サポートライフサイクル

SUSE Edgeは、SUSEが提供する定評あるサポートに支えられています。SUSEは、エンタープライズ品質のサポートサービスの提供において確固たる実績を誇るテクノロジリーダーです。詳細については、https://www.suse.com/lifecycle、およびサポートポリシーのページ(https://www.suse.com/support/policy.html)を参照してください。サポートケースの作成、SUSEが重大度レベルを分類する方法、またはサポートの範囲について質問がある場合は、テクニカルサポートハンドブック(https://www.suse.com/support/handbook/)を参照してください。

このマニュアルの発行時点では、SUSE Edgeの各マイナーバージョン(「3.0」など)は12か月間の運用サポートでサポートされ、最初の6か月間は「完全」サポート、その後の6か月間は「保守サポート」が提供されます。「完全サポート」の対象期間中に、SUSEは新機能(既存の機能を損なわないもの)の導入や、バグ修正の投入、セキュリティパッチの提供を行う場合があります。「保守サポート」の期間中には、重大なセキュリティ修正とバグ修正のみが提供され、その他の修正はSUSEの裁量で提供されます。

明記されていない限り、記載されているコンポーネントはすべて一般提供(GA)とみなされ、SUSEの標準のサポート範囲の対象となります。一部のコンポーネントは「技術プレビュー」として記載されている場合があります。この場合、SUSEは評価のためにGA前の機能への早期アクセスをお客様に提供しますが、これらの機能には標準のサポートポリシーが適用されず、運用ユースケースには推奨されません。SUSEでは、技術プレビューのコンポーネントに関するフィードバックや、当該コンポーネントの改良についてのご提案を心からお待ちしております。しかし、機能がお客様のニーズを満たさない場合やSUSEが求める成熟度に達しない場合、一般提供になる前に技術プレビューの機能を廃止する権利を留保します。

SUSEは場合により、機能の廃止やAPIの仕様変更を行わなければならないことがあることに注意してください。機能の廃止やAPIの変更の理由としては、機能が新しい実装によって更新または置き換えられた、新しい機能セットが導入された、アップストリームの技術が利用できなくなった、アップストリームコミュニティによって互換性のない変更が導入された、などが考えられます。これは特定のマイナーリリース(x.z)内で発生することは意図されていないため、すべてのzストリームリリースではAPIの互換性と機能が維持されます。SUSEは、廃止に関する警告をリリースノート内で十分に余裕をもって提供し、併せて回避策、推奨事項、サービスの中断を最小限に抑える軽減策も提供するよう努めます。

SUSE Edgeチームはコミュニティからのフィードバックも歓迎しており、https://www.github.com/suse-edgeの各コードリポジトリ内で問題を報告できます。

33.9 ソースコードの取得

このSUSE製品には、GNU General Public License (GPL)やその他のさまざまなオープンソースライセンスの下でSUSEにライセンスされた素材が含まれます。SUSEはGPLに従ってGPLでライセンスされた素材に対応するソースコードを提供する必要があるほか、その他すべてのオープンソースライセンスの要件にも準拠します。よって、SUSEはすべてのソースコードを利用可能にしており、一般的にSUSE Edge GitHubリポジトリ(https://www.github.com/suse-edge)にあります。また、依存コンポーネントについてはSUSE Rancher GitHubリポジトリ(https://www.github.com/rancher)にあり、特にSLE Microについてはhttps://www.suse.com/download/sle-microの「Medium 2」でソースコードをダウンロードできます。