MariaDB Optimization & Performance Tuning Guide

Complete guide to optimizing MariaDB for production environments

1. Swappiness Configuration

Swappiness is a critical kernel parameter that controls how aggressively the Linux kernel swaps memory pages from RAM to disk. For database servers like MariaDB, proper swappiness configuration is essential to prevent service crashes and maintain optimal performance.

Why Swappiness Matters: When the InnoDB buffer pool is mapped from memory to disk, proper swappiness settings prevent performance degradation and potential MariaDB service crashes.

Recommended Values

Storage Type Recommended Swappiness Reason
Standard HDD/SSD 1 Minimizes disk I/O for database operations
Ultra-fast NVMe SSD 1-5 Can handle slightly more swap activity due to speed

Checking Current Swappiness

To verify your current swappiness configuration, use the following command:

sudo sysctl -a | grep vm.swappiness

Expected output:

vm.swappiness = 1

Modifying Swappiness

To permanently change the swappiness value:

Important: A server reboot is required for swappiness changes to take effect.
  1. Open the custom overrides configuration file:
    sudo nano /etc/sysctl.d/custom-overrides.conf
  2. Locate or add the swappiness directive:
    vm.swappiness = 1
  3. Change the value as needed (e.g., to 5 for NVMe systems)
  4. Save the file and exit the editor
  5. Reboot the server:
    sudo reboot
  6. After reboot, verify the new setting:
    sudo sysctl -a | grep vm.swappiness

2. Understanding Schemas and Databases in MySQL/MariaDB

In MySQL and MariaDB, the terms "schema" and "database" are often used interchangeably, but they have subtle technical differences that are important to understand.

Database

A database in MySQL refers to the entire collection of data and objects, including:

  • Tables
  • Views
  • Stored Procedures
  • Indexes

Schema

A schema is a logical grouping within a database used to organize and manage database objects such as:

  • Tables
  • Views
  • Procedures

A database can contain one or more schemas, and each schema can contain multiple database objects.

Viewing Databases

To list all databases in your MariaDB installation:

sudo mysql
MariaDB [(none)]> SHOW DATABASES;

Sample output showing default databases:

+--------------------+
| Database           |
+--------------------+
| information_schema |
| mysql              |
| performance_schema |
| sys                |
+--------------------+

3. Performance Schema Configuration

The Performance Schema is a powerful feature in MariaDB that collects and provides access to performance-related data, enabling database administrators to monitor and optimize server performance.

Performance Schema Architecture

MySQL Server Internals
(Resource Usage, Query Execution, Events)
Performance Schema
(Collects Raw Performance Data)
SYS Schema
(User-Friendly Views & Reports)
Database Administrator
(Analysis & Optimization)

Performance Schema vs SYS Schema

Feature Performance Schema SYS Schema
Purpose Collects raw performance data Provides user-friendly interface
Data Type Low-level metrics and events High-level views and reports
Accessibility Requires complex queries Simplified queries and helper functions
Use Case Deep performance analysis Quick troubleshooting and monitoring

Enabling Performance Schema

MariaDB includes both Performance Schema and SYS Schema by default, but the Performance Schema needs to be enabled in the configuration.

Configuration Location: /etc/mysql/mariadb.conf.d/50-server.cnf
  1. Navigate to the configuration directory:
    cd /etc/mysql/mariadb.conf.d
  2. Create a backup of the configuration file:
    sudo cp 50-server.cnf 50-server.cnf.back
  3. Open the configuration file:
    sudo nano 50-server.cnf
  4. Locate the [mysqld] section and add the following directives under the # * Temp dir comment:
    # Enable Performance Schema
    performance_schema = ON
    performance-schema-instrument = 'stage/%=ON'
    performance-schema-consumer-events-stages-current = ON
    performance-schema-consumer-events-stages-history = ON
    performance-schema-consumer-events-stages-history-long = ON
  5. Save the file and exit (Ctrl+X, then Y, then Enter)
  6. Restart MariaDB to apply changes:
    sudo systemctl restart mariadb

Creating a Bash Alias for Quick Restart

To simplify frequent MariaDB restarts during configuration, create a bash alias:

nano ~/.bash_aliases

Add the following line:

alias mariare='sudo systemctl restart mariadb'

Save, exit, and reload your shell:

exit
# Log back in

Now you can restart MariaDB simply by typing:

mariare

4. Query Cache Management

The MySQL Query Cache is a reserved memory area within the MySQL daemon designed to store query results for instant retrieval when the same query is executed again.

Performance Paradox: While query caching sounds beneficial, in real-world scenarios it often degrades performance due to lock contention. The query cache locks cached records, causing other threads to wait, which often makes direct querying faster.

Why Query Cache is Disabled by Default

Lock Contention

When a query result is cached, the cache entry is locked. Other threads requesting the same data must wait for the lock to be released, creating bottlenecks.

Cache Invalidation

