MySQL のバイナリログ、REDO ログ、UNDO ログの使用方法

WBOY
リリース: 2023-06-03 12:59:24
転載
1668 人が閲覧しました

MySQL的binlog、redo log和undo log怎么使用

1. Binlog

Binlog は、データベース内で実行された書き込み操作に関する情報を記録するために使用されます。クエリ操作は除外され、バイナリ形式でディスクに保存されます。 binlog は mysql の論理ログであり、サーバー層によって記録されます。任意のストレージ エンジンを使用する Mysql データベースは binlog ログを記録します。

  • 論理ログ: 単純に SQL ステートメントとして理解できます;

  • 物理ログ: MySQL 内のデータはデータ ページに保存されます。物理ログはデータ ページ上の変更を記録します。ここにコード スニペットを挿入します。

バイナリログは追加によって書き込まれ、各バイナリ ファイルのサイズは max_binlog_size パラメータを通じて設定できます。ファイル サイズが指定された値に達すると、ログを保存するために新しいファイルが生成されます。

binlog 使用シナリオ
プロジェクト 実際のアプリケーションでは、binlog には 2 つの主な使用シナリオ、つまりマスター/スレーブ レプリケーションとデータ リカバリがあります。

  • マスター/スレーブ レプリケーション: マスター側でバイナリ ログを有効にし、バイナリ ログを各スレーブ側に送信します。スレーブ側はバイナリ ログを再生して、マスターとスレーブのデータの一貫性を実現します。

  • データリカバリ: mysqlbinlog ツールを使用してデータをリカバリします。

#MySQL マスター/スレーブ同期原則
MySQL的binlog、redo log和undo log怎么使用MySQL的binlog、redo log和undo log怎么使用

    #マスター ノードのバイナリ ダンプ スレッド
  • スレーブ ノードがマスター ノードに接続すると、マスター ノードはログ ダンプ スレッドを作成して、バイナリ ログの内容を送信します。バイナリ ログの操作を読み取るとき、このスレッドはマスター ノードのバイナリ ログをロックします。読み取りが完了すると、スレーブ ノードを起動する前であってもロックは解放されます。


    #Slaveノード I/O スレッド
  • スレーブ ノード上でスレーブ開始コマンドが実行されると、スレーブ ノードはマスター ノードに接続するための I/O スレッドを作成し、マスター ライブラリ内の更新されたバイナリログを要求します。 I/O スレッドは、マスター ノードのバイナリ ログ ダンプ プロセスから更新を受信した後、それをローカルのリレーログに保存します。

  • スレーブ ノード SQL スレッド
  • SQL スレッドは、次の処理を担当します。リレーログの読み取り 内容は特定の操作に解析されて実行され、最終的にマスターとスレーブのデータの一貫性が確保されます。
  • MySQL データベースのマスターとスレーブの同期原理



  • binlog の内容

上で述べたように、binlog は論理ログであり、単純に SQL ステートメントとして理解できますが、実際には、実行された SQL ステートメントの逆ロジックも含まれています。 delete は削除自体と逆挿入情報に対応し、update には対応する更新が実行される前後のデータ行に関する情報が含まれ、insert には独自の挿入情報と対応する削除情報が含まれます。
binlog 形式

binlog 形式には、ステートメント、行、混合の 3 つがあります。 MySQL 5.7.7 より前では、デフォルトでステートメントが使用され、MySQL 5.7.7 以降では、デフォルトで行が使用されていました。ログの形式は、my.ini 構成ファイルの binlog-format を通じて変更できます。 (1) ステートメント: SQL ステートメントに基づくステートメントベースのレプリケーション (SBR) データを変更する各 SQL ステートメントはバイナリログに記録されます。

利点: 特定の行の変更を具体的に記録する必要がないため、スペースが節約され、IO が削減され、パフォーマンスが向上します。
  • 欠点: sysdate() や sleep() などの操作を実行すると、マスター データとスレーブ データの間で不整合が生じる可能性があります。
  • (2) 行: 行ベース レプリケーション (RBR)、それは発生します。 SQL ステートメントのコンテキスト関連情報は記録されませんが、どのレコードが変更されたかの詳細は記録されます。

