2026年7月9日

2026年7月9日

WordPressのデータベースレプリケーションを設定する方法|MySQLのソース・レプリカ構成と読み書き分離

WordPressのデータベースレプリケーションは、MySQL側で「ソース(書き込みを受ける側)」と「レプリカ(複製を受け取る側)」を構成し、WordPressは基本的にソースへ接続したまま使うのが最も手堅い形です。読み込みをレプリカに振り分けたい場合は、HyperDB系のドロップインやProxySQLなどを別途組み合わせます。この記事では、MySQL 8.4 を例に GTID を使ったレプリケーションの設定手順と、WordPress側の接続方法、監視と切り替えの考え方を解説します(2026年10月現在)。

レプリケーションで何が得られるか

レプリケーションは、ソースで実行された変更をバイナリログ経由でレプリカに送り、同じ内容を再現する仕組みです。WordPressで導入する目的は、主に次の3つです。

  • 障害時の待機系:ソースが壊れても、レプリカを昇格させれば短時間で復旧できます。
  • バックアップの負荷を逃がす:バックアップをレプリカで取れば、ソースの応答速度に影響しにくくなります。
  • 読み込みの負荷分散:読み込みのクエリをレプリカに振り分けます。

ただし、レプリケーションはバックアップの代わりにはなりません。誤って記事を削除した操作も、そのままレプリカに複製されます。

また、WordPress本体には読み込みと書き込みを別のサーバーに振り分ける機能がなく、wp-config.php の DB_HOST は1つだけです。まずは「待機系とバックアップ用」として導入し、読み込み分散は必要になってから検討する順番をおすすめします。

前提と用語

ここでは次の構成を例にします。IPアドレスは自分の環境に置き換えてください。

  • ソース:10.0.0.10(WordPressが現在接続しているDBサーバー)
  • レプリカ:10.0.0.11(新しく用意するDBサーバー)
  • データベース名:wordpress

MySQL 8.0 の途中から、用語が「マスター/スレーブ」から「ソース/レプリカ」に変わり、コマンドも CHANGE REPLICATION SOURCE TO・START REPLICA・SHOW REPLICA STATUS に移りました。MySQL 8.4 では SHOW MASTER STATUS などの古い構文は使えません。MariaDB は独自のGTIDと従来の構文を使うため、この記事の手順はそのままでは当てはまりません。

作業はソースの設定変更と再起動を含みます。事前に mysqldump などでデータベースのバックアップを取り、作業時間帯をアクセスの少ない時間に設定してください。

手順1:ソース側の設定

ソースの MySQL 設定ファイル(Ubuntu なら /etc/mysql/mysql.conf.d/mysqld.cnf など、環境によって異なります)の [mysqld] セクションに次を追加します。

[mysqld]
server_id                = 1
log_bin                  = mysql-bin
gtid_mode                = ON
enforce_gtid_consistency = ON
bind-address             = 10.0.0.10
  • server_id はサーバーごとに異なる値にします。同じ値だと複製が始まりません。
  • log_bin でバイナリログを有効にします(MySQL 8.x では既定で有効ですが、名前を明示しておくと管理しやすくなります)。
  • gtid_mode と enforce_gtid_consistency で GTID(トランザクションごとの通し番号)を有効にします。レプリカが「どこまで受け取ったか」を自動で管理するため、ログファイル名と位置を手で指定せずに済みます。
  • bind-address はレプリカから接続できるアドレスにします。127.0.0.1 のままだと外部から接続できません。

設定したら MySQL を再起動し、ファイアウォールで 3306番ポートをレプリカのIPアドレスからだけ許可します。インターネット全体に3306番を開けないでください。

次に、レプリケーション専用のユーザーを作ります。

CREATE USER 'repl'@'10.0.0.11' IDENTIFIED BY 'your-strong-password' REQUIRE SSL;
GRANT REPLICATION SLAVE ON *.* TO 'repl'@'10.0.0.11';

