MySQL レプリケーションの方式をまとめてみた

本記事は TechHarmony Advent Calendar 2024 12/24付の記事です

こんにちは!2024年度入社の野上です。

私は現在MySQLのレプリケーションを実装する案件に携わっており、勉強の毎日です。

初めて聞く用語も多く、用語をMySQLの公式ドキュメントで調べてみては、また知らない用語が現れることが多々。

レプリケーションの方式がたくさんある。。。何が違うんだろう。。。

そんな私が、初心者ながらレプリケーションの方式をまとめて記事にしました。

MySQLで初めてレプリケーションを実装される方が、方式を選ぶ際のご参考になれば嬉しいです。

 

レプリケーションとは

まずレプリケーション(英:replication)は、日本語で「複製」という意味です。
ここでMySQLのレプリケーションとは、MySQLのデータベースを違うサーバに複製するということを指します。

 

レプリケーションの目的

なぜレプリケーションが必要になるのか。それは、以下のような目的があります。

  • 可用性の向上
    • ソースサーバ(メインで使用するDBサーバ)に障害が発生した際に、レプリカサーバ(複製されたDBサーバ)を参照先とすることでシステムの稼働が停止することを防ぎます。
  • 負荷分散
    • 複数のサーバからの参照を分散させることで、処理時間の短縮が期待できます。

 

レプリケーションの動作

レプリケーションという概念は理解できたと思いますが、実際にレプリケーションはどのような動作が行われているのかはわかりづらいと思います。

以下にレプリカサーバにデータの変更がレプリケーションされるまでの動作を説明します。

 

  1. ソースサーバに対してトランザクションのコミットが実行される
    • トランザクションとは、データベース操作の複数の処理をまとめて1つの処理単位としたものです。  
    • トランザクションを開始後、複数の処理を行い、「コミット」を実行することで、そのトランザクションに含まれる処理がデータベースに反映されます。
  2. コミットを実行したトランザクションがバイナリログに書き込まれる
    • バイナリログとは、データベース内で行われたすべての変更の記録を保持するログファイルのことです。
  3. レプリカサーバ上のI/Oスレッドがソースサーバの変更を検知してリレーログに書き込む
    • I/Oスレッドとは、レプリカサーバで動作するプロセスのことで、バイナリログを読み取り、レプリカサーバのリレーログへ書き込む処理を行います。
    • リレーログとは、ソースサーバから転送されたログを記録するファイルのことです。
  4. SQLスレッドがリレーログを読み取りレプリカサーバのデータベースに適用する
    • SQLスレッドとは、レプリカサーバで動作するプロセスのことで、リレーログを読み取ってソースサーバと同様の変更をデータベースに反映させる処理を行います。

 

レプリケーション方式

MySQLではソースとレプリカのレプリケーションの方式を選択することができます。

方式は、レプリカ上のI/Oスレッドがソースの変更をリレーログに書き込む処理を、コミットの完了までに含むかどうかで異なります。

連続するトランザクション処理では、処理時間に差が生まれます。処理をコミット完了までに含まない場合は処理時間短縮できます。

しかし、この処理をコミットの完了までに含まない場合、障害発生時にソースとレプリカの整合性が保たれない場合があります。

つまり、方式を選択することで、パフォーマンスや可用性が変化するということです。

よって、方式はシステムの要件に合わせて決定する必要があります。

本記事では、以下の方式について違いを説明します。

  1. 非同期レプリケーション
  2. 準同期レプリケーション
  3. グループレプリケーション

 

非同期レプリケーション

MySQLのデフォルトのレプリケーション方式です。
トランザクションに含む処理は以下の通りです。

 コミットを実行する

 ソースで「データの更新」と「バイナリログの更新」を行う

 コミットが完了する

以下の流れはトランザクションの処理に含まれません。

❶ ソースのバイナリログの更新を検知し、I/Oスレッドが更新を受け取ってレプリカのリレーログに書き込む

❷ SQLスレッドがリレーログの内容をデータに反映させる