利点: 各行レコードの変更の詳細が詳細に記録されるため、データを正しくコピーできない状況は発生しません。
  • 欠点 : 各レコード変更の詳細が詳細に記録されるため、大量のログ コンテンツが生成されます。 update ステートメントがあり、多くのレコードが変更されたとすると、変更された各レコードは binlog に記録されます。特に、テーブルの変更操作では、テーブル構造の変更によりレコードの各行が変更され、その結果、ログの量が突然増加します。
  • (3)混合:上記によると、Statement と Row にはそれぞれ長所と短所があるため、混合バージョンはこの 2 つを混合したものであるように見えます。通常はステートメント形式で保存しますが、ステートメントが解けない場合は行形式で保存します。
  • 特に、上で述べたように、新しいバージョン (MySQL 5.7.7 以降) では、デフォルトで行形式が使用されます。ここでの行も、それに応じて最適化されています。テーブル変更操作が発生した場合、記録にはステートメント形式が使用されます。残りの操作では引き続き行形式が使用されます。


binlog フラッシュのタイミング

InnoDB ストレージ エンジンの場合、binlog はトランザクションが送信されたときにのみ記録されます。この時点では、レコードはまだメモリ内にあります。 、MySQL は sync_binlog を渡し、binlog のフラッシュのタイミングを制御します。値の範囲は 0 ~ N:

  • 0: ディスクへのフラッシュは強制されず、いつディスクに書き込むかはシステムが決定します;

  • 1: バイナリログは、ディスクに書き込む;

  • N: N トランザクションごとに、バイナリログがディスクに書き込まれます;

上記からわかるように、sync_binlog の最も安全な設定は 1 であり、これは MySQL バージョン 5.7.7 以降のデフォルト値でもあります。ただし、より大きな値を設定するとデータベースのパフォーマンスが向上するため、実際の状況では、値を適切に増やし、ある程度の一貫性を犠牲にしてパフォーマンスを向上させることもできます。

binlog の物理ファイル サイズ

my.ini 構成ファイルにある max_binlog_size パラメータを構成することで、binlog のサイズを制御できます。ログのサイズが binlog ファイルの容量制限を超えると、システムは新しいファイルを作成してログの保存を継続します。トランザクションが比較的大きい場合、またはログが増えて、トランザクションが占有する物理スペースが大きすぎる場合はどうすればよいでしょうか? MySQL には自動削除メカニズムが用意されており、これは my.ini 設定ファイルのexpire_logs_days パラメータを日単位で設定することで解決できます。このパラメータが 0 の場合は削除されないことを意味し、N の場合は N 日目後に自動的に削除されることを意味します。

2. redo ログ

redolog は、InnoDB エンジンの独自のログ システムです。これは主にトランザクションの耐久性とクラッシュセーフ機能を実現するために使用されます。 Redolog は物理ログであり、SQL ステートメントの実行後にデータ ページ上の特定の変更を記録します。
MySQL の実行中にデータがディスクからメモリにロードされることは誰もが知っています。 SQL文を実行してデータを変更した場合、実際には変更内容は一時的にメモリ上に保存されるだけで、このときに電源が切れるなどの事情が発生すると変更内容は失われます。したがって、データを変更した後、MySQL はこれらのメモリ レコードをディスクにフラッシュする機会を探します。しかし、主に 2 つの側面でパフォーマンスの問題があります:

InnoDB はページのデータ単位でディスクと対話し、完全なデータ ページがフラッシュされた場合、トランザクションはページ上の数バイトのみを変更する可能性があります。ディスクに戻すと、リソースが無駄になります。

トランザクションには、複数のデータ ページが含まれる場合があります。これらのデータ ページは、論理的に連続しているだけで、物理的に連続していません。ランダム IO を使用します。パフォーマンスが低すぎます。

したがって、MySQL は、トランザクションによってデータ ページに加えられた特定の変更を記録し、その REDO ログをディスクにフラッシュするように REDO ログを設計しました。疑問に思われるかもしれませんが、もともと io を減らしたかったのですが、これでは別の io が追加されるのではないか? InnoDB の設計者は、設計の開始時にこれらを考慮しました。通常、REDO ログ ファイルは小さく、ディスクのフラッシュ中にシーケンシャル I/O が使用されます。ランダム I/O と比較してパフォーマンスが向上します。

