

 **Bantu meningkatkan halaman ini ** 

Terjemahan disediakan oleh mesin penerjemah. Jika konten terjemahan yang diberikan bertentangan dengan versi bahasa Inggris aslinya, utamakan versi bahasa Inggris.

Untuk berkontribusi pada panduan pengguna ini, pilih GitHub ** tautan ** Edit halaman ini di yang terletak di panel kanan setiap halaman.

Terjemahan disediakan oleh mesin penerjemah. Jika konten terjemahan yang diberikan bertentangan dengan versi bahasa Inggris aslinya, utamakan versi bahasa Inggris.

# Identifikasi ambang metrik penskalaan untuk inferensi AI
<a name="ml-inference-autoscaling-thresholds"></a>

**Tip**  
 [Daftar ](https://events.eksworkshop.com/workshops/genai/) untuk AI/ML lokakarya Amazon EKS mendatang.

Bagian ini menunjukkan cara memuat uji server inferensi vLLM di Amazon EKS untuk mengidentifikasi kapan server tersebut menjadi jenuh. Gunakan hasil uji beban untuk mengonfigurasi kedalaman antrian dan ambang latensi untuk penskalaan otomatis horizontal di [Inferensi AI skala otomatis dengan HPA dan KEDA](ml-inference-autoscaling-hpa-keda.md) bagian selanjutnya.

Panduan ini menggunakan alat-alat berikut:
+  [k6 ](https://k6.io/) (Grafana k6) adalah alat pengujian beban sumber terbuka, dijalankan sebagai gambar `grafana/k6` wadah, yang mengirimkan permintaan inferensi ke replika pada tingkat permintaan terkontrol.
+  [Ministral-3-8B-Instruct-2512 model ](https://huggingface.co/mistralai/Ministral-3-8B-Instruct-2512) pada `g6e.4xlarge` contoh. Anda dapat menerapkan metodologi yang sama untuk model open source dan jenis GPU apa pun.

## Prasyarat
<a name="_prerequisites"></a>

Bagian ini dibangun di atas dua bagian sebelumnya dalam dokumentasi. Selesaikan keduanya sebelum Anda mulai:
+  **[Pengaturan Cluster ](ml-cluster-setup.md) ** menyediakan cluster EKS dengan GPU NodePool, tumpukan Pem [ antauan kube-prometheus- ](ml-cluster-setup-cli.md#cluster-setup-cli-monitoring) stack (Prometheus dan Grafana), dan bucket Amazon S3 untuk bobot model. [Model bobot ember S3](ml-cluster-setup-cli.md#cluster-setup-cli-model-bucket)
+  **[Load & Serve Model ](ml-inference-load-serve-model.md) ** s menyebarkan server inferensi vLLM dan membuat. [`vllm-inference-app` ServiceMonitor ](ml-inference-load-serve-model.md#ml-inference-load-serve-model-monitoring)

Konfirmasikan setiap item di bawah ini sebelum Anda mulai, dan lengkapi bagian yang ditautkan terlebih dahulu jika pemeriksaan gagal.

Jika Anda membuka terminal baru, tetapkan nama cluster dan wilayah yang Anda gunakan sebelumnya:

```
export CLUSTER_NAME=ai-eks-docs
export AWS_REGION=us-east-2
```

Tangkap nama bucket model Amazon S3 yang dibuat dalam [ langkah-langkah Peng ](ml-cluster-setup.md) aturan Cluster. Generator beban meneruskan nilai ini ke vLLm.

```
MODEL_BUCKET=$(aws s3api list-buckets \
  --query "Buckets[?starts_with(Name, '${CLUSTER_NAME}-models-')].Name | [0]" \
  --output text)
echo "Model bucket: ${MODEL_BUCKET}"
```

### Konfirmasikan tumpukan pemantauan sedang berjalan
<a name="_confirm_the_monitoring_stack_is_running"></a>

kube-prometheus-stack dari pengaturan [ Monit ](ml-cluster-setup-cli.md#cluster-setup-cli-monitoring) oring berjalan di namespace. `monitoring`

```
kubectl get pods -n monitoring
```

Polong Prometheus dan Grafana harus: `Running`

```
NAME                                              READY   STATUS    RESTARTS   AGE
kube-prometheus-stack-grafana-6f9c8b7d5c-2xk9p    3/3     Running   0          3h
kube-prometheus-stack-operator-7b8c9d6f4-q4m7n    1/1     Running   0          3h
prometheus-kube-prometheus-stack-prometheus-0     2/2     Running   0          3h
```

Jika ini hilang, selesaikan [ pengaturan Pem ](ml-cluster-setup-cli.md#cluster-setup-cli-monitoring) antauan sebelum melanjutkan.

### Konfirmasikan model vLLM sedang berjalan
<a name="_confirm_the_vllm_model_is_running"></a>

Pener `vllm-inference-app` apan dan `vllm-inference-svc` Layanan dari Model [ Load & Serve ](ml-inference-load-serve-model.md) berjalan di `default` namespace.

```
kubectl get deployment vllm-inference-app
```

Deployment harus dilaporkan `1/1` siap:

```
NAME                 READY   UP-TO-DATE   AVAILABLE   AGE
vllm-inference-app   1/1     1            1           3h
```

Jika Deployment hilang atau belum siap, selesaikan [ Load & Serve Model ](ml-inference-load-serve-model.md) s sebelum melanjutkan.

### Akses Grafana
<a name="_access_grafana"></a>

Anda menonton uji beban di dasbor vLLM yang telah dimuat sebelumnya, jadi pastikan penyeimbang beban Grafana yang Anda atur di bagian Akses Grafana dapat dijang [ kau. ](ml-cluster-setup-cli.md#cluster-setup-cli-grafana-loadbalancer) Cetak URL-nya:

```
echo "http://$(kubectl get ingress kube-prometheus-stack-grafana -n monitoring -o jsonpath='{.status.loadBalancer.ingress[0].hostname}')"
```

Buka URL di browser Anda dan masuk dengan nama pengguna `admin` dan kata sandi dari perintah berikut:

```
kubectl --namespace monitoring get secrets kube-prometheus-stack-grafana -o jsonpath="{.data.admin-password}" | base64 -d ; echo
```

### Konfirmasikan bahwa vLLM ada ServiceMonitor
<a name="_confirm_the_vllm_servicemonitor_exists"></a>

Yang dibuat dalam [ langkah ](ml-inference-load-serve-model.md#ml-inference-load-serve-model-monitoring) Monitor vLLM `vllm-inference-app` ServiceMonitor, berjalan di `default` namespace dan memberi tahu Prometheus di mana harus mengikis metrik vLLM.

```
kubectl get servicemonitor vllm-inference-app
```

Keluaran yang diharapkan

```
NAME                 AGE
vllm-inference-app   3h
```

Jika hilang, selesaikan langkah [ Monitor vLLM](ml-inference-load-serve-model.md#ml-inference-load-serve-model-monitoring).

## Langkah 1: Panaskan GPU
<a name="_step_1_warm_up_the_gpu"></a>

Meskipun model dimuat ke dalam memori GPU dan replika melaporkan Siap, permintaan pertama membutuhkan waktu lebih lama daripada yang berikutnya karena vLLM dan GPU selesai menginisialisasi pada kesimpulan pertama. vLLM menangkap grafik CUDA, mengkompilasi dan menyetel otomatis kernel GPU, dan mengalokasikan kumpulan memori cache KV, sementara GPU meningkatkan kecepatan clock dari idle ke rentang dorongannya.

Ini adalah biaya satu kali, jadi mengukur ambang batas sebelum pemanasan mencatat pekerjaan startup alih-alih penyajian kondisi mapan. Pemanasan berikut mengirimkan 100 permintaan berurutan untuk menyelesaikan inisialisasi ini, sehingga uji beban yang mengikuti mengukur kapasitas kondisi mapan.

Pertama, buat ConfigMap yang menampung skrip pemanasan (`warmup.js`). Skrip membaca model target dari variabel `MODEL` lingkungan, yang ditetapkan oleh Job dari `MODEL_BUCKET` nilai yang Anda tangkap sebelumnya:

**Example pemanasan k6 ConfigMap**  

```
cat << 'EOF' | kubectl apply -f -
apiVersion: v1
kind: ConfigMap
metadata:
  name: vllm-warmup-script
  namespace: default
data:
  warmup.js: |
    import http from 'k6/http';

    export default function () {
      const payload = JSON.stringify({
        model: __ENV.MODEL,
        prompt: 'Write a brief technical explanation about cloud computing concepts.',
        max_tokens: 100,
        temperature: 0.7,
      });
      const params = { headers: { 'Content-Type': 'application/json' }, timeout: '240s' };
      http.post('http://vllm-inference-svc:8000/v1/completions', payload, params);
    }
EOF
```

Kemudian jalankan Pekerjaan pemanasan. Satu klien mengirimkan 100 permintaan berurutan:

**Example Warm-up Pekerjaan**  

```
cat << EOF | kubectl apply -f -
apiVersion: batch/v1
kind: Job
metadata:
  name: vllm-warmup
  namespace: default
spec:
  backoffLimit: 0
  template:
    spec:
      restartPolicy: Never
      containers:
        - name: k6
          image: grafana/k6:latest
          env:
            - name: MODEL
              value: "s3://${MODEL_BUCKET}/Ministral-3-8B-Instruct-2512/"
          args: ["run", "--vus", "1", "--iterations", "100", "/scripts/warmup.js"]
          volumeMounts:
            - name: script
              mountPath: /scripts
      volumes:
        - name: script
          configMap:
            name: vllm-warmup-script
EOF
```

Tunggu hingga pemanasan selesai (butuh beberapa menit):

```
kubectl wait --for=condition=complete job/vllm-warmup --timeout=600s
```

Buka Grafana (buka nama host penyeimbang beban; lihat [ Akses Grafana ](ml-cluster-setup-cli.md#cluster-setup-cli-grafana-loadbalancer) untuk detailnya) dan arahkan ke Dasbor> Pemantauan GPU> Peng ** ujian Kinerja - Analisis Beban vLLM. ** **Panel Tingkat ** Permintaan vLLM menunjukkan ledakan lalu lintas pemanasan. **Panel ** VllM Average Latency menunjukkan bahwa permintaan pertama lebih lambat, yang merupakan biaya pemanasan GPU satu kali.

 **Dasbor vLLM menunjukkan efek pemanasan GPU pada latensi ** 

![Lalu lintas pemanasan singkat meledak dengan latensi permintaan pertama turun dari sekitar 2,6 detik ke garis dasar yang stabil saat GPU memanas.](https://docs.aws.amazon.com/id_id/eks/latest/userguide/images/ml-inference-autoscaling-thresholds-gpu-warm-up.png)


Kemudian hapus Pekerjaan Pemanasan:

```
kubectl delete job vllm-warmup
```

## Langkah 2: Kirim beban dengan meningkatkan tarif permintaan
<a name="_step_2_send_load_at_increasing_request_rates"></a>

Pada langkah ini, Anda menjalankan uji beban yang mengirimkan permintaan ke replika vLLM tunggal pada tingkat yang meningkat: 10, 20, 30, 40, 50, 60, dan 70 permintaan per detik. Ini mensimulasikan meningkatnya permintaan pengguna. Pengujian menggunakan k6 dalam model tingkat kedatangan konstan, di mana variabel `TARGET_RPS` lingkungan menetapkan tingkat permintaan target. Setiap kecepatan berjalan selama 60 detik untuk memungkinkan metrik stabil, diikuti dengan jeda 30 detik sebelum kenaikan tarif berikutnya.

Tujuan dari pengujian ini adalah untuk mengidentifikasi titik saturasi, yang merupakan tingkat permintaan di mana replika tunggal tidak dapat lagi mengikuti permintaan yang masuk. Anda memantau kedalaman antrian (`vllm:num_requests_waiting`) dan latensi ujung ke ujung (`vllm:e2e_request_latency_seconds`). Meningkatkan kedalaman antrian dan latensi menunjukkan bahwa replika mendekati saturasi.

Pertama, buat ConfigMap yang memegang skrip uji beban k6 (). `script.js` Skrip membaca model target dari variabel `MODEL` lingkungan, yang ditetapkan setiap pod dari `MODEL_BUCKET` nilai yang Anda tangkap sebelumnya:

**Example uji beban k6 ConfigMap**  

```
cat << 'EOF' | kubectl apply -f -
apiVersion: v1
kind: ConfigMap
metadata:
  name: vllm-loadtest-script
  namespace: default
data:
  script.js: |
    import http from 'k6/http';

    // Dictionary of 10-letter words for variation (prevents prompt caching)
    const words = [
      'revolution', 'technology', 'javascript', 'kubernetes', 'basketball',
      'strawberry', 'watermelon', 'blackberry', 'throughout', 'background',
      'playground', 'understand', 'everything', 'protection', 'complexity'
    ];

    export const options = {
      noConnectionReuse: true,
      scenarios: {
        constant_request_rate: {
          executor: 'constant-arrival-rate',
          rate: __ENV.TARGET_RPS || 10,  // Overridden by TARGET_RPS env var
          timeUnit: '1s',
          duration: __ENV.DURATION || '60s',  // Overridden by DURATION env var
          preAllocatedVUs: 50,
          maxVUs: 500,
        },
      },
    };

    export default function () {
      const randomWord = words[Math.floor(Math.random() * words.length)];
      const payload = JSON.stringify({
        model: __ENV.MODEL,
        prompt: `Starting with the word "${randomWord}", write a brief technical explanation about cloud computing concepts. Cover containerization, orchestration, and scalability in about 80 words.`,
        max_tokens: 100,
        temperature: 0.7,
      });
      const params = { headers: { 'Content-Type': 'application/json' }, timeout: '240s' };
      http.post('http://vllm-inference-svc:8000/v1/completions', payload, params);
    }
EOF
```

Kemudian jalankan uji beban pada setiap tingkat permintaan. Loop berikut mengirimkan Pekerjaan terpisah untuk setiap tarif:

**Example Loop uji beban**  

```
for RPS in 10 20 30 40 50 60 70; do
  echo "=== Testing at ${RPS} req/s ==="
  cat << EOF | kubectl apply -f -
apiVersion: batch/v1
kind: Job
metadata:
  name: vllm-loadtest-${RPS}
  namespace: default
  labels:
    app: vllm-loadtest
spec:
  backoffLimit: 0
  template:
    metadata:
      labels:
        app: vllm-loadtest
    spec:
      restartPolicy: Never
      containers:
        - name: k6
          image: grafana/k6:latest
          env:
            - name: K6_PROMETHEUS_RW_SERVER_URL
              value: "http://kube-prometheus-stack-prometheus.monitoring.svc.cluster.local:9090/api/v1/write"
            - name: MODEL
              value: "s3://${MODEL_BUCKET}/Ministral-3-8B-Instruct-2512/"
            - name: TARGET_RPS
              value: "${RPS}"
            - name: DURATION
              value: "60s"
          args: ["run", "-o", "experimental-prometheus-rw", "/scripts/script.js"]
          volumeMounts:
            - name: script
              mountPath: /scripts
      volumes:
        - name: script
          configMap:
            name: vllm-loadtest-script
EOF
  kubectl wait --for=condition=complete job/vllm-loadtest-${RPS} --timeout=180s
  sleep 30
done
```

Tonton metrik di Grafana saat pengujian berjalan (lihat Langkah 3). Setiap tingkat membuat Job (`vllm-loadtest-10`through`vllm-loadtest-70`) sendiri, sehingga Anda dapat memeriksa proses apa pun dengan`kubectl get jobs`. Setelah selesai, hapus semua Load-test Jobs:

```
kubectl delete jobs -l app=vllm-loadtest
```

## Langkah 3: Mengukur metrik di bawah beban
<a name="_step_3_measure_metrics_under_load"></a>

Saat beban berjalan, perhatikan dua metrik yang mendorong penskalaan otomatis:
+  **Queue `vllm:num_requests_waiting` deep ** () — berapa banyak permintaan yang menunggu untuk diproses.
+  **latensi ujung ke ujung p95 ** (`vllm:e2e_request_latency_seconds`) — waktu respons persentil ke-95.

### Lihat metrik di Grafana
<a name="_view_the_metrics_in_grafana"></a>

Buka Grafana (buka nama host penyeimbang beban dan masuk sebagai`admin`; lihat [ Akses Grafana ](ml-cluster-setup-cli.md#cluster-setup-cli-grafana-loadbalancer) untuk detailnya) dan arahkan ke Dasbor> Pemantauan GPU> Peng ** ujian Kinerja - Analisis Beban VllM. ** Dasbor ini membaca dari Amazon Managed Service for Prometheus, sehingga panel dapat menunda status langsung hingga satu menit karena metrik ditulis dari jarak jauh dalam batch.

 **Pengujian Kinerja - Dasbor Analisis Beban vLLm selama uji beban ** 

![Enam panel yang menunjukkan CPU pod k6 dan penggunaan memori per tugas uji beban, tingkat permintaan vLLM naik secara bertahap, latensi rata-rata meningkat setelah replika jenuh, token yang dihasilkan per permintaan, dan kedalaman antrian melonjak dari nol pada saturasi.](https://docs.aws.amazon.com/id_id/eks/latest/userguide/images/ml-inference-autoscaling-thresholds-load-test.png)


Berdasarkan hasil uji beban, kedalaman antrian tetap mendekati nol melalui 50 permintaan bersamaan. Kemudian meningkat tajam pada 60 permintaan bersamaan, memuncak antara sekitar 150 dan 350 permintaan antri. Pada saat yang sama, latensi ujung ke ujung p95 naik dari baseline stabil sekitar 2,5 detik menjadi 6-10 detik. Perilaku ini menunjukkan timbulnya kelebihan beban berkelanjutan dan menyarankan bahwa penskalaan otomatis harus dimulai sebelum kedalaman antrian mencapai tingkat yang menyebabkan latensi mendekati 10 detik. Titik awal praktis adalah memicu penskalaan ketika kedalaman antrian melebihi 25 permintaan selama 30-60 detik. Sebagai sinyal sekunder, Anda juga dapat memicu penskalaan ketika latensi ujung ke ujung p95 melebihi 5 detik selama interval yang sama. Ini membantu memperhitungkan pola beban kerja di mana latensi meningkat sebelum kedalaman antrian menumpuk.

## Langkah 4: Pilih metrik dan ambang batas untuk diskalakan
<a name="_step_4_choose_the_metrics_and_thresholds_to_scale_on"></a>

Menggunakan metrik yang diamati pada titik saturasi, Anda menentukan ambang batas yang digunakan untuk mengonfigurasi penskalaan otomatis di bagian berikutnya.
+  **Queue `vllm:num_requests_waiting` deep ** () — jumlah permintaan yang menunggu untuk diproses setelah replika menjadi jenuh. Atur ambang batas di atas titik di mana antrian pertama tetap positif, sehingga lonjakan sementara tidak memicu penskalaan. Untuk uji beban di bagian ini, kedalaman antrian tetap mendekati nol melalui 50 permintaan bersamaan dan meningkat tajam menjadi sekitar 150-350 permintaan antrian pada 60 permintaan bersamaan. Titik awal praktis adalah memicu penskalaan ketika kedalaman antrian melebihi ** 25 permintaan ** selama 30-60 detik.
+  **Latensi ** (`vllm:e2e_request_latency_seconds`) — waktu respons ujung ke ujung saat replika mendekati batas kapasitasnya. Tetapkan ambang batas di bawah SLO latensi Anda, sehingga autoscaler berskala sebelum latensi yang terlihat pengguna menjadi tidak dapat diterima. Untuk uji beban di bagian ini, latensi ujung ke ujung p95 tetap stabil sekitar 2,5 detik dan meningkat menjadi 6-10 detik pada saturasi. Sebagai sinyal sekunder, titik awal praktis adalah memicu penskalaan ketika latensi ujung ke ujung p95 melebihi ** 5 detik ** selama 30-60 detik. Ini membantu memperhitungkan pola beban kerja di mana latensi meningkat sebelum kedalaman antrian menumpuk atau ketika latensi meningkat tanpa antrian.
+  **Scale-down**— tingkat di mana autoscaler menghapus replika setelah permintaan turun. Menurunkan lebih lambat daripada Anda menaikkan. Untuk contoh ini, kurangi hanya ketika kedalaman antrian `0` dan latensi ujung ke ujung p95 di bawah 3 detik selama 5 menit. Ini mencegah autoscaler menghapus replika selama jeda singkat dalam lalu lintas dan membantu menghindari osilasi.

Nilai-nilai ini memberikan titik awal untuk mengonfigurasi penskalaan otomatis di bagian berikutnya. Ulangi proses ini untuk model, jenis GPU, dan pola permintaan Anda sendiri untuk menentukan ambang batas yang sesuai untuk penerapan Anda.