Popular self-hosted media servers include Plex , Emby , and Jellyfin . This setup uses Jellyfin because it is free and open source, has no premium tier, and does not require an external account.
This guide uses Arch Linux package names and service-management commands. Other distributions provide different installation steps.
Installation
Install the server and web client packages:
sudo pacman -S jellyfin-server jellyfin-web
Service management
Inspect the Jellyfin service:
systemctl status jellyfin.service
Start or restart it for the current session:
sudo systemctl start jellyfin.service
sudo systemctl restart jellyfin.service
Stop it when it is not needed:
sudo systemctl stop jellyfin.service
To start Jellyfin immediately and automatically after future boots, enable the service instead:
sudo systemctl enable --now jellyfin.service
I start the service manually because I only use it while watching media.
Expose a media directory to Jellyfin
The service runs as the jellyfin user, which normally cannot traverse a private home directory. Avoid weakening the permissions on your entire home directory just to expose one media folder.
For example, bind-mount ~/media at /jellyfin:
sudo mkdir -p /jellyfin
sudo mount --bind "$HOME/media" /jellyfin
# Unmount it later with:
# sudo umount /jellyfin
Add /jellyfin as a library folder in the Jellyfin web client.
A bind mount avoids traversing the parent home directory, but it does not replace the permissions on the media itself. The jellyfin user still needs read access to files and read-and-execute access to directories. Test that access before scanning the library:
sudo -u jellyfin ls /jellyfin
This manual mount disappears after a reboot. Use a carefully reviewed /etc/fstab bind-mount entry if the library should always be available; I prefer to mount it only when needed.
Firewall configuration
Jellyfin's default HTTP port is 8096. If UFW is active and other devices on the local network need access, allow only the relevant subnet or device.
For a server at 192.168.1.110 on the 192.168.1.0/24 network:
sudo ufw allow from 192.168.1.0/24 to any port 8096 proto tcp
To allow only one device, such as a Chromecast at 192.168.1.66:
sudo ufw allow from 192.168.1.66 to any port 8096 proto tcp
Replace these example addresses with the actual subnet or device address on your network. Do not copy them without checking your network configuration.
Web client
After starting the service, open the local web client:
http://localhost:8096/
The initial setup flow creates users and media libraries. Devices on the allowed local network can connect through the server's LAN address, such as http://192.168.1.110:8096/.
Android apps
The official Jellyfin app can browse and stream the server's library from Android devices. Finamp is an alternative focused on music playback and offline downloads.
Experience in 2023
When I wrote these notes, Jellyfin worked well enough for my local library despite occasional interface bugs, subtitle overlap, and problems transcoding 4K content for an older Chromecast. Those observations describe my 2023 setup rather than the current state of the applications.