secrets と鍵の一覧(どこに何を置くか)
置き場所を間違えると消える / 漏れるものだけを列挙します。
置き場所の使い分け
| 置き場所 |
対象 |
注意 |
Wrangler secret(wrangler secret put) |
API Worker が使う秘密 |
平文 vars はデプロイで消えます。必ず secret に入れる |
| Cloudflare Pages 環境変数 |
web のビルド時 env(VITE_*)と Pages Function の env |
Production / Preview で別々に設定する |
| GitHub Actions secrets |
CI がデプロイに使う資格情報 |
|
| Supabase |
DB 側の秘密は持たせない |
資格情報は暗号化して列に入れる(下記 KEK) |
API Worker(apps/api)
| 名前 |
用途 |
CLAUDE_API_KEY |
OCR(Claude) |
GOOGLE_VISION_API_KEY |
OCR(文字抽出) |
OPENAI_API_KEY |
OCR(モデル切替時) |
RESEND_API_KEY |
招待・通知メール(Resend) |
JWNET_CREDENTIAL_KEK |
JWNET 資格情報の暗号化鍵 |
JWNET_CREDENTIAL_KEK について
- JWNET の本番方式は標準EDI(ADR 0024)。本鍵(AES-256-GCM・AAD=
tenantId:env)は搬送方式に依らず流用するため標準EDI でも必要です。
- JWNET から交付される値ではありません。 我々が生成するランダムな鍵です。
- 生成:
openssl rand -base64 32(base64 で 32 byte)
- 登録:
wrangler secret put JWNET_CREDENTIAL_KEK(staging / production それぞれ)
- 未登録でも既存機能に影響はありませんが、JWNET の資格情報を保存しようとすると 503 に
なります(平文フォールバックはしません)。
- 暗号化は AES-256-GCM で、AAD に
tenantId:env を束ねています(他行への暗号文の移植を無効化)。
- 鍵のローテーションは現状できません(
key_version は 1 固定)。必要になった時点で
migration を伴う対応が必要です。
- この値を会話ログ・issue・PR 本文に貼らないでください。
Cloudflare Pages(web)
| 名前 |
Production |
Preview |
VITE_SUPABASE_URL |
/supabase |
/supabase |
SUPABASE_PROXY_TARGET |
prod プロジェクトの API URL |
dev プロジェクトの API URL |
VITE_SUPABASE_ANON_KEY |
prod の anon (publishable) key |
dev の anon key |
⚠️ VITE_SUPABASE_URL に Supabase の URL を直接入れないこと(ADR 0018)。
企業 DLP 配下の顧客でブラウザから *.supabase.co が遮断され「failed to fetch」になった
実障害があり、同一オリジンプロキシへ切り替えました。戻すと再発します。
GitHub Actions
| 名前 |
用途 |
CLOUDFLARE_API_TOKEN / CLOUDFLARE_ACCOUNT_ID |
Worker のデプロイ |
| Supabase の DB URL(dev / prod) |
supabase db push |
接続は常に Supavisor SESSION pooler :5432 を使います(db.*.supabase.co は IPv6-only で
Actions から到達できません)。
やってはいけないこと
- 本番の
service_role キーを会話・issue・PR に貼る
- 秘密を平文 vars(Wrangler の
[vars])に置く(デプロイで消えます)
- dev と prod を相互配線する(別プロジェクトとして完全に分離します)