View a markdown version of this page

生成 AI 推論エンドポイントのベンチマーク - Amazon SageMaker AI

翻訳は機械翻訳により提供されています。提供された翻訳内容と英語版の間で齟齬、不一致または矛盾がある場合、英語版が優先します。

生成 AI 推論エンドポイントのベンチマーク

SageMaker AI ベンチマークサービスは、SageMaker AI エンドポイントでホストされている大規模言語モデル (LLMs) のパフォーマンスを測定します。NVIDIA AIPerf を使用してベンチマークを実行し、リクエストのレイテンシー、スループット、最初のトークンまでの時間、トークン間のレイテンシーなどのメトリクスを生成します。

前提条件

ベンチマークジョブを作成する前に、以下が必要です。

  • OpenAI 互換のチャット完了 API をサポートする LLM をホストしているInServiceステータスの SageMaker AI エンドポイント

  • ベンチマーク出力用の Amazon S3 バケット

  • エンドポイントと出力バケットへの SageMaker AI アクセスを許可する IAM 実行ロール

ステップ 1: ベンチマークジョブを作成する

ベンチマークジョブは、特定の SageMaker AI エンドポイントをターゲットとし、ワークロード設定を参照します。

Python (boto3)

response = client.create_ai_benchmark_job( AIBenchmarkJobName="my-benchmark-job", BenchmarkTarget={ "Endpoint": { "Identifier": "my-sagemaker-endpoint" } }, OutputConfig={ "S3OutputLocation": "s3://DOC-EXAMPLE-BUCKET/benchmark-results/" }, AIWorkloadConfigIdentifier="my-benchmark-config", RoleArn="arn:aws:iam::111122223333:role/ExampleRole", ) print(response["AIBenchmarkJobArn"])

AWS CLI

aws sagemaker create-ai-benchmark-job \ --ai-benchmark-job-name "my-benchmark-job" \ --benchmark-target '{"Endpoint": {"Identifier": "my-sagemaker-endpoint"}}' \ --output-config '{"S3OutputLocation": "s3://DOC-EXAMPLE-BUCKET/benchmark-results/"}' \ --ai-workload-config-identifier "my-benchmark-config" \ --role-arn "arn:aws:iam::111122223333:role/ExampleRole" \ --region us-west-2

エンドポイントが推論コンポーネントを介して複数のモデルをホストする場合は、 の InferenceComponentsパラメータで指定できますBenchmarkTarget

エンドポイントが VPC にある場合は、セキュリティグループ IDsやサブネットなどのVpcConfig設定で NetworkConfigパラメータを渡します。

SageMaker AI でフルマネージド MLflow を使用してベンチマーク結果を追跡するには、 に MlflowConfig オブジェクトを追加しますOutputConfig。詳細については、「MLflow を使用して推論の推奨事項とベンチマーク結果を追跡する」を参照してください。

推論コンポーネントのベンチマーク

エンドポイントがモデルを直接デプロイする代わりに推論コンポーネントを使用する場合は、 でベンチマークする推論コンポーネントを指定する必要がありますBenchmarkTarget。推論コンポーネントを指定すると、ベンチマークサービスはエンドポイントのデフォルトモデルではなく、それらの特定のコンポーネントにリクエストをルーティングします。

InferenceComponents リスト内の 1 つ以上の推論コンポーネント名または ARNs を渡します。

Python (boto3)

response = client.create_ai_benchmark_job( AIBenchmarkJobName="my-ic-benchmark", BenchmarkTarget={ "Endpoint": { "Identifier": "my-multi-model-endpoint", "InferenceComponents": [ {"Identifier": "my-inference-component-llama"} ] } }, OutputConfig={ "S3OutputLocation": "s3://DOC-EXAMPLE-BUCKET/benchmark-results/" }, AIWorkloadConfigIdentifier="my-benchmark-config", RoleArn="arn:aws:iam::111122223333:role/ExampleRole", )

AWS CLI

