Cloud Run サービスから GKE 上の Cloud Service Mesh ワークロードにトラフィックを転送する
このページでは、Istio API を使用してフルマネージド Envoy サイドカーを活用するために、Cloud Run サービスから GKE 上の Cloud Service Mesh ワークロードにネットワーク トラフィックを安全に転送する方法について説明します。
始める前に
以降のセクションでは、Cloud Service Mesh が有効になっている GKE クラスタがあることを前提としています。
GKE Service がデプロイされていない場合は、次のコマンドを使用してサンプル サービスをデプロイします。
cat <<EOF > /tmp/service.yaml
apiVersion: v1
kind: Service
metadata:
name: ads
spec:
ports:
- port: 9999
targetPort: 8000
selector:
run: ads
type: ClusterIP
---
apiVersion: apps/v1
kind: Deployment
metadata:
name: ads
spec:
replicas: 1
selector:
matchLabels:
run: ads
template:
metadata:
labels:
run: ads
spec:
containers:
- image: docker.io/waip/simple-http:v1.0.1
name: my-http2-svc
ports:
- protocol: TCP
containerPort: 8000
securityContext:
fsGroup: 1337
EOF
kubectl apply -f /tmp/service.yaml
VirtualService
ホストのカスタム ドメインを構成する
仮想サービスは、トラフィック ルーティング ルールを定義します。一致したトラフィックは、名前付き宛先サービスに送信されます。
新しいマネージド ゾーンを作成します。
gcloud dns managed-zones create ZONE_NAME \ --description="zone for service mesh routes" \ --dns-name=DNS_SUFFIX. \ --networks=default \ --visibility=private
ここで
- ZONE_NAME はゾーンの名前です(「prod」など)。
- DNS_SUFFIX は有効な DNS ホストです(「mesh.private」など)。
リソース レコードセットを作成します。
IP=10.0.0.1 gcloud dns record-sets create '*.'"DNS_SUFFIX." --type=A --zone="ZONE_NAME" \ --rrdatas=10.0.0.1 --ttl 3600
IP(RFC 1918 必須)が未使用であることを確認します。または、静的内部 IP を予約します。
外部 Cloud Run クライアントの
VirtualService
をエクスポートします。cat <<EOF > virtual-service.yaml apiVersion: networking.istio.io/v1alpha3 kind: VirtualService metadata: name: VIRTUAL_SERVICE_NAME namespace: NAMESPACE spec: hosts: - GKE_SERVICE_NAME.DNS_SUFFIX gateways: - external-mesh http: - route: - destination: host: GKE_SERVICE_NAME EOF kubectl apply -f virtual-service.yaml
ここで
- VIRTUAL_SERVICE_NAME は
VirtualService
の名前です。 - NAMESPACE は、提供されているサンプル サービスを使用する場合は
default
です。それ以外の場合は、NAMESPACE を Namespace の名前に置き換えます。 - GKE_SERVICE_NAME は、提供されているサンプル サービスを使用する場合は
ads
です。それ以外の場合は、GKE_SERVICE_NAME を GKE サービスの名前に置き換えます。
- VIRTUAL_SERVICE_NAME は
既存の VirtualService
にターゲットとして external-mesh
ゲートウェイを追加することは可能ですが、Kubernetes Service を外部 Cloud Run クライアントにエクスポートするには、明確な VirtualService
を確立する必要があります。別の VirtualService
を用意することで、既存の GKE クライアントに影響を与えることなく、エクスポートされたサービスとその構成を簡単に管理できるようになります。また、VirtualServices
の一部フィールドはメッシュ外部 VirtualServices
では無視されますが、GKE サービスでは想定どおりに機能します。そのため、VirtualServices
の管理とトラブルシューティングを個別に行うことに利点がある場合があります。
GKE クライアントが VirtualService
構成も受信するには、mesh
または mesh/default
ゲートウェイを追加する必要があります。
メッシュ外部 VirtualService
は、VirtualService
宛先の Kubernetes Service と同じ Namespace で定義する必要があります。
サービス メッシュに参加するように Cloud Run サービスを構成する
Cloud Run サービスをサービス メッシュに参加させる手順は次のとおりです。
Cloud Service Mesh GKE クラスタをバッキングするメッシュ ID を確認します。
MESH=$(kubectl get controlplanerevision --namespace istio-system -o json | jq -r '.items[0].metadata.annotations["mesh.cloud.google.com/external-mesh"]')
メッシュ ID を使用して Cloud Run サービスをデプロイし、クラスタの VPC ネットワークにも接続します。
gcloud alpha run deploy --mesh "$MESH" --network default \ mesh-svc --image=fortio/fortio \ --region=REGION --project=PROJECT_ID --no-allow-unauthenticated
Cloud Run サービスが GKE ワークロードにリクエストを送信できることを確認します。
TEST_SERVICE_URL=$(gcloud run services describe mesh-svc --region REGION --format="value(status.url)" --project=PROJECT_ID) curl -H "Authorization: Bearer $(gcloud auth print-identity-token)" "$TEST_SERVICE_URL/fortio/fetch/GKE_SERVICE_NAME.DNS_SUFFIX"
出力は有効な HTTP 200 レスポンスになります。
トラブルシューティング
このセクションでは、Cloud Service Mesh と Cloud Run の一般的なエラーのトラブルシューティング方法について説明します。
Cloud Run サイドカーログ
Envoy エラーは Cloud Logging に記録されます。
たとえば、Cloud Run サービス アカウントにメッシュ プロジェクトの trafficdirector クライアント ロールが付与されていない場合、次のようなエラーがログに記録されます。
StreamAggregatedResources gRPC config stream to trafficdirector.googleapis.com:443 closed: 7, Permission 'trafficdirector.networks.getConfigs' denied on resource '//trafficdirector.googleapis.com/projects/525300120045/networks/mesh:test-mesh/nodes/003fb3e0c8927482de85f052444d5e1cd4b3956e82b00f255fbea1e114e1c0208dbd6a19cc41694d2a271d1ab04b63ce7439492672de4499a92bb979853935b03d0ad0' (or it may not exist).
CSDS
trafficdirector クライアントの状態は CSDS を使用して取得できます。
gcloud alpha container fleet mesh debug proxy-status --membership=<CLUSTER_MEMBERSHIP> --location=<CLUSTER_LOCATION>
External Clients:
....