How to Automatically Backup Your Self-Hosted Ghost Blog

This is a guide on how you can automatically backup your self-hosted Ghost CMS blog automatically.

5 months ago   •   2 min read

By Aquasp
Table of contents

Introduction

Ghost is an incredibly fast and elegant blogging platform. But unlike WordPress, it doesn’t have built-in one-click backup plugins.

That changes today.

In this guide, you’ll set up a fully automated daily backup system that:

  • Dumps your MySQL database
  • Backs up all themes, images, and content
  • Compresses everything into a single .zip
  • Uploads it securely to your cloud storage (pCloud, NextCloud, Google Drive, Dropbox, etc.)

All using free tools: rclone + a simple bash script + cron.

Let’s get started.

Step 1: Install Rclone

sudo apt update && sudo apt install -y rclone

Rclone is the Swiss Army knife of cloud storage — it supports over 70 providers.

Full list: https://rclone.org/overview/

Step 2: Configure Rclone (Connect Your Cloud Storage)

Run:

rclone config

Follow the prompts:

  • n → new remote
  • Name it something like ghost-backup or pcloud
  • Choose your provider (e.g., webdav for NextCloud, pcloud, google drive, etc.)
  • Enter your credentials/URL when asked

Test it works:

rclone ls ghost-backup:

You should see your remote files (or an empty folder if new).

Type q to quit.

Step 3: Get Your Ghost Database Credentials

Log in as your Ghost user (not root):

su - yourghostuser
cd /var/www/ghost   # or wherever you installed Ghost
cat config.production.json

Look for the database section. You’ll see something like:

"database": {
  "client": "mysql",
  "connection": {
    "host": "localhost",
    "user": "ghost_db_user",
    "password": "yoursecretpassword",
    "database": "ghost_prod"
  }
}

Write down:

  • Database name (ghost_prod)
  • Username (ghost_db_user)
  • Password

Step 4: Create the Backup Script

Create the script as root:

nano /root/backup-ghost.sh

Paste this (then edit the variables below):

#!/bin/bash

# === EDIT THESE VALUES ===
GHOST_USER="yourghostuser"          # e.g. ghost
GHOST_PATH="/var/www/ghost"         # path to your Ghost install
DB_NAME="ghost_prod"                # from config.production.json
DB_USER="ghost_db_user"             # from config.production.json
DB_PASS="yoursecretpassword"        # from config.production.json
BACKUP_NAME="theselfhostingart-blog"   # name for your backup zip
RCLONE_REMOTE="ghost-backup"        # name you gave in rclone config
RCLONE_PATH="/"                     # folder in your cloud (use / for root)
# =========================

DATE=$(date +'%Y-%m-%d_%H-%M')
BACKUP_DIR="/home/$GHOST_USER/backups/$DATE"
ZIP_FILE="$BACKUP_DIR/$BACKUP_NAME-$DATE.zip"

echo "Starting Ghost backup: $DATE"

# Create backup directory
mkdir -p "$BACKUP_DIR"

# Backup database
echo "Backing up database..."
mysqldump -u "$DB_USER" -p"$DB_PASS" --add-drop-table "$DB_NAME" | gzip > "$BACKUP_DIR/db.sql.gz"

# Backup content folder (themes, images, etc.)
echo "Backing up content folder..."
rsync -av --exclude='logs' --exclude='cache' "$GHOST_PATH/content/" "$BACKUP_DIR/content/"

# Compress everything
echo "Compressing backup..."
zip -r "$ZIP_FILE" "$BACKUP_DIR/content" "$BACKUP_DIR/db.sql.gz" > /dev/null

# Upload to cloud
echo "Uploading to cloud storage..."
rclone copy "$ZIP_FILE" "$RCLONE_REMOTE:$RCLONE_PATH"

# Cleanup: remove local backups older than 1 day (optional but recommended)
echo "Cleaning up old local backups..."
find /home/$GHOST_USER/backups -type d -mtime +1 -exec rm -rf {} +

echo "Backup complete: $ZIP_FILE → $RCLONE_REMOTE:$RCLONE_PATH"

Make it executable:

chmod +x /root/backup-ghost.sh

Test it manually first:

/root/backup-ghost.sh

Check your cloud storage — you should see a file like:
theselfhostingart-blog-2025-04-05_03-22.zip

Step 5: Automate with Cron (Daily Backups)

crontab -e

Add this line for daily backup at 2:00 AM:

cron0 2 * * * /usr/bin/bash /root/backup-ghost.sh >> /var/log/ghost-backup.log 2>&1

Save and exit.

Your Ghost blog is now automatically backed up every day.

What’s Included in the Backup?

  • Full database (posts, users, settings)
  • All uploaded images
  • Custom themes
  • Everything needed to restore or migrate

You can even send this .zip to Ghost(Pro) support — they can import it directly.

Bonus: Restore in Case of Disaster

To restore:

  1. Install fresh Ghost
  2. Unzip backup
  3. Import DB: gunzip < db.sql.gz | mysql -u user -p dbname
  4. Replace content/ folder
  5. Run ghost restart

Credits & Thanks

This method is inspired and improved from this excellent post:
How to Automatically Backup Ghost Blogs – Kenton Vizdos

Thank you, Kenton!


If you found this helpful, please share it or subscribe to The Self Hosting Art.
Your self-hosted blog now sleeps better at night. 😴💾

Thank you for reading!

Spread the word

Keep reading