Situation: You are on-call and notice a read-replica is read-only or replication lag > threshold. Follow this concise runbook to restore service safely.Detection thresholds- Alert when replica replication_lag > 5s for OLTP-critical, > 30s for analytical; or replica reports read_only = ON unexpectedly; or >5% of app reads fail.Immediate inspection (run as DBA/ops user)- Check replica status (MySQL/MariaDB):bash
mysql -e "SHOW SLAVE STATUS\G"
- Check replication lag (Postgres):bash
psql -c "SELECT now()-pg_last_xact_replay_timestamp() AS lag;"
- Check read-only flag:bash
mysql -e "SELECT @@read_only;"
psql -c "SHOW default_transaction_read_only;"
- Check disk, IO, CPU, network:bash
top; iostat -x 1 3; df -h
Immediate mitigations (fast, reversible)1. Redirect new read traffic away from the unhealthy replica to other replicas or primary via load balancer / service discovery. Example: disable node in HAProxy/ProxySQL or mark instance OUT in service registry.2. If app can tolerate stale reads, lower SLA by switching to other replicas; notify stakeholders.Short-term fixes (non-destructive)- If replication thread stopped, try restart (MySQL):bash
mysql -e "START SLAVE;"
- For Postgres:bash
pg_ctl reload && repmgr standby clone/check; -- use cluster tooling
- If IO or disk pressure, free space (rotate logs), kill long queries causing bloat.When to promote a replica- Promote when master unreachable or replica consistently healthy and up-to-date (lag < 1s) and failover authorized.- Verify replica has all transactions: MySQL SHOW SLAVE STATUS Slave_IO_State = 'Waiting for master to send event' and Seconds_Behind_Master = 0; Postgres replay timestamp ~ master.Promote steps (MySQL example)1. Stop writes to old master (if alive): put it in maintenance.2. On chosen replica:bash
mysql -e "STOP SLAVE; RESET SLAVE ALL; SET GLOBAL read_only=OFF;"
3. Point app write endpoint to new master and update DNS/HAProxy/ProxySQL.4. Reconfigure other replicas to replicate from new master:bash
CHANGE MASTER TO MASTER_HOST='new-master', MASTER_USER='repl', MASTER_PASSWORD='pw', MASTER_LOG_FILE='file', MASTER_LOG_POS=pos;
START SLAVE;
Promote steps (Postgres example)- Use repmgr/Patroni/etcd workflow; manual:1. Promote:bash
pg_ctl promote -D /var/lib/postgresql/data
2. Reconfigure old primary (when recovered) as replica: update recovery.conf / primary_conninfo and start.Post-recovery verification- Confirm replication healthy: Seconds_Behind_Master ≈ 0 or lag < threshold.- Run smoke tests: read queries, write to master, consistency checks (row counts, checksums).- Monitor metrics and alerts for 30–60 minutes.- Run integrity: compare high-watermark txn IDs / binlog positions.- Document incident: root cause, actions taken, timeline, and postmortem.Notes and safety- Prefer redirecting reads over promoting unless master is dead.- Always snapshot binlog/LSN before destructive ops.- Communicate with team and stakeholders before failover if SLA allows.