Any modification to a table invalidates all cached queries related to that table, making the cache ineffective for frequently updated databases.

Direct Query Efficiency

Modern storage systems and query optimizers often retrieve data faster directly from disk or buffer pools than from cache.

Checking Query Cache Status

To verify query cache support and status:

sudo mysql
MariaDB [(none)]> SHOW VARIABLES LIKE 'have_query_cache';

Expected output:

+------------------+-------+
| Variable_name    | Value |
+------------------+-------+
| have_query_cache | YES   |
+------------------+-------+

To check if the query cache is enabled:

MariaDB [(none)]> SHOW VARIABLES LIKE 'query_cache%';

Key variable to check:

+------------------+-------+
| Variable_name    | Value |
+------------------+-------+
| query_cache_type | OFF   |
+------------------+-------+
Recommended Configuration: By default, MariaDB disables the query cache (query_cache_type = OFF). This is the optimal configuration for most production environments and should remain disabled.

MariaDB Console Tips

Clearing the Screen: Unlike standard terminal sessions, the clear command doesn't work in the MariaDB console. Instead, use Ctrl+L to clear the screen and reposition your cursor.

5. Hostname Resolution Optimization

When a new client connects to MySQL/MariaDB, the server creates a new thread to handle the request. By default, this thread performs a time-consuming DNS resolution process that negatively impacts performance.

Default Connection Process (Without skip-name-resolve)

Client Connects with IP Address
Check Hostname Cache
(If not found, proceed)
Resolve IP → Hostname
(DNS Lookup)
Resolve Hostname → IP
(Reverse DNS Lookup)
Verify IP Matches Original
Connection Established
Performance Impact: The double DNS lookup process (forward and reverse) adds significant latency to each connection, especially on servers with many simultaneous connections.

Disabling Hostname Resolution

To eliminate this overhead, configure MariaDB to use only IP addresses:

  1. Navigate to the configuration directory:
    cd /etc/mysql/mariadb.conf.d
  2. Open the server configuration file:
    sudo nano 50-server.cnf
  3. Locate the commented directive (usually under the [mysqld] section after the Performance Schema directives):
    # skip-name-resolve
  4. Uncomment it by removing the hash symbol:
    skip-name-resolve
  5. Save and exit (Ctrl+X, Y, Enter)
  6. Restart MariaDB:
    mariare
Result: With skip-name-resolve enabled, the MySQL server will only use IP addresses, completely bypassing the hostname resolution process and significantly improving connection performance.

6. Log File Management

MariaDB log files can accumulate rapidly and consume significant disk space, especially on smaller servers. Uncontrolled log growth can lead to MariaDB becoming unresponsive or even causing server crashes.

Critical Issue: On servers with limited disk space, log files growing unchecked over time can fill the disk, causing MariaDB to crash and potentially making the entire server unresponsive.

Binary Log Retention

The expire_logs_days parameter controls how long MariaDB retains binary log files. By default, this is set to 10 days, which can be excessive for smaller servers.

Configuring Log Retention

Follow these steps to reduce log retention from 10 days to 3 days:

  1. Log into MariaDB:
    sudo mysql
  2. Check the current setting:
    MariaDB [(none)]> SHOW VARIABLES LIKE 'expire_logs_days';
    Expected output:
    +------------------+-------+
    | Variable_name    | Value |
    +------------------+-------+
    | expire_logs_days | 10    |
    +------------------+-------+
  3. Set the new value (runtime change):
    MariaDB [(none)]> SET GLOBAL expire_logs_days = 3;
  4. Flush binary logs to rotate and apply changes:
    MariaDB [(none)]> FLUSH BINARY LOGS;
    Important: Flushing binary logs ensures proper rotation and prevents corruption of MySQL transactional logs.
  5. Exit MariaDB:
    MariaDB [(none)]> EXIT;

Making the Change Permanent

To ensure this setting persists across server reboots:

  1. Open the configuration file:
    sudo nano /etc/mysql/mariadb.conf.d/50-server.cnf
  2. Search for the directive (Ctrl+W, then type "expire"):
    Ctrl+W
    expire
  3. Locate the line:
    expire_logs_days = 10
  4. Change it to:
    expire_logs_days = 3
  5. Save and exit (Ctrl+X, Y, Enter)
  6. Restart MariaDB:
    mariare
  7. Verify the change:
    sudo mysql
    MariaDB [(none)]> SHOW VARIABLES LIKE 'expire_logs_days';
    Expected output:
    +------------------+-------+
    | Variable_name    | Value |
    +------------------+-------+
    | expire_logs_days | 3     |
    +------------------+-------+

7. InnoDB Storage Engine Optimization

InnoDB is the default and recommended storage engine for MariaDB, providing a balance of high reliability and high performance. Proper configuration of InnoDB parameters is crucial for optimal database performance.

What is a Storage Engine?

A database storage engine is the underlying software component that a database management system uses to create, read, update, and delete (CRUD) data from a database. InnoDB specifically excels at handling concurrent transactions and maintaining data integrity.

