Professional Cloud Developer試験では、単にアプリケーションを開発するだけでなく、セキュリティ・可用性・運用性を考慮したクラウドネイティブな設計が求められます。
本記事では、Cloud Storageの署名付きURLによる安全なファイル共有、GKEにおけるDeploymentとServiceを活用した高可用なサービス設計、さらにkubeconfigを利用した効率的なマルチクラスター運用について解説します。
これらはいずれも試験で頻出する実践的なテーマであり、実務でも重要なベストプラクティスです。アプリケーション開発から運用までを見据えたGoogle Cloudの設計パターンを学びながら、Professional Cloud Developer試験の理解を深めていきましょう。
今回も音声ファイルも挿入していますので、ブログの内容を音声でご確認いただけます。通勤中などにご利用いただければと思います。
是非、最後までご覧いただけると嬉しいです。
Cloud Storage署名付きURLで実現する安全な期間限定ファイル共有
外部ユーザーへファイルを安全に共有したい場合、Cloud Storage の IAM だけでは対応が難しいケースがあります。
特に、Google アカウントを持たない顧客やパートナーへ、一時的にファイルを公開したい場面では、署名付きURLが有効な選択肢となります。
署名付きURLを利用すれば、特定のオブジェクトに対して、指定した期間だけアクセス権を付与できます。さらに、ダウンロードだけでなく、アップロードや削除といった操作も細かく制御可能です。
本記事では、Cloud Storage の署名付きURLの仕組みから実装方法、セキュリティ上の注意点までを体系的に解説します。
⚠️ 署名付きURLはXML APIエンドポイント専用
署名付きURLはCloud StorageのXML APIエンドポイントを通じたアクセスにのみ使用できます。JSON APIエンドポイントでは機能しないため、実装時に注意してください。
1. 要件をどのように満たすか:設計のポイント
今回の3つの要件は、署名付きURLの機能を組み合わせることでスマートに解決できます。
要件①:許可されたPDFファイルにのみアクセスできる(個別認可)
ユーザーからのリクエストをアプリケーションサーバーで一度受け止め、データベース(Firestoreなど)のユーザー権限情報と照合します。アクセスが許可されている場合のみ、その特定のPDFファイルに対する署名付きURLをオンデマンドで生成してユーザーに返します。
要件②:24時間のみリクエスト可能(有効期限の設定)
V4署名付きURLの有効期限は最大7日間(168時間)まで設定できます。URLの生成時に「現在時刻から24時間」を指定することで、期限が切れたURLからのアクセスはCloud Storage 側で自動的に拒否(HTTP 403)されます。
要件③:Googleアカウントを持たないユーザーへの対応
URL自体に「一時的なアクセス許可証(暗号署名)」が埋め込まれているため、ユーザーはGoogleにログインすることなく、ブラウザでURLをクリックするだけでPDFを閲覧・操作できます。
2. 読み取り、書き込み、削除の個別制御
署名付きURLは、作成時に指定する HTTPメソッド によって、ユーザーができる操作を厳密に制限できます。24時間の制限内で、操作ごとに異なるURLを発行する設計にします。
| 操作 | 対応するHTTPメソッド | 挙動 |
|---|---|---|
| 読み取り(ダウンロード) | GET | ユーザーはPDFをブラウザで閲覧、またはダウンロードできます。 |
| 書き込み(アップロード・更新) | PUT | ユーザーは指定されたパスにPDFをアップロード(または上書き)できます。 |
| 削除 | DELETE | ユーザーはバケット内のそのPDFファイルを削除できます。 |
⚠️ GET用に作成された署名付きURLを使って、ファイルを削除(DELETE)することはできません。操作ごとに専用のURLを発行する必要があります。
3. 実装アプローチ:URLをどのように署名するか?
アプローチA:クライアントライブラリ(ヘルパー)の利用【強く推奨】
Google Cloudが提供する各種言語(Python, Node.js, Go, Javaなど)のクライアントライブラリには、URLを生成するためのヘルパー関数が用意されています。複雑な暗号署名の計算をライブラリが裏で代行してくれるため、最も安全かつ最小限の手間で実装できます。
<Python>
from google.cloud import storage
from google.auth import compute_engine
from google.auth.transport import requests
import datetime
def generate_download_url(bucket_name, blob_name, service_account_email):
# 認証情報を明示的に取得
credentials = compute_engine.IDTokenCredentials(
requests.Request(),
audience="",
service_account_email=service_account_email,
)
storage_client = storage.Client(credentials=credentials)
bucket = storage_client.bucket(bucket_name)
blob = bucket.blob(blob_name)
url = blob.generate_signed_url(
version="v4",
expiration=datetime.timedelta(hours=24),
method="GET",
service_account_email=service_account_email,
credentials=credentials,
)
return url
アプローチB:手動での署名作成
ライブラリが使用できない環境では、手動で署名を構築する必要があります。プロセスは以下の通り厳密に定義されています。
1. 正規リクエスト(Canonical Request)の作成:仕様の統一
HTTPメソッド、オブジェクトのパス、クエリパラメータ、ヘッダー情報を特定の規則(アルファベット順など)に従って並べ替え、1つの標準化されたテキスト文字列を作成し、そのSHA256ハッシュ値を計算します。
2. 署名対象文字列(String to Sign)の作成:メタデータの結合
使用する署名アルゴリズム(例:GOOG4-RSA-SHA256)、リクエストの生成日時、認証情報のスコープ、そしてステップ1で作成した正規リクエストのhexエンコードされたハッシュ値を結合します。
3. 署名の計算とURLの結合:暗号署名
サービスアカウントの秘密鍵(RSA)を用いて、ステップ2の「署名対象文字列」に対してRSA-SHA256署名を行います。得られた署名はhexエンコード(16進数文字列)し、最終的なURLのクエリパラメータ(X-Goog-Signature)として付加します。
⚠️ エンコードの注意
署名のエンコードはhex(16進数) です。Base64ではありません。IAM signBlob APIを使用する場合、レスポンスはBase64エンコードされているため、まずBase64デコードし、その後hexエンコードする必要があります。
4. セキュリティ・ベストプラクティス
時期的に重要な機密ファイルを扱うため、以下のセキュリティ対策を必ず適用してください。
- 最小権限のサービスアカウント
URLの署名を行うサービスアカウントには、バケット全体の管理者権限(storage.admin)を与えてはいけません。対象のバケットに対して、PDFの読み書き・削除に必要な権限(Storage オブジェクト閲覧者、Storage オブジェクト作成者など)のみを付与した専用のサービスアカウントを用意してください。 - アプリケーション側での二重チェック
署名付きURLを発行する前に、アプリケーションサーバー側で「本当にこのユーザーにこのファイルを見せてよいか」の認可チェック(セッション確認やDB照合)を必ず行ってください。URLを発行した後は、Cloud Storage 側での制御に移ります。
Cloud Storage署名付きURLで実現する安全な期間限定ファイル共有のまとめ
GCSの署名付きURLは、「認証されていない(Googleアカウントを持たない)ユーザー」に対して、「期間限定」かつ「特定の操作」のみを許可するための非常に強力な仕組みです。
- アプリケーションサーバーでユーザーのアクセス権をチェック。
- クライアントライブラリを使用して、24時間期限の GET / PUT / DELETE 別のURLをオンデマンド生成。
- 生成されたURLをユーザーに渡し、Googleログインなしでのセキュアなアクセスを実現。
この設計パターンを採用することで、セキュリティガバナンスを維持しながら、ユーザーフレンドリーなファイル共有機能を構築することができます。
DeploymentとServiceで実現する高可用性と安定したサービス間通信
Kubernetes(GKE)でマイクロサービスを運用する際には、高可用性と安定したサービス間通信の実現が重要な課題となります。
しかし、Podは障害やスケーリングによって頻繁に作成・削除されるため、IPアドレスを前提とした設計では運用が困難になります。
こうした課題を解決するために、Kubernetesでは Deployment と Service という中核リソースが提供されています。Deployment はアプリケーションの可用性と自己修復を担い、Service は変化するPod群に対して安定した通信経路を提供します。
さらに、クラスタ内DNSを活用することで、マイクロサービス同士を固定のサービス名で接続できるようになります。
本記事では、Kubernetesにおける標準的なマイクロサービス設計パターンと実装方法について解説します。
1. Deployment:指定したレプリカ数の維持と自己修復
マイクロサービスを構成するコンテナ(Pod)は、本質的に「使い捨て(エフェメラル)」な存在です。ノードの障害や予期せぬエラーによって、Podはいつでも消滅する可能性があります。これを管理し、システムの望ましい状態(Desired State)を維持するのが Deployment の役割です。
常に指定されたレプリカ数をキープする仕組み
Deploymentオブジェクトで spec.replicas: 3 と定義すると、Kubernetesの内部では ReplicaSet コントローラが自動的に生成されます。
ReplicaSetは常に稼働中のPod数を監視(リコンシリエーション・ループ)しており、以下のような挙動で可用性を担保します。
- Podが落ちた場合:即座に新しいPodをスケジュールして補填します(自己修復)。
- 負荷に応じて増減する場合:レプリカ数を変更するだけで、ダウンタイムなしにPodがスケールアウト/インします。
<他のワークロードコントローラとの違い>
| コントローラ名 | 主な用途・特徴 | マイクロサービスでの採用基準 |
|---|---|---|
| Deployment | ステートレスなアプリケーションの管理。ローリングアップデートが可能。 | 推奨(API、Webフロントエンド等) |
| StatefulSet | 永続データや、Podごとに固定の識別子が必要な場合。 | データベースや分散ストア等 |
| DaemonSet | クラスタ内のすべてのノードで必ず1つずつ動かしたい場合。 | ログコレクタ(Fluentd)、監視エージェント等 |
2. Service:動的なPod群を束ねる安定したエンドポイント
DeploymentによってPodの数は維持されますが、新しく作り直されたPodには毎回異なるIPアドレスが割り当てられます。
これでは、サービスAからサービスBを呼び出す際に、送信先のIPアドレスを特定できません。この「動的に変わるPodのIPアドレス」を背後に隠し、フロントに対して唯一の固定IPアドレスを提供するのが Service オブジェクトです。
仕組み:ラベルセレクタによる動的紐付け
Serviceは、Podの持つ「ラベル(Labels)」を基準に、自身がトラフィックを振り分ける対象(Endpoints)を決定します。
<Yamlファイル>
apiVersion: v1
kind: Service
metadata:
name: payment-service
namespace: default
spec:
selector:
app: payment-service
ports:
- protocol: TCP
port: 80
targetPort: 8080
type: ClusterIP
Deployment側で生成されるPodに app: payment-service というラベルが付与されていれば、Podが再起動してIPアドレスが変わっても、Serviceは自動的にそれを検知してルーティング対象を更新します。
3. クラスタ内DNS:一貫したDNS名でのサービス間アドレス指定
GKEクラスタ内には、標準でDNSサーバー(kube-dns / CoreDNS)が稼働しています。Kubernetesで新しいServiceを作成すると、このDNSサーバーに自動的にサービス名とClusterIPのペアが登録されます。
これにより、マイクロサービス同士はIPアドレスを意識することなく、安定したDNS名を使って通信することができます。
DNS名の名前解決ルール
<基本フォーマット>
<サービス名>.<名前空間名>.svc.cluster.local
パターンA:同じ名前空間内の通信
例えば、frontend 名前空間に属するPodから、同じ名前空間の auth-service を呼び出す場合。
- 指定するアドレス:
http://auth-service(ポート80の場合)またはhttp://auth-service:<ポート番号> - 同じ名前空間内であれば、サービス名だけで自動的に名前解決が可能です。Serviceのポートが80(HTTP標準)であればポート番号の指定も省略できます。
パターンB:異なる名前空間をまたぐ通信
frontend 名前空間のPodから、payment 名前空間にある order-service を呼び出す場合。
- 指定するアドレス:
http://order-service.payment.svc.cluster.local:<ポート番号> - 異なる名前空間であっても、FQDN(完全修飾ドメイン名)を指定することでお互いを確実に呼び出すことができます。
4. 実践的なマニフェスト構成例
以下は、注文管理サービス(order-service)を3つのレプリカで維持しつつ、内部DNS名 order-service で公開するための標準的なマニフェスト(YAML)構成です。
<Yamlファイル>
apiVersion: apps/v1
kind: Deployment
metadata:
name: order-deployment
namespace: microservices
spec:
replicas: 3 # 常に3つのレプリカを維持
selector:
matchLabels:
app: order-service
template:
metadata:
labels:
app: order-service # ServiceがこのPodを見つけるためのラベル
spec:
containers:
- name: order-app
image: gcr.io/[PROJECT_ID]/order-service:v1.0
ports:
- containerPort: 8080
---
apiVersion: v1
kind: Service
metadata:
name: order-service # これがクラスタ内のDNS名になります
namespace: microservices
spec:
type: ClusterIP # クラスタ内部専用の公開モード(デフォルト)
selector:
app: order-service # 上記のDeployment(Pod)のラベルと一致させる
ports:
- protocol: TCP
port: 80 # サービスがクラスタ内で受けるポート
targetPort: 8080 # バックエンドのコンテナがリッスンしているポート
この2つのリソースを kubectl apply することで、同じクラスタ内の他のアプリケーションからは http://order-service(同一Namespace、ポート80の場合)でいつでも3つのPodにロードバランシングされた通信が行えるようになります。
DeploymentとServiceで実現する高可用性と安定したサービス間通信のまとめ
Deployment と Service の組み合わせは、Kubernetes におけるマイクロサービス運用の基本となる設計パターンです。
Deployment を利用することで、指定したレプリカ数の維持や自己修復、ローリングアップデートを自動化できます。一方、Service は動的に変化するPod群の前段に安定したエンドポイントを提供し、サービス間通信をシンプルにします。さらに、クラスタ内DNSにより、IPアドレスを意識することなくサービス名ベースで通信できるため、疎結合なアーキテクチャを実現できます。
運用時は、接続先をIPアドレスではなくService名として管理し、設定ファイルや環境変数から注入する設計が推奨されます。これらの仕組みを活用することで、高可用性・拡張性・保守性を兼ね備えたクラウドネイティブなシステム基盤を構築できます。
kubeconfig自動設定とマルチクラスター切り替え完全ガイド
GKEを利用する現場では、開発・検証・本番など複数のクラスターを同時に運用するケースが珍しくありません。しかし、接続設定や認証情報の管理を手作業で行うと、運用ミスや作業負荷の増加につながります。
そこで活用したいのが、gcloud container clusters get-credentials による kubeconfig の自動設定機能です。
本記事では、GKEクラスターへの接続設定を自動化する仕組みから、複数クラスターを安全に切り替える方法、さらに運用時のベストプラクティスまで詳しく解説します。効率的で安全なマルチクラスター運用の基礎を身につけましょう。
1. 魔法のコマンド:get-credentials の役割
GKEクラスターへの接続設定を自動化する鍵が、以下のコマンドです。
<gcloudコマンド>
gcloud container clusters get-credentials
このコマンドをローカル環境で実行すると、gcloud CLIが裏側で以下の作業をすべて自動で処理します。
- 対象GKEクラスターの接続先エンドポイント(IPアドレス)の取得
- クラスターの認証用CA証明書の取得
- ローカルの構成ファイル(デフォルトは
~/.kube/config)への「クラスター」「ユーザー」「コンテキスト」の自動追加
開発者は、面倒なパラメーター設定やセキュリティキーのコピペ作業から完全に解放されます。
2. 導入のステップ:環境構築から認証情報の取得まで
1. gcloud CLI と kubectl のインストール:ツールの準備
ローカル環境に gcloud CLI をインストールし、最新の状態にアップデートします。合わせて、Kubernetesの操作ツールである kubectl と、GKE専用の認証プラグインを導入します。
<gcloudコマンド>
# gcloudのアップデート
gcloud components update
# kubectl と GKE認証プラグインのインストール
gcloud components install kubectl gke-gcloud-auth-plugin
2. Google Cloud アカウントへのログイン:初期認証
gcloud CLIに対して、対象のGoogle CloudプロジェクトやGKEクラスターへのアクセス権(IAM権限)を持つアカウントでログインします。
<gcloudコマンド>
# gcloud CLIの認証
gcloud auth login
# アプリケーションデフォルト認証の設定(SDK・Terraform等との連携にも必要)
gcloud auth application-default login
gcloud config set project [PROJECT_ID]
💡application-default loginについてgcloud auth loginはgcloudコマンド自体の認証に使用されます。ローカル開発でTerraformやGoogle CloudのクライアントSDKも使用する場合は、gcloud auth application-default loginも合わせて実行しておくことを推奨します。GKEのkubectl操作自体はgcloud auth loginのみで問題ありません。
3. 認証情報のダウンロード(get-credentials):自動設定の実行
ターゲットとなるGKEクラスターの情報を指定してコマンドを実行します。クラスターが「リージョン」か「ゾーン」のどちらで構築されているかに応じてフラグを使い分けます。
<gcloudコマンド>
# ゾーンクラスターの場合
gcloud container clusters get-credentials [クラスター名] --zone [ゾーン名]
# リージョンクラスターの場合
gcloud container clusters get-credentials [クラスター名] --region [リージョン名]
コマンドが成功すると、kubeconfigに新しい設定が追記され、自動的にそのクラスターが「アクティブ(現在操作対象の環境)」に設定されます。そのまま kubectl get nodes などのコマンドを実行すれば、GKEクラスターの情報を取得できます。
3. 複数GKEクラスターを簡単に切り替える仕組み
実際の開発現場では、「開発環境(dev)」「検証環境(stg)」「本番環境(prod)」など、複数のクラスターを並行して操作することが多々あります。get-credentials は、このようなマルチクラスター環境で真価を発揮します。
コンテキスト(Context)による管理
get-credentials を実行するたびに、ローカルの kubeconfig ファイルには「コンテキスト」と呼ばれる接続セットが追加されます。コンテキストは、以下のようにGKE固有の規則に従って自動で名前が付けられます。
gke_[プロジェクトID]_[場所]_[クラスター名]
すでに設定済みのクラスターであれば、再度 get-credentials を実行し直す必要はありません。kubectl の機能を使って、ローカル側で一瞬で切り替えることができます。
コマンドによる環境の切り替え方法
① 現在登録されているクラスター(コンテキスト)の一覧を確認する
<kubectlコマンド>
kubectl config get-contexts
※現在アクティブな環境には左側に * マークがつきます。
② 操作対象のクラスターを切り替える
<kubectlコマンド>
kubectl config use-context gke_my-project_asia-northeast1_dev-cluster
このコマンドを実行した瞬間から、以降の kubectl コマンドはすべて dev-cluster に対して実行されるようになります。
4. 運用のベストプラクティスと注意点
gke-gcloud-auth-plugin の導入を忘れずに
現在のGKEでは、セキュリティ強化のため専用の認証プラグイン(gke-gcloud-auth-plugin)の利用が必須となっています。インストールされていない場合、kubectl 実行時に以下のような警告・エラーが表示されます。
WARNING: the gke-gcloud-auth-plugin, which is needed for continued use
of kubectl, was not found or is not executable.
このエラーが出た場合は、gcloud components install gke-gcloud-auth-plugin を実行してプラグインを導入してください。
プロンプト(ターミナル)へのコンテキスト表示
複数のクラスターを切り替えて使っていると、「開発環境のつもりでコマンドを打ったら本番環境だった」という重大な事故が起きるリスクがあります。kubectx や kube-ps1 といったオープンソースの拡張ツールを導入し、現在のコンテキスト名を常時ターミナルのプロンプトに表示させておくことを強く推奨します。
kubeconfig自動設定とマルチクラスター切り替え完全ガイドのまとめ
GKEの運用では、gcloud container clusters get-credentials を利用することで、クラスター接続に必要な認証情報や kubeconfig の設定を自動化できます。
取得した接続情報はコンテキストとして管理されるため、kubectl config use-context を使って複数クラスターを簡単に切り替えられます。また、gke-gcloud-auth-plugin の導入や、現在のコンテキストをターミナル上に表示する仕組みを取り入れることで、誤操作のリスクを大幅に低減できます。
これらの運用方法を習得することで、マルチクラスター環境でも安全かつ効率的なGKE管理を実現できるようになります。
まとめ
今回は、下記3点について説明しました。
- Cloud Storage署名付きURLで実現する安全な期間限定ファイル共有
- DeploymentとServiceで実現する高可用性と安定したサービス間通信
- kubeconfig自動設定とマルチクラスター切り替え完全ガイド
今回取り上げた3つのテーマは、クラウドネイティブなアプリケーション開発において重要な役割を担います。
Cloud Storageの署名付きURLを利用することで、Googleアカウントを持たないユーザーにも安全な期間限定アクセスを提供できます。
また、DeploymentとServiceを組み合わせることで、高可用性と安定したサービス間通信を実現でき、スケーラブルなマイクロサービス基盤を構築できます。
さらに、kubeconfigとコンテキスト管理を活用することで、複数のGKEクラスターを安全かつ効率的に運用できます。
これらの知識はProfessional Cloud Developer試験だけでなく、実際のGoogle Cloud開発・運用の現場でも欠かせないスキルとなるでしょう。
これからも、Macのシステムエンジニアとして、日々、習得した知識や経験を発信していきますので、是非、ブックマーク登録してくれると嬉しいです!
それでは、次回のブログで!
