Azure Red Hat OpenShift (ARO) でスケーラブルなノード管理・運用


はじめに

Azure Red Hat OpenShiftは、AzureのフルマネージドのOpenShiftサービスです。ワンコマンドで簡単にOpenShiftのKubernetesクラスターをAzureに作成でき、かつサポートもRed Hat社に個別に連絡を取る必要はなく、マイクロソフトが一元的にサポートします。以下、ARO(Azure Red Hat OpenShiftの頭文字を合わせたもの)と記述します。
以前の記事でAROの作成方法について記載しましたが、今回はOpenShiftをAzureで稼働する際の非常に大きなメリットとなる、スケーラブルなノードの管理・運用についてご紹介したいと思います。

AROにおけるノード管理・運用の利点

一般的にOpenShiftをオンプレミス等で構築した場合、ノードの追加やスペックの変更といった作業をすぐに実施することは、サーバの追加導入や設置・設定等が必要であり難しい場合が多いと思います。これに対してAROでは、AzureとOpenShiftが密に連携することで、OpenShiftのノードの追加・変更が簡単に実施できます。特に、AROの最も重要な特徴は、OpenShiftの管理者やアプリ開発者がAzureのポータルやAzure CLIを操作したりAzure管理者に依頼することなく、セルフサービスでノードの追加・更新等の作業を実施できる点です。これにより、OpenShiftのユーザーが自由にクラスターのリソースを制御できるため、アプリの開発や運用に集中でき、さまざまな場面で作業の効率化とスピードアップが可能になります。
この特徴により、特に次のようなケースで大きな利点があると思います。

(1)アプリの成長に合わせたスモールスタートとノードの拡張
最初は小さい構成で始め、アプリやサービスの成長に合わせて次第にノードを追加したり、メモリを大量消費するアプリに対応するために大容量メモリのノードを追加することが可能です。

(2)アプリの負荷変動に合わせたノードの自動拡張
アプリに対する接続や要求数の変動に対応するため、アプリのインスタンス(pod)の拡張と連動してノードの自動スケールを実施することが可能です。

(3)ノードの自動修復
アプリが稼働するノードの障害発生時に、ノードを自動的に修復できます。

以下では、AROにおけるAzureとOpenShiftの密連携の肝となるMachine API Operatorについて説明し、続けて上記の3つのケースについてAROでの操作方法をご紹介して行きます。

Machine API Operatorとは

Machine API OperatorはOpenShiftにおいてKubernetesクラスターノードのライフサイクルを管理する機能であり、ノードの管理をKubernetesネイティブな宣言的な方法で管理可能とします。
Machine API Operatorは下図の通り、様々なコントローラとCRDで構成されています。

特にノード管理において利用するリソースは、MachineSetになります。ユーザーがMachineSetを定義・更新することで、対応するMachineリソースが自動的に構成されます。さらに、Machineリソースに基づきAzureのVMやノードの追加や削除、更新が実施されます。

アプリの成長に合わせたスモールスタートとノードの拡張

ノードの追加および削除

AROでは、OpenShiftのWebコンソールや、OpenShift CLI(OC)などを用いて簡単にノードの追加や削除が可能です。この操作は、MachineSetリソースのspec.replicas(VMインスタンス数)の値を変更するだけです。
Webコンソールの場合、Administratorモードにおいて、左側に並ぶメニューの中のCompute内にあるMachine Setsを選択します。すると、下記のようにMachineSetリソースの一覧が表示されます。Machines欄は、リソース定義におけるVMインスタンス数のうち、何台のVMが実際に稼働中なのかを示しています。

既定で定義されているMachineSetリソースの名前の末尾は、稼働するリージョンとアベイラビリティゾーンとなります。例えば、東日本(japaneast)リージョンのアベイラビリティゾーン1で稼働するワーカーノード用のVMの場合、*-worker-japaneast1などです。なお、ノードの名前は、対応するMachineSetの名前の末尾にさらにランダムな英数字が追加され、*-worker-japaneast1-x2v7rなどとなります。(注: WebコンソールのMachinesメニューの画面を利用すれば、ノードのVMがどのリージョンやアベイラビリティゾーンで稼働しているかを一覧表示して確認可能です。また、Machineリソースの名前と対応するノードの名前は同じものとなります。)