aws sagemaker create-ai-benchmark-job \ --ai-benchmark-job-name "my-ic-benchmark" \ --benchmark-target '{ "Endpoint": { "Identifier": "my-multi-model-endpoint", "InferenceComponents": [ {"Identifier": "my-inference-component-llama"} ] } }' \ --output-config '{"S3OutputLocation": "s3://DOC-EXAMPLE-BUCKET/benchmark-results/"}' \ --ai-workload-config-identifier "my-benchmark-config" \ --role-arn "arn:aws:iam::111122223333:role/ExampleRole" \ --region us-west-2
注記

エンドポイントが推論コンポーネント用に設定されている場合、ベンチマークターゲットInferenceComponentsで を指定しないと、ジョブは失敗し、モデルがエンドポイントに直接デプロイされていないことを示すエラーが表示されます。inference-component-basedエンドポイントをベンチマークするときは、常に InferenceComponentsパラメータを含めます。

マルチ LoRA エンドポイントのベンチマーク

複数の LoRA アダプターを提供するエンドポイントをベンチマークするには、各アダプターを の推論コンポーネントとして指定しますBenchmarkTarget。オプションで、model_selection_strategyワークロードパラメータを使用して、ベンチマークがアダプター間でリクエストを分散する方法を制御できます。戦略を指定しない場合、デフォルトは ですround_robin

まず、ワークロード設定を作成します。次の例には、オプションの model_selection_strategyパラメータが含まれています。

# Create a workload config for multi-LoRA benchmarking workload_spec = { "benchmark": {"type": "aiperf"}, "parameters": { "prompt_input_tokens_mean": 550, "output_tokens_mean": 150, "concurrency": 10, "streaming": True, "tokenizer": "meta-llama/Llama-3.2-1B", "model_selection_strategy": "round_robin" }, "secrets": { "hf_token": "arn:aws:secretsmanager:us-west-2:111122223333:secret:my-hf-token-AbCdEf" }, "tooling": {"api_standard": "openai"} } import json client.create_ai_workload_config( AIWorkloadConfigName="multi-lora-config", WorkloadSpec={"Inline": json.dumps(workload_spec)} )

次に、すべての LoRA アダプター推論コンポーネントをターゲットとするベンチマークジョブを作成します。

response = client.create_ai_benchmark_job( AIBenchmarkJobName="multi-lora-benchmark", BenchmarkTarget={ "Endpoint": { "Identifier": "my-lora-endpoint", "InferenceComponents": [ {"Identifier": "lora-adapter-customer-support"}, {"Identifier": "lora-adapter-code-generation"}, {"Identifier": "lora-adapter-summarization"} ] } }, OutputConfig={ "S3OutputLocation": "s3://DOC-EXAMPLE-BUCKET/multi-lora-results/" }, AIWorkloadConfigIdentifier="multi-lora-config", RoleArn="arn:aws:iam::111122223333:role/ExampleRole", )

model_selection_strategy パラメータはオプションであり、ベンチマークツールが指定された推論コンポーネント間でリクエストを分散する方法を決定します。次の値を指定できます。

  • round_robin (デフォルト) — 各アダプターはリクエストを順番に受け取ります。n 番目のリクエストは、 (n mod number-of-models) 番目のアダプターに送信されます。

  • random — 各リクエストはランダムにアダプターに均等に割り当てられます。

を指定しない場合model_selection_strategy、ベンチマークはround_robinデフォルトで を使用します。

合成イメージを使用したマルチモーダルエンドポイントのベンチマーク

ワークロード設定の一部として合成イメージを生成することで、ビジョン言語モデルをベンチマークできます。ベンチマークサービスは AIPerf を使用して、設定可能なディメンションと形式のイメージを作成し、base64 でエンコードされたペイロードとしてエンドポイントに送信します。

次の例では、合成イメージを使用してビジョン言語モデルをベンチマークするためのワークロード設定を作成します。

import json workload_spec = { "benchmark": {"type": "aiperf"}, "parameters": { "image_width_mean": 640, "image_height_mean": 480, "prompt_input_tokens_mean": 100, "output_tokens_mean": 150, "concurrency": 8, "request_count": 100, "streaming": True, "tokenizer": "meta-llama/Llama-3.2-1B" }, "secrets": { "hf_token": "arn:aws:secretsmanager:us-west-2:111122223333:secret:my-hf-token-AbCdEf" } } client.create_ai_workload_config( AIWorkloadConfigName="image-benchmark-config", WorkloadSpec={"Inline": json.dumps(workload_spec)} )

