Hadoop namenode高可用性分析:QJMコアソースコードの解釈

Hadoop namenode高可用性分析:QJMコアソースコードの解釈

背景紹介

HDFS namenodeは、書き込み操作を受け入れるとログを記録します。最も古いHDFSログはローカルに書き込まれます。再起動または失敗するたびに、データの不整合なしに、ローカルミラーファイル+操作ログを介してダウンタイム前の状態に復元できます。ハイアベイラビリティ(HA)を実現したい場合は、ログを1台のマシンに書き込みます。ディスクに問題があると、再起動後の復旧ができず、データの不整合が発生します。新しく作成したファイルが存在せず、削除に成功する現象です。これは、分散ストレージシステムでは許容できないものです。

スタンドアロンシステムでは、問題を確実に回復できるようにWAL(事前書き込みログ)ログが使用されます.HDFSの対応する操作ログ(EditLog)は、各操作の動作の説明を記録するために使用されます。ここでは、editlogの形式を簡単に紹介します。

ファイル形式

  • 後述のセグメントであるログedits_inprogress_txidの編集、txidはログファイルの最初のトランザクションIDを表します
  • ファイナライズされたログは、一貫性があり、edits_fristTxit_endTxidが変更されなくなったログファイルです。

コンテンツフォーマット

ファイルヘッダー:バージョン番号+トランザクションヘッダー識別子があります

ドキュメントの内容

1操作タイプ-1バイト
2ログ長-4バイト
3トランザクションtxid-8バイト
4特定のコンテンツ
5チェックサム-4バイト

ファイルの終わり:トランザクション識別子

以前にジャーナル分散ログがない場合、ログがフラッシュされるたびに識別子INVALID_TXIDがログの最後に追加され、次のフラッシュで識別子が上書きされますが、現在のバージョンではこの識別子が削除されることに注意してください

スタンドアロンシステムの信頼性はeditlogを介して実現できますが、分散環境では、ネームノードの高可用性を確保するために、少なくとも2つのネームモードが必要です。高可用性と高信頼性を実現するための最初のステップは、HDFS操作ログ(EditLog)にコピーがあることを確認することです。ただし、コピーの存在は新しい問題を引き起こします。複数のコピー間の一貫性を確保する方法は、分散ストレージによって解決する必要がある問題です。このため、Clouder社はこの問題を解決するためにQJM(Quorum Journal Manager)を開発しました。

ジャーナルノードクラスター

Journalノードは、paxosのアイデアに従って設計されています。今回の書き込みが成功した場合でも、書き込みの半分だけが成功を返します。したがって、ジャーナルはクラスターを形成するために3つのユニットを展開する必要があります。コアとなるアイデアは、クォーラムの半分以上を複数のジャーナルノードに非同期で書き込むことです。

ロギングプロセス

編集ログを複数のノードに書き込むプロセスを簡単に説明します。

ActiveNamenodeはログをJournalNodeに書き込み、RPCを使用して
StandbyNamenodeに接続し、finallyログを同期してミラーファイルを生成し、JournalNodeはHTTPを使用してデータを直接同期します。

ActiveNamenodeは、トランザクション要求を受信するたびにログを書き込みます。このログ書き込みプロセスを分析するための優れた記事がインターネット上に多数あります。ここでは、学習する価値のあるものといくつかの優れた設計アイデアの概要を示します。

1バッチフラッシュディスク

これは、ログを書き込むための一般的な方法であると言えます。すべてのログがディスクにフラッシュされると、効率が非常に低くなります。バッチがフラッシュされると、多くの小さなIOをマージできます(MySQLグループコミットと同様)。

2ダブルバッファスイッチング

bufCurrentログ書き込みバッファ
bufReadyディスクフラッシュするためバッファ

ダブルバッファがない場合は、ログバッファがいっぱいであるため、ディスクを強制的にフラッシュする必要があります。ディスクのフラッシュは、オペレーティングシステムのカーネルバッファだけでなく、ディスクデバイスにも書き込むことがわかっています。これは非常に時間のかかる操作です。ダブルバッファ、ディスクフラッシュ操作、ログ書き込み操作を同時に実行できるため、Namenodeのスループットが大幅に向上します。