次に、MachineSetsの一覧画面から、ノード数を変更したいMachineSetを選択します。下記のようにMachineSetの詳細画面が表示されますので、画面のDesired Countのすぐ下をクリックします。Edit Machine Countというウインドウが現れますので、所望のノード数を入力してsaveを選択してください。これにより、現在のノード数との差分となるMachineリソースおよびノードが自動的に追加・削除されます。ノードの追加時間はおおよそ数分程度です。また、ノードの削除では、ノードのスケジュール不可状態への変更やpodのeviction開始も自動的に実施されます。

また、OpenShift CLIを用いたノード数の変更は、下記を実行するだけです。

$ oc scale --replicas=<ノード数> machineset <MachineSetの名前> -n openshift-machine-api

ノードのスペック変更

新規のMachineSetリソースを新たに定義することで、例えば大容量メモリのノードをAROクラスターに新たに追加することが可能です。MachineSetのspec.template.providerSpec. value.vmSizeに所望のVMサイズを指定することができます。利用可能なVMサイズの一覧はこちらのドキュメントを参照ください。
また、MachineSetリソースには、VMのOSディスク容量やアベイラビリティゾーンなど、様々なパラメータを指定することができますが、新規に全てを入力するのは大変です。そこで、VMサイズを変更するだけであれば、既定のMachineSetをコピーして、一部だけ変更するのがおすすめです。だたしその場合、VMサイズの変更だけでなく、MachineSetの名前と関連するラベルやラベルセレクターの値を変更することも必要ですので、ご注意ください。

MachineSetの新規作成は、WebコンソールのMachine Setsメニューを選択して表示される画面において、右上のCreate Machine Setボタンをクリックして作成できます。
参考に、下記に汎用VMサイズ(Standard_D4s_v3)よりメモリ容量をvCPU比で2倍搭載するVMサイズ(Standard_E4s_v3)とした新たなMachineSetの例を示します。

apiVersion: machine.openshift.io/v1beta1
kind: MachineSet
metadata:
  name: <name>
  namespace: openshift-machine-api
  labels:
    machine.openshift.io/cluster-api-cluster: <cluster>
    machine.openshift.io/cluster-api-machine-role: worker
    machine.openshift.io/cluster-api-machine-type: worker
spec:
  replicas: 1
  selector:
    matchLabels:
      machine.openshift.io/cluster-api-cluster: <cluster>
      machine.openshift.io/cluster-api-machineset: <name> #MachineSetの名前と一致させる
  template:
    metadata:
      labels:
        machine.openshift.io/cluster-api-cluster: <cluster>
        machine.openshift.io/cluster-api-machine-role: worker
        machine.openshift.io/cluster-api-machine-type: worker
        machine.openshift.io/cluster-api-machineset: <name> #MachineSetの名前と一致させる
    spec:
      metadata: {}
      providerSpec:
        value:
          osDisk:
            diskSizeGB: 128
            managedDisk:
              storageAccountType: Premium_LRS
            osType: Linux
          networkResourceGroup: <resourcegroup>
          publicLoadBalancer: <cluster>
          userDataSecret:
            name: worker-user-data
          vnet: <vnet>
          credentialsSecret:
            name: azure-cloud-credentials
            namespace: openshift-machine-api
          zone: '1' #アベイラビリティゾーンを指定
          metadata:
            creationTimestamp: null
          publicIP: false
          resourceGroup: <managedresourcegroup>
          kind: AzureMachineProviderSpec
          location: japaneast
          vmSize: Standard_E4s_v3 #VMサイズを指定
          image:
            <snip>
          subnet: <subnet>
          apiVersion: azureproviderconfig.openshift.io/v1beta1

アプリの負荷変動に合わせたノードの自動拡張

AROでは、ノードの自動スケーリングが可能です。これにより、例えばノードのリソースが不足してpodがデプロイできない場合に、自動的にノードを追加してpodをデプロイ可能とします。また、一部のノードが長い期間にわたって不要な状態が続く場合にノードの数を削減します。一般的には、podのHPA(Horizontal Pod Autoscaler)と組み合わせて利用することが前提になると思います。

自動スケーリングに利用するには、ClusterAutoscalerMachineAutoscalerの二種類の定義を設定する必要があります。以下それぞれの設定方法についてご紹介します。