REDO ログの基本概念
REDOLOG は 2 つの部分で構成されます。1 つはメモリ内のログ キャッシュ REDO ログ バッファで、もう 1 つはメモリ内のログ ファイル REDO ログ ファイルです。ディスク。データ レコードが変更されるたびに、これらの変更はまず REDO ログ バッファに書き込まれ、その後、メモリ内の変更が REDO ログ ファイルにフラッシュされる適切な機会を待ちます。最初にログを書き込んでからディスクに書き込むこの技術が WAL (Write-Ahead Logging) 技術です。 REDO ログはデータ ページの前にディスクにフラッシュされることに注意してください。クラスタード インデックス、セカンダリ インデックス、および UNDO ページへの変更はすべて REDO ログに記録する必要があります。

コンピュータ オペレーティング システムでは、ユーザー空間のバッファ データは通常、ディスクに直接書き込むことができず、オペレーティング システムのカーネル空間バッファ (OS バッファ) を経由する必要があります。)。したがって、REDO ログ バッファを REDO ログ ファイルに書き込むと、実際には最初に OS バッファに書き込まれ、次にシステム コール fsync() を通じて REDO ログ ファイルにフラッシュされます。プロセスは次のとおりです。
mysql サポート innodb_flush_log_at_trx_commit パラメータを使用して、REDO ログ バッファを REDO ログ ファイルに書き込む 3 つのタイミングを設定できます。各パラメータ値の意味は次のとおりです: MySQL的binlog、redo log和undo log怎么使用

パラメータ値 0 (遅延書き込み) 1 (リアルタイム書き込み、リアルタイムブラッシング) 2 (リアルタイム書き込み、遅延ブラッシング)

MySQL的binlog、redo log和undo log怎么使用
redo ログの記録形式
REDO ログは固定サイズ、周期書き込み形式を採用しており、REDO ログがいっぱいになると再度最初から書き込まれます。なぜこのように設計されているのでしょうか?
REDO ログの主な目的は、データ ページのフラッシュの要件を軽減することです。 Redolog はデータ ページの変更を記録しますが、データ ページもディスクにフラッシュバックされると、これらの記録は役に立たなくなります。したがって、MySQL が以前の redolog の有効期限が切れたと判断すると、新しいデータが無効なデータを上書きします。では、対象となるべきかどうかはどのように判断すればよいのでしょうか?
MySQL的binlog、redo log和undo log怎么使用
上の図はREDOログファイルの模式図で、write posはREDOLOGが現在記録しているログシーケンス番号LSN(ログシーケンス番号)を表します。データ ページがディスクにフラッシュされると、REDO ログ ファイル内の LSN が更新され、この LSN より前のデータがディスクに書き込まれたことが示されます。この LSN がチェック ポイントです。書き込み pos とチェック ポイントの間の部分は、新しいレコードを記録するために使用される redolog の予備部分です。チェック ポイントと書き込み pos の間の部分は、redolog によって記録されたデータ ページの変更された部分ですが、データ ページは現時点では、部分はディスクにフラッシュされていません。書き込み pos がチェック ポイントに追いつくと、まずチェック ポイントを前方に押し出し、その位置を空けてから、新しいログを記録します。

innodb を起動すると、前回正常にシャットダウンされたか異常にシャットダウンされたかに関係なく、常に回復操作が実行されます。リカバリ中、最初にデータ ページ内の LSN がチェックされ、この LSN が REDO ログ内の LSN、つまり書き込み位置より小さい場合、データ ページ上の未完了の操作が REDO ログに記録されていることを意味します。そして、最も近いチェックポイントから開始され、データの同期が開始されます。

データ ページの LSN が redolog の LSN より大きい可能性はありますか?答えはもちろん可能です。これが発生すると、redolog 以降の部分はやり直しされません。これ自体、実行された内容をやり直す必要がないことを意味するためです。
REDO ログと binlog の違い

