Gunakan instans Fleet ACK One (Distributed Cloud Container Platform for Kubernetes) untuk menjadwalkan dan mendistribusikan pekerjaan Apache Spark di beberapa kluster. Pendekatan ini memungkinkan Anda menjalankan beban kerja batch Spark pada kapasitas kluster yang menganggur tanpa bersaing dengan beban kerja layanan online dalam penggunaan sumber daya.
Cara kerja
Instal komponen
ack-spark-operatorpada setiap sub-kluster tempat pekerjaan Spark akan dijalankan.Buat
SparkApplicationdanPropagationPolicypada instans Fleet.Global Scheduler (komponen penjadwalan multi-kluster dari instans Fleet) membandingkan permintaan sumber daya pekerjaan Spark terhadap kapasitas tersisa masing-masing sub-kluster terkait dan memilih target terbaik.
Untuk sub-kluster yang menjalankan Kubernetes 1.28 atau lebih baru, instans Fleet mendukung preoccupation sumber daya guna meningkatkan tingkat keberhasilan penjadwalan.
Instans Fleet mendistribusikan
SparkApplicationke sub-kluster yang dipilih.ACK Spark Operator di sub-kluster menjalankan Pod
driverdanexecutorSpark. Instans Fleet memantau status berjalan pekerjaan tersebut. Jikadrivergagal dijalankan karena sumber daya tidak mencukupi, instans Fleet menarik kembaliSparkApplicationsetelah timeout dan menjadwalkan ulang ke sub-kluster lain yang memiliki kapasitas mencukupi.
Prasyarat
Sebelum memulai, pastikan Anda telah:
Memiliki instans Fleet yang dikaitkan dengan dua kluster atau lebih yang menjalankan Kubernetes 1.18 atau lebih baru. Untuk informasi selengkapnya, lihat Mengelola kluster terkait.
Kebijakan Resource Access Management (RAM)
AliyunAdcpFullAccessdilampirkan pada RAM user Anda. Untuk informasi selengkapnya, lihat Memberikan izin kepada RAM user.Tool baris perintah AMC telah diinstal. Untuk informasi selengkapnya, lihat Menggunakan AMC command line.
Langkah 1: Instal ack-spark-operator pada sub-kluster
Instal komponen ack-spark-operator pada setiap sub-kluster tempat Anda ingin menjalankan pekerjaan Spark.
Masuk ke Konsol ACK. Di panel navigasi sebelah kiri, pilih Marketplace > Marketplace.
Pada halaman Marketplace, klik tab App Catalog, lalu cari dan klik ack-spark-operator.
Pada halaman ack-spark-operator, klik Deploy.
Pada panel Deploy, pilih kluster dan namespace, lalu klik Next.
Pada langkah Parameters, konfigurasikan parameter dan klik OK.
Tabel berikut menjelaskan parameter utama. Anda dapat melihat semua konfigurasi parameter di bagian Parameters pada halaman ack-spark-operator.
| Parameter | Deskripsi | Default |
|---|---|---|
controller.replicas | Jumlah replika controller. | 1 |
webhook.replicas | Jumlah replika webhook. | 1 |
spark.jobNamespaces | Namespace tempat pekerjaan Spark dapat dijalankan. Atur ke [""] untuk semua namespace, atau daftarkan namespace spesifik yang dipisahkan koma, contohnya ["ns1","ns2","ns3"]. | ["default"] |
spark.serviceAccount.name | Nama ServiceAccount yang dibuat secara otomatis di setiap namespace yang tercantum dalam spark.jobNamespaces. Operator juga membuat sumber daya kontrol akses berbasis peran (RBAC) yang sesuai. Tentukan nama kustom di sini jika Anda berencana merujuknya saat mengirimkan pekerjaan Spark. | spark-operator-spark |
Langkah 2: Buat PriorityClass dan distribusikan ke sub-kluster
Berikan prioritas rendah pada pekerjaan Spark agar tidak bersaing dengan beban kerja layanan online dalam penggunaan sumber daya.
Menggunakan file kubeconfig instans Fleet, buat
PriorityClassberprioritas rendah dengan nilaivaluenegatif:apiVersion: scheduling.k8s.io/v1 kind: PriorityClass metadata: name: low-priority value: -1000 globalDefault: false description: "Low priority for Spark applications"Buat
ClusterPropagationPolicypada instans Fleet untuk mendistribusikanPriorityClasske sub-kluster target. Untuk mendistribusikan ke semua kluster terkait, hapus bidangclusterAffinity.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 kluster Anda. - ${cluster2-id} # ID kluster Anda. # labelSelector: # matchLabels: # key: value replicaScheduling: replicaSchedulingType: Duplicated
Langkah 3: Kirim pekerjaan Spark pada instans Fleet
(Opsional) Buat dan distribusikan namespace ke sub-kluster
Jika namespace tempat SparkApplication akan dijalankan belum ada pada instans Fleet, buat terlebih dahulu. Namespace tersebut juga harus tercantum dalam parameter spark.jobNamespaces yang dikonfigurasi pada Langkah 1.
Buat namespace pada instans Fleet:
kubectl create ns xxxBuat
ClusterPropagationPolicyuntuk mendistribusikan namespace ke setiap sub-kluster:apiVersion: policy.one.alibabacloud.com/v1alpha1 kind: ClusterPropagationPolicy metadata: name: ns-policy spec: resourceSelectors: - apiVersion: v1 kind: Namespace name: xxx placement: clusterAffinity: clusterNames: - ${cluster1-id} # ID kluster Anda. - ${cluster2-id} # ID kluster Anda. replicaScheduling: replicaSchedulingType: Duplicated
Buat PropagationPolicy untuk SparkApplication
Buat PropagationPolicy pada instans Fleet. Kebijakan ini memberi tahu Global Scheduler untuk mendistribusikan semua sumber daya SparkApplication dari versi API sparkoperator.k8s.io/v1beta2 ke sub-kluster target menggunakan penjadwalan Gang.
apiVersion: policy.one.alibabacloud.com/v1alpha1
kind: PropagationPolicy
metadata:
name: sparkapp-policy
namespace: default
spec:
preserveResourcesOnDeletion: false
propagateDeps: true # Secara otomatis menyebarkan sumber daya dependen (seperti ServiceAccount yang dirujuk dalam spesifikasi driver) ke sub-kluster target.
placement:
clusterAffinity:
clusterNames:
- ${cluster1-id} # ID kluster Anda.
- ${cluster2-id} # ID kluster Anda.
# labelSelector:
# matchLabels:
# key: value
replicaScheduling:
replicaSchedulingType: Divided
customSchedulingType: Gang
resourceSelectors:
- apiVersion: sparkoperator.k8s.io/v1beta2
kind: SparkApplicationKirim SparkApplication
Buat SparkApplication pada instans Fleet. Atur priorityClassName ke PriorityClass yang dibuat pada Langkah 2 untuk driver dan executor.
Global Scheduler menggunakan nilai memory dan cores dalam spesifikasi driver dan executor sebagai permintaan sumber daya Kubernetes. Sistem ini membandingkan total sumber daya yang diminta terhadap kapasitas tersisa masing-masing sub-kluster untuk memilih kluster target. Sesuaikan nilai-nilai ini agar mencerminkan sumber daya aktual yang dibutuhkan pekerjaan Anda—nilai yang terlalu kecil dapat menyebabkan penjadwalan berhasil tetapi pekerjaan gagal saat runtime; nilai yang terlalu besar dapat mencegah penjadwalan jika tidak ada kluster yang memiliki kapasitas mencukupi.
Setelah Anda membuat SparkApplication, PropagationPolicy dari langkah sebelumnya mendistribusikannya ke sub-kluster yang dipilih.
apiVersion: sparkoperator.k8s.io/v1beta2
kind: SparkApplication
metadata:
name: spark-pi
namespace: default # Pastikan namespace ini tercantum dalam parameter spark.jobNamespaces.
spec:
type: Scala
mode: cluster
image: registry-cn-hangzhou.ack.aliyuncs.com/ack-demo/spark:3.5.4
imagePullPolicy: IfNotPresent
mainClass: org.apache.spark.examples.SparkPi
mainApplicationFile: local:///opt/spark/examples/jars/spark-examples_2.12-3.5.4.jar
arguments:
- "1000"
sparkVersion: 3.5.4
driver:
cores: 1
memory: 512m
priorityClassName: low-priority
serviceAccount: spark-operator-spark # Ganti dengan nama kustom yang Anda tentukan pada Langkah 1.
executor:
instances: 1
cores: 1
memory: 512m
priorityClassName: low-priority
restartPolicy:
type: NeverLangkah 4: Verifikasi pekerjaan Spark
Periksa status pekerjaan dan hasil penjadwalan
Jalankan perintah berikut pada instans Fleet untuk melihat status pekerjaan Spark:
kubectl get sparkappOutput yang diharapkan:
NAME STATUS ATTEMPTS START FINISH AGE spark-pi RUNNING 1 2025-02-24T12:10:34Z <no value> 11sJalankan perintah berikut untuk memastikan sub-kluster tujuan penjadwalan pekerjaan:
kubectl describe sparkapp spark-piOutput yang diharapkan:
Normal ScheduleBindingSucceed 2m29s default-scheduler Binding has been scheduled successfully. Result: {c6xxxxx:0,[{driver 1} {executor 1}]}Jalankan perintah berikut untuk melihat status pekerjaan di sub-kluster terkait:
kubectl amc get sparkapp -MOutput yang diharapkan:
NAME CLUSTER STATUS ATTEMPTS START FINISH AGE ADOPTION spark-pi c6xxxxxxx COMPLETED 1 2025-02-24T12:10:34Z 2025-02-24T12:11:20Z 61s YJalankan perintah berikut untuk menanyakan status Pod:
kubectl amc get pod -MOutput yang diharapkan:
NAME CLUSTER READY STATUS RESTARTS AGE spark-pi-driver c6xxxxxxx 0/1 Completed 0 68sJalankan perintah berikut untuk melihat detail lengkap pekerjaan Spark di sub-kluster:
kubectl amc get sparkapp spark-pi -m ${member clusterid} -oyaml
Pemecahan masalah
Jika pekerjaan tidak mencapai status COMPLETED, gunakan perintah berikut untuk mendiagnosis masalah.
Pekerjaan macet di `PENDING` atau tidak dijadwalkan:
Periksa event pada SparkApplication untuk melihat apakah Global Scheduler melaporkan kegagalan penjadwalan:
kubectl describe sparkapp spark-piCari event dengan alasan ScheduleBindingFailed atau serupa. Penyebab umum meliputi sumber daya tidak mencukupi di semua sub-kluster atau PriorityClass tidak ditemukan di kluster target.
Driver Pod tidak dimulai:
Periksa event Pod driver di sub-kluster:
kubectl amc get pod -M
kubectl amc describe pod spark-pi-driver -m ${member clusterid}Operator tidak berjalan di sub-kluster:
Konfirmasi bahwa ack-spark-operator sedang berjalan di sub-kluster:
kubectl amc get pod -n spark-operator -M