ClusterAutoscalerの定義

ClusterAutoscalerはクラスター全体をスコープとした自動スケーリングの設定です。Webコンソールから定義可能です。まず、Administratorモードの左側メニューのAdministration内にあるCustom Resource Definitionsを選択します。クラスターのCRD一覧が表示されるので、ClusterAutoscalerを検索して選択してください。

ClusterAutoscalerのCRDを選択してクリックすると、下図の画面が表示されますので、Instancesタブを選択し、画面に表示されるCreate Cluster AutoscalerボタンをクリックしてClusterAutoscalerリソースを定義します。

参考に、Clusterautoscalerリソースの定義の例を下記に記載します。この例では、最大12ノードまで拡張可能で、ノードの追加または削除後は次のスケーリングまで3分間は待機する設定としています。なお、各項目の詳細はこちらのドキュメントに記載されていますので、ご参照ください。

apiVersion: "autoscaling.openshift.io/v1"
kind: "ClusterAutoscaler"
metadata:
  name: default
spec:
  podPriorityThreshold: -10 
  resourceLimits:
    maxNodesTotal: 12
    cores:
      min: 4
      max: 128 
    memory:
      min: 4 
      max: 256 
  scaleDown: 
    enabled: true 
    delayAfterAdd: 3m 
    delayAfterDelete: 3m 
    delayAfterFailure: 30s 
    unneededTime: 60s 

MachineAutoscalerの定義

MachineAutoscalerは、特定のMachineSetリソースに対する自動スケーリングの設定です。ClusterAutoscalerの設定後に、少なくとも1つのMachineSetに対するMachineAutoscalerを設定する必要があります。こちらもWebコンソールから定義可能で、しかもYAMLを記述する必要なく簡単に作成することができます。
WebコンソールのAdministratorモードで、左側メニューのMachine Setsを選択し、MachineSetリソースの一覧を表示してください。次に、MachineAutoscalerを設定したいMachineSetリソースの右端にドットが縦に3つ連なったアイコンがありますので、そちらをクリックした際に表示されるメニューから、Create Autoscalerを選択してクリックします。すると、Minimum ReplicasとMaxmum Replicasの入力ウインドウが表示されるので、数値を入力してCreateをクリックすると、MachineAutoscalerが作成されます。他のMachineSetリソースに対しても自動スケーリングを設定する場合は、同様の操作を実施してMachineAutoscalerを作成してください。

ノードの自動修復

AROのワーカーノードで異常が発生した場合に、自動修復することができます。異常状態となったノードは削除され、新たなノードが追加されます。この機能を利用するには、MachineHealthCheckリソースを定義します。
MachineHealthCheckリソースの作成はWebコンソールから可能です。WebコンソールのAdministratorモードで、左側メニューのCompute内にあるMachine Health Checksを選択し、表示される画面よりCreate Machine Health Cehckボタンをクリックしてください。
参考に、下記にMachineHealthCheckの定義例を示します。この定義では、ワーカーノードの状態がReady状態であることが5分間以上確認できない場合、ノードの修復処理が実行されます。

apiVersion: machine.openshift.io/v1beta1
kind: MachineHealthCheck
metadata:
  name: example
  namespace: openshift-machine-api
spec:
  selector:
    matchLabels:
      machine.openshift.io/cluster-api-machine-role: worker
      machine.openshift.io/cluster-api-machine-type: worker
  unhealthyConditions:
    - type: Ready
      status: Unknown
      timeout: 300s
    - type: Ready
      status: 'False'
      timeout: 300s
  maxUnhealthy: 1
  nodeStartupTimeout: 10m

(注:MachineHealthCheckリソースは特定のOpenShiftバージョンでは既定で定義されている場合があります)

終わりに

今回の記事では、Azure Red Hat OpenShift(ARO)のノード管理についてご紹介しました。AROではAzureとOpenShiftが連携することで、ノードの追加やスペック変更、スケーリング、高可用構成および障害対応をOpenShiftからのリソース定義や操作によって制御できることをご説明しました。これにより、OpenShiftの利用者がAzureの管理者を巻き込まずに効率的かつ迅速にアプリの開発・運用に集中できると思います。

[関連資料]
Azure のマネージドなOpenShift サービス – ARO の運用のコツ
Scale an Azure Red Hat OpenShift cluster