権限名は今も REPLICATION SLAVE のままです。接続元をレプリカのIPに限定し、REQUIRE SSL で暗号化された接続だけを許可しています。WordPressが使っているDBユーザーとは別のユーザーにしてください。

手順2:レプリカ側の設定

レプリカにも MySQL をインストールし、設定ファイルに次を追加して再起動します。ソースと同じメジャーバージョン(またはそれより新しいバージョン)にしておくとトラブルが起きにくくなります。

[mysqld]
server_id                = 2
log_bin                  = mysql-bin
relay_log                = relay-bin
gtid_mode                = ON
enforce_gtid_consistency = ON
read_only                = ON
super_read_only          = ON

read_only と super_read_only は、レプリカに誤って書き込まないための設定です。レプリカに直接書き込むとソースとの内容がずれ、複製が止まる原因になります。レプリケーションによる反映はこの設定があっても行われます。

手順3:初期データをコピーする

レプリケーションは「設定した時点以降の変更」を送る仕組みなので、開始前にソースのデータをレプリカに写しておく必要があります。ソースで次のように書き出します。

# ソースで実行: ロックを最小限にして WordPress のDBを書き出す
mysqldump -u root -p --single-transaction --routines --triggers --events \
  --databases wordpress > wordpress.sql

--single-transaction を付けると、InnoDBのテーブルを一貫した状態で、サイトを止めずに書き出せます。GTIDが有効なサーバーでは、ダンプファイルに「ここまでのトランザクションは適用済み」という情報(GTID_PURGED)が自動で含まれ、レプリカはその続きから受け取ります。

ファイルをレプリカに転送し、読み込みます。

# レプリカで実行
mysql -u root -p < wordpress.sql

ここで「GTID_EXECUTED が空でないため GTID_PURGED を設定できない」という趣旨のエラーが出ることがあります。レプリカ側ですでに何らかの操作(ユーザー作成など)を行い、レプリカ独自のGTIDが記録されている場合です。新しく用意したレプリカであれば、レプリカ側で RESET BINARY LOGS AND GTIDS;(MySQL 8.0 では RESET MASTER;)を実行してから読み込み直します。このコマンドはバイナリログを消すため、ソースでは実行しないでください。

ソースに WordPress 以外のデータベースがあると、レプリカに無いデータベースへの変更が届いて複製が止まることがあるため、DBサーバーはWordPress専用にしておくと扱いやすくなります。

手順4:レプリケーションを開始する

レプリカで、接続先のソースを指定して開始します。

CHANGE REPLICATION SOURCE TO
  SOURCE_HOST = '10.0.0.10',
  SOURCE_USER = 'repl',
  SOURCE_PASSWORD = 'your-strong-password',
  SOURCE_AUTO_POSITION = 1,
  SOURCE_SSL = 1;

START REPLICA;
SHOW REPLICA STATUS\G

SOURCE_AUTO_POSITION = 1 が GTID を使って自動で位置を合わせる指定です。SHOW REPLICA STATUS\G の結果で、次の項目を確認します。

  • Replica_IO_Running: Yes と Replica_SQL_Running: Yes:両方 Yes なら複製が動いています。
  • Seconds_Behind_Source:ソースからどれだけ遅れているかの目安です。通常は 0 か小さい値になります。
  • Last_IO_Error / Last_SQL_Error:止まっている場合はここに原因が出ます。接続エラーならユーザー・パスワード・ファイアウォール・bind-address を、SQLエラーなら初期データの不一致を疑います。

最後に、ソースで記事を1件下書き保存し、レプリカの wp_posts テーブルに反映されるかを見ると、実際に動いていることを確認できます。

WordPress側の接続をどうするか

待機系・バックアップ用として使う(推奨)

wp-config.php は変更せず、WordPressはソースにだけ接続します。レプリカはバックアップ取得と障害時の切り替え用に使います。WordPress側に変更がないので、プラグインとの相性問題も起きません。

