PostgreSQL streaming replica lag et CPU élevé sur le réplica

anais56 25/01/2026
RÉSOLU
anais56
Auteur Actif
Avatar de anais56
anais56
Auteur Actif

Salut à tous.

On a un setup PostgreSQL 14 en streaming replication et depuis quelques jours on observe un lag de réplication qui augmente de manière intermittente sur notre réplica secondaire. Le truc bizarre c'est que le primaire est stable niveau charge CPU et IOPS, mais le réplica a des pics de CPU qui montent à 80-90% juste avant que le lag ne devienne visible. On est sur des instances EC2 avec des NVMe.

Une idée d'où je devrais commencer à chercher ?

25/01/2026 à 15:02

13 commentaires

marie-regnier
Membre Actif
Avatar de marie-regnier
marie-regnier
Membre Actif

C'est la galère quand le réplica tousse. La première chose à regarder c'est ce que fait le réplica au moment des lags. Va voir pg_stat_wal_receiver et pg_stat_replication sur ton réplica. Quels sont les replay_lag et sync_state ?

Modifié le 23/05/2026 à 16:20

En parallèle des stats PG, il faut voir ce que fait l'OS. Un iostat -x 5 sur le réplica peut montrer si ton problème est I/O bound. Regarde en particulier les colonnes r/s et w/s sur le volume des WAL, et le %util.

Modifié le 23/05/2026 à 16:20
anais56
Auteur Actif
Avatar de anais56
anais56
Auteur Actif

Ok j'ai ça.

SELECT replay_lag, sync_state FROM pg_stat_wal_receiver;

Le replay_lag monte jusqu'à 30 secondes parfois, et sync_state est async. L'iostat sur le volume WAL montre un r/s très élevé pendant les pics, genre 5000-6000 lectures par seconde, avec un %util à 100%. Des écritures normales.

Modifié le 23/05/2026 à 16:20
marie-regnier
Membre Actif
Avatar de marie-regnier
marie-regnier
Membre Actif

5000 lectures par seconde sur le volume WAL d'un réplica ? C'est énorme. Un réplica ne devrait faire que des écritures et des lectures séquentielles pour la relecture des WAL. Ça sent les full_page_writes ou un problème de checkpoint.

Vérifie SHOW full_page_writes; et SHOW checkpoint_completion_target; sur le primaire et le réplica.

Modifié le 23/05/2026 à 16:20
anais56
Auteur Actif
Avatar de anais56
anais56
Auteur Actif

full_page_writes est à on sur les deux, ce qui est le setting par défaut et recommandé. checkpoint_completion_target est à 0.9. La taille des WAL est 1GB.

Modifié le 23/05/2026 à 16:20

FPW on est la bonne pratique, mais ça génère plus de WAL et donc plus de travail pour le réplica. Le CPU élevé en system mode avec beaucoup de r/s pourrait indiquer que le kernel galère avec le fsync ou que l'IO scheduler est pas optimal pour la charge de relecture. Ou même la décompression si wal_compression est actif.

Modifié le 23/05/2026 à 16:20
anais56
Auteur Actif
Avatar de anais56
anais56
Auteur Actif

J'ai vérifié, wal_compression est à off. Le CPU est bien en system sur l'OS. Donc pas de décompression. Ça pointe vers un souci kernel/IO.

Quelle est la valeur de effective_io_concurrency sur ton réplica ? Et le wal_sync_method ?

Modifié le 23/05/2026 à 16:20
marie-regnier
Membre Actif
Avatar de marie-regnier
marie-regnier
Membre Actif

effective_io_concurrency est à 1. wal_sync_method est fdatasync. Je sais que 1 c'est pas terrible mais nos NVMe sont censés être rapides.

Modifié le 23/05/2026 à 16:20

effective_io_concurrency=1 avec des NVMe c'est un crime. Tu donnes une seule requête d'IO au kernel à la fois. Monte ça à 256 ou même 512, et même plus si ton NVMe supporte un queue depth très élevé. Le kernel peut mieux paralléliser les relectures (même si c'est surtout pour les lectures data, ça peut impacter la latence générale du système).

Pense aussi à ton I/O scheduler. Quel est-il ? cat /sys/block/nvme0n1/queue/scheduler

Modifié le 23/05/2026 à 16:20
anais56
Auteur Actif
Avatar de anais56
anais56
Auteur Actif

Je viens de passer effective_io_concurrency à 256 sur le réplica. J'ai redémarré PG. Le replay_lag est moins fréquent mais les pics de CPU system et de r/s sont toujours là. Le scheduler est mq-deadline.

Modifié le 23/05/2026 à 16:20
marie-regnier
Membre Actif
Avatar de marie-regnier
marie-regnier
Membre Actif

mq-deadline est généralement bon mais pas toujours pour des workloads spécifiques comme la relecture WAL. Pour des NVMe modernes qui gèrent eux-mêmes l'ordonnancement, noop est souvent la meilleure option. Ça réduit l'overhead kernel et laisse le contrôleur NVMe faire son boulot.

Essaie de changer le scheduler en noop pour ton device NVMe sur le réplica. Ça se fait à chaud pour tester, mais pour la persistance c'est dans GRUB ou udev rules.

echo noop > /sys/block/nvme0n1/queue/scheduler
Modifié le 23/05/2026 à 16:20

Oui le noop est le classique pour les NVMe. Si ça persiste après ça, on peut regarder les options de montage de ton système de fichiers. Par défaut ext4 ou xfs peuvent avoir des overheads.

Les dirty_ratio et dirty_background_ratio du kernel peuvent aussi jouer si le kernel passe son temps à flusher des pages sale. Mais ce serait plus en w/s qu'en r/s.

Modifié le 23/05/2026 à 16:20
anais56
Auteur Actif
Avatar de anais56
anais56
Auteur Actif

J'ai basculé le scheduler en noop sur le réplica. La différence est flagrante. Le replay_lag est stable, zéro pic de CPU en system mode, et le r/s sur le volume WAL est retombé à des niveaux normaux (moins de 100). C'était bien le mq-deadline qui créait des frictions avec la relecture des WAL sur le NVMe.

Merci à vous deux pour le diagnostic chirurgical ! Ça m'a sauvé un week-end.

Modifié le 23/05/2026 à 16:20

Laisser une réponse

Vous devez être connecté pour poster un message !

Rejoindre la communauté

Recevoir les derniers articles gratuitement en créant un compte !

S'inscrire