A focused repair tool for malformed or physically corrupted jellyfin.db databases, such as SQLite Error 11: 'database disk image is malformed', while preserving valid configuration wherever possible.
This script rebuilds the database file using a sqlite3 .dump / .read pipeline instead of blindly deleting it, aiming to:
- Preserve: user accounts, server settings, library definitions, API keys, and other configuration data.
- Allow Jellyfin to safely rebuild: library index and scan state on next startup.
- This script directly operates on the core Jellyfin database at
/var/lib/jellyfin/data/jellyfin.db. - Always run it with care and read this document fully before use.
Key points:
- Compatibility:
- Designed for Jellyfin 10.x.
- Primarily developed and tested on later 10.11.x versions.
- Uses
sqlite3 .dumpat the file level, so it is schema-agnostic and not tightly coupled to specific Jellyfin versions. - Relevant for 10.10.7 as a pre-migration check before the EF Core-based schema changes in 10.11.0.
- Use cases:
- Recover from
jellyfin.dbcorruption (e.g., SQLite Error 11, malformed disk image, broken library index tables). - Pre-migration repair on 10.10.7 before upgrading to 10.11.0 to reduce risk of migration failures.
- Recover from
- Backups and safety:
- The script automatically creates a timestamped backup of the original database at:
~/JellyFin_DB_Backups/(undersudo, this resolves to/root/JellyFin_DB_Backups).
- Media files are never deleted by this script.
- Strongly recommended: before major upgrades or migrations, manually back up the entire
/var/lib/jellyfin/data/directory to an independent location.
- The script automatically creates a timestamped backup of the original database at:
If you are not comfortable restoring from backups or reconfiguring Jellyfin, review this README carefully before proceeding.
- Linux environment (e.g., Debian/Ubuntu/Arch) with Jellyfin installed as a system service.
- Jellyfin service running as the
jellyfinuser (default packaged installs). sudoprivileges.sqlite3command-line tool installed and available inPATH.
From the cloned repository directory:
cd "JellyFin DB Fix"
sudo ./jellyfin_db_fix.shDefaults are:
- Database path:
/var/lib/jellyfin/data/jellyfin.db - Service name:
jellyfin - Service control via:
systemctl
Custom installations:
- If your Jellyfin instance uses a different service name, user, or data path, review and adjust the variables at the top of [
jellyfin_db_fix.sh](JellyFin DB Fix/jellyfin_db_fix.sh:17) before running.
In order:
- Stops the Jellyfin service using
systemctl stop jellyfin. - Creates
~/JellyFin_DB_Backups/if needed. - Copies the existing
jellyfin.dbinto a timestamped backup file in that directory. - Runs
sqlite3with.dumpagainst the existingjellyfin.dband writes the output to a temporary SQL file. - Creates a new clean database file and imports the dumped SQL (
.read) into it. - Swaps the old database file for the rebuilt one.
- Removes stale SQLite journal files:
.db-shmand.db-wal. - Fixes ownership on the new database (and data directory as needed) using
chown jellyfin:jellyfinto avoid permission issues. - Starts the Jellyfin service using
systemctl start jellyfin. - Cleans up temporary files.
On next startup, Jellyfin will:
- Detect and rebuild any missing or invalid library index data.
- Perform a fresh media library scan against a structurally healthy database.
The script implements a conservative database repair workflow:
- Service control:
- Stops Jellyfin before touching
jellyfin.dbto avoid concurrent writes. - Restarts Jellyfin after the repair via [
cleanup_and_restart()](JellyFin DB Fix/jellyfin_db_fix.sh:31), which callssystemctl start jellyfin.
- Stops Jellyfin before touching
- Safe backup:
- Ensures a backup directory exists at
"$HOME/JellyFin_DB_Backups"and writes:jellyfin.db.corrupted.<timestamp>.bak
- Copy is performed with
sudo cpto handle permissions.
- Ensures a backup directory exists at
- Dump and rebuild:
-
Executes:
sudo sqlite3 "$DB_FULL_PATH" ".dump" > "$TEMP_SQL_FILE"
-
Creates a new database:
sudo sqlite3 "$NEW_DB_FILE" ".read $TEMP_SQL_FILE"
-
This process:
- Reads logical schema and data,
- Discards low-level file corruption,
- Re-emits clean SQL to reconstruct the database.
-
- Swap and cleanup:
- Moves the original
jellyfin.dbaside (suffix.corrupted_old). - Moves the rebuilt file into place as
jellyfin.db. - Deletes old journal files:
$DB_FULL_PATH-shm$DB_FULL_PATH-wal
- Moves the original
- Permissions:
- Runs
chown jellyfin:jellyfinon the repaired database (and, in full reset, on the data directory) so Jellyfin can read/write normally.
- Runs
Compared to manually deleting jellyfin.db:
- Preserves:
- User accounts.
- Server configuration and preferences.
- Library definitions and paths.
- API keys and other critical configuration tables.
- Allows:
- Jellyfin to rebuild the heavy library index data safely on next start.
- Minimizes:
- Risk of unnecessary full reconfiguration.
- Downtime due to misconfiguration introduced by starting from scratch.
This approach is intentionally schema-agnostic at the SQLite file level and is compatible with Jellyfin 10.x installations that use the standard jellyfin.db layout, including migrations such as the EF Core transition in 10.11.0, provided the underlying data is logically dumpable.
When corruption is extreme:
- If the
sqlite3 .dumpstep fails (non-zero exit, e.g., Exit Code 1), the script:- Logs that the database may be too severely corrupted.
- Invokes the interactive [
full_reset()](JellyFin DB Fix/jellyfin_db_fix.sh:40) workflow.
Full reset workflow:
- Prompts for explicit confirmation:
"Are you sure you want to proceed with a full database reset? (y/N):"
- On confirmation:
- Deletes the corrupted
jellyfin.db. - Deletes associated journal files (
.db-shm,.db-wal). - Fixes directory ownership for the Jellyfin data directory.
- Restarts the Jellyfin service.
- Deletes the corrupted
- Effect:
- Jellyfin starts as a fresh installation, showing the initial setup wizard.
- All prior:
- User accounts,
- Server configuration,
- Library definitions,
- History and watch state are reset.
- Media files on disk are not touched or removed.
If you decline the reset:
- The script aborts so you can attempt manual recovery.
- Q: Is this only for a specific Jellyfin version?
- A: It is built around standard
jellyfin.dbusage and thesqlite3 .dumpmechanism, so it is generally suitable for Jellyfin 10.x. It has been primarily validated on later 10.11.x but is also useful on 10.10.7 as a pre-migration repair step.
- A: It is built around standard
- Q: Does this delete or modify my media files?
- A: No. It only operates on the Jellyfin database and related SQLite journal files.
- Q: What about custom installs (non-default paths/users)?
- A: Defaults are:
- DB path:
/var/lib/jellyfin/data/jellyfin.db - Service:
jellyfin - User/group:
jellyfin:jellyfinIf your environment differs, adjust the configuration variables at the top of [jellyfin_db_fix.sh](JellyFin DB Fix/jellyfin_db_fix.sh:17) accordingly before running.
- DB path:
- A: Defaults are:
- Q: Why is there both a backup and a
.corrupted_oldfile?- A: The backup in
~/JellyFin_DB_Backups/is your off-disk safety copy. The.corrupted_oldfile in-place is an immediate fallback and audit artifact.
- A: The backup in
Special thanks to user "AfterShock" on Reddit for raising critical questions about:
- Version compatibility across Jellyfin 10.x.
- The 10.10.7 to 10.11.0 EF Core migration path.
- Practical concerns around corruption, migration safety, and repair strategies.
Their input helped refine the compatibility notes and documentation for this tool.