#意味
トランザクションが送信されると、REDO ログ バッファー内のログがOS バッファには書き込まれませんが、毎秒 OS バッファに書き込み、fsync() を呼び出して REDO ログ ファイルに書き込みます。つまり、0 に設定すると、データは (約) 毎秒ディスクに書き込まれ、システムがクラッシュすると 1 秒間のデータが失われます。
トランザクションが送信されるたびに、REDO ログ バッファー内のログが OS に書き込まれます。バッファと fsync() が呼び出され、REDO ログ ファイルにフラッシュされます。この方法では、システムがクラッシュしてもデータは失われませんが、各送信がディスクに書き込まれるため、IO パフォーマンスは低下します。
各送信は OS バッファーにのみ書き込まれ、その後 fsync() が毎秒呼び出され、 OS バッファ内のデータ ログは REDO ログ ファイルに書き込まれます。
##REDO ログbinlogファイル サイズREDO ログのサイズは固定です。 Binlog は、構成パラメータ max_binlog_size を通じて各 binlog ファイルのサイズを設定できます。 実装方法REDO ログは InnoDB エンジン層によって実装され、すべてのエンジンがこれを備えているわけではありません。 Binlog はサーバー層で実装されており、すべてのエンジンで binlog ログを使用できます記録方法REDO ログはループ書き込み方式で記録されます。最後まで書き込むと最初に戻ってループでログを書き込みます。 binlog は追加で記録されます。ファイル サイズが指定された値より大きい場合、以降のログは新しいファイルに記録されます適用可能なシナリオredo ログはクラッシュ リカバリに適しています (クラッシュ セーフ)binlog はマスター/スレーブ レプリケーションとデータ リカバリに適しています

これは、binlog と REDO ログの違いからわかります。binlog ログはアーカイブにのみ使用され、binlog のみに依存するとクラッシュ セーフ機能がありません。ただし、REDO ログだけは機能しません。REDO ログは InnoDB に固有であり、ログ内のレコードはディスクに書き込まれた後に上書きされるからです。したがって、データベースをシャットダウンして再起動したときにデータが失われないように、binlog と REDO ログの両方を同時に記録する必要があります。
2 段階の送信
上記では redolog と binlog について簡単に紹介しましたが、データを変更する場合、これらの変更を保存して実装しますが、1 つは物理ログ、もう 1 つは論理ログです。では、彼らはどのようにして修正プロセスを実行したのでしょうか?

今実行する update ステートメントがあるとします。 update from table_name set c=c 1 where id=2 の場合、実行プロセスは次のとおりです。

  • First locate id=2 このレコード;

  • エグゼキュータは、エンジンによって与えられた行データを取得し、この値に 1 を加えて、新しいデータ行を取得し、エンジン インターフェイスを呼び出します。この新しいデータ行を書き込みます;

  • エンジンはこの新しいデータ行をメモリに更新し、更新操作を redolog に記録します。この時点では、redolog は準備状態です。 。次に、実行が完了し、いつでもトランザクションを送信できることを実行者に通知します。

  • 実行者は、この操作のバイナリログを生成し、バイナリログをディスクに書き込みます。

  • #エグゼキューターはエンジンのコミット トランザクション インターフェイスを呼び出し、エンジンは書き込まれたばかりの REDO ログをコミット状態に変更し、更新が完了します。

#概略図は次のとおりです。


MySQL的binlog、redo log和undo log怎么使用 REDOログの書き込みを準備とコミットの 2 つのステップに分割するこのプロセスは、2 フェーズ コミットと呼ばれます。

redolog と binlog はどちらもトランザクションのコミット ステータスを表すために使用できます。2 フェーズ コミットは 2 つの状態の論理的な一貫性を維持するために使用されます。 2 フェーズ コミットを使用せず、一方を最初に記述し、次にもう一方を記述した場合、問題が発生する可能性があります。

現時点では、更新はまだ例として使用されています。現在の id=2 で、フィールド c=0 があると仮定します。次の状況をそれぞれ分析します:


最初に redolog を書き込み、次に binlog を書き込みます redolog が最初に書き込まれると仮定します。完了しましたが、binlog はまだ書き込まれていません。書き終えたとき、MySQL が突然例外に遭遇し、再起動されました。 redolog は以前に書き込まれているため、システムの再起動後も変更されたレコードがまだ存在するため、リカバリ後のこの行の c の値は 1 になります。ただし、システムが再起動されたため、このレコードはバイナリログに存在しません。後でログをバックアップすると、このステートメントは保存されたバイナリログには存在しません。次に、このバイナリ ログを使用して一時ライブラリを復元する必要がある場合、このステートメントのバイナリ ログが失われているため、今回は一時ライブラリは更新されないことがわかります。復元された行の c の値は 0 です。元のライブラリの値と同じですが、異なります。

最初に binlog を書き込み、次に redolog を書き込みます。 最初に binlog を書き込み、次に redolog を書き込むときにシステムを再起動します。再起動後、redolog には c を変更した記録はなく、この時点では c の値は 0 のままです。ただし、binlog には「c を 0 から 1 に変更する」というログが記録されています。そのため、後で binlog を使用して復元すると、トランザクションが 1 つ増えてしまい、復元された行の c の値は 1 となり、元のデータベースの値とは異なります。

したがって、要約すると、最初にログが書き込まれ、次に別のログが書き込まれると、データベースのステータスは、binlog を使用して復元されたライブラリのステータスと一致しなくなります。

3. undo log

undolog は主に、特定の行レコードが変更される前の状態を記録するために使用され、変更前のデータを記録します。 undolog を使用すると、トランザクションがロールバックされたときにレコードをトランザクション開始前の状態に復元できます。トランザクションの原子性と耐久性も undolog によって実現されます。アンドゥ ログは主にデータの論理的な変更を記録します。たとえば、INSERT ステートメントは DELETE アンドゥ ログに対応します。各 UPDATE ステートメントについては、反対側の UPDATE アンドゥ ログに対応するため、エラーが発生したときにロールアップできます。トランザクション前のデータ状態に戻ります。データ回復プロセス中に、binlog と redolog を組み合わせることで、データ回復の正確性を保証できます。

アンドゥログの機能プロセスは次のとおりです:


MySQL的binlog、redo log和undo log怎么使用

  • トランザクションが開始される前に、変更前のバージョンをアンドゥログに書き込みます;

  • 変更を開始し、変更したデータをメモリに保存します;

  • アンドゥログをディスクに保存します;

  • データ ページをディスクにフラッシュします;

  • トランザクションの送信;

redolog と同様に、undolog もデータ ページをフラッシュする必要がありますディスクに戻ります。アンドゥログが完了すると、そこに記録された情報を使用してトランザクションをロールバックし、データを回復できます。

トランザクションでは、同じデータが複数回変更される可能性があるため、各変更前の記録をアンドゥログに記録する必要がありますか?この場合、アンドゥログのログ量が多くなりすぎるため、この時にリドログが活躍することになります。トランザクション内で同じレコードが変更された場合、undolog はトランザクション開始前の元のレコードのみを記録し、このレコードが再度変更されると、redolog はその後の変更を記録します。データ回復プロセスでは、redolog と undolog の機能を調整し、ロールフォワード操作とロールバック操作を行うことによってデータ回復が完了します。プロセスは次のとおりです:
MySQL的binlog、redo log和undo log怎么使用


以上がMySQL のバイナリログ、REDO ログ、UNDO ログの使用方法の詳細内容です。詳細については、PHP 中国語 Web サイトの他の関連記事を参照してください。

関連ラベル:
ソース:yisu.com
このウェブサイトの声明
この記事の内容はネチズンが自主的に寄稿したものであり、著作権は原著者に帰属します。このサイトは、それに相当する法的責任を負いません。盗作または侵害の疑いのあるコンテンツを見つけた場合は、admin@php.cn までご連絡ください。
最新の問題
人気のチュートリアル
詳細>
最新のダウンロード
詳細>
ウェブエフェクト
公式サイト
サイト素材
フロントエンドテンプレート
私たちについて 免責事項 Sitemap
PHP中国語ウェブサイト:福祉オンライン PHP トレーニング,PHP 学習者の迅速な成長を支援します!