
🌐 Aussi en: English · Deutsch · Español
Deep Dive de la série autour de l’Ansible Tour. Niveau : administration Linux avancée. Le tour explique les rôles ; les deep dives expliquent la technique en dessous – comment elle fonctionne, pourquoi elle est là, ce que cette installation en fait exactement, comment l’exploiter au quotidien et ce qui aurait existé d’autre.
Les deux applications reposent ici sur MariaDB. Le blog la fait tourner comme pod à côté de WordPress (partie 3), les deux serveurs Nextcloud directement sur l’hôte (partie 4). Cet article explique ce qu’InnoDB fait de la mémoire et du disque, quelle poignée de réglages compte pour ces charges, ce que disent les mesures – et comment une seule ligne dans une unité systemd a fait que SELinux n’a pas protégé la base pendant cinq semaines.
🧭 Comment fonctionnent MariaDB et InnoDB
Le buffer pool : la base vit en RAM
InnoDB, le moteur de stockage derrière chaque table ici, lit et écrit les données par pages de 16 Ko. Les pages lues restent dans le buffer pool, un grand bloc de mémoire ; la lecture suivante de la même ligne ne coûte aucun accès disque. Les modifications sont faites d’abord dans le buffer pool et écrites plus tard dans les fichiers de données. Le chiffre le plus important d’un serveur MariaDB est donc la part des demandes de pages auxquelles le buffer pool peut répondre – le taux de succès.
Redo log et doublewrite : pourquoi un crash ne perd rien
Avant qu’une page modifiée soit écrite dans son fichier de données, la modification est consignée dans le redo log, un journal séquentiel. Après un crash, InnoDB le rejoue et chaque transaction validée est de retour. Le doublewrite buffer protège contre une page écrite à moitié lors d’une coupure de courant : chaque page va d’abord dans une zone séparée, puis à sa vraie place, de sorte qu’une page déchirée peut être réparée depuis la copie.
Un réglage décide à quelle fréquence le redo log est forcé sur disque. Avec innodb_flush_log_at_trx_commit = 1 (défaut), chaque commit attend un fsync. Avec 2, le journal est écrit au commit mais synchronisé une seule fois par seconde – beaucoup plus rapide pour de nombreuses petites écritures, au risque de perdre jusqu’à une seconde de commits lors d’un crash brutal de toute la machine (pas de MariaDB seule).
Tables temporaires : mémoire ou disque
Les requêtes avec GROUP BY, DISTINCT, UNION ou certains tris ont besoin d’une table temporaire interne. Elle est créée en mémoire jusqu’à tmp_table_size (et max_heap_table_size) ; une plus grande – ou une avec des colonnes TEXT/BLOB, que le moteur mémoire ne peut pas contenir – va sur disque dans tmpdir. WordPress et Nextcloud utilisent généreusement les colonnes TEXT, les tables temporaires sur disque ne sont donc pas le signe d’un mauvais réglage mais inévitables. La seule question est de savoir où se trouve « le disque ».
Connexions, threads, le slow log
Chaque connexion client reçoit un thread et ses propres tampons ; max_connections limite leur nombre et avec lui la consommation mémoire dans le pire cas. Le slow query log enregistre chaque instruction plus lente que long_query_time – le premier endroit où regarder quand une page est lente.
🛡️ Pourquoi elle est là
- Les deux applications sont construites et testées avec. WordPress ne prend officiellement en charge rien d’autre ; Nextcloud recommande MySQL ou MariaDB.
- Une série LTS. 10.11 reçoit des correctifs jusqu’en février 2028 ; les mises à jour au sein de la série sont petites et prévisibles.
- Gouvernance communautaire. MariaDB est développée par la MariaDB Foundation et l’entreprise, pas par un seul éditeur avec ses propres priorités.
🔧 Ce que fait ce dépôt
Deux façons de faire tourner la même base
| Blog | Serveurs Nextcloud | |
|---|---|---|
| Où | Pod dans K3s (mariadb:10.11.19) | Sur l’hôte, dépôt MariaDB Community, série fixée à 10.11 |
| Rôle | blog_k3s_deploy | next_mariadb |
| Buffer pool | 384 Mo | 2 Go / 512 Mo |
tmpdir | volume en mémoire (512 Mo) | tmpfs fourni par systemd (4 Go) |
| Joignable via | Service ClusterIP, NetworkPolicy : seulement le pod WordPress | 0.0.0.0:3306, nftables : seulement le réseau des pods |
| SELinux | container_t avec ses propres catégories MCS | mysqld_t |
Pourquoi deux façons ? Le blog a été construit dès le départ « tout dans le cluster ». Pour Nextcloud, la base est le composant le plus lourd et le plus précieux, et sur l’hôte elle bénéficie du bac à sable systemd complet, de son propre domaine SELinux et des outils de sauvegarde de la distribution sans conteneur au milieu.
Les réglages qui comptent
[mysqld]
innodb_buffer_pool_size = 2G # per host (512M on the small one)
innodb_flush_method = O_DIRECT # no double caching in the page cache
innodb_flush_log_at_trx_commit = 2 # sync the redo log once per second
innodb_linux_aio = aio # io_uring is disabled in the kernel
max_connections = 50 # measured peak: 15
tmp_table_size = 32M
max_heap_table_size = 32M
slow_query_log = 1
long_query_time = 1
skip_name_resolve = 1 # pod IPs cannot be resolved anywayinnodb_linux_aio = aio: AlmaLinux désactive io_uring (kernel.io_uring_disabled = 2). La valeur par défaut « auto » l’essayait quand même d’abord, écrivait un avertissementEPERMà chaque démarrage, puis revenait de toute façon à l’AIO Linux classique.skip_name_resolve: chaque connexion depuis un pod déclenchait une résolution DNS inverse pour une adresse10.42.xqui ne peut jamais réussir – de la latence à la connexion et un avertissement par connexion dans le journal. Sans risque, car aucun compte n’est autorisé par nom d’hôte.max_connections = 50: le pic mesuré était de 15 et 10 connexions ; 50 laisse de la marge et borne la mémoire dans le pire cas.
Tables temporaires en RAM
Quatre à six pour cent de toutes les tables temporaires vont sur disque sur ces serveurs – colonnes TEXT, voir plus haut. Depuis le 16 octobre 2026, ce « disque » est de la RAM : le drop-in systemd donne à MariaDB son propre /tmp en tmpfs (TemporaryFileSystem=/tmp:size=4G), le pod du blog y monte un volume en mémoire. Un tmpfs n’occupe de la mémoire que tant que des fichiers existent ; 4 Go laissent de la place aux fichiers de tri d’une reconstruction d’index lors d’une mise à niveau de Nextcloud. Un piège en chemin : combiné à PrivateTmp=yes, le répertoire privé sur disque l’emporte et le tmpfs est ignoré sans un mot.
Le bac à sable – et cinq semaines sans SELinux
Le drop-in 99-hardening.conf retire à la base presque tout ce dont elle n’a pas besoin : aucune capability (un serveur sur le port 3306 n’en a besoin d’aucune), NoNewPrivileges, un système de fichiers en lecture seule sauf le répertoire de données et celui des journaux, un filtre d’appels système, aucun accès aux paramètres du noyau, aux modules ou aux journaux, MemoryDenyWriteExecute.
L’unité de la distribution démarre MariaDB via /bin/sh -c "… galera_recovery …; exec mariadbd". Avec NoNewPrivileges, SELinux refuse la transition de domaine depuis le shell (initrc_t) vers mysqld_t, sauf si la politique l’autorise explicitement – ce qui n’est pas le cas. Résultat : du 11 septembre au 16 octobre 2026, MariaDB a tourné en initrc_t, un domaine que SELinux restreint à peine, alors que chaque contrôle indiquait « enforcing ». La correction tient en une ligne : ExecStart=/usr/sbin/mariadbd $MYSQLD_OPTS, démarré directement par systemd, sans le shell qui n’existe que pour les clusters Galera. Le deep dive SELinux raconte toute l’histoire ; la leçon pour tout durcissement : vérifier ps -eZ, pas seulement le mode.
Comptes
- L’utilisateur de l’application ne peut se connecter que depuis le réseau des pods (
10.42.%), pas de n’importe où. - Les comptes anonymes, la base
testet un droit proxy sur un nom d’hôte, devenu sans objet avecskip_name_resolve, sont supprimés. - Chaque exporteur a son propre utilisateur aux droits minimaux (
PROCESS,BINLOG MONITOR,SELECT) – sur les hôtes Nextcloud, l’exporteur réutilisait autrefois le mot de passe root, son fichier de configuration contenait donc de fait le mot de passe root. - Root sur l’hôte s’authentifie via
/root/.my.cnf; dans le pod, le mot de passe root vient d’un Secret Kubernetes monté comme fichier, pas comme variable d’environnement.
📊 Mesuré
| Blog | Nextcloud A (plus grand) | Nextcloud B | |
|---|---|---|---|
| Version | 10.11.19 | 10.11.19 | 10.11.19 |
| Données + index | 47 Mo | 361 Mo | 58 Mo |
| Buffer pool | 384 Mo | 2 Go | 512 Mo |
| Buffer pool inutilisé | 87 % | 84 % | 89 % |
| Taux de succès depuis le redémarrage (~9–11 h) | 99,70 % | 99,45 % | 99,66 % |
| Tables temporaires sur « disque » (tmpfs) | 3,3 % | 6,0 % | 4,1 % |
| Pic de connexions | 6 | 15 | 10 |
| Requêtes lentes (> 1 s) | 0 | 0 | 0 |
Ces bases sont petites. Toute la base Nextcloud du plus grand serveur tient cinq fois dans son buffer pool, et le taux de succès dépasse déjà 99 % après quelques heures – les échecs sont presque tous la première lecture après le redémarrage du matin. Aucune requête n’a duré plus d’une seconde. Deux conclusions : aller au-delà de ce qui est fait ici n’apporterait rien de mesurable, et les buffer pools sont généreux ; sur le plus grand serveur il pourrait descendre à 1 Go et rendre de la mémoire – avec 23 Go de RAM, aucune raison de le faire.
🧰 Exploitation au quotidien
# host (Nextcloud): root via /root/.my.cnf
mariadb -e "SHOW GLOBAL STATUS LIKE 'Innodb_buffer_pool_read%'"
mariadb -e "SHOW ENGINE INNODB STATUS\G" | less
tail -f /var/log/mariadb/slow.log
# pod (blog): root password from the mounted Secret
k3s kubectl -n wordpress exec -it deploy/mariadb -c mariadb -- \
sh -c 'MYSQL_PWD="$(cat /etc/secrets/db-root-password)" mariadb -uroot'
# is it confined?
ps -eZ | grep mariadbd
# a consistent dump without locking the application
mariadb-dump --single-transaction --quick --routines --events nextcloud | gzip > nc.sql.gzSauvegardes
Une machine de sauvegarde récupère chaque nuit par SSH un dump de chaque base (--single-transaction prend un instantané cohérent sans verrouiller les tables InnoDB), garde les 14 derniers après avoir vérifié que chacun est complet, et versionne le tout pendant 365 jours. Restaurer, c’est gunzip < dump | mariadb nextcloud dans une base vide – testé, pas supposé.
Mises à niveau
Au sein de la série, le paquet de l’hôte vient du dépôt fixé et dnf-automatic installe les correctifs de sécurité ; le pod du blog suit l’épinglage d’image dans versions.yml. Changer de série – vers la LTS suivante – est une étape délibérée : dump d’abord, changer le dépôt ou l’image, démarrer, lancer mariadb-upgrade, vérifier l’application.
Mots de passe
Tous les mots de passe des bases sont dans le vault Ansible. En changer un, c’est : le modifier dans le vault, lancer le playbook – il pose le nouveau mot de passe dans MariaDB et dans la configuration de l’application au cours du même passage.
🆘 Antisèche : symptôme → commande
La version courte de cet article, pour le moment où quelque chose ne va pas. À lancer sur l’hôte en root ; <…> sont des espaces réservés.
| Symptôme | Commande |
|---|---|
| Tourne-t-elle, et confinée ? | systemctl status mariadb |
| Elle ne démarre pas | journalctl -u mariadb -n 50 |
| L’application est lente | tail -f /var/log/mariadb/slow.log |
| Verrous ou interblocages | mariadb -e "SHOW ENGINE INNODB STATUS\G" | less |
| Le buffer pool est-il assez grand ? | mariadb -e "SHOW GLOBAL STATUS LIKE 'Innodb_buffer_pool_read%'" |
| Un shell SQL sur le blog | k3s kubectl -n wordpress exec -it deploy/mariadb -c mariadb -- \ |
| Un dump avant une modification | mariadb-dump --single-transaction --quick --routines --events nextcloud | gzip > nc.sql.gz |
| Les tables sont-elles saines ? | mariadb-check --all-databases |
| Plus de graphiques de base de données dans Grafana | systemctl status mysqld_exporter |
🔭 La suite
- Restauration à un instant donné. Avec le journal binaire activé, une restauration pourrait viser n’importe quelle seconde entre deux dumps nocturnes. Avec ces volumes d’écriture, le dump nocturne suffit ; ce serait le premier changement si cela cessait d’être vrai.
- La série LTS suivante bien avant février 2028, testée d’abord sur le plus petit serveur Nextcloud.
- Analyse des requêtes avec le performance schema dans Grafana – aujourd’hui, il n’y a rien de lent à analyser.
⚖️ Alternatives – et pourquoi MariaDB
| Option | Point fort | Pourquoi pas ici |
|---|---|---|
| PostgreSQL | Excellente base, Nextcloud la prend en charge | WordPress ne la prend pas en charge nativement ; deux moteurs pour deux applications doubleraient l’exploitation. |
| MySQL 8 | L’original, pris en charge par les deux | Piloté par un seul éditeur, fonctionnalités qui divergent de MariaDB ; aucun avantage pour ces charges. |
| SQLite | Pas de serveur du tout | Bien pour des tests, pas pour un Nextcloud multi-utilisateur avec des écritures concurrentes. |
| MariaDB 10.11 LTS | Prise en charge par les deux, gouvernance communautaire, série longue durée | Choisie. |
MariaDB est le composant le moins excitant de cette installation, et c’est un compliment. Les découvertes intéressantes n’étaient pas dans la base, mais autour : dans l’unité système qui la démarrait, dans le noyau qui désactivait une interface d’E/S, dans le répertoire où s’écrivaient les tables temporaires. La base elle-même a simplement fait son travail – sans une seule requête de plus d’une seconde.


