Set up MariaDB
Install, secure, create a database and user, allow remote access only where needed, back up with mariadb-dump.
5 min read
On this page
MariaDB is the database server most PHP applications such as WordPress expect. This guide installs it from your distribution's repositories.
Covers Debian 12 and 13, Ubuntu 22.04 and 24.04, AlmaLinux 9 and Rocky Linux 9. All commands run as root; to log in, see Connect via SSH.
Install
Debian and Ubuntu:
apt update
apt install -y mariadb-serverAlmaLinux and Rocky Linux:
dnf install -y mariadb-server
systemctl enable --now mariadbIs the service running?
systemctl status mariadb
mariadb --versionSecure it
mariadb-secure-installationThe script asks a few questions. Good answers for a new server:
| Question | Answer |
|---|---|
| Enter current password for root | just press Enter |
| Switch to unix_socket authentication | n (root already logs in via the socket) |
| Change the root password | n |
| Remove anonymous users | y |
| Disallow root login remotely | y |
| Remove test database | y |
| Reload privilege tables | y |
After that, root can only reach the database locally as the Linux root user, without a password:
mariadbType exit to leave the console.
Create a database and user
Each application gets its own database and its own user. Never use root for an application. First generate a strong password:
openssl rand -base64 24Then in the MariaDB console (mariadb), with your names and the password:
CREATE DATABASE myapp CHARACTER SET utf8mb4 COLLATE utf8mb4_unicode_ci;
CREATE USER 'myapp'@'localhost' IDENTIFIED BY 'YOUR-PASSWORD';
GRANT ALL PRIVILEGES ON myapp.* TO 'myapp'@'localhost';
FLUSH PRIVILEGES;'myapp'@'localhost' means the user may only log in from the server itself. That is right for an application on the same VPS.
Check that it worked
mariadb -u myapp -p myapp -e 'SELECT CURRENT_USER(), DATABASE();'After the password you should see myapp@localhost and myapp.
Remote access, only if needed
If the application runs on the same server, skip this section. MariaDB then only listens on 127.0.0.1, which is the safest state.
If you need access from another machine, allow it from one fixed address only. In the example, 203.0.113.10 stands for the address you connect from.
-
Let MariaDB listen on all addresses. The file depends on the system:
- Debian and Ubuntu:
/etc/mysql/mariadb.conf.d/50-server.cnf - AlmaLinux and Rocky Linux:
/etc/my.cnf.d/mariadb-server.cnf
In the
[mysqld]section (Debian/Ubuntu) or[mariadb]or[mysqld](Alma/Rocky):inibind-address = 0.0.0.0Then
systemctl restart mariadb. - Debian and Ubuntu:
-
Create a user for that address only:
sqlCREATE USER 'myapp'@'203.0.113.10' IDENTIFIED BY 'YOUR-PASSWORD'; GRANT ALL PRIVILEGES ON myapp.* TO 'myapp'@'203.0.113.10'; FLUSH PRIVILEGES;Do not use
'%'as the host. That allows login attempts from anywhere. -
Open port 3306 in the firewall for that address only.
Debian and Ubuntu with
ufw:bashufw allow from 203.0.113.10 to any port 3306 proto tcpAlmaLinux and Rocky Linux with
firewalld:bashfirewall-cmd --permanent --add-rich-rule='rule family="ipv4" source address="203.0.113.10" port port="3306" protocol="tcp" accept' firewall-cmd --reload
Back up with mariadb-dump
A dump is an SQL file you can restore the database from. Create a folder and back up one database:
mkdir -p /var/backups/mariadb
chmod 700 /var/backups/mariadb
mariadb-dump --single-transaction --routines --triggers myapp | gzip > /var/backups/mariadb/myapp-$(date +%F).sql.gzAll databases at once:
mariadb-dump --single-transaction --routines --triggers --all-databases | gzip > /var/backups/mariadb/all-$(date +%F).sql.gz--single-transaction creates a consistent snapshot without locking the tables (for InnoDB, the default).
Restore into an empty database:
gunzip -c /var/backups/mariadb/myapp-2026-11-05.sql.gz | mariadb myappA dump on the same server does not help if the server is gone. How to create it every night and copy it off the server is covered in Cron jobs and timers and Set up backups.
Common errors
ERROR 1045 (28000): Access denied. Wrong password, or the user only exists for a different host.SELECT User, Host FROM mysql.user;lists them.ERROR 2002: Can't connect to local server through socket. The service is not running.systemctl status mariadbandjournalctl -u mariadbshow why, often a full disk (df -h).- No connection from outside. Check with
ss -tlnp | grep 3306that MariaDB listens on0.0.0.0, then the firewall and the user's host. - Broken umlauts or emojis. The database was not created with
utf8mb4. Use the statement above for new databases.
What next
- WordPress with this database: PHP and WordPress.
- Automate backups: Set up backups.
If you get stuck, open a ticket.