データ復旧

アクティブネームノードのクラッシュ後にデータが復元されます。スタンバイネームノードが引き継いだ後、アクティブネームノードに変更した後に最初に行う必要があるのは、以前のアクティブネームノードのクラッシュを復元することです。これにより、ジャーナルノードの編集ログデータに一貫性がなくなります。したがって、スタンバイノードが正式に動作可能であることをアナウンスできる場合、ジャーナルノードクラスタのデータは一貫している必要があります。以下は主にリカバリアルゴリズムを分析します。リカバリアルゴリズムは正式にはマルチパクソスアルゴリズムに基づいています。

マルチパクソス

Paxosプロトコルは、分散システムで最も複雑なプロトコルです。インターネットは主に概念と理論に関するものであり、実践に関するものではないため、この記事はPaxosをよりよく理解するためにも書かれています。Paxosはインターネット上にたくさんの情報を持っています。Denboによって最近共有されたpptを読むことができます。これは非常に理解しやすいです。
マルチパクソスはパクソスの改良版です。ベーシックパクソスはパクソスのラウンドごとに新しい提案を生成します。これは通常、zkリーダー選挙のように、複数のポイントによって記述され、誰でも選挙を開始できます。ただし、ほとんどの分散システムにはリーダーがあり、すべてにプロポーザルを開始するリーダーがあります。最初のプロポーザル番号を使用して、承認フェーズを直接実行できます。qjmの実践からすると、RAFTに少し似ています。リーダーの役割を持っています。現在の提案番号エポックを再利用する

データ回復プロセス:

1分離
2リカバリソースの選択
3リカバリ

1つの分離

回復を始める前に、彼は突然の復活を防ぎ、脳の分裂を引き起こすために彼の元を隔離する必要があります。分離手段はnew​​Epochで、新しいエポックを再生成します。アルゴリズムは、すべてのjnノードの中で最大のものを計算し、1を加算してから、ジャーナルノードクラスターにエポックを更新するように命令します。更新後、前任者が復活した場合、エポックがジャーナルクラスターよりも小さいため、ジャーナルノードクラスターにデータを書き込むことができず、拒否されます。

新しいエポックコードは次のように生成されます。
Hadoop namenode高可用性分析:QJMコアソースコードの解釈

拒否されたコードは次のとおりです。
Hadoop namenode高可用性分析:QJMコアソースコードの解釈

2リカバリソースを選択します

分離が成功したら、復元するコピーを選択する必要があります。namenodeのクラッシュの時刻が異なるため、各ジャーナルの最新のセグメントファイルに一貫性がありません。したがって、ジャーナルクラスターの最新のコピーからの情報が必要です。
Hadoop namenode高可用性分析:QJMコアソースコードの解釈

3回復

分離が成功すると、回復が始まります。分散システムでは、各ノードのデータについて合意に達するために、古典的なアルゴリズムはPaxosです。Paxosによると、2つの段階に分けられ、次のように説明されます。QJMの2つの段階は、PrepareRecoverとAccepteRecoverに対応します。Paxosであることに注意してください。それはマルチパクソスです、違いはエポックが再利用するということです。コアアルゴリズムはPaxosです。

3.1 PrepareRecovery

すべてのジャーナルノードにプロポーザルを送信し、復元されたセグメントを選択して、セグメントに関する次の情報を返します。

  1. セグメントがあるかどうか
  2. セグメントがある場合は、セグメントのステータスが添付されます
  3. commitTxnIdジャーナルノードがコミットしたトランザクションIDのcommitTxnId。QJMは、ログの同期が行われるたびに、各AsyncLoggerのcommitdTxnIdを更新します。ジャーナルノードは、各要求で渡されたcommitTxnIdもチェックします。それより大きい場合は、ローカルで更新されます。
  4. lastWriterEpochの最新のログファイルに対応する番号は、新しいセグメントが書き込まれるたびに、つまりstartLogSegmentRPC呼び出しごとに記録または更新されます。
  5. AcceptedInEpochは、最後に受け入れられた提案番号を再開し、受け入れフェーズで永続化しました。AcceptedInEpochがLastWriterEpochより大きくなるのはいつですか?paxosプロトコルの実行後に受け入れが成功した場合、エポックが1であり、lastWriterEpochも1であると想定します。現在のエポック2(newEpoch)でしたが、ファイナライズされたとき、最後のジャーナルノードに送信されたときにActiveNamenodeがクラッシュしました。この時点では、ファイナライズリクエストを受信して​​いません。彼のAcceptedInEpochは2で、lastWriterEpochはstargLogSegmentがないため1のままです。 、したがって、まだ1です。この場合、次回paxosリカバリを実行するときに、AcceptedInEpochに対応するセグメントを復元する必要があります。これは、コミットフェーズで2セグメントコミット(2PC)が失敗したときに一貫性を確保するための、フォールトトレラントな方法でもあります。描いてください。

3.2 AccepteRecovery

PrepareRecoveryで選択した結果に応じて、アルゴリズムに従ってセグメントを選択し、すべてのジャーナルに承認リクエストを送信して、指定したセグメントに同意するように伝えます。合意に達する方法については、以下で分析します。

PrepareRecoverはPaxosの最初のステージに対応し、AccepteRecoverは2番目のステージに対応します

特定の2PC実装を分析する前に、写真を撮って一般的なプロセスを理解してください
Hadoop namenode高可用性分析:QJMコアソースコードの解釈

上図の主なプロセスは次のように要約されます。

  • 回復の準備
  • PrepareRecoverRequest
  • prepareResponse
  • checkRequestを実行し、同期ソースとしてセグメントを選択します
  • 回復を受け入れる
  • クライアントがAcceptRecoveryを開始します
  • ジャーナルはAcceptRecoveryリクエストを受け入れます
  • リクエストを受け入れた後、セグメントにトランザクションが含まれているかどうかを確認します
  • リクエストを受け入れた後、最後のパクソが正常に完了したかどうかを確認します。ここでの確認は、データを同期する必要があるかどうかを判断することです。
  • コミット

各段階の主な行動分析は次のとおりです。

PrepareRecoverRequest(P1a)

最初の段階で、提案を開始します

Hadoop namenode高可用性分析:QJMコアソースコードの解釈
サーバージャーナル(prepareResponse)P1b:
Hadoop namenode高可用性分析:QJMコアソースコードの解釈
checkRequest

ジャーナルはnewEpochでプロポーザルを開始し、checkRequestを介してプロポーザルを受け入れ、プロポーザル番号エポックの有効性を確認し、対応する操作を実行します。

Hadoop namenode高可用性分析:QJMコアソースコードの解釈
同期ソースとしてセグメントを選択します

リカバリの準備の最初の段階が完了した後、ノードの半分以上が戻ってきた場合は、返されたこれらのログファイルセグメントから最適なコピーを選択する必要があります。これが選択アルゴリズムです

選択したアルゴリズムは次のとおりです。

  1. 一部のジャーナルノードには対応するセグメントが含まれていない可能性があるため、復元するセグメントを含むファイルを選択することができます。
  2. 両方ともセグメントファイルを保護し、startTxidを確認します。等しくない場合、これは非論理的です。例外をスローします。
  3. セグメントがある場合は、それらのステータスを比較します。finalizedは最新のものを表すため、FinalizerはInProgressよりも優先されます
  4. 両方のセグメントがファイナライズされている場合は、それらの長さが同じであるかどうかを確認します。ファイナライズされたものは変更されず、長さは同じである必要があるため、不整合も異常です。同じ場合は1つ選択してください
  5. エポックを比較します。エポックが異なる場合は、最新のエポックを選択します。ここでは、上記のAcceptedInEpochとlastWriterEpochの比較に特に注意してください。
  6. エポックが等しい場合は、セグメントファイルの長さを比較し、
    Hadoop namenode高可用性分析:QJMコアソースコードの解釈
    AcceptRecovery(P2a)を開始するために長いクライアントを選択します。

第1段階の完了は、承認要求を開始するための提案として提案応答から値を選択することです。選択アルゴリズムは上記で説明した後、承認要求が発行されます。

ジャーナルはAcceptRecoveryリクエストを受け入れます(P2b)

承認フェーズでは、承認フェーズで承認が行われるため、提案番号のエポックを確認する必要があります。

Hadoop namenode高可用性分析:QJMコアソースコードの解釈

1リクエストを受け入れた後、セグメントにトランザクションが含まれているかどうかを確認します

Hadoop namenode高可用性分析:QJMコアソースコードの解釈

2リクエストを受け入れた後、最後のパクソが正常に完了したかどうかを確認します。ここでの確認は、データを同期する必要があるかどうかを判断することです。

前回復元されなかったデータ、つまり、paxosの最後のラウンドが失敗し、新しい復元が開始されたかどうかを確認します。ここでは、paxosインスタンスの最後のラウンドが完了して正しく終了するかどうかを確認します。正常に終了しない場合は、提案番号を確認する必要があります。この受け入れのエポック数が最後のパクソスのエポックよりも小さい場合、それは間違っています。
Hadoop namenode高可用性分析:QJMコアソースコードの解釈

currentSegmentは、現在のジャーナルのローカルログセグメントです。他のジャーナルノードからデータを同期する必要がある場合が2つあります。

1. currentSegmentがnullです。この場合、ログをジャーナルに送信する前にアクティブなnamenodeがクラッシュし、新しいセグメントでした
。2。ファイルは存在しますが、セグメントの長さが復元するセグメントの長さと一致していません。

クライアントが正常に回復した後、成功したリターンの半分以上をファイナライズします

受け入れが成功したら、第3段階、コミットを実行します。これがファイナライズ操作です。ファイルの名前を変更して、namenodeで読み取れるようにします。

Hadoop namenode高可用性分析:QJMコアソースコードの解釈

ジャーナルノードの障害

分散ログシステムでは、通常の論理処理に加えて、災害にどのように耐えるかが重要であり、QJMコアは半分以上であるため、半分以上の場合は直接書き込まないでください。ただし、1つだけが失敗した場合は許容できます。

ジャーナルノードクラッシュの1つの場合、QJMは失敗したジャーナルノードにログストリームを送信せず、outOfSyncをtrueとしてマークします。ノードにデータを再度送信するのはいつですか。新しいログファイルを書き込むとき、つまりstartLogSegment RPC要求が行われると、要求が成功した後、対応するノードoutOfSyncがtrueであるかどうかを確認し、trueの場合はfalseを再マークして、ログの受け入れを開始します。ログの書き込み中の場合、ネットワークの切断などのノードの一時的な障害とその後の回復があります。新しいログファイルを書き込む前に、QJMは書き込みプロセス中に障害が発生したノードにのみハートビートを送信し、現在のトランザクションID(txid)をすぐに送信しません。書き始めて、考えてみてください。すぐに書いたらどうなりますか?障害期間中のトランザクションはノードに書き込まれないため、少なくともトランザクションが切断されます。

著者について

Shanghai Oudian Cloud Information Technology Co.、Ltd。のアーキテクトであるPeng Rongxinは、分散ストレージや並行処理などの基盤となるテクノロジーに個人的に興味を持っており、学んでいます。

関連読書

  • 建築家が理解する必要のあるパクソスの原則、歴史、実際の戦闘
  • ケース❤S3、Cassandra、HDFSデザインの隠された高可用性ルール
  • ZooKeeperでは本当に低いですか?数千のノードシナリオの構成サービスプランに関するディスカッション-高可用性アーキテクチャシリーズ

技術的な独創性と建築実践の記事は、公式アカウントの「お問い合わせ」メニューから送信できます。高可用性フレームワーク「ArchNotes」WeChat公式アカウントからのものであることを示し、次のQRコードを含めてください。

利用性の高いアーキテクチャ

インターネットの構築方法を変える

Hadoop namenode高可用性分析:QJMコアソースコードの解釈
QRコードを長押しして、「高可用性アーキテクチャ」の公式アカウントをフォローします

年末に重い:高可用性アーキテクチャは、技術アーキテクチャの未来を促進するためにGIACグローバルインターネットアーキテクチャ会議を主催します。クリックして元のテキストを読み、イベント登録ページに入ります。
Hadoop namenode高可用性分析:QJMコアソースコードの解釈

おすすめ

転載: blog.51cto.com/14977574/2547422