このガイドでは、実装例として Ray Serve と Ray Operator アドオンを使用して、Google Kubernetes Engine(GKE)に Stable Diffusion モデルをデプロイして提供する方法の例を示します。
Ray と Ray Serve について
Ray は、AI / ML アプリケーション向けのオープンソースのスケーラブルなコンピューティング フレームワークです。Ray Serve は、分散環境でのモデルのスケーリングとサービングに使用される Ray のモデル サービング ライブラリです。詳細については、Ray ドキュメントの Ray Serve をご覧ください。
RayCluster リソースまたは RayService リソースを使用して、Ray Serve アプリケーションをデプロイできます。本番環境では、次の理由から RayService リソースを使用する必要があります。
- RayService アプリケーションのインプレース アップデート
- RayCluster リソースのゼロダウンタイム アップグレード
- 高可用性の Ray Serve アプリケーション
目標
このガイドは、生成 AI をご利用のお客様、GKE の新規または既存のユーザー、ML エンジニア、MLOps(DevOps)エンジニア、プラットフォーム管理者で、Ray を使用してモデルを提供するために Kubernetes コンテナ オーケストレーション機能を使用することに関心のある方を対象としています。
- GPU ノードプールを含む GKE クラスタを作成します。
- RayCluster カスタム リソースを使用して Ray クラスタを作成します。
- Ray Serve アプリケーションを実行します。
- RayService カスタム リソースをデプロイします。
費用
このドキュメントでは、課金対象である次のコンポーネントを使用します。 Google Cloud
料金計算ツールを使うと、予想使用量に基づいて費用の見積もりを生成できます。
このドキュメントに記載されているタスクの完了後、作成したリソースを削除すると、それ以上の請求は発生しません。詳細については、クリーンアップをご覧ください。
始める前に
Cloud Shell には、kubectl、gcloud CLI など、このチュートリアルに必要なソフトウェアがプリインストールされています。Cloud Shell を使用しない場合は、gcloud CLI をインストールする必要があります。
- アカウントにログインします。 Google Cloud を初めて使用する場合は、 アカウントを作成して、実際のシナリオで Google プロダクトのパフォーマンスを評価してください。 Google Cloud新規のお客様には、ワークロードの実行、テスト、デプロイができる無料クレジット $300 分を差し上げます。
-
Google Cloud CLI をインストールします。
-
外部 ID プロバイダ(IdP)を使用している場合は、まず連携 ID を使用して gcloud CLI にログインする必要があります。
-
gcloud CLI を初期化するには、次のコマンドを実行します:
gcloud init -
プロジェクトを作成または選択します Google Cloud 。
プロジェクトを選択または作成するために必要なロール
- プロジェクトを選択する: プロジェクトの選択には特定の IAM ロールは必要ありません。ロールが付与されているプロジェクトを選択できます。
-
プロジェクトを作成する: プロジェクトを作成するには、プロジェクト作成者ロール
(
roles/resourcemanager.projectCreator)が必要です。これにはresourcemanager.projects.create権限が含まれています。詳しくは、ロールを付与する方法をご覧ください。
-
プロジェクトを作成します。 Google Cloud
gcloud projects create PROJECT_ID
PROJECT_IDは、作成する Google Cloud プロジェクトの名前に置き換えます。 -
作成した Google Cloud プロジェクトを選択します。
gcloud config set project PROJECT_ID
PROJECT_IDは、 Google Cloud プロジェクトの名前に置き換えます。
GKE API を有効にします。
API を有効にするために必要なロール
API を有効にするには、 権限を含む Service Usage 管理者 IAM ロール(
roles/serviceusage.serviceUsageAdmin)が必要です。serviceusage.services.enable詳しくは、ロールを付与する方法をご覧ください。gcloud services enable container.googleapis.com
-
Google Cloud CLI をインストールします。
-
外部 ID プロバイダ(IdP)を使用している場合は、まず連携 ID を使用して gcloud CLI にログインする必要があります。
-
gcloud CLI を初期化するには、次のコマンドを実行します:
gcloud init -
プロジェクトを作成または選択します Google Cloud 。
プロジェクトを選択または作成するために必要なロール
- プロジェクトを選択する: プロジェクトの選択には特定の IAM ロールは必要ありません。ロールが付与されているプロジェクトを選択できます。
-
プロジェクトを作成する: プロジェクトを作成するには、プロジェクト作成者ロール
(
roles/resourcemanager.projectCreator)が必要です。これにはresourcemanager.projects.create権限が含まれています。詳しくは、ロールを付与する方法をご覧ください。
-
プロジェクトを作成します。 Google Cloud
gcloud projects create PROJECT_ID
PROJECT_IDは、作成する Google Cloud プロジェクトの名前に置き換えます。 -
作成した Google Cloud プロジェクトを選択します。
gcloud config set project PROJECT_ID
PROJECT_IDは、 Google Cloud プロジェクトの名前に置き換えます。
GKE API を有効にします。
API を有効にするために必要なロール
API を有効にするには、 権限を含む Service Usage 管理者 IAM ロール(
roles/serviceusage.serviceUsageAdmin)が必要です。serviceusage.services.enable詳しくは、ロールを付与する方法をご覧ください。gcloud services enable container.googleapis.com
-
ユーザー アカウントにロールを付与します。次の IAM ロールごとに次のコマンドを 1 回実行します。
roles/container.clusterAdmin, roles/container.admingcloud projects add-iam-policy-binding PROJECT_ID --member="user:USER_IDENTIFIER" --role=ROLE
次のように置き換えます。
PROJECT_ID: プロジェクト ID。USER_IDENTIFIER: ユーザー アカウントの識別子。例:myemail@example.com。ROLE: ユーザー アカウントに付与する IAM ロール。
環境を準備する
環境の準備手順は次のとおりです。
Google Cloud コンソールで
(Cloud Shell をアクティブにする)をクリックして、 Google Cloud コンソールから Cloud Shell セッションを起動します。 Google Cloud コンソールの下部ペインでセッションが起動します。
環境変数を設定します。
export PROJECT_ID=PROJECT_ID export CLUSTER_NAME=rayserve-cluster export COMPUTE_REGION=us-central1 export COMPUTE_ZONE=us-central1-c export CLUSTER_VERSION=CLUSTER_VERSION export TUTORIAL_HOME=`pwd`次のように置き換えます。
PROJECT_ID: Google Cloudのプロジェクト ID。CLUSTER_VERSION: 使用する GKE のバージョン。1.30.1以降にする必要があります。
GitHub リポジトリのクローンを作成します。
git clone https://github.com/GoogleCloudPlatform/kubernetes-engine-samples作業ディレクトリを変更します。
cd kubernetes-engine-samples/ai-ml/gke-ray/rayserve/stable-diffusionPython 仮想環境を作成します。
venv
python -m venv myenv && \ source myenv/bin/activateConda
次のコマンドを実行します。
conda create -c conda-forge python=3.9.19 -n myenv && \ conda activate myenv
serve runを使用して Serve アプリケーションをデプロイする場合、Ray はローカル クライアントの Python バージョンが Ray クラスタで使用されているバージョンと一致することを想定しています。rayproject/ray:2.37.0イメージは Python 3.9 を使用します。別のクライアント バージョンを実行している場合は、適切な Ray イメージを選択します。Serve アプリケーションの実行に必要な依存関係をインストールします。
pip install ray[serve]==2.37.0 pip install torch pip install requests
クラスタと GPU ノードプールを作成する
GPU ノードプールを含む Autopilot または Standard GKE クラスタを作成します。
Autopilot
Autopilot クラスタを作成します。
gcloud container clusters create-auto ${CLUSTER_NAME} \
--enable-ray-operator \
--cluster-version=${CLUSTER_VERSION} \
--location=${COMPUTE_REGION}
Standard
Standard クラスタを作成します。
gcloud container clusters create ${CLUSTER_NAME} \ --addons=RayOperator \ --cluster-version=${CLUSTER_VERSION} \ --machine-type=c3d-standard-8 \ --location=${COMPUTE_ZONE} \ --num-nodes=1GPU ノードプールを作成します。
gcloud container node-pools create gpu-pool \ --cluster=${CLUSTER_NAME} \ --machine-type=g2-standard-8 \ --location=${COMPUTE_ZONE} \ --num-nodes=1 \ --accelerator type=nvidia-l4,count=1,gpu-driver-version=latest
RayCluster リソースをデプロイする
RayCluster リソースをデプロイするには:
次のマニフェストを確認します。
このマニフェストでは、RayCluster リソースを記述しています。
マニフェストをクラスタに適用します。
kubectl apply -f ray-cluster.yamlRayCluster リソースの準備ができていることを確認します。
kubectl get raycluster出力は次のようになります。
NAME DESIRED WORKERS AVAILABLE WORKERS CPUS MEMORY GPUS STATUS AGE stable-diffusion-cluster 2 2 6 20Gi 0 ready 33sこの出力の
STATUS列のreadyは、RayCluster リソースの準備が完了したことを示します。
RayCluster リソースに接続する
RayCluster リソースに接続するには:
GKE が RayCluster Service を作成したことを確認します。
kubectl get svc stable-diffusion-cluster-head-svc出力は次のようになります。
NAME TYPE CLUSTER-IP EXTERNAL-IP PORT(S) AGE pytorch-mnist-cluster-head-svc ClusterIP 34.118.238.247 <none> 10001/TCP,8265/TCP,6379/TCP,8080/TCP 109sRay ヘッドへのポート転送セッションを確立します。
kubectl port-forward svc/stable-diffusion-cluster-head-svc 8265:8265 2>&1 >/dev/null & kubectl port-forward svc/stable-diffusion-cluster-head-svc 10001:10001 2>&1 >/dev/null &Ray クライアントが localhost を使用して Ray クラスタに接続できることを確認します。
ray list nodes --address http://localhost:8265出力は次のようになります。
======== List: 2024-06-19 15:15:15.707336 ======== Stats: ------------------------------ Total: 3 Table: ------------------------------ NODE_ID NODE_IP IS_HEAD_NODE STATE NODE_NAME RESOURCES_TOTAL LABELS 0 1d07447d7d124db641052a3443ed882f913510dbe866719ac36667d2 10.28.1.21 False ALIVE 10.28.1.21 CPU: 2.0 ray.io/node_id: 1d07447d7d124db641052a3443ed882f913510dbe866719ac36667d2 # Several lines of output omitted
Ray Serve アプリケーションを実行する
Ray Serve アプリケーションを実行するには:
Stable Diffusion Ray Serve アプリケーションを実行します。
serve run stable_diffusion:entrypoint --working-dir=. --runtime-env-json='{"pip": ["torch", "torchvision", "diffusers==0.12.1", "huggingface_hub==0.25.2", "transformers", "fastapi==0.113.0"], "excludes": ["myenv"]}' --address ray://localhost:10001出力は次のようになります。
2024-06-19 18:20:58,444 INFO scripts.py:499 -- Running import path: 'stable_diffusion:entrypoint'. 2024-06-19 18:20:59,730 INFO packaging.py:530 -- Creating a file package for local directory '.'. 2024-06-19 18:21:04,833 INFO handle.py:126 -- Created DeploymentHandle 'hyil6u9f' for Deployment(name='StableDiffusionV2', app='default'). 2024-06-19 18:21:04,834 INFO handle.py:126 -- Created DeploymentHandle 'xo25rl4k' for Deployment(name='StableDiffusionV2', app='default'). 2024-06-19 18:21:04,836 INFO handle.py:126 -- Created DeploymentHandle '57x9u4fp' for Deployment(name='APIIngress', app='default'). 2024-06-19 18:21:04,836 INFO handle.py:126 -- Created DeploymentHandle 'xr6kt85t' for Deployment(name='StableDiffusionV2', app='default'). 2024-06-19 18:21:04,836 INFO handle.py:126 -- Created DeploymentHandle 'g54qagbz' for Deployment(name='APIIngress', app='default'). 2024-06-19 18:21:19,139 INFO handle.py:126 -- Created DeploymentHandle 'iwuz00mv' for Deployment(name='APIIngress', app='default'). 2024-06-19 18:21:19,139 INFO api.py:583 -- Deployed app 'default' successfully.Ray Serve ポート(8000)へのポート転送セッションを確立します。
kubectl port-forward svc/stable-diffusion-cluster-head-svc 8000:8000 2>&1 >/dev/null &Python スクリプトを実行します。
python generate_image.pyこのスクリプトは、
output.pngという名前のファイルにイメージを生成します。イメージは次の例のようになります。
RayService をデプロイする
RayService カスタム リソースは、RayCluster リソースと Ray Serve アプリケーションのライフサイクルを管理します。
RayService の詳細については、Ray のドキュメントで Ray Serve アプリケーションをデプロイすると本番環境ガイドをご覧ください。
RayService リソースをデプロイする手順は次のとおりです。
次のマニフェストを確認します。
このマニフェストでは、RayService カスタム リソースを記述しています。
マニフェストをクラスタに適用します。
kubectl apply -f ray-service.yamlService が準備できたことを確認します。
kubectl get svc stable-diffusion-serve-svc出力は次のようになります。
NAME TYPE CLUSTER-IP EXTERNAL-IP PORT(S) AGE stable-diffusion-serve-svc ClusterIP 34.118.236.0 <none> 8000/TCP 31mRay Serve Service へのポート転送を構成します。
kubectl port-forward svc/stable-diffusion-serve-svc 8000:8000 2>&1 >/dev/null &前のセクションの Python スクリプトを実行します。
python generate_image.pyこのスクリプトにより、前のセクションで生成されたイメージと同様のイメージが生成されます。
Ray ワークロードをモニタリングする
RayJob の詳細を表示するには、コンソールの [Kubernetes Engine] > [AI/ML] > [ジョブ] セクションに移動します。 Google Cloud
コンソールで RayJob を表示する Google Cloud
クリーンアップ
プロジェクトを削除する
プロジェクトを削除します。 Google Cloud
gcloud projects delete PROJECT_ID
リソースを個別に削除する
クラスタを削除するには、次のように入力します。
gcloud container clusters delete ${CLUSTER_NAME}
次のステップ
- Google Cloud に関するリファレンス アーキテクチャ、図、ベスト プラクティスを確認する。Cloud アーキテクチャ センターをご覧ください。