次のパラメータは合成イメージの生成を制御します。

パラメータ タイプ デフォルト 説明
image_width_mean float なし ピクセル単位の平均画像幅。
image_width_stddev float なし イメージ幅の標準偏差。リクエスト間でイメージディメンションを変更するように を設定します。
image_height_mean float なし ピクセル単位の平均画像の高さ。
image_height_stddev float なし 画像の高さの標準偏差。
image_batch_size int 1 リクエストあたりのイメージの数。
image_format string png イメージ形式 有効な値: png (lossless)、 jpeg (lossy, smaller files)、 random (randomly selects PNG or JPEG per image)。

可変サイズのイメージ

標準偏差パラメータを使用して、さまざまなディメンションのイメージを生成し、イメージサイズが異なる実際のワークロードをシミュレートします。

workload_spec = { "benchmark": {"type": "aiperf"}, "parameters": { "image_width_mean": 800, "image_width_stddev": 200, "image_height_mean": 600, "image_height_stddev": 150, "image_batch_size": 2, "concurrency": 4, "request_count": 50, "streaming": True, "tokenizer": "meta-llama/Llama-3.2-1B" } }

合成ビデオを使用したマルチモーダルエンドポイントのベンチマーク

ワークロード設定の一部として合成ビデオを生成することで、ビデオ入力を処理するマルチモーダルモデルをベンチマークできます。ベンチマークサービスは、AIPerf の合成ビデオ生成を使用して、設定可能な解像度、フレームレート、期間、エンコーディングのビデオを作成し、base64 でエンコードされたペイロードとしてエンドポイントに送信します。

注記

ビデオ生成はデフォルトで無効になっています。有効にするには、ワークロード設定video_heightvideo_widthと の両方を指定する必要があります。

次の例では、合成ビデオで 640 x 480 解像度のマルチモーダルモデルをベンチマークするためのワークロード設定を作成します。

import json workload_spec = { "benchmark": {"type": "aiperf"}, "parameters": { "video_width": 640, "video_height": 480, "video_fps": 4, "video_duration": 5.0, "output_tokens_mean": 150, "concurrency": 4, "request_count": 50, "streaming": True, "tokenizer": "meta-llama/Llama-3.2-1B" }, "secrets": { "hf_token": "arn:aws:secretsmanager:us-west-2:111122223333:secret:my-hf-token-AbCdEf" } } client.create_ai_workload_config( AIWorkloadConfigName="video-benchmark-config", WorkloadSpec={"Inline": json.dumps(workload_spec)} )

ビデオパラメータ

次のパラメータは合成ビデオの生成を制御します。

パラメータ タイプ デフォルト 説明
video_width int なし ピクセル単位のフレーム幅。ビデオ生成を有効にするvideo_heightには、 で設定する必要があります。
video_height int なし フレームの高さはピクセル単位です。ビデオ生成を有効にするvideo_widthには、 で設定する必要があります。
video_fps int 4 1 秒あたりのフレーム数。
video_duration float 5.0 クリップ期間は秒単位です。
video_batch_size int 1 リクエストあたりのビデオの数。
video_synth_type string moving_shapes 合成パターン。有効な値: moving_shapes (アニメーションジオメトリシェイプ)、 grid_clock (クロックアニメーション付きグリッド)、 noise (ランダムピクセルノイズ)。
video_format string ウェブ コンテナ形式。有効な値: webm
video_codec string libvpx-vp9 ビデオコーデック。サポートされている値: libvpx-vp9 (VP9、WebM)。
注記

ベンチマークサービスは、WebM 形式の VP9 エンコーディングのみをサポートします。

埋め込みオーディオトラック

ビデオとオーディオを一緒に処理するモデルの場合、生成されたビデオに合成オーディオトラックを埋め込むことができます。オーディオはデフォルトで無効になっています。(1モノ) または 2 (ステレオ) video_audio_num_channelsに設定して有効にします。

パラメータ タイプ デフォルト 説明
video_audio_num_channels int 0 0 = 無効、1 = モノラル、2 = ステレオ。
video_audio_sample_rate int 44100 Hz 単位のサンプルレート (8000~96000)。
video_audio_codec string 自動 オーディオコーデック。WebM libvorbisの場合は 、MP4 aacの場合は を自動選択します。aac、、libvorbisまたは で上書きできますlibopus
video_audio_depth int 16 サンプルあたりのビット深度 (8、16、24、または 32)。