Critical InnoDB Parameters

InnoDB Buffer Pool Size

The amount of memory allocated to the InnoDB buffer pool, which holds frequently accessed data and indexes.

Formula: 80% of total server RAM

Impact: Most important MariaDB configuration setting for performance

InnoDB Log File Size

The size of the transaction log file, which records all database modifications before they are committed.

Formula: 25% of InnoDB Buffer Pool Size

Purpose: Enables transaction rollback and prevents data corruption

Configuration Formula Summary

Server RAM Buffer Pool Size (80%) Log File Size (25% of Buffer Pool)
1 GB 800 MB 200 MB
2 GB 1600 MB 400 MB
4 GB 3200 MB 800 MB
8 GB 6400 MB 1600 MB
CRITICAL PROCEDURE: Changing the InnoDB log file size requires a specific procedure to prevent InnoDB table corruption. DO NOT simply change the value and restart MariaDB.

Correct Procedure for Changing InnoDB Settings

Safe InnoDB Configuration Change Process

1. Check Current Values
2. STOP MariaDB Service
3. Modify Configuration File
4. START MariaDB Service
5. Verify New Values

Step-by-Step Configuration

Step 1: Check Current Values

sudo mysql
MariaDB [(none)]> SHOW VARIABLES LIKE 'innodb_buffer%';

Expected default output:

+-------------------------+-----------+
| Variable_name           | Value     |
+-------------------------+-----------+
| innodb_buffer_pool_size | 134217728 |
+-------------------------+-----------+

Check log file size:

MariaDB [(none)]> SHOW VARIABLES LIKE 'innodb_log%';

Default output:

+---------------------------+----------+
| Variable_name             | Value    |
+---------------------------+----------+
| innodb_log_file_size      | 100663296|
+---------------------------+----------+
Note: Values are shown in bytes. To convert to MB, divide by 1,048,576.
Default Buffer Pool: 134217728 bytes = 128 MB
Default Log File: 100663296 bytes = 96 MB
EXIT;

Step 2: STOP MariaDB Service

sudo systemctl stop mariadb
CRITICAL: Always stop MariaDB BEFORE modifying InnoDB settings in the configuration file.

Step 3: Modify Configuration

sudo nano /etc/mysql/mariadb.conf.d/50-server.cnf

Search for the InnoDB section (Ctrl+W, then type "innodb"):

Ctrl+W
innodb

You'll find a commented example:

# innodb_buffer_pool_size = 8G

Below this, add your custom values. For a 1GB server:

innodb_buffer_pool_size = 800M
innodb_log_file_size = 200M
Format Note: For sizes, always use whole megabytes (e.g., 3200M, NOT 3.2G). This ensures clarity and prevents configuration errors.

Example for 4GB server:
Buffer Pool: 80% of 4000MB = 3200MB
Log File: 25% of 3200MB = 800MB

Configuration:
innodb_buffer_pool_size = 3200M
innodb_log_file_size = 800M

Save and exit (Ctrl+X, Y, Enter)

Step 4: START MariaDB Service

sudo systemctl start mariadb

Step 5: Verify New Values

sudo mysql
MariaDB [(none)]> SHOW VARIABLES LIKE 'innodb_buffer%';
MariaDB [(none)]> SHOW VARIABLES LIKE 'innodb_log%';
EXIT;

Monitoring Server Resources

It's essential to monitor your server's RAM usage to ensure your InnoDB configuration is appropriate:

htop

In htop:

  • Monitor the "Mem" bar to see total RAM usage
  • Ensure sufficient RAM remains available for the operating system and other services
  • Press 'Q' to quit htop
Optimization Complete: At this point, you have completed all basic MariaDB optimizations. Further optimization should be performed after installing WordPress or your application, based on actual usage patterns and performance metrics.

Summary & Best Practices

Configuration Checklist

Setting Recommended Value Status
Swappiness 1 (or up to 5 for NVMe) ✓ Configured
Performance Schema ON ✓ Enabled
Query Cache OFF (default) ✓ Disabled
skip-name-resolve Enabled ✓ Active
expire_logs_days 3 ✓ Set
InnoDB Buffer Pool 80% of RAM ✓ Optimized
InnoDB Log File Size 25% of Buffer Pool ✓ Optimized

Key Takeaways

Always Backup First

Create backups of configuration files before making any changes. Use the .back extension for easy identification.

Follow Proper Procedures

Especially for InnoDB settings, always stop MariaDB before configuration changes and start it after.

Verify Changes

After every configuration change, verify the new values are active using SHOW VARIABLES queries.

Monitor Performance

Use tools like htop to monitor system resources and ensure configurations are appropriate for your hardware.

Next Steps: These optimizations provide a solid foundation for MariaDB performance. Further tuning should be done after installing your application (e.g., WordPress) and analyzing real-world usage patterns through the Performance Schema and SYS Schema.