Migrating Plex from a VM to Docker

In a previous article, I described migrating Plex from one VM to another. In recently rebuilding my virtualization server, now called Cordelia, I decided against creating a VM for Plex. I have a few Docker containers running on it and decided to let Plex be another rather than constricting it to a set amount of memory and core count through a VM.

Migrating from a Plex VM to the Docker container is pretty straightforward. Just a few things to keep in mind. Along with creating a script you can run whenever there are server updates, since you can’t just… install a new version over the existing one like you could before.

Note: If you’re considering migrating Plex to Docker or running anything through Docker, make sure to install Docker CE from Docker’s repository. Don’t install the version of Docker from your distribution’s repositories. This will ensure you have the latest version – meaning also the latest security updates – and greatest compatibility.

I’ll also presume in this article that you know your way around a Linux setup, particularly the bash command line. You don’t need to be great with Docker containers, but some knowledge there will be helpful as well.

Backing up the server

First step is to back up the library on the original server. As root or an administrator, after stopping Plex Media Server:

cd /var/lib
sudo tar cvf plexmediaserver.tar plexmediaserver/
gzip plexmediaserver.tar

This should give you a .tar.gz backup of your Plex instance. I have a pretty large library – over 400 movies and specials, over 300 music albums, and 37 TV shows, most of which are complete series (and yes, I own physical copies or licenses to everything on it) – so my backup ended up being over 4GB. Compressed. Your mileage will vary.

My Plex server pulled from NFS shares on my NAS, so I made sure to also copy off the relevant fstab entries so I could restore them. Make note of however you have your media mounted to your Plex VM or physical server, the actual paths to the media. For example, on my Plex VM, I had the media mounted to these paths, meaning these paths are also what the Plex Docker container would be looking for:

  • /mnt/tv
  • /mnt/movies
  • /mnt/music

Transfer the backup file off the server somehow and shut it down.

Mount points

Here is where things get a little tricky. I think it best I just illustrate this using my directory mounts. To recap, these were the paths to the media I had with my Plex VM, meaning these are the paths the container will want:

  • /mnt/tv
  • /mnt/movies
  • /mnt/music

Paths work far different in containers compared to a virtual machine. When you install the Plex service on a virtual machine, it can see all paths it has permission to access.

Containers are a bit more isolated. This means you don’t have to worry about a container having access to more than you want it to, but it does mean you have to explicitly mount into the container whatever you want it to access.

There isn’t anything wrong, per se, with maintaining these mount points on the Docker host. It’s not like I’m going to have any other Docker containers using them. But I instead chose to consolidate those mount points under a subdirectory under /mnt on Cordelia:

  • /mnt/media/tv
  • /mnt/media/movies
  • /mnt/media/music

Why do this? It’s cleaner and means a simpler set of commands for creating the container.

Had I kept the same mount points as before – e.g., /mnt/tv, etc. – I would need a separate volume switch for each. Having everything under one subdirectory, though, means having just one volume switch that catches everything, as you’ll see in a little bit.

However you create the mount points, don’t forget to add them to your /etc/fstab file for your Docker host.

Your library

Now you’ll need another directory for your library files – i.e. the compressed archive you created above. Just find a suitable spot. You can even put it back at /var/lib/plexmediaserver if you want, following the restore commands in my previous Plex article. I have it on Cordelia’s NVMe drive.

Just remember that the archive you created above will create a directory called plexmediaserver when you extract it. And, obviously (hopefully), do NOT delete the archive until you confirm everything is working.

Creating/updating the Plex container

sudo docker stop plex
sudo docker rm plex

sudo docker pull plexinc/pms-docker

sudo docker run \
-d \
--name plex \
--network host \
-e TZ="America/Chicago" \
-v /path/to/plexmediaserver:/config \
-v /path/to/media:/mnt \
-h plexmedia \
plexinc/pms-docker

Copy and paste the above script into a shell file on your server – e.g. “update-plex.sh” – and give it proper permissions. Whenever Plex tells you there’s a new version available, just run the above script. Obviously (hopefully) the first time you run this, the commands to stop and remove the Plex container will print out errors because… the container doesn’t exist yet.

  • /path/to/plexmediaserver is the path where you extracted your backup archive
  • /path/to/media is, in my instance, the /mnt/media directory I mentioned above

If I had kept the separate mount points, I’d need individual -v switches for each path – e.g. -v /mnt/movies:/mnt/movies. Having all of them consolidated under /mnt/media, though, means I need just the one -v switch in the above script.

The latter volume mount is what ensures the Plex container has the same path for the library files. So when the library says the episodes for Game of Thrones, for example, are at /mnt/tv/Game of Thrones, it can still find them even though the Docker host has that path mounted as /mnt/media/tv/Game of Thrones.

After you create the container for the first time, you’ll want to interact with the container to make sure your mount points are set up properly:

sudo docker exec -it plex bash

Under /config you should see just one directory: Library. Under Library should be… everything else Plex will be looking for. And check your media mount point to make sure the directories there look as they did on your previous VM.

If any of the mount points don’t look right, you will need to massage the script above and re-run it to create a new container. Then just rinse and repeat with interacting with the container to validate the mount points.

Don’t forget to add the needed ports to your firewall: you must open 32400/TCP, and if you intend to use DLNA, you need to open 1900/UDP and 32469/TCP.

Making sure it all works

And lastly, of course, open one of your Plex clients and try playing something to verify everything works and that it doesn’t show the media item as “unavailable”. If anything is “unavailable”, you need to double-check your -v paths in your script. Use “Get Info” on the media item to see what path it’s trying to use to find it so you can double-check everything.