オンラインサービスを実行する複数の Container Service for Kubernetes (ACK) クラスターがあり、オンラインサービスを中断せずにクラスター内のアイドルリソースを使用して Spark ジョブを実行する場合、Distributed Cloud Container Platform for Kubernetes (ACK One) が提供する複数クラスター Spark ジョブのスケジューリングと分散を使用できます。このトピックでは、ACK One Fleet インスタンスと ACK Koordinator コンポーネントを使用して、Fleet インスタンスに関連付けられたクラスター内のアイドルリソースを使用して、複数クラスターにわたって Spark ジョブをスケジュールおよび分散する方法について説明します。これは、複数クラスターのアイドルリソースを活用するのに役立ちます。ジョブの優先順位とコロケーション機能を構成して、オンラインサービスが Spark ジョブの影響を受けないようにすることができます。
背景情報
複数クラスターでアイドルリソースを使用して Spark ジョブをスケジュールおよび分散するには、次の機能が必要です。
ACK One Fleet インスタンスによって提供される複数クラスター Spark ジョブのスケジューリングと分散 (アイドルリソース対応スケジューリングを含む)。
ACK Spark Operator によってサポートされる Koordinator のコロケーション。
ACK Koordinator の単一クラスター コロケーション。
手順:
複数の ACK クラスターを ACK Fleet インスタンスに関連付け、関連付けられた各クラスターに ACK Koordinator と ACK Spark Operator をデプロイします。
Fleet インスタンスの
SparkApplicationとPropagationPolicyを作成します。Fleet インスタンスの複数クラスタースケジューリングコンポーネント (グローバルスケジューラ) は、関連付けられた各サブクラスターの残りのリソースに基づいて、Spark ジョブのリソースリクエストを照合します。
Kubernetes バージョンが 1.28 以降のサブクラスターの場合、Fleet インスタンスはリソースプリエンプションをサポートして Spark ジョブのスケジューリングの成功率を向上させます。
Fleet インスタンスがジョブをスケジュールした後、
SparkApplicationはスケジュールされ、関連付けられたクラスターに分散されます。関連付けられたクラスターでは、ACK Spark Operator が Spark ジョブの
driverとexecutorを実行します。同時に、Fleet インスタンスはサブクラスター内の Spark ジョブの実行ステータスを監視します。リソース不足のためにdriverを実行できない場合、Fleet インスタンスは一定期間後にSparkApplicationを再利用し、SparkApplication を十分なリソースを持つ他の関連付けられたクラスターに再スケジュールします。
前提条件
Fleet インスタンスは、Kubernetes バージョンが 1.18 以降の複数のクラスターに関連付けられています。詳細については、「関連付けられたクラスターを管理する」をご参照ください。
Resource Access Management (RAM) ポリシー AliyunAdcpFullAccess が RAM ユーザーにアタッチされています。詳細については、「RAM ユーザーに権限を付与する」をご参照ください。
AMC コマンドラインツールがインストールされています。
ack-koordinator (旧称 ack-slo-manager) がインストールされている 各関連クラスター内。
手順 1: 各関連クラスターに ack-koordinator をデプロイする
ACK コンソール にログインします。左側のナビゲーションウィンドウで、[クラスター] をクリックします。
[クラスター] ページで、変更するクラスターの名前をクリックします。左側のナビゲーションウィンドウで、 を選択します。
[ConfigMap] ページで、[YAML から作成] をクリックします。次の YAML テンプレートをテンプレート コードエディタ にコピーします。詳細については、「コロケーションの概要」をご参照ください。
# ack-slo-config ConfigMap の例。 apiVersion: v1 kind: ConfigMap metadata: name: ack-slo-config namespace: kube-system data: colocation-config: |- { "enable": true } resource-qos-config: |- { "clusterStrategy": { "lsClass": { "cpuQOS": { "enable": true }, "memoryQOS": { "enable": true }, "resctrlQOS": { "enable": true } }, "beClass": { "cpuQOS": { "enable": true }, "memoryQOS": { "enable": true }, "resctrlQOS": { "enable": true } } } } resource-threshold-config: |- { "clusterStrategy": { "enable": true } }
手順 2: (オプション) Fleet インスタンスに名前空間を作成し、関連付けられたクラスターに名前空間を配布する
関連付けられたクラスターに ack-spark-operator をインストールする前に、クラスターに Spark ジョブ専用のネームスペースがあることを確認してください。クラスターに Spark ジョブ専用のネームスペースがない場合、ack-spark-operator は正常にインストールされません。Fleet インスタンスに名前空間を作成し、ClusterPropagationPolicy を作成して、各関連クラスターに名前空間を配布できます。この例では、spark という名前の名前空間が作成され、各関連クラスターに配布されます。
Fleet インスタンスの kubeconfig ファイルを使用して Fleet インスタンスに接続し、次のコマンドを実行して spark という名前の名前空間を作成します。
kubectl create ns sparkClusterPropagationPolicyを作成して、特定のルールに一致する関連クラスターに名前空間を配布します。すべての関連クラスターに名前空間を配布する場合は、clusterAffinityパラメーターを空のままにします。apiVersion: policy.one.alibabacloud.com/v1alpha1 kind: ClusterPropagationPolicy metadata: name: ns-policy spec: resourceSelectors: - apiVersion: v1 kind: Namespace name: spark placement: clusterAffinity: clusterNames: - ${cluster1-id} # 関連付けられたクラスターの ID。 - ${cluster2-id} # 関連付けられたクラスターの ID。 replicaScheduling: replicaSchedulingType: Duplicated
手順 3: 関連付けられたクラスターに ack-spark-operator をインストールする
Spark ジョブを実行する関連クラスターに ack-spark-operator 2.1.2 以降をインストールします。
ACK コンソール にログインします。左側のナビゲーションウィンドウで、 を選択します。
[マーケットプレイス] ページで、[アプリカタログ] タブをクリックします。ack-spark-operator を見つけてクリックします。
[ack-spark-operator] ページで、[デプロイ] をクリックします。
[デプロイ] パネルで、クラスターと名前空間を選択し、[次へ] をクリックします。
[パラメーター] ステップで、[チャートバージョン] ドロップダウンリストから 2.1.2 を選択し、パラメーター コードエディタ の
jobNamespacesパラメーターにspark名前空間を追加して、[OK] をクリックします。重要spark.jobNamespacesパラメーターで、作成するSparkApplicationのnamespaceを指定する必要があります。次の表に、いくつかのパラメーターについて説明します。[ack-spark-operator] ページの [パラメーター] セクションでパラメーターの構成を見つけることができます。
パラメーター
説明
例
controller.replicasコントローラーレプリカの数。
デフォルト値: 1。
webhook.replicasWebhook レプリカの数。
デフォルト値: 1。
spark.jobNamespacesSpark ジョブを実行できる名前空間。このパラメーターを空のままにすると、すべての名前空間で Spark ジョブを実行できます。複数の名前空間はコンマ (,) で区切ります。
デフォルト値:
["default"]。[""]: すべての名前空間。["ns1","ns2","ns3"]: 1 つ以上の名前空間を指定します。
spark.serviceAccount.nameSpark ジョブは、
spark.jobNamespacesで指定された各名前空間に、spark-operator-sparkという名前の ServiceAccount と対応するロールベースアクセス制御 (RBAC) リソースを自動的に作成します。ServiceAccount のカスタム名を指定し、Spark ジョブを送信するときにカスタム名を指定できます。デフォルト値:
spark-operator-spark。
手順 4: Fleet インスタンスに PriorityClass を作成し、関連付けられたクラスターに PriorityClass を配布する
送信された Spark ジョブがオンラインサービスで使用されているリソースを占有したり、オンラインサービスに影響を与えたりしないようにするために、Spark ジョブにオンラインサービスよりも低い優先順位を割り当てることをお勧めします。
Fleet インスタンスの kubeconfig ファイルを使用して、優先度の低い
PriorityClassを作成し、valueを負の値に設定します。apiVersion: scheduling.k8s.io/v1 kind: PriorityClass metadata: name: low-priority value: -1000 globalDefault: false description: "Spark アプリケーションの優先度低"Fleet インスタンスに
ClusterPropagationPolicyを作成して、PriorityClassを指定されたクラスターに配布します。すべての関連クラスターにPriorityClassを配布する場合は、clusterAffinityパラメーターを削除できます。apiVersion: policy.one.alibabacloud.com/v1alpha1 kind: ClusterPropagationPolicy metadata: name: priority-policy spec: preserveResourcesOnDeletion: false resourceSelectors: - apiVersion: scheduling.k8s.io/v1 kind: PriorityClass placement: clusterAffinity: clusterNames: - ${cluster1-id} # クラスターの ID。 - ${cluster2-id} # クラスターの ID。 # labelSelector: # matchLabels: # key: value replicaScheduling: replicaSchedulingType: Duplicated
手順 5: Fleet インスタンスのコロケーションアーキテクチャで SparkApplication を送信する
次の YAML テンプレートを使用して
PropagationPolicyを作成します。PropagationPolicy は、sparkoperator.k8s.io/v1beta2API バージョンを使用するすべてのSparkApplicationsを、特定のルールに一致する関連クラスターに配布するために使用されます。すべての関連クラスターに SparkApplications を配布する場合は、clusterAffinityパラメーターを空のままにします。apiVersion: policy.one.alibabacloud.com/v1alpha1 kind: PropagationPolicy metadata: name: sparkapp-policy namespace: spark spec: preserveResourcesOnDeletion: false propagateDeps: true placement: clusterAffinity: clusterNames: - ${cluster1-id} # 関連付けられたクラスターの ID。 - ${cluster2-id} # 関連付けられたクラスターの ID。 # labelSelector: # matchLabels: # key: value replicaScheduling: replicaSchedulingType: Divided customSchedulingType: Gang resourceSelectors: - apiVersion: sparkoperator.k8s.io/v1beta2 kind: SparkApplicationFleet インスタンスに Spark ジョブを作成します。
SparkApplicationにsparkoperator.k8s.io/koordinator-colocation: "true"アノテーションを追加して、アイドルリソースを使用して SparkApplication のdriverポッドとexecutorポッドをスケジュールします。次の SparkApplication テンプレートは、アイドルリソースを使用してdriverポッドとexecutorポッドをスケジュールします。apiVersion: sparkoperator.k8s.io/v1beta2 kind: SparkApplication metadata: name: spark-pi namespace: spark spec: arguments: - "50000" driver: coreLimit: 1000m cores: 1 memory: 512m priorityClassName: low-priority template: metadata: annotations: sparkoperator.k8s.io/koordinator-colocation: "true" spec: containers: - name: spark-kubernetes-driver serviceAccount: spark-operator-spark executor: coreLimit: 1000m cores: 1 instances: 1 memory: 1g priorityClassName: low-priority template: metadata: annotations: sparkoperator.k8s.io/koordinator-colocation: "true" spec: containers: - name: spark-kubernetes-executor image: registry-cn-hangzhou.ack.aliyuncs.com/ack-demo/spark:3.5.4 mainApplicationFile: local:///opt/spark/examples/jars/spark-examples_2.12-3.5.4.jar mainClass: org.apache.spark.examples.SparkPi mode: cluster restartPolicy: type: Never sparkVersion: 3.5.4 type: Scala
手順 6: Spark ジョブのステータスを確認する
Fleet インスタンスで次のコマンドを実行して、Spark ジョブのステータスを表示します。
kubectl get sparkapp -nspark予期される出力:
NAME STATUS ATTEMPTS START FINISH AGE spark-pi RUNNING 1 2025-03-05T11:19:43Z <no value> 48sFleet インスタンスで次のコマンドを実行して、Spark ジョブのスケジュール先となる関連クラスターをクエリします。
kubectl describe sparkapp spark-pi -nspark予期される出力:
Normal ScheduleBindingSucceed 2m29s default-scheduler バインディングは正常にスケジュールされました。結果: {c6xxxxx:0,[{driver 1} {executor 1}]}Fleet インスタンスで次のコマンドを実行して、リソース分散のステータスをクエリします。
kubectl get rb spark-pi-sparkapplication -nspark予期される出力:
NAME SCHEDULED FULLYAPPLIED OVERRIDDEN ALLAVAILABLE AGE spark-pi-sparkapplication True True True TrueFleet インスタンスで次のコマンドを実行して、関連クラスター内の Spark ジョブのステータスを確認します。
kubectl amc get sparkapp -M -nspark予期される出力:
NAME CLUSTER STATUS ATTEMPTS START FINISH AGE ADOPTION spark-pi c6xxxxxxx COMPLETED 1 2025-02-24T12:10:34Z 2025-02-24T12:11:20Z 61s YFleet インスタンスで次のコマンドを実行して、ポッドのステータスをクエリします。
kubectl amc get pod -M -nspark予期される出力:
NAME CLUSTER READY STATUS RESTARTS AGE spark-pi-3c0565956608ad6d-exec-1 c6xxxxxxx 1/1 Running 0 2m35s spark-pi-driver c6xxxxxxx 1/1 Running 0 2m50sFleet インスタンスで次のコマンドを実行して、関連クラスター内の Spark ジョブの詳細を表示します。
kubectl amc get sparkapp spark-pi -m ${member clusterid} -oyaml -nspark