Do not choose a universal Jellyfin memory limit; start with a measured workload, reserve memory for the host and neighboring containers, and only hard-cap after observing real peaks.
Does your container grow until the host swaps, or does a low limit cause repeated OOM kills? Measure idle usage, library scans, metadata work, concurrent transcodes, and the memory available to Docker or the VM before changing the limit. A limit is safe only when the original workload still completes and the host retains recovery margin.
Separate Normal Cache Growth From Resident Memory Pressure
First compare container RSS, cache, swap, and host free memory during idle and during the busiest repeatable job. Filesystem cache can look large without being a leak, while resident growth plus OOM events indicates a real constraint.
A basic Docker Jellyfin deployment commonly starts around a few gigabytes and needs more for transcoding, but the correct value depends on the workload (workload-based memory baseline).
If RSS stays flat while cache rises and the host has reclaimable memory, monitor rather than tightening the cap. If RSS climbs with swap or OOM-kill messages, continue to the transcode and library tests.
Test the Limit Under the Trigger That Fails
Run one library scan, one representative transcode, and the expected concurrent stream count while recording cgroup memory usage, memory events, swap, and host pressure. Change only the memory limit between runs.
A limit that passes idle playback but fails during subtitles, HDR conversion, or indexing is not a valid production setting. Record which trigger caused the failure so you do not raise the cap for an unrelated bottleneck.
If the container is killed, raise the limit only after reducing unnecessary transcode cache or separating heavy jobs. If the host itself swaps, lower concurrency or move a role; giving Jellyfin all remaining RAM simply moves the failure to another service.
Set a Stop Boundary and Verify Persistence
Keep a soft alert below the hard limit and leave enough memory for the host, storage services, and a clean restart. A hard cap should protect the host, not conceal an unbounded process or an undersized machine.
After changing the limit, stop and recreate the container once, then repeat the original scan and playback trigger. Check that the configured limit is still active after recreation and that the database remains writable.
Stop tuning and escalate when OOM events continue at a limit that leaves no host margin, the database becomes corrupt, or the process grows without a reproducible workload. Preserve logs and the last known-good configuration before making a larger change.
Recheck Peak Playback After a Cold Restart
Reboot the host, wait for storage mounts and neighboring containers, and reproduce the same multi-user stream mix that originally exposed the limit. Do not validate only with an idle dashboard or a single Direct Play session.
Recovery is proven when playback remains stable, no swap storm appears, the container stays below its cap, and a fresh backup or restart completes without memory-related errors. Compare the result with the baseline recorded before tuning.
Keep the setting when the peak workload passes with measurable host margin. If it fails only after another container starts, split the resource budget or reschedule the competing job instead of increasing Jellyfinโs limit again.
Support & Tips
More to Read

How to Optimize Jellyfin Database Connections for Concurrent Containers
Start with one database owner and measured SQLite lock behavior; add a different backend only when concurrency and recovery justify the complexity.

How to Prevent Duplicate Jobs or Imports in Jellyfin
Duplicate work usually comes from overlapping schedulers or more than one writer; assign one owner, one path, and one completion check.

How to Repair Jellyfin After Its Database Volume Fills Up
Stop writes, preserve the database and WAL files, free space without deleting state blindly, then verify integrity and the original workload.

