Service Mesh(ASM)トラフィックスケジューリングスイートによって提供される QuotaSchedulingPolicy CustomResourceDefinition(CRD)は、指定されたリクエスト呼び出しクォータに達した後の優先度ベースのリクエストスケジューリングをサポートしています。システムで処理されているリクエストのレートが指定されたクォータを超えると、後続のリクエストはキューに入れられ、優先度の高いリクエストがより速く処理されます。このトピックでは、トラフィックスケジューリングスイートによって提供される QuotaSchedulingPolicy を使用してリクエスト呼び出しクォータ管理を実装する方法について説明します。
背景情報
QuotaSchedulingPolicy は、トークンバケットアルゴリズムを使用して、指定されたサービスを呼び出すリクエストのレートを制御し、レートが指定されたクォータを超えたときにリクエストをキューに入れます。 QuotaSchedulingPolicy は次の方法で機能します。
トークンバケットアルゴリズムを使用するレートリミッターは、リクエストレートを制限するために使用されます。レートリミッターのアルゴリズム実装の詳細については、「RateLimitingPolicy を使用してユーザー固有のスロットリングを実装する」の「背景情報」セクションをご参照ください。
リクエストレートがクォータ制限を超えると、後続のリクエストはキューに入れられ、前のリクエストが処理された後に宛先サービスに送信されます。これにより、リクエストレートは常に指定された値に維持されます。さらに、優先度の高いリクエストは、キューから取り出されて宛先サービスに送信される可能性が高くなります。
スロットリングシナリオとは異なり、QuotaSchedulingPolicy を使用する場合、リクエストレートがクォータ制限を超えても、QuotaSchedulingPolicy はリクエストを直接拒否するのではなく、優先度キューに入れます。 QuotaSchedulingPolicy は、リクエストレートがクォータ制限内にあることを保証しながら、優先度に基づいてリクエストをスケジュールします。
前提条件
Container Service for Kubernetes(ACK)マネージドクラスターが ASM インスタンスに追加されており、ASM インスタンスのバージョンが V1.21.6.95 以降であること。詳細については、「ASM インスタンスへのクラスターの追加」をご参照ください。
kubectl を使用して ACK クラスターに接続していること。詳細については、「クラスターの kubeconfig ファイルを取得し、kubectl を使用してクラスターに接続する」をご参照ください。
ASM トラフィックスケジューリングスイートが有効になっていること。詳細については、「ASM トラフィックスケジューリングスイートを有効にする」をご参照ください。
ACK クラスターのデフォルトの名前空間で、自動サイドカープロキシインジェクションが有効になっていること。詳細については、「グローバル名前空間の管理」をご参照ください。
ingressgateway という名前の ASMイングレスゲートウェイが作成され、ポート 80 が有効になっていること。詳細については、「イングレスゲートウェイの作成」をご参照ください。
HTTPBin アプリケーションがデプロイされ、ゲートウェイ経由でアクセスできること。詳細については、「HTTPBin アプリケーションのデプロイ」をご参照ください。
手順 1:QuotaSchedulingPolicy を作成する
kubectl を使用して ASM インスタンスに接続します。詳細については、「コントロールプレーンで kubectl を使用して Istio リソースにアクセスする」をご参照ください。
次の内容を含む quotaschedulingpolicy.yaml ファイルを作成します。
apiVersion: istio.alibabacloud.com/v1 kind: QuotaSchedulingPolicy metadata: name: quotascheduling namespace: istio-system spec: quota_scheduler: bucket_capacity: 10 fill_amount: 10 rate_limiter: interval: 1s scheduler: workloads: - label_matcher: match_labels: http.request.header.user_type: guest parameters: priority: 50.0 name: guest - label_matcher: match_labels: http.request.header.user_type: subscriber parameters: priority: 200.0 name: subscriber selectors: - service: httpbin.default.svc.cluster.local次の表に、いくつかのフィールドについて説明します。関連フィールドの詳細については、「QuotaSchedulingPolicy フィールドの説明」をご参照ください。
フィールド
説明
fill_amount
interval フィールドで指定された時間間隔内に追加されるトークンの数。この例では、値は 10 で、これは interval フィールドで指定された各間隔の後でトークンバケットに 10 個のトークンが追加されることを示します。
interval
トークンがトークンバケットに追加される間隔。この例では、値は 1s で、これはトークンバケットに 1 秒ごとに 10 個のトークンが追加されることを示します。
bucket_capacity
トークンバケットの最大トークン数。リクエストレートがトークンバケットの補充レートよりも低い場合、トークンバケット内のトークン数は最大数である
bucket_capacityに達するまで増加し続けます。bucket_capacityは、ある程度のバーストトラフィックを許可するために使用されます。この例では、値は 10 で、fill_amountフィールドの値と同じです。この場合、バーストトラフィックは許可されません。workloads
リクエストヘッダーの
user_typeに基づいて 2 種類のリクエストが定義されています:guestとsubscriber。guestタイプのリクエストの優先度は 50 で、subscriberタイプのリクエストの優先度は 200 です。selectors
スロットリングポリシーが適用されるサービス。この例では、httpbin.default.svc.cluster.local サービスが使用されており、これは httpbin.default.svc.cluster.local サービスで同時実行制限が実行されることを示します。
次のコマンドを実行して QuotaSchedulingPolicy を作成します。
kubectl apply -f quotaschedulingpolicy.yaml手順 2:QuotaSchedulingPolicy が有効になっていることを確認する
この例では、ストレステストツールである Fortio を使用します。詳細については、GitHub Web サイトの Fortio の「インストール」セクションをご参照ください。
2 つのターミナルを開き、次の 2 つのストレステストコマンドを同時に実行してテストを開始します。テスト全体を通して、2 つのターミナルが想定どおりに動作していることを確認してください。2 つのターミナルでのテストでは、10 個の同時リクエストがサービスに送信され、1 秒あたりのクエリ数(QPS)は 10,000 で、これはサービスが処理できる同時リクエスト数を大幅に超えています。
fortio load -c 10 -qps 10000 -H "user_type:guest" -t 30s -timeout 60s -a http://${ASMイングレスゲートウェイのIPアドレス}/status/201fortio load -c 10 -qps 10000 -H "user_type:subscriber" -t 30s -timeout 60s -a http://${ASMイングレスゲートウェイのIPアドレス}/status/202説明上記のコマンドの
${ASMイングレスゲートウェイのIPアドレス}を、ASMイングレスゲートウェイの IP アドレスに置き換えます。ASMイングレスゲートウェイの IP アドレスを取得する方法の詳細については、「Istio リソースを使用してトラフィックをサービスの異なるバージョンにルーティングする」トピックの手順 3 のサブステップ 1 をご参照ください。テスト 1 からの予期される出力:
... # target 50% 4.83333 # target 75% 5.20763 # target 90% 5.38203 # target 99% 5.48668 # target 99.9% 5.49714 Sockets used: 10 (for perfect keepalive, would be 10) Uniform: false, Jitter: false Code 201 : 70 (100.0 %) Response Header Sizes : count 70 avg 249.94286 +/- 0.2871 min 248 max 250 sum 17496 Response Body/Total Sizes : count 70 avg 249.94286 +/- 0.2871 min 248 max 250 sum 17496 All done 70 calls (plus 10 warmup) 4566.839 ms avg, 2.1 qps Successfully wrote 4693 bytes of Json data to 2024-07-26-232250_114_55_5_155_status_201_iZbp1cz9ur77robaiv085tZ.jsonテスト 2 からの予期される出力:
fortio load -c 10 -qps 10000 -H "user_type:subscriber" -t 30s -timeout 60s -a http://114.55.xx.xx/status/202 ... # target 50% 0.253333 # target 75% 1.875 # target 90% 4.26635 # target 99% 4.47301 # target 99.9% 4.49367 Sockets used: 10 (for perfect keepalive, would be 10) Uniform: false, Jitter: false Code 202 : 250 (100.0 %) Response Header Sizes : count 250 avg 250.264 +/- 0.4408 min 250 max 251 sum 62566 Response Body/Total Sizes : count 250 avg 250.264 +/- 0.4408 min 250 max 251 sum 62566 All done 250 calls (plus 10 warmup) 1226.657 ms avg, 8.0 qps Successfully wrote 4509 bytes of Json data to 2024-07-26-232250_114_55_5_155_status_202_iZbp1cz9ur77robaiv085tZ.json上記の出力は、テスト 2 の平均リクエストレイテンシがテスト 1 の約 1/4 であり、QPS がテスト 1 の約 4 倍であることを示しています。これは、以前に定義されたポリシーでは、subscriber タイプのリクエストの優先度が guest タイプのリクエストの 4 倍であるためです。2 つのテストで 30 秒以内に合計 320 個のリクエストが処理されます。ウォームアップに使用された 20 個のリクエストを除くと、サービスが受信したリクエストレートは 1 秒あたりちょうど 10 リクエストです。これは、サービスが受信したリクエストが常に指定された制限内にあることを証明しています。
関連情報
Grafana で QuotaSchedulingPolicy が有効になっているかどうかを確認できます。Grafana の Prometheus インスタンスが ASM トラフィックスケジューリングスイート で構成されていることを確認する必要があります。
次の内容を Grafana にインポートして、QuotaSchedulingPolicy のダッシュボードを作成できます。
ダッシュボードは次のとおりです。