ここでは、レプリカサーバでの処理が、トランザクションの処理に含まれていません。
これが「非同期」と呼ばれる所以です。

 

ここで非同期レプリケーションのメリット・デメリットをまとめます。

メリット
  • パフォーマンス
    • レプリカへの更新反映を待たずにコミットを完了させるため、他の方式と比較して処理時間が短いです。
デメリット
  • 可用性の不安
    • レプリカへの更新反映前にソースで障害発生すると、障害発生前の変更がレプリカに反映されません。

 

準同期レプリケーション

準同期レプリケーションは、トランザクションに含まれる処理が非同期レプリケーションと異なります。

トランザクションに含む処理は以下の通りです。

 コミットを実行する

 ソースで「データの更新」と「バイナリログの更新」を行う

 ソースのバイナリログの更新を検知し、I/Oスレッドが更新を受け取ってレプリカのリレーログに書き込む。

④ コミットが完了する

以下の流れはトランザクションの処理に含まれません。

❶ SQLスレッドがリレーログの内容をデータに反映させます。

準同期レプリケーションでは、レプリカへのログの転送を待ってからコミットが完了するのです。

 

ここで準同期レプリケーションのメリット・デメリットをまとめます。

メリット
  • 可用性
    • レプリカへログが転送されるのを待ってからコミットが完了するため、ソースで障害が発生してもコミットが完了したデータの変更をレプリカが失いません。
デメリット
  • パフォーマンス
    • レプリカへログが転送されることを待つため、コミットが完了するまでの応答速度が遅くなります。

 

グループレプリケーション

グループレプリケーションは3台以上のDBサーバで構成される際に使用されます。

全てのサーバが、プライマリ(グループレプリケーションでは書き込みが行われるサーバを『ソース』ではなく『プライマリ』と呼ぶ)やレプリカにもなり得るため、トランザクションの実行有無の管理が大変です。

この方式は『GTID(グローバルトランザクションID)』が導入されたことで、可能となりました。

GTIDとは・・・
 発生元のサーバー (ソース) でコミットされた各トランザクションに関連付けられる一意の識別子です。 この識別子は、レプリケーション構成内のすべてのサーバーで一意です。
 GTIDを使用することで、どのサーバにどのトランザクションまで実行してあるのかがわかるため、レプリケーション設定時にレプリケーションを始めるトランザクションを自動で設定してくれます。

 

トランザクションに含む処理は以下の通りです。

 コミットを実行する

 プライマリで「データの更新」と「バイナリログの更新」を行う

 プライマリのバイナリログの更新を検知し、プライマリ以外のサーバのI/Oスレッドが更新を受け取ってリレーログに書き込む

④ コミットが完了する

以下の流れはトランザクションの処理に含まれません。

❶ プライマリ以外のサーバのSQLスレッドがリレーログの内容をデータに反映させます。

プライマリ以外のサーバにログを転送してからコミットが完了する点は準同期レプリケーションと同様ですが、
グループレプリケーションではすべてのサーバへログの転送が行われたことを待ってからコミット完了されます。(設定により変更も可能)

 

ここでグループレプリケーションのメリット・デメリットをまとめます。

 

メリット
  • 可用性
    • 2つ以上のサーバにレプリケーションを行うため、2台構成のレプリケーションと比較して可用性が向上します。
    • レプリカが1台の準同期レプリケーションよりも可用性が高いです。
  • 負荷分散
    • 全てのサーバがプライマリになることができるため、負荷を分散させることが可能です。
デメリット
  • パフォーマンス
    • グループ内すべてのサーバへ更新を転送することを待つため、処理速度が低下します。
    • 準同期よりも処理速度は遅くなります。

 

まとめ

本記事ではMySQLのレプリケーション方式について、各方式の利点をまとめました。

実際、レプリケーション方式はシステムが求める要件によって選択する必要があります。

この記事にまとめたような各方式の利点を軸に、レプリケーション方式を選択してみてください!

タイトルとURLをコピーしました