ビデオベンチマークの例

低解像度動画の理解

workload_spec = { "benchmark": {"type": "aiperf"}, "parameters": { "video_width": 320, "video_height": 240, "video_fps": 2, "video_duration": 3.0, "video_synth_type": "moving_shapes", "concurrency": 4, "request_count": 50, "streaming": True, "tokenizer": "meta-llama/Llama-3.2-1B" } }

HD ビデオベンチマーク

workload_spec = { "benchmark": {"type": "aiperf"}, "parameters": { "video_width": 1920, "video_height": 1080, "video_fps": 8, "video_duration": 10.0, "concurrency": 2, "request_count": 20, "streaming": True, "tokenizer": "meta-llama/Llama-3.2-1B" } }

マルチモーダルモデルのオーディオ付きビデオ

workload_spec = { "benchmark": {"type": "aiperf"}, "parameters": { "video_width": 640, "video_height": 480, "video_fps": 4, "video_duration": 5.0, "video_audio_num_channels": 1, "video_audio_sample_rate": 16000, "concurrency": 4, "request_count": 50, "streaming": True, "tokenizer": "meta-llama/Llama-3.2-1B" } }

混合テキストと動画

ビデオとテキストプロンプトを組み合わせて、ビデオの質問への回答または字幕ワークロードを実行します。

workload_spec = { "benchmark": {"type": "aiperf"}, "parameters": { "video_width": 640, "video_height": 480, "video_fps": 4, "video_duration": 5.0, "prompt_input_tokens_mean": 100, "output_tokens_mean": 50, "concurrency": 8, "request_count": 100, "streaming": True, "tokenizer": "meta-llama/Llama-3.2-1B" } }

パフォーマンスに関する考慮事項

  • 解像度とフレームレートが高いほど、ビデオエンコーディング時間とペイロードサイズが増加します。高スループットテストには、低解像度 (320×240 または 640×480) を使用します。

  • WebM 形式の VP9 (libvpx-vp9) は、サポートされている唯一のコーデックであり、ペイロードのベンチマークに適切な圧縮を提供します。

  • オーディオは、ビデオストリームと比較して最小限のオーバーヘッドを追加します。音声に焦点を当てたワークロードには、16 kHz のモノラル (1) を使用します。

ステップ 2: ジョブのステータスをモニタリングする

終了状態になるまでジョブステータスをポーリングします。

Python (boto3)

import time while True: response = client.describe_ai_benchmark_job( AIBenchmarkJobName="my-benchmark-job" ) status = response["AIBenchmarkJobStatus"] print(f"Status: {status}") if status in ("Completed", "Failed", "Stopped"): break time.sleep(30) if status == "Completed": print(f"Results at: {response['OutputConfig']['S3OutputLocation']}") elif status == "Failed": print(f"Job failed: {response.get('FailureReason', 'unknown')}")

AWS CLI

aws sagemaker describe-ai-benchmark-job \ --ai-benchmark-job-name "my-benchmark-job" \ --region us-west-2

ステップ 3: ベンチマーク結果を確認する

ベンチマーク結果は、指定した Amazon S3 出力場所に書き込まれます。結果には、次の主要なメトリクスが含まれます。

request_throughput

1 秒あたりのリクエスト数。

request_latency

パーセンタイルの内訳を含むEnd-to-endのリクエストレイテンシー (P50、P90、P99)。

time_to_first_token

リクエストの送信から最初のトークンの受信までの時間。

inter_token_latency

連続する出力トークン間の時間。

output_token_throughput

1 秒あたりに生成された出力トークン。

各メトリクスには、統計概要として、平均、最小、最大、P50、P90、P99、標準偏差が含まれます。

カスタム形式のエンドポイントのベンチマーク

エンドポイントがカスタムリクエストまたはレスポンス形式 (DJL カスタムハンドラー、TensorRT-LLM ネイティブ形式、OpenAI チャット完了 API をサポートしていないその他のサービングフレームワークなど) を使用している場合は、Jinja2 テンプレートを使用してベンチマークを行い、エンドポイントのペイロードシェイプを定義できます。

