今すぐローカル用だけ設定すれば、デプロイを待たずにテストできます。本番 URLは後から追加できます。
はじめに
Spring Boot + Nuxt 3 で構築したWebアプリに「Googleアカウント連携(OAuth)」を実装しました。
ローカル開発環境での設定から、AWS ECS + Terraform を使った本番デプロイまでの流れをまとめます。
この記事でわかること
- Google OAuth 2.0 の認証フロー
- Google Cloud Console へのアプリ登録手順
- ローカル開発環境(Spring Boot)での設定方法
- AWS Secrets Manager + Terraform を使った本番環境への設定
Google OAuth とは
ユーザーが「Googleでログイン」ボタンを押すと、パスワードをアプリに渡すことなく、Googleが身元を保証してくれる仕組みです。
フローのポイント
| 要素 | 役割 |
|---|---|
client_id |
アプリの識別子(公開してよい) |
client_secret |
アプリの秘密鍵(絶対に公開しない) |
redirect_uri |
Googleが認証後にコードを送る先のURL |
state |
CSRF防止用のランダム文字列(Redisに一時保存) |
code |
一時的な認証コード(トークンと交換する) |
1. Google Cloud Console へのアプリ登録
1-1. プロジェクト作成
Google Cloud Console にアクセスし、新規プロジェクトを作成します。

