Migrating a Jellyfin Domain
Join me in my quest to migrate my Jellyfin installation to a new domain.
Let’s start off with the current situation. I used to run Jellyfin under some old domain that is mostly decommissioned by now. Jellyfin is literally the only thing that’s still running on there (as I could migrate Plex without the end-users even knowing). But to not inconvenience the folks that still have the old domain configured in their browser bookmarks or one of the thousand Jellyfin clients out there, I’ve kept it alive so far, with both domains pointing to the same reverse proxy and being forwarded to the same Jellyfin instance.
This has worked fine for years, but I am not happy with it. In the long run, I want to let the old domain expire, so I have to migrate the users away from there. This will never fully be done, and removing the domain will inconvenience folks, but slowly migrating off of the old domain will be a start.
That’s why today, I am testing how a bunch of Jellyfin clients handle an HTTP 308 redirect to a new domain.
Current Situation
The current situation may best be described by posting the Reverse Proxy (Apache httpd) VirtualHost config that’s running everything:
<VirtualHost *:80>
ServerName jellyfin.new.example.com
ServerAlias jellyfin.old.example.com
RewriteEngine On
RewriteCond %{HTTPS} off
RewriteRule ^ https://%{HTTP_HOST}%{REQUEST_URI}
</VirtualHost>
<VirtualHost *:443>
ServerName jellyfin.new.example.com
ServerAlias jellyfin.old.example.com
SSLEngine on
SSLCertificateFile /etc/pki/tls/certs/jellyfin.new.example.com.crt
SSLCertificateKeyFile /etc/pki/tls/private/jellyfin.new.example.com.key
SSLCertificateChainFile /etc/pki/tls/certs/jellyfin.new.example.com-fullchain.crt
ProxyPass "/" "http://localhost:8095/"
ProxyPassReverse "/" "http://localhost:8095/"
</VirtualHost>
The certificates are configured to contain both CNs for the old and the new domain. Also, obviously, I’ve redacted the actual domains.
The Plan
The plan is simple. Install as many Jellyfin clients as I can find, add an HTTP 308 to the config and see what happens. As I don’t have an Android available right now, I’ll only be testing iOS clients, but I imagine the behaviors should be similar. The new config looks like this:
<VirtualHost *:80>
ServerName jellyfin.new.example.com
RewriteEngine On
RewriteCond %{HTTPS} off
RewriteRule ^ https://%{HTTP_HOST}%{REQUEST_URI}
</VirtualHost>
<VirtualHost *:443>
ServerName jellyfin.new.example.com
SSLEngine on
SSLCertificateFile /etc/pki/tls/certs/jellyfin.new.example.com.crt
SSLCertificateKeyFile /etc/pki/tls/private/jellyfin.new.example.com.key
SSLCertificateChainFile /etc/pki/tls/certs/jellyfin.new.example.com-fullchain.crt
ProxyPass "/" "http://localhost:8095/"
ProxyPassReverse "/" "http://localhost:8095/"
</VirtualHost>
<VirtualHost *:80>
ServerName jellyfin.old.example.com
RewriteEngine On
RewriteCond %{HTTPS} off
RewriteRule ^ https://jellyfin.new.example.com%{REQUEST_URI} [R=302]
</VirtualHost>
<VirtualHost *:443>
ServerName jellyfin.old.example.com
SSLEngine on
SSLCertificateFile /etc/pki/tls/certs/jellyfin.new.example.com.crt
SSLCertificateKeyFile /etc/pki/tls/private/jellyfin.new.example.com.key
SSLCertificateChainFile /etc/pki/tls/certs/jellyfin.new.example.com-fullchain.crt
RewriteEngine On
RewriteRule ^ https://jellyfin.new.example.com%{REQUEST_URI} [R=308]
</VirtualHost>
The Results Are In
It’s a mixed bag. Obviously, for the web client, the user gets redirected to the new domain and, since no cookies are being sent, has to log in again. This was to be expected and I don’t think there is any way around this.
The apps however are where things get interesting. All of them internally follow the redirect, which is good so far, and all of them don’t send the login data to the new domain (also good). So all of them get an HTTP 401 back. This is where they diverge. While the official Jellyfin apps know how to handle this and re-displays the login page (best case scenario), every single third-party app I’ve tried just tells the user there was an authentication error, HTTP 401 error, or similar things. So all of them have to be reconfigured.
In the light of this I have checked my Jellyfin/reverse proxy logs to see how many people actually use a third-party app, and luckily it’s only two persons, both using the Infuse app. I’ve messaged them separately, but both know tech enough to change the domain themselves.
For the people using the official app, I expect to have to reset some passwords in the near future, but this is life as a homelab sysadmin after all.
Since things worked out less bad than I expected, I will leave the redirect in place and may be able to fully decommission the domain in the next decade.