#!/bin/bash # generate-keys.sh — Generate a new JWT secret and matching Supabase API keys. # # This script generates a cryptographically secure JWT_SECRET and derives # ANON_KEY and SERVICE_ROLE_KEY JWTs from it. Run this script and update # the supabase secrets in your Wild Cloud instance before going to production. # # Usage: # wild app run supabase generate-keys [JWT_SECRET=] # # The script uses kubectl exec to run inside the cluster. Requires: # - python3 with hmac, hashlib, base64, json modules (standard library) # - The supabase namespace to exist # # After running, update secrets.yaml in your instance with the output values. set -e NAMESPACE="supabase" INSTANCE="${WILD_INSTANCE:-$(wild instance current 2>/dev/null || echo 'test-cloud')}" # Generate or use provided JWT secret if [ -n "$JWT_SECRET" ]; then SECRET="$JWT_SECRET" else SECRET=$(python3 -c "import secrets; print(secrets.token_urlsafe(48))") fi # Generate HS256 JWT tokens using python3 (no external deps needed) GENERATE_JWT=$(cat <<'PYEOF' import sys, hmac, hashlib, base64, json, time def b64url_encode(data): if isinstance(data, str): data = data.encode() return base64.urlsafe_b64encode(data).rstrip(b'=').decode() def make_jwt(secret, role): header = b64url_encode(json.dumps({"alg": "HS256", "typ": "JWT"}, separators=(',', ':'))) # Tokens valid for 10 years from now now = int(time.time()) exp = now + (10 * 365 * 24 * 3600) payload = b64url_encode(json.dumps({ "role": role, "iss": "supabase", "iat": now, "exp": exp }, separators=(',', ':'))) signing_input = f"{header}.{payload}" sig = hmac.new(secret.encode(), signing_input.encode(), hashlib.sha256).digest() signature = b64url_encode(sig) return f"{signing_input}.{signature}" secret = sys.argv[1] role = sys.argv[2] print(make_jwt(secret, role)) PYEOF ) ANON_KEY=$(python3 -c "$GENERATE_JWT" "$SECRET" "anon") SERVICE_ROLE_KEY=$(python3 -c "$GENERATE_JWT" "$SECRET" "service_role") echo "" echo "=== Supabase JWT Keys ===" echo "" echo "Add these to your secrets.yaml (or update via 'wild secrets set'):" echo "" echo " jwtSecret: |" echo " $SECRET" echo "" echo " anonKey: |" echo " $ANON_KEY" echo "" echo " serviceRoleKey: |" echo " $SERVICE_ROLE_KEY" echo "" echo "IMPORTANT: After updating secrets.yaml, redeploy Supabase:" echo " wild app deploy supabase" echo "" echo "The existing database will have its JWT secret updated on next pod restart."