diff --git a/infra/ansible/roles/deploy/templates/Caddyfile.j2 b/infra/ansible/roles/deploy/templates/Caddyfile.j2 index e83c061..7d3f5b0 100644 --- a/infra/ansible/roles/deploy/templates/Caddyfile.j2 +++ b/infra/ansible/roles/deploy/templates/Caddyfile.j2 @@ -35,7 +35,31 @@ mqtt.{{ domain }} { # To move it to app.{{ domain }}, create the A record first, then change this # line — the reverse_proxy target stays the same either way. {{ domain }} { - reverse_proxy localhost:3000 { - header_up X-Forwarded-For {remote_host} + route { + # Firebase Auth's sign-in handler, served from our own origin. + # + # signInWithPopup opens {{ firebase_auth_handler_host | default('discord-radio-bot-461301.firebaseapp.com') }}/__/auth/handler and + # then reads back state the opener wrote. Chrome now partitions third-party + # storage, so when that handler is on a different site from the app the + # popup cannot see that state: it opens, fails, and closes instantly with no + # console or network trace. The handler page says so itself if you visit it + # directly ("storage-partitioned browser environment"). + # + # Proxying the handler through this domain makes it same-site, which is + # Google's documented fix. Host must be rewritten upstream or Firebase + # Hosting will not recognise the request. + # + # NEXT_PUBLIC_FIREBASE_AUTH_DOMAIN must be set to {{ domain }} in the CI + # build secrets to match, and {{ domain }} must be listed in the Firebase + # console's authorised domains. Changing only one of the three does nothing. + handle /__/auth/* { + reverse_proxy https://{{ firebase_auth_handler_host | default('discord-radio-bot-461301.firebaseapp.com') }} { + header_up Host {{ firebase_auth_handler_host | default('discord-radio-bot-461301.firebaseapp.com') }} + } + } + + reverse_proxy localhost:3000 { + header_up X-Forwarded-For {remote_host} + } } }