mirror of
https://github.com/acedanger/shell.git
synced 2025-12-06 02:20:11 -08:00
jellyfin restoration info and shell scripts
This commit is contained in:
91
jellyfin/restore_corrupted_database.md
Normal file
91
jellyfin/restore_corrupted_database.md
Normal file
@@ -0,0 +1,91 @@
|
|||||||
|
# Jellyfin SQLite Database Repair Guide
|
||||||
|
|
||||||
|
This document explains how to use the `fix_jellyfin_db.sh` script to repair a corrupted Jellyfin `library.db` file.
|
||||||
|
|
||||||
|
**Warning:** Repeated database corruption is a strong indicator of an underlying issue, most commonly a failing hard drive or SSD. If you have to run this script more than once, you should immediately investigate the health of your storage device using tools like `smartctl`.
|
||||||
|
|
||||||
|
## How to Use the Script
|
||||||
|
|
||||||
|
1. **Save the Script:**
|
||||||
|
Save the script content to a file named `fix_jellyfin_db.sh` on your server.
|
||||||
|
|
||||||
|
2. **Make it Executable:**
|
||||||
|
Open a terminal and navigate to the directory where you saved the file. Run the following command to make it executable:
|
||||||
|
```bash
|
||||||
|
chmod +x fix_jellyfin_db.sh
|
||||||
|
```
|
||||||
|
|
||||||
|
3. **Run the Script:**
|
||||||
|
The script must be run with `sudo` because it needs to stop/start system services and modify files in `/var/lib/jellyfin/`.
|
||||||
|
```bash
|
||||||
|
sudo ./fix_jellyfin_db.sh
|
||||||
|
```
|
||||||
|
|
||||||
|
The script will print its progress as it executes each step.
|
||||||
|
|
||||||
|
## What the Script Does: A Step-by-Step Breakdown
|
||||||
|
|
||||||
|
The script automates the standard "dump and restore" method for SQLite recovery.
|
||||||
|
|
||||||
|
#### Step 1: Stops the Jellyfin Service
|
||||||
|
To prevent any other process from reading or writing to the database during the repair, the script first stops Jellyfin.
|
||||||
|
```bash
|
||||||
|
systemctl stop jellyfin
|
||||||
|
```
|
||||||
|
|
||||||
|
#### Step 2: Backs Up the Corrupted Database
|
||||||
|
Your corrupted database is never deleted. It is copied to a new file with a timestamp, ensuring you have a fallback.
|
||||||
|
```bash
|
||||||
|
# Example backup name: library.db.corrupt.2023-10-27-14:30:00
|
||||||
|
cp library.db library.db.corrupt.[timestamp]
|
||||||
|
```
|
||||||
|
|
||||||
|
#### Step 3: Dumps Data to an SQL File
|
||||||
|
It uses the `sqlite3` command-line tool to read every piece of data it can from the corrupted database and write it as a series of SQL commands to a text file named `library_dump.sql`.
|
||||||
|
```bash
|
||||||
|
sqlite3 library.db .dump > library_dump.sql
|
||||||
|
```
|
||||||
|
|
||||||
|
#### Step 4: Patches the Dump File
|
||||||
|
If the dump process hit a severe error, it writes `ROLLBACK;` at the end of the dump file. This would cause the import to fail. The script checks for this exact line and replaces it with `COMMIT;`, forcing SQLite to save all the data it was able to salvage.
|
||||||
|
```bash
|
||||||
|
sed -i '$ s/ROLLBACK; -- due to errors/COMMIT;/' library_dump.sql
|
||||||
|
```
|
||||||
|
|
||||||
|
#### Step 5: Restores the Database
|
||||||
|
The script renames the original corrupted file and then creates a brand new, empty `library.db` by feeding it the `library_dump.sql` file. This rebuilds the entire database structure from scratch, leaving all corruption behind.
|
||||||
|
```bash
|
||||||
|
# Move old DB
|
||||||
|
mv library.db library.db.repaired-from
|
||||||
|
|
||||||
|
# Create new DB from dump
|
||||||
|
sqlite3 library.db < library_dump.sql
|
||||||
|
```
|
||||||
|
|
||||||
|
#### Step 6: Verifies the New Database
|
||||||
|
The script checks that the new database file is not empty. It then runs `PRAGMA integrity_check`, which should return `ok` on a healthy database.
|
||||||
|
```bash
|
||||||
|
sqlite3 library.db "PRAGMA integrity_check;"
|
||||||
|
```
|
||||||
|
|
||||||
|
#### Step 7: Sets Permissions and Restarts Jellyfin
|
||||||
|
Finally, it sets the correct `jellyfin:jellyfin` ownership and file permissions on the new database file and restarts the Jellyfin service.
|
||||||
|
```bash
|
||||||
|
chown jellyfin:jellyfin library.db
|
||||||
|
chmod 664 library.db
|
||||||
|
systemctl start jellyfin
|
||||||
|
```
|
||||||
|
|
||||||
|
## Post-Repair Actions
|
||||||
|
|
||||||
|
After the script completes successfully, you should verify that your Jellyfin library, users, and watch history are intact.
|
||||||
|
|
||||||
|
The script leaves the backup files in `/var/lib/jellyfin/data/` for safety:
|
||||||
|
- `library.db.corrupt.[timestamp]`
|
||||||
|
- `library.db.repaired-from`
|
||||||
|
- `library_dump.sql`
|
||||||
|
|
||||||
|
Once you have confirmed Jellyfin is working correctly for a day or two, you can safely delete these files to save space:
|
||||||
|
```bash
|
||||||
|
sudo rm /var/lib/jellyfin/data/library.db.corrupt.* /var/lib/jellyfin/data/library.db.repaired-from /var/lib/jellyfin/data/library_dump.sql
|
||||||
|
```
|
||||||
124
jellyfin/restore_corrupted_database.sh
Normal file
124
jellyfin/restore_corrupted_database.sh
Normal file
@@ -0,0 +1,124 @@
|
|||||||
|
#!/bin/bash
|
||||||
|
|
||||||
|
# ==============================================================================
|
||||||
|
# Jellyfin SQLite Database Repair Script
|
||||||
|
#
|
||||||
|
# This script automates the process of recovering a corrupted Jellyfin
|
||||||
|
# library.db file by dumping its content to an SQL file and re-importing
|
||||||
|
# it into a new, clean database.
|
||||||
|
#
|
||||||
|
# MUST BE RUN AS ROOT OR WITH SUDO.
|
||||||
|
# ==============================================================================
|
||||||
|
|
||||||
|
# --- Configuration ---
|
||||||
|
JELLYFIN_DATA_DIR="/var/lib/jellyfin/data"
|
||||||
|
DB_FILE="library.db"
|
||||||
|
DUMP_FILE="library_dump.sql"
|
||||||
|
# --- End Configuration ---
|
||||||
|
|
||||||
|
# --- Safety Checks ---
|
||||||
|
# Check if running as root
|
||||||
|
if [ "$EUID" -ne 0 ]; then
|
||||||
|
echo "ERROR: This script must be run as root or with sudo."
|
||||||
|
exit 1
|
||||||
|
fi
|
||||||
|
|
||||||
|
# Check if sqlite3 is installed
|
||||||
|
if ! command -v sqlite3 &> /dev/null; then
|
||||||
|
echo "ERROR: sqlite3 is not installed. Please install it first."
|
||||||
|
echo "On Debian/Ubuntu: sudo apt-get install sqlite3"
|
||||||
|
exit 1
|
||||||
|
fi
|
||||||
|
|
||||||
|
# Navigate to the data directory or exit if it doesn't exist
|
||||||
|
cd "$JELLYFIN_DATA_DIR" || { echo "ERROR: Could not find Jellyfin data directory at $JELLYFIN_DATA_DIR"; exit 1; }
|
||||||
|
|
||||||
|
echo "--- Jellyfin DB Repair Initialized ---"
|
||||||
|
|
||||||
|
# --- Step 1: Stop Jellyfin and Backup ---
|
||||||
|
echo "[1/8] Stopping the Jellyfin service..."
|
||||||
|
systemctl stop jellyfin
|
||||||
|
echo "Service stopped."
|
||||||
|
|
||||||
|
# Create a timestamped backup
|
||||||
|
TIMESTAMP=$(date +%F-%T)
|
||||||
|
CORRUPT_DB_BACKUP="library.db.corrupt.$TIMESTAMP"
|
||||||
|
echo "[2/8] Backing up corrupted database to $CORRUPT_DB_BACKUP..."
|
||||||
|
if [ -f "$DB_FILE" ]; then
|
||||||
|
cp "$DB_FILE" "$CORRUPT_DB_BACKUP"
|
||||||
|
echo "Backup created."
|
||||||
|
else
|
||||||
|
echo "ERROR: $DB_FILE not found! Cannot proceed."
|
||||||
|
systemctl start jellyfin # Try to start the service again
|
||||||
|
exit 1
|
||||||
|
fi
|
||||||
|
|
||||||
|
|
||||||
|
# --- Step 2: Dump the Database ---
|
||||||
|
echo "[3/8] Dumping data from the corrupted database to $DUMP_FILE..."
|
||||||
|
# We use .dump, which will try to read everything possible.
|
||||||
|
# Using 'tee' to avoid permission issues with redirection.
|
||||||
|
sqlite3 "$DB_FILE" .dump | tee "$DUMP_FILE" > /dev/null
|
||||||
|
echo "Dump complete."
|
||||||
|
|
||||||
|
|
||||||
|
# --- Step 3: Fix the Dump File if Necessary ---
|
||||||
|
echo "[4/8] Checking dump file for errors..."
|
||||||
|
# If the dump process encountered an unrecoverable error, it ends with ROLLBACK.
|
||||||
|
# We must change it to COMMIT to save the salvaged data.
|
||||||
|
if grep -q "ROLLBACK;" "$DUMP_FILE"; then
|
||||||
|
echo "-> Found 'ROLLBACK'. Changing to 'COMMIT' to salvage data..."
|
||||||
|
sed -i '$ s/ROLLBACK; -- due to errors/COMMIT;/' "$DUMP_FILE"
|
||||||
|
echo "-> Dump file patched."
|
||||||
|
else
|
||||||
|
echo "-> No 'ROLLBACK' found. Dump file appears clean."
|
||||||
|
fi
|
||||||
|
|
||||||
|
|
||||||
|
# --- Step 4: Restore from Dump ---
|
||||||
|
echo "[5/8] Moving old corrupted database aside..."
|
||||||
|
mv "$DB_FILE" "${DB_FILE}.repaired-from"
|
||||||
|
echo "[6/8] Importing data into a new, clean database. This may take a moment..."
|
||||||
|
sqlite3 "$DB_FILE" < "$DUMP_FILE"
|
||||||
|
|
||||||
|
|
||||||
|
# --- Step 5: Verification and Cleanup ---
|
||||||
|
# Check if the new database file was created and is not empty
|
||||||
|
if [ ! -s "$DB_FILE" ]; then
|
||||||
|
echo "!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!"
|
||||||
|
echo "!! CRITICAL ERROR: The new database is empty! !!"
|
||||||
|
echo "!! The repair has FAILED. Restoring old DB. !!"
|
||||||
|
echo "!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!"
|
||||||
|
mv "${DB_FILE}.repaired-from" "$DB_FILE" # Restore the moved file
|
||||||
|
systemctl start jellyfin
|
||||||
|
exit 1
|
||||||
|
fi
|
||||||
|
|
||||||
|
echo "-> New database created successfully."
|
||||||
|
|
||||||
|
# Run integrity check
|
||||||
|
echo "[7/8] Verifying integrity of the new database..."
|
||||||
|
INTEGRITY_CHECK=$(sqlite3 "$DB_FILE" "PRAGMA integrity_check;")
|
||||||
|
|
||||||
|
if [ "$INTEGRITY_CHECK" == "ok" ]; then
|
||||||
|
echo "-> SUCCESS! Integrity check passed."
|
||||||
|
else
|
||||||
|
echo "-> WARNING: Integrity check on new DB reported: $INTEGRITY_CHECK"
|
||||||
|
echo "-> The database may still have issues, but is likely usable."
|
||||||
|
fi
|
||||||
|
|
||||||
|
|
||||||
|
# --- Step 6: Finalize ---
|
||||||
|
echo "[8/8] Setting correct file permissions and restarting Jellyfin..."
|
||||||
|
chown jellyfin:jellyfin "$DB_FILE"
|
||||||
|
chmod 664 "$DB_FILE"
|
||||||
|
systemctl start jellyfin
|
||||||
|
echo "-> Jellyfin service started."
|
||||||
|
|
||||||
|
echo ""
|
||||||
|
echo "--- Repair Process Complete ---"
|
||||||
|
echo "Your Jellyfin database has been repaired and the service restarted."
|
||||||
|
echo "Please check your Jellyfin web interface to ensure everything is working."
|
||||||
|
echo "Backup files ($CORRUPT_DB_BACKUP, ${DB_FILE}.repaired-from, $DUMP_FILE) have been kept in $JELLYFIN_DATA_DIR for safety."
|
||||||
|
echo ""
|
||||||
|
echo "IMPORTANT: Repeated corruption is a sign of a failing disk. Please check your disk health."
|
||||||
Reference in New Issue
Block a user