To back up MariaDB with mariabackup you copy the InnoDB data files directly, then run a prepare step that makes the copy consistent. This guide walks through installing mariabackup, taking a full backup, adding daily incrementals, and restoring everything on a Linux VPS.
mariabackup is the physical backup tool shipped with MariaDB. Unlike mysqldump, which writes SQL statements, it copies tablespaces and redo logs, so it is much faster on large databases and restores to the exact same state. The trade-off is that you must prepare the backup before it is usable, and restore means replacing the data directory.
Before you start
You need:
- A Linux VPS running MariaDB 10.x or 11.x, with root or sudo access.
- The
mariadb-backuppackage installed (it is not always part of the base server package). - Free disk space at least the size of your data directory. Check with
sudo du -sh /var/lib/mysql. - A dedicated backup user with the right privileges.
Create that user first. Log in as root on the database:
CREATE USER 'backup'@'localhost' IDENTIFIED BY 'strong-password-here';
GRANT RELOAD, PROCESS, LOCK TABLES, REPLICATION CLIENT, SELECT, SHOW VIEW ON *.* TO 'backup'@'localhost';
FLUSH PRIVILEGES;Warning: A backup stored only on the same VPS is not a backup. Copy finished backups to another machine or object storage before you rely on them.
Install mariabackup
On Ubuntu 22.04/24.04 and Debian 12:
sudo apt update
sudo apt install -y mariadb-backupOn AlmaLinux and Rocky Linux 8 or 9:
sudo dnf install -y MariaDB-backupConfirm the version and that it matches your server's major version:
mariabackup --version
mariadb --versionNote: mariabackup must match the MariaDB server version series. If the versions differ, check the MariaDB documentation for the compatible package before you continue.
Take a full backup
Create a place to keep backups and run the first full copy:
sudo mkdir -p /var/backups/mariadb
sudo mariabackup --backup \
--target-dir=/var/backups/mariadb/full-$(date +%F) \
--user=backup --password='strong-password-here'The command finishes with completed OK!. Inside the target directory you will find ibdata1, the .ibd tablespace files, xtrabackup_checkpoints and xtrabackup_binlog_info. The binlog info file records the log position at the end of the copy, which you need later for point-in-time recovery.
InnoDB tables are copied without blocking writes for long. MyISAM tables are locked briefly during the copy, so expect a short pause if you still use them.
Tip: Keep the password out of your shell history by putting credentials in /root/.my.cnf with mode 600:
[client]
user=backup
password=strong-password-hereThen drop --user and --password from every command below.
Prepare the backup
A raw backup is not consistent yet. Prepare it so the data files and redo logs agree:
sudo mariabackup --prepare --target-dir=/var/backups/mariadb/full-2026-01-01You should see InnoDB: Starting crash recovery followed by completed OK!. Only a prepared backup can be restored.
Add incremental backups
A common pattern is a weekly full backup plus daily incrementals. Each incremental stores only the pages changed since the previous one:
sudo mariabackup --backup \
--target-dir=/var/backups/mariadb/inc-2026-01-02 \
--incremental-basedir=/var/backups/mariadb/full-2026-01-01The next day, point --incremental-basedir at the previous incremental, not at the full backup:
sudo mariabackup --backup \
--target-dir=/var/backups/mariadb/inc-2026-01-03 \
--incremental-basedir=/var/backups/mariadb/inc-2026-01-02To restore, you merge them in order. Prepare the base with --apply-log-only, then apply each incremental. Use --apply-log-only on every step except the last one:
sudo mariabackup --prepare --apply-log-only --target-dir=/var/backups/mariadb/full-2026-01-01
sudo mariabackup --prepare --apply-log-only --target-dir=/var/backups/mariadb/full-2026-01-01 \
--incremental-dir=/var/backups/mariadb/inc-2026-01-02
sudo mariabackup --prepare --target-dir=/var/backups/mariadb/full-2026-01-01 \
--incremental-dir=/var/backups/mariadb/inc-2026-01-03Warning: Dropping --apply-log-only from an intermediate step rolls back uncommitted transactions too early and corrupts the merged backup. Keep the flag on all but the final prepare.
Restore a mariabackup backup
Warning: Restoring replaces the entire data directory. Every database and table currently on the server is lost. Confirm the backup is prepared and take a copy of the current data directory first.
sudo systemctl stop mariadb
sudo mv /var/lib/mysql /var/lib/mysql.old
sudo mkdir -p /var/lib/mysql
sudo mariabackup --copy-back --target-dir=/var/backups/mariadb/full-2026-01-01
sudo chown -R mysql:mysql /var/lib/mysql
sudo systemctl start mariadb--copy-back leaves the backup directory untouched. If you want to save disk space, --move-back moves the files instead, but then the backup is gone.
Check it works
Log in and confirm your data is present:
mysql -e "SHOW DATABASES;"
mysql -e "SELECT COUNT(*) FROM your_app.users;"Then check the backup metadata to confirm the log position was recorded:
cat /var/backups/mariadb/full-2026-01-01/xtrabackup_checkpointsThe last_lsn value should match the prepared state. Finally, restore the same backup onto a scratch VPS and start MariaDB there. A backup you have never restored is only a guess.
Troubleshooting
Can't connect to local MySQL server through socket— mariabackup is looking at the wrong socket path. Pass--socket=/run/mysqld/mysqld.sock, or check where your server actually listens. See fixing the MySQL socket error.ERROR 1045 (28000): Access denied for user 'backup'@'localhost'— the backup user is missing privileges or the password is wrong. Re-grantRELOAD,PROCESS,LOCK TABLESandREPLICATION CLIENT. See fixing MySQL error 1045.- Prepare fails with
Cannot open datafileor a redo log error — the incrementals were merged in the wrong order, or--apply-log-onlywas omitted. Start again from the full backup and apply them in date order. - MariaDB will not start after restore, error 13 permission denied — file ownership is wrong. Run
sudo chown -R mysql:mysql /var/lib/mysqland start the service again. - The backup directory fills the disk — check sizes with
du -sh /var/backups/mariadb/*and stream backups off-server with--stream=xbstreampiped intosshor an object storage client.
Next steps
Automate the full backup weekly and the incrementals daily with cron, and copy the results off the VPS every night. If you want a portable SQL copy alongside the physical one, read how to back up and restore MySQL databases with mysqldump. To recover to a precise moment rather than the last backup, see MySQL point-in-time recovery using binary logs. For whole-server backups, including config files and web roots, follow backing up your Linux VPS with rsync, restic and cron.