ベンチマークサービスは、合成プロンプトまたはカスタムプロンプトを使用してリクエストごとにテンプレートをレンダリングし、ペイロードを SageMaker AI エンドポイントに転送します。また、JMESPath クエリを指定して、エンドポイントのレスポンスから生成されたテキストを抽出します。

ペイロードテンプレートを作成する

エンドポイントのリクエスト形式を Jinja2 テンプレートファイルとして定義します。テンプレートでは、次の変数を使用できます。

可変 説明
text 最初のテキストコンテンツ (合成またはデータセットから)。
texts すべてのテキストコンテンツのリスト。
model モデル名。
max_tokens 出力トークンの制限。
stream ストリーミングが有効になっているかどうか。

|tojson フィルターを使用して、文字列値を適切に JSON エスケープします。次の例は、ツール呼び出し形式の DJL エンドポイントのテンプレートを示しています。

{ "messages": [{"role": "user", "content": {{ text|tojson }}}], "tools": [ {"function": {"name": "Chit_Chat", "description": "casual conversation", "parameters": {"type": "object", "properties": {}}}} ], "max_tokens": {{ max_tokens }} }

テンプレートファイルを Amazon S3 にアップロードします (例: s3://DOC-EXAMPLE-BUCKET/templates/my_endpoint_template.jinja)。

ワークロード設定を作成する

テンプレートファイルを参照するワークロード設定を作成します。extra_inputs パラメータを使用して、テンプレートパスとレスポンス抽出クエリを指定します。テンプレートファイルをDatasetConfigチャネル経由でベンチマークコンテナに配信します。

import json TEMPLATE_LOCAL_PATH = "/opt/ml/input/data/template/my_endpoint_template.jinja" RESPONSE_FIELD = "generation_details.generations[0].content" workload_spec = { "benchmark": {"type": "aiperf"}, "parameters": { "extra_inputs": f"payload_template:{TEMPLATE_LOCAL_PATH} response_field:{RESPONSE_FIELD}", "tokenizer": "meta-llama/Llama-3.2-1B", # ... other benchmark parameters (concurrency, request_count, etc.) }, } response = client.create_ai_workload_config( AIWorkloadConfigName="custom-format-config", AIWorkloadConfigs={"WorkloadSpec": {"Inline": json.dumps(workload_spec)}}, DatasetConfig={ "InputDataConfig": [ { "ChannelName": "template", "DataSource": { "S3DataSource": { "S3Uri": "s3://DOC-EXAMPLE-BUCKET/templates/my_endpoint_template.jinja", } }, } ] }, )

は、ベンチマークコンテナ内でファイルが表示される場所ChannelNameを決定します。という名前のチャネルtemplateは、 でファイルを利用可能にします/opt/ml/input/data/template/<filename>

response_field 値は、エンドポイントのレスポンスから生成されたテキストを抽出する JMESPath クエリです。一般的なパターンは次のとおりです。

  • choices[0].message.content — OpenAI 形式

  • generation_details.generations[0].content — DJL 形式

  • output.text — シンプルなテキストレスポンス

を省略するとresponse_field、ベンチマークツールはレスポンス形式を自動検出します。

ベンチマークを実行する

エンドポイントをターゲットとするベンチマークジョブを作成します。サービスは のpayload_templateキーからテンプレートモードを自動的に検出extra_inputsし、適切なプロキシパスを介してリクエストをルーティングします。

response = client.create_ai_benchmark_job( AIBenchmarkJobName="custom-format-benchmark", BenchmarkTarget={"Endpoint": {"Identifier": "my-custom-endpoint"}}, OutputConfig={"S3OutputLocation": "s3://DOC-EXAMPLE-BUCKET/results/"}, AIWorkloadConfigIdentifier="custom-format-config", RoleArn="arn:aws:iam::111122223333:role/ExampleRole", )

考慮事項

  • テンプレートは、Amazon S3 を介してファイルとして配信する必要があります。JSON のカンマがパラメータパーサーと競合するため、extra_inputs文字列内のインライン JSON テンプレートはサポートされていません。

  • 単一の推論コンポーネントを持つエンドポイントがサポートされています。複数の推論コンポーネントを持つエンドポイントは、任意のペイロード形式から各リクエストをルーティングするコンポーネントをサービスが判断できないため、テンプレートモードではサポートされません。

  • ストリーミングエンドポイントと非ストリーミングエンドポイントの両方がサポートされています。ワークロードパラメータ"streaming": false"streaming": trueまたは を設定します。

ベンチマークプロンプトとレスポンスを関連付ける

ベンチマークジョブが完了すると、出力アーティファクトには、後処理のために結合できるリクエストごとの入出力データが含まれます。これにより、品質評価、安全監査、設定間のレスポンス比較、予期しないモデル動作のデバッグなどのユースケースが可能になります。

出力アーティファクトのベンチマーク

Amazon S3 出力場所のoutput.tar.gzアーカイブには、プロンプトとレスポンスの相関関係に関連する以下のファイルが含まれています。

inputs.json

生成された会話の完全な合成データセット。各レコードには、 session_idと完全なリクエストペイロード (メッセージ、max_tokens、モデル) があります。

outputs.json

エンドポイントに送信されたリクエストのリクエストごとのレスポンスメタデータ。各レコードには、モデルのレスポンステキスト、リクエストごとのレイテンシー、出力トークン数、および入力にマッピングconversation_idされる が含まれます。

入力を出力に結合する

conversation_idフィールドoutputs.jsonと の session_idフィールドを使用して、プロンプトとレスポンスを関連付けますinputs.json

import json # Load the artifacts extracted from output.tar.gz in your S3 output location with open("inputs.json") as f: inputs = json.load(f) with open("outputs.json") as f: outputs = json.load(f) # Build lookup tables and join inputs_by_id = {rec["session_id"]: rec for rec in inputs["data"]} outputs_by_id = {rec["conversation_id"]: rec for rec in outputs["data"]} matched_ids = set(inputs_by_id.keys()) & set(outputs_by_id.keys()) print(f"Matched: {len(matched_ids)} prompt-response pairs") # Display a correlated sample for sid in sorted(matched_ids)[:3]: in_rec = inputs_by_id[sid] out_rec = outputs_by_id[sid] prompt = in_rec["payloads"][0]["messages"][0]["content"][:100] response = out_rec.get("response_text", "")[:100] latency = out_rec["metrics"]["request_latency"] print(f"\n[{sid}] Latency: {latency:.0f}ms") print(f" Prompt: {prompt}...") print(f" Response: {response}...")

重要な注意事項

  • 結合キー。conversation_id の を使用してoutputs.jsonsession_idの と照合しますinputs.json。位置インデックスsession_numとして を使用しないでください。実行順序を表します。同時実行数が 1 より大きい場合の入力作成順序とは異なります。

  • すべての入力に出力があるわけではありません。inputs.json ファイルには、生成されたデータセットプールがすべて含まれています。request_count がプールサイズより小さい場合、会話のサブセットのみがエンドポイントに送信されます。一致しない入力は、生成されたが使用されていない会話です。

  • 出力スキーマ。の各レコードoutputs.jsonにはconversation_id、、response_textmetrics ( request_latency および を使用output_sequence_length)、タイミングフィールド (request_start_ns、) が含まれますrequest_end_ns

ベンチマークリソースを管理する

次のオペレーションを使用して、ベンチマークジョブとワークロード設定を管理します。

# List benchmark jobs response = client.list_ai_benchmark_jobs(MaxResults=10) for job in response["AIBenchmarkJobs"]: print(f"{job['AIBenchmarkJobName']} - {job['AIBenchmarkJobStatus']}") # Stop a running job client.stop_ai_benchmark_job( AIBenchmarkJobName="my-benchmark-job" ) # Delete a job (must be in a terminal state) client.delete_ai_benchmark_job( AIBenchmarkJobName="my-benchmark-job" ) # List workload configurations response = client.list_ai_workload_configs(MaxResults=10) for config in response["AIWorkloadConfigs"]: print(f"{config['AIWorkloadConfigName']} - {config['AIWorkloadConfigArn']}") # Delete a workload configuration client.delete_ai_workload_config( AIWorkloadConfigName="my-benchmark-config" )