1-2. OAuth 同意画面の設定
APIとサービス → OAuth 同意画面 を開きます。
ユーザーの種類: 外部
アプリ名: (アプリの名前)
サポートメール: (メールアドレス)
注意: 本番公開前は「テスト」状態のままで、テストユーザーに自分のメールアドレスを追加しておきます。
1-3. OAuth クライアントIDの作成
APIとサービス → 認証情報 → 認証情報を作成 → OAuth クライアントID を選択。
アプリケーションの種類: ウェブアプリケーション
名前: (任意)
承認済みのリダイレクト URI:
ローカル用: http://localhost:8080/api/v1/auth/oauth/link/GOOGLE/callback
本番用: https://your-domain.com/api/v1/auth/oauth/link/GOOGLE/callback
ハマりポイント: リダイレクト URI にパスを含める場合、末尾に / を付けてはいけません。Googleに弾かれます。
作成後、クライアントID と クライアントシークレット が表示されます。この2つを次のステップで使います。
2. ローカル開発環境での設定(Spring Boot)
Spring Boot 側の実装
application.yml に以下のプロパティを定義します:
mannschaft:
google:
client-id: ${MANNSCHAFT_GOOGLE_CLIENT_ID:}
client-secret: ${MANNSCHAFT_GOOGLE_CLIENT_SECRET:}
link-redirect-uri: ${MANNSCHAFT_GOOGLE_LINK_REDIRECT_URI:http://localhost:8080/api/v1/auth/oauth/link/GOOGLE/callback}
Spring Boot の Relaxed Binding により、環境変数 MANNSCHAFT_GOOGLE_CLIENT_ID が自動的に mannschaft.google.client-id にマッピングされます。
環境変数の設定方法(3つのアプローチ)
A. application-local.yml に直書き(シンプルだが git に入れないよう注意)
# application-local.yml(.gitignore に追加すること)
mannschaft:
google:
client-id: "your-client-id"
client-secret: "your-client-secret"
B. ~/.profile に書く(WSL2 や Linux で常駐サーバーを動かす場合)
# ~/.profile に追記
export MANNSCHAFT_GOOGLE_CLIENT_ID="your-client-id"
export MANNSCHAFT_GOOGLE_CLIENT_SECRET="your-client-secret"
起動スクリプト(例: backend-loop.sh)内で ~/.profile を読み込むよう設定します:
#!/bin/bash
export HOME=/home/yourname
source ~/.profile 2>/dev/null || true # ← これが必要
cd /home/yourname/your-project/backend
while true; do
./gradlew bootRun
sleep 3
done
ハマりポイント: ~/.profile を設定しても起動スクリプトが source していなければ環境変数は読み込まれません。Spring Boot を直接起動する場合は問題ありませんが、ラッパースクリプト経由の場合は要確認です。
C. IntelliJ IDEA / VS Code の実行設定
IDE の実行設定(Run Configuration)に環境変数として直接入力できます。
設定確認
BE を起動して以下の URL を叩いたとき、Google の認証画面に遷移すれば成功です。
GET /api/v1/users/me/oauth/link/GOOGLE/auth-url
client_id が空のまま(設定が読み込まれていない)場合、Googleから以下のエラーが返ります:
エラー 400: invalid_request
Missing required parameter: client_id
3. 本番環境(AWS ECS)での設定
本番環境では、シークレットを安全に管理する必要があります。
client_secret をコードや設定ファイルに直書きすると、git 履歴に残るリスクがあります。
アーキテクチャ
なぜ Secrets Manager を使うのか
| 方法 | 問題点 |
|---|---|
environment ブロックに直書き |
Terraform の tfstate に 平文で残る |
| SSM Parameter Store(通常) | tfstate に平文が残る(SecureString でも) |
| Secrets Manager(採用) | 箱だけ Terraform で管理、値は別途投入 → tfstate に残らない |
Terraform の設定
① Secrets Manager の「箱」を作成
# modules/app/main.tf
resource "aws_secretsmanager_secret" "google_oauth" {
name = "${var.prefix}/google-oauth"
description = "Google OAuth credentials (client_id / client_secret)"
recovery_window_in_days = 7
}
aws_secretsmanager_secret_version は書きません。値は手動投入します。
② ECS タスク定義の secrets ブロックで参照
container_definitions = jsonencode([
{
name = "${var.prefix}-app"
image = "${aws_ecr_repository.backend.repository_url}:latest"
# 非秘密の環境変数
environment = [
{ name = "SPRING_PROFILES_ACTIVE", value = "prod" },
# ...
]
# 秘密はSecretsManagerから注入(平文をtfstateに残さない)
secrets = [
{
name = "MANNSCHAFT_GOOGLE_CLIENT_ID"
valueFrom = "${aws_secretsmanager_secret.google_oauth.arn}:client_id::"
},
{
name = "MANNSCHAFT_GOOGLE_CLIENT_SECRET"
valueFrom = "${aws_secretsmanager_secret.google_oauth.arn}:client_secret::"
}
]
}
])
デプロイ手順
Step 1: Google Console に本番用リダイレクト URI を追加
https://your-domain.com/api/v1/auth/oauth/link/GOOGLE/callback
Step 2: Terraform を apply
cd infra/terraform/envs/prod
terraform apply
Step 3: Secrets Manager に値を投入
aws secretsmanager put-secret-value \
--secret-id "your-prefix/google-oauth" \
--secret-string '{
"client_id": "your-client-id.apps.googleusercontent.com",
"client_secret": "your-client-secret"
}'
Step 4: ECS にデプロイ
タスクが起動するとき、ECS が Secrets Manager から値を自動的に取得して環境変数として渡します。Spring Boot には MANNSCHAFT_GOOGLE_CLIENT_ID / MANNSCHAFT_GOOGLE_CLIENT_SECRET として届きます。
まとめ
| 環境 | 設定方法 | シークレットの置き場所 |
|---|---|---|
| ローカル(IDE) | Run Configuration に直接入力 | ローカルのみ |
| ローカル(常駐サーバー) |
~/.profile に export |
ローカルのみ |
| 本番(AWS ECS) | Terraform で Secrets Manager を定義し ECS に注入 | AWS Secrets Manager |
やってしまいがちなミス集
-
client_secretをapplication.ymlに書いてコミット → git 履歴から漏洩します -
リダイレクト URI の末尾に
/を付ける → Google に弾かれます -
起動スクリプトが
~/.profileを読んでいない → 環境変数が Spring Boot に届きません -
Terraform に
aws_secretsmanager_secret_versionを書く → tfstate に平文が残ります - 本番用リダイレクト URI を Google Console に追加し忘れる → 本番でだけ OAuth が動きません