読み込みをレプリカに振り分ける

読み込みを分散したい場合は、wp-content/db.php に置くドロップインで WordPress のデータベース接続クラスを置き換える方法があります。代表的なのが Automattic の HyperDB と、その派生の LudicrousDB です。設定ファイルでソースを書き込み・読み込み用、レプリカを読み込み専用として登録します。HyperDB の設定例は次のような形です。

<?php
// db-config.php(HyperDB の設定ファイル)
$wpdb->add_database( array(
	'host'     => '10.0.0.10',
	'user'     => DB_USER,
	'password' => DB_PASSWORD,
	'name'     => DB_NAME,
	'write'    => 1,
	'read'     => 1,
) );
$wpdb->add_database( array(
	'host'     => '10.0.0.11',
	'user'     => DB_USER,
	'password' => DB_PASSWORD,
	'name'     => DB_NAME,
	'write'    => 0,
	'read'     => 1,
) );

この場合、WordPressのDBユーザーをレプリカにも作っておく必要があります(ソースで作ればレプリケーションで複製されます)。また、ドロップインは開発状況や対応バージョンが変わることがあるので、導入前に配布元の最新情報を確認してください。

読み込み分散で欠かせないのがレプリケーションの遅延への配慮です。記事を保存した直後にレプリカから読むと、まだ反映されていない古いデータが表示されることがあります。HyperDB系には、同じリクエスト内で書き込みをした後は読み込みもソースに送る仕組みがありますが、管理画面はソースだけに接続させるなど、運用側でも余裕を持たせておくと安全です。WordPressを変更したくない場合は、ProxySQL のようなプロキシでSELECT文だけをレプリカに送る方法もあります。

監視と障害時の切り替え

レプリケーションは、止まっても WordPress 側では気づきにくいのが難点です。定期的に状態を確認する仕組みを用意します。

# レプリカで実行: 複製の状態と遅延だけを抜き出す(認証は ~/.my.cnf などで設定)
mysql -e "SHOW REPLICA STATUS\G" \
  | grep -E "Replica_IO_Running:|Replica_SQL_Running:|Seconds_Behind_Source:|Last_IO_Error:|Last_SQL_Error:"

これを cron で定期実行し、No が含まれる場合や遅延が大きい場合に通知するようにしておくと、停止に早く気づけます。監視ツールを使っているなら、同じ項目を監視対象に加えます。

ソースが壊れたときは、レプリカで複製を止めて書き込み可能にし、WordPressの接続先を切り替えます。

-- レプリカで実行(ソースが復旧しないと判断した後)
STOP REPLICA;
RESET REPLICA ALL;
SET GLOBAL super_read_only = OFF;
SET GLOBAL read_only = OFF;

その後 wp-config.php の DB_HOST をレプリカのアドレスに変更し、設定ファイルの read_only も外します。古いソースが復旧しても、そのまま書き込みを受け付けさせると2台のデータが食い違うため、新しいレプリカとして作り直します。切り替え手順はテスト環境で一度通しておくのが理想です。

まとめ

  • レプリケーションは MySQL 側で設定し、WordPress はまずソースに接続したまま、レプリカを待機系とバックアップ用に使う形が手堅い構成です。
  • MySQL 8.4 では CHANGE REPLICATION SOURCE TO / START REPLICA / SHOW REPLICA STATUS を使い、GTID と SOURCE_AUTO_POSITION = 1 で位置合わせを自動化します。
  • 初期データは mysqldump --single-transaction で写し、レプリカは read_only と super_read_only で保護します。
  • 読み込み分散は HyperDB 系のドロップインや ProxySQL で行い、レプリケーション遅延を前提に設計します。
  • レプリケーションはバックアップの代わりにならないので、定期バックアップと状態監視を併用します。

お気軽にご相談ください

お見積りへ お問い合わせへ
▲