MariaDB Guide — MySQL Replacement with Advanced Features
MariaDB is a community-developed fork of MySQL, created by the original MySQL developers, offering complete backward compatibility with MySQL while adding advanced storage engines, clustering, and performance optimizations.
What You’ll Learn
By the end of this tutorial, you’ll understand the key differences between MariaDB and MySQL, work with the Aria storage engine, set up Galera clustering for high availability, use MariaDB’s enhanced JSON functions, and leverage the performance schema for query optimization.
Why MariaDB Matters
MariaDB has become the default MySQL replacement for many Linux distributions (Red Hat, Fedora, openSUSE) and major companies like Google, Wikipedia, and Deutsche Telekom. DodaZIP migrated from MySQL to MariaDB for its cloud metadata store, benefiting from MariaDB’s improved performance and clustering. Durga Antivirus Pro uses MariaDB for its threat signature database with Galera clustering for redundancy.
MariaDB Learning Path
flowchart LR
A[SQL Basics] --> B[MySQL]
B --> C[MariaDB]
C --> D[PostgreSQL]
D --> E[MongoDB]
E --> F[Database Design]
C --> G{You Are Here}
style G fill:#f90,color:#fff
What Is MariaDB? (The “Why” First)
Think of MariaDB as MySQL but better. When Oracle acquired MySQL in 2009, the original creators worried about MySQL becoming a closed product. They forked the codebase and created MariaDB — which stays open-source, adds new features faster, and maintains 100% compatibility with MySQL. If you know MySQL, you already know 90% of MariaDB. But MariaDB adds things MySQL doesn’t have: Aria storage engine, Galera clustering built-in, more JSON functions, and better performance.
MariaDB vs MySQL
| Feature | MySQL | MariaDB |
|---|---|---|
| Storage engine | InnoDB (default) | InnoDB or Aria |
| Clustering | Group Replication | Galera Cluster (built-in) |
| JSON functions | Basic | Extended (JSON_TABLE, JSON_EXISTS) |
| Temporary tables | Memory or InnoDB | Aria (faster, disk-based) |
| Sequences | No | Yes (Oracle-style) |
| Thread pooling | Enterprise only | Included in community |
| License | Dual (GPL/Commercial) | GPL (fully free) |
Installing MariaDB
# On Ubuntu/Debian
sudo apt update
sudo apt install mariadb-server mariadb-client -y
# On RHEL/Fedora
sudo dnf install mariadb-server -y
# Start the service
sudo systemctl start mariadb
sudo systemctl enable mariadb
# Secure installation
sudo mysql_secure_installation
# Verify version
mysql --version
# Expected: mysql Ver 15.1 Distrib 10.11.x-MariaDBCreating Tables with Aria Storage Engine
Aria is MariaDB’s own storage engine, optimized for both transactional and non-transactional workloads:
-- Create a table with Aria engine (faster for temporary data)
CREATE TABLE cache_entries (
cache_id INT AUTO_INCREMENT PRIMARY KEY,
cache_key VARCHAR(255) NOT NULL,
cache_value LONGBLOB NOT NULL,
expires_at TIMESTAMP,
created_at TIMESTAMP DEFAULT CURRENT_TIMESTAMP,
INDEX idx_cache_key (cache_key),
INDEX idx_expires (expires_at)
) ENGINE=Aria TRANSACTIONAL=1;
-- Create a fast non-transactional log table
CREATE TABLE access_logs (
log_id BIGINT AUTO_INCREMENT PRIMARY KEY,
ip_address VARCHAR(45) NOT NULL,
url VARCHAR(2048) NOT NULL,
status_code INT,
response_time_ms INT,
logged_at TIMESTAMP DEFAULT CURRENT_TIMESTAMP,
INDEX idx_logged_at (logged_at)
) ENGINE=Aria PAGE_CHECKSUM=1;Aria Engine Benefits:
- Crash-safe (even without transaction log, Aria recovers automatically)
- Faster than InnoDB for temporary tables and logs
- Supports both transactional (
TRANSACTIONAL=1) and non-transactional modes - Built-in page checksums for data integrity
- Used by MariaDB internally for
internal_tmp_disk_storage_engine
MariaDB-Specific SQL Features
Sequences (Oracle-Compatible)
-- Create a sequence (MySQL doesn't have these!)
CREATE SEQUENCE order_seq
START WITH 10000
INCREMENT BY 1
MINVALUE 10000
MAXVALUE 99999;
-- Use it like in Oracle
INSERT INTO orders (order_id, customer_id, total_amount)
VALUES (NEXT VALUE FOR order_seq, 1, 150.00);
-- Check current value
SELECT PREVIOUS VALUE FOR order_seq;Enhanced JSON Functions
-- Create a table with JSON column
CREATE TABLE products (
product_id INT AUTO_INCREMENT PRIMARY KEY,
name VARCHAR(200) NOT NULL,
attributes JSON
) ENGINE=InnoDB;
-- Insert JSON data
INSERT INTO products (name, attributes) VALUES
('Laptop', JSON_OBJECT('cpu', 'Intel i7', 'ram', '16GB', 'storage', '512GB SSD')),
('Monitor', '{"size": "27 inch", "resolution": "4K", "ports": ["HDMI", "USB-C"]}');
-- Query JSON with MariaDB-specific functions
SELECT
name,
JSON_EXISTS(attributes, '$.cpu') AS has_cpu,
JSON_VALUE(attributes, '$.resolution') AS resolution,
attributes
FROM products;
-- Output:
-- name | has_cpu | resolution | attributes
-- Laptop | 1 | NULL | {"cpu":"Intel i7","ram":"16GB","storage":"512GB SSD"}
-- Monitor | 0 | 4K | {"size":"27 inch","resolution":"4K","ports":["HDMI","USB-C"]}
-- JSON_TABLE (convert JSON to relational rows)
SELECT *
FROM JSON_TABLE(
'[{"id":1,"name":"Alice"},{"id":2,"name":"Bob"}]',
'$[*]' COLUMNS (
id INT PATH '$.id',
name VARCHAR(50) PATH '$.name'
)
) AS jt;Galera Cluster — Multi-Master Replication
Galera is MariaDB’s built-in synchronous multi-master clustering:
flowchart TB
subgraph Galera Cluster
N1[Node 1 - Primary]
N2[Node 2 - Primary]
N3[Node 3 - Primary]
end
App1[App Server 1] --> N1
App2[App Server 2] --> N2
App3[App Server 3] --> N3
N1 <--> N2
N2 <--> N3
N1 <--> N3
subgraph Data Flow
N1 --> W1[Write Set]
W1 --> C[Certification]
C --> N2
C --> N3
end
Every node can accept writes. Galera synchronously replicates each write to all nodes. If one node fails, the cluster continues with no data loss.
Galera Configuration Example
# /etc/mysql/mariadb.conf.d/galera.cnf
[galera]
wsrep_on = ON
wsrep_provider = /usr/lib/galera/libgalera_smm.so
wsrep_cluster_name = "dodatech_cluster"
wsrep_cluster_address = "gcomm://192.168.1.10,192.168.1.11,192.168.1.12"
wsrep_node_name = "node1"
wsrep_node_address = "192.168.1.10"
binlog_format = ROW
default_storage_engine = InnoDB
innodb_autoinc_lock_mode = 2# Start cluster (first node)
galera_new_cluster
# Join other nodes
systemctl start mariadbPerformance Schema and Query Profiling
-- Enable performance schema
SET GLOBAL performance_schema = ON;
-- Find slow queries
SELECT
digest_text AS query,
count_star AS executions,
ROUND(avg_timer_wait / 1000000000, 2) AS avg_ms,
ROUND(max_timer_wait / 1000000000, 2) AS max_ms,
sum_rows_examined AS total_rows_examined
FROM performance_schema.events_statements_summary_by_digest
WHERE digest_text NOT LIKE '%performance_schema%'
ORDER BY avg_timer_wait DESC
LIMIT 10;
-- Output:
-- query | executions | avg_ms | max_ms | total_rows_examined
-- SELECT * FROM products WHERE name LIKE ? | 150 | 45.20 | 234.10 | 150000
-- INSERT INTO access_logs ... | 50000 | 0.50 | 5.20 | 0
-- Analyze a specific query
EXPLAIN FORMAT=JSON
SELECT p.name, COUNT(o.order_id) AS orders
FROM products p
LEFT JOIN orders o ON p.product_id = o.product_id
GROUP BY p.product_id;Common MariaDB Errors
1. ERROR 1290 (HY000): The MariaDB server is running with the --skip-grant-tables option
This happens when you restart MariaDB with --skip-grant-tables for password recovery and forget to flush privileges. Fix: Run FLUSH PRIVILEGES; and set a new password.
2. ERROR 2002 (HY000): Can't connect to local MySQL server through socket
MariaDB isn’t running or the socket file is in a different location. Fix: Check with systemctl status mariadb and verify socket path with mysqladmin variables | grep socket.
3. Galera: WSREP has not yet prepared node for application use
The node hasn’t finished joining the cluster. Fix: Check SHOW STATUS LIKE 'wsrep_ready' and SHOW STATUS LIKE 'wsrep_local_state_comment'. The node must reach state Synced before accepting queries.
4. ERROR 1067 (42000): Invalid default value for 'created_at'
MariaDB has stricter NO_ZERO_DATE and STRICT_TRANS_TABLES modes enabled by default. Fix: Use DEFAULT CURRENT_TIMESTAMP or relax sql_mode: SET GLOBAL sql_mode = 'STRICT_TRANS_TABLES'.
5. ERROR 1071 (42000): Specified key was too long
InnoDB/WyD’s index key length limit in MariaDB. Fix: Use prefix indexes: INDEX idx_name(name(191)) or change column encoding to a more compact one.
6. AUTO_INCREMENT Gap with Galera
-- Galera with innodb_autoinc_lock_mode=2 causes gaps
INSERT INTO products (name) VALUES ('Product A');
-- ID might be 1, next INSERT gets 3, not 2Fix: This is normal for Galera. Don’t rely on contiguous AUTO_INCREMENT values. Galera uses distributed sequence generation.
7. ERROR 1819 (HY000): Your password does not satisfy the current policy requirements
MariaDB’s validate_password plugin is active. Fix: Use a stronger password (upper/lower/digit/special) or adjust policy with SET GLOBAL validate_password.policy = LOW.
Practice Questions
1. What is the main difference between MariaDB and MySQL?
MariaDB is a community fork of MySQL with additional features like Aria storage engine, built-in Galera clustering, sequences, and extended JSON functions. It’s fully compatible with MySQL but adds features that MySQL doesn’t have in its community edition.
2. What is the Aria storage engine?
Aria is MariaDB’s own storage engine, designed as a crash-safe alternative to MyISAM. It supports both transactional and non-transactional modes, page checksums for data integrity, and is faster than InnoDB for temporary tables and logging workloads.
3. How does Galera Cluster differ from MySQL replication?
MySQL uses asynchronous master-slave replication (one-way). Galera is synchronous multi-master (all nodes can write). Galera automatically handles conflict resolution and provides stronger consistency guarantees.
4. Challenge: Write a query that uses a sequence to generate invoice numbers.
CREATE SEQUENCE invoice_seq START WITH 100000;
CREATE TABLE invoices (
invoice_number INT DEFAULT (NEXT VALUE FOR invoice_seq) PRIMARY KEY,
customer_id INT NOT NULL,
total DECIMAL(12,2) NOT NULL,
created_at TIMESTAMP DEFAULT CURRENT_TIMESTAMP
);
INSERT INTO invoices (customer_id, total) VALUES (1, 250.00);
SELECT * FROM invoices;5. How does MariaDB’s JSON support differ from MySQL’s?
MariaDB supports JSON_EXISTS() (test for path existence), JSON_TABLE() (convert JSON to relational rows), and JSON_VALUE() (extract scalar values) — functions that MySQL added later or doesn’t have. MariaDB also stores JSON as LONGTEXT internally, giving it more flexibility for indexing.
Real-World Task: Build a Multi-Master E-Commerce Backend
Design a MariaDB Galera cluster schema for an e-commerce application — like DodaZIP’s cloud marketplace:
-- Create database
CREATE DATABASE marketplace CHARACTER SET utf8mb4 COLLATE utf8mb4_unicode_ci;
USE marketplace;
-- Products table (InnoDB for transactions)
CREATE TABLE products (
product_id INT AUTO_INCREMENT PRIMARY KEY,
name VARCHAR(200) NOT NULL,
description TEXT,
price DECIMAL(12,2) NOT NULL,
stock_quantity INT NOT NULL DEFAULT 0,
created_at TIMESTAMP DEFAULT CURRENT_TIMESTAMP,
INDEX idx_price (price),
INDEX idx_name (name)
) ENGINE=InnoDB;
-- High-speed access log (Aria for performance)
CREATE TABLE request_log (
log_id BIGINT AUTO_INCREMENT PRIMARY KEY,
method VARCHAR(10),
path VARCHAR(500),
status_code INT,
duration_ms INT,
ip_address VARCHAR(45),
logged_at TIMESTAMP DEFAULT CURRENT_TIMESTAMP,
INDEX idx_path (path(100)),
INDEX idx_logged_at (logged_at)
) ENGINE=Aria;
-- Insert sample data
INSERT INTO products (name, price, stock_quantity) VALUES
('Smart Watch', 199.99, 50),
('Wireless Earbuds', 79.99, 200),
('Laptop Stand', 34.99, 150);
-- Monitor Galera cluster status
SHOW STATUS LIKE 'wsrep_%';FAQ
Try It Yourself
Install MariaDB and explore its unique features:
-- List available storage engines
SHOW ENGINES;
-- Output includes: InnoDB, Aria, MyISAM, MEMORY, CSV
-- Check MariaDB version-specific features
SELECT @@version, @@version_comment;
-- Test sequence (only in MariaDB 10.3+)
CREATE SEQUENCE test_seq;
SELECT NEXT VALUE FOR test_seq; -- 1
SELECT NEXT VALUE FOR test_seq; -- 2
-- Use INVISIBLE columns (MariaDB 10.3+)
CREATE TABLE config (
config_id INT PRIMARY KEY,
config_key VARCHAR(100) UNIQUE,
config_value TEXT,
internal_note VARCHAR(500) INVISIBLE
);
-- The INVISIBLE column won't appear in SELECT * queries
INSERT INTO config VALUES (1, 'app_name', 'MyApp', 'Set during installation');
SELECT * FROM config;
-- Only shows: config_id, config_key, config_valueThese features power Doda Browser’s configuration management and Durga Antivirus Pro’s signature update system with MariaDB’s advanced replication and high-speed logging capabilities.
What’s Next
Congratulations on completing this MariaDB tutorial! Here’s where to go from here:
- Practice daily — Consistency is more important than long study sessions
- Build a project — Apply what you learned by building something real
- Explore related topics — Check out other tutorials in the same category
- Join the community — Discuss with other learners and share your progress
Remember: every expert was once a beginner. Keep coding!
Built by the developers of Doda Browser, DodaZIP, and Durga Antivirus Pro.
Built by the developers of DodaTech
Doda Browser, DodaZIP & Durga Antivirus Pro