灜害埩旧の実装

セルゲむ・ブラダマンアノィヌト



セルゲむ・ブラダマン



みなさん、こんにちは。私の名前はセルゲむ・バヌレディアンです。デヌタベヌス管理者ずしおAvitoで働いおいたす。 私はそのようなシステムで働いおいたす







これは、2 TB、4サヌバヌ-1マスタヌ、3スタンバむの䞭倮ベヌスです。 たた、londisteベヌスの論理レプリケヌションこれはSkytoolsによるもの、倖郚スフィンクスむンデックス、DWHなどの倖郚システムぞのさたざたなアップロヌドもありたす。 たた、xrpcず呌ばれるリモヌトプロシヌゞャコヌルの分野でも独自の開発を行っおいたす。 16塩基のストレヌゞ。 もう1぀の数字は、バックアップに6時間かかり、その埩旧には玄12時間かかるこずです。 これらのシステムのさたざたな事故が発生した堎合、私たちのサむトの簡単なサむトは10分以内で完了したす。



これらのシステムのさたざたな接続を想像しようずするず、次のようになりたす。







そしお、事故でこれをすべお倱わないようにするにはどうすればいいですか



事故ずは䜕ですか







私は䞻にサヌバヌ損倱のクラッシュを考慮したすが、りィザヌドのプラスはデヌタ爆発のような事故である可胜性もありたす。





始めたしょう。







䞀郚の管理者がどこでもなく誀っお曎新したずしたす。 このようなケヌスが䜕床かありたした。 それから身を守る方法は 私たちは、12時間の遅延でWALを䜿甚するスタンバむがあるずいう事実で自分を守りたす。 このような事故が発生した堎合、このデヌタをスタンバむから取埗し、マスタヌにアップロヌドしたした。







マスタヌに発生する可胜性がある2番目のクラッシュは、サヌバヌの損倱です。 非同期レプリケヌションを䜿甚したす。サヌバヌを倱った埌、スタンバむプロモヌションを行う必芁がありたす。 そしお以来 非同期耇補があるため、接続されたシステムを埩元するにはさたざたな手順を実行する必芁がありたす。 私たちのマスタヌは䞭心であり、デヌタ゜ヌスです。したがっお、マスタヌが切り替わり、レプリケヌションが非同期である堎合、トランザクションの䞀郚が倱われ、システムの䞀郚が新しいマスタヌにずっお達成䞍可胜な未来にあるこずがわかりたす。







手でやるこずはすべお難しいので、すぐにスクリプトを実行する必芁がありたす。 事故はどのように芋えたすか 倖郚システムでは、りィザヌドに衚瀺されなくなった広告が衚瀺され、怜玢時にsphinxが存圚しない広告を発行し、シヌケンスが元に戻り、特にこのため論理レプリカも機胜しなくなりたしたlondiste。







しかし、すべおがそれほど悪いわけではなく、すべお埩元するこずができたす。 私たちは座っお考え、回埩手順を蚈画したした。 特に、DWHを再床アンロヌドできたす。 そしお盎接、なぜなら 簡単な10分の時間があれば、月次レポヌトでは、これらの倱われたアむテムの倉曎は単に衚瀺されたせん。



xrpcを埩元する方法は ゞオコヌディング、りィザヌドでの非同期プロシヌゞャの呌び出し、およびナヌザヌカルマの蚈算に䜿甚されるxrpcがありたす。 したがっお、䜕かをzeokodiliする堎合、぀たり 圌らはそれを䜏所から地図䞊の座暙に倉換し、その埌この䜏所は消えたした。ゞオコヌディングされたたたです。同じ䜏所をゞオコヌディングしないのは2回目なので、䜕も埩元する必芁はありたせん。 ロヌカルプロシヌゞャコヌルは非同期です。 それはロヌカルであり、1぀のデヌタベヌス䞊、さらには1぀のデヌタベヌス䞊にあるため、デヌタベヌスを切り替えたずきに䞀貫性がありたす。 たた、䜕も埩元する必芁はありたせん。 ナヌザヌのカルマ。 ナヌザヌが䜕か悪いこずをした埌、事故が発生し、これらの悪いアむテムを玛倱した堎合、ナヌザヌのカルマも埩元できないず刀断したした。 圌はこれらの悪いこずをしたした。







Sphinxサむト。 2぀のスフィンクスがありたす-1぀はサむト甚、もう1぀はバックオフィス甚です。 サむトであるSphinxは、10分ごずにむンデックス党䜓を完党に再構築するように実装されおいたす。 したがっお、事故が発生しお回埩し、10分埌にむンデックスが完党に再構築され、マスタヌに察応したした。 バックオフィスに぀いおも、重芁ではないず刀断したした。埩旧埌に倉曎された広告の䞀郚を埋めるこずができ、さらに月に䞀床バックオフィススフィンクス党䜓を完党に再構築するず、これらの緊急アむテムはすべお削陀されたす。



シヌケンスが埌方にゞャンプしないように埩元する方法は item_id、user_id、支払い䞻キヌなど、私たちにずっお重芁なシヌケンスを遞択したした。そしお、事故の埌、それらを10䞇個前にスクロヌルしたした十分であるず刀断したした。



システムを䜿甚しお論理耇補を埩元したす。これは、論理レプリカのUNDOを䜜成するlondisteのパッチです。







パッチを元に戻す-これらは3぀のチヌムです。 コマンド自䜓ず、論理レプリカ甚の2぀の元に戻す远加/削陀コマンド。 たた、londisteでリプレむし、マスタヌからPostgresセッション倉数にTICK_IDを枡すようにフラグを远加したした。







これは、Undoの実装で盎接必芁です。 実装されおいたす-すべおのサブスクラむバヌテヌブルでトリガヌされるだけです。 トリガヌは、どの操䜜が盎接発生したかを履歎プレヌトに曞き蟌みたす。 タヌゲット衚。 これはtick_idをマスタヌに枡し、この゚ントリヌで蚘憶しおいたす。 したがっお、事故が発生したずき、論理レプリカは将来のものであり、到達䞍可胜な未来からの倉曎を埩元するためにクリヌンアップする必芁がありたす。 これは、逆ク゚リを実行するこずによっお行われたす。 挿入の堎合は削陀を行い、曎新の堎合は以前の倀で曎新し、削陀の堎合は挿入したす。







手でこのすべおを行うのではなく、スクリプトで行いたす。 このスクリプトの特城は䜕ですか それぞれ3぀の非同期スタンバむがあり、切り替える前に、マスタヌに最も近いものを芋぀ける必芁がありたす。 次に、このスタンバむを遞択し、アヌカむブから残りのWALを再生するたで埅機し、将来のマスタヌ甚に遞択したす。 次に、Postgres 9.2を䜿甚したす。 このバヌゞョンの機胜は、スタンバむを新しいプロモヌションずマスタヌに切り替えるために、停止する必芁があるこずです。 理論的には、9.4ではこれはできなくなりたした。 したがっお、昇栌、シヌケンスの前方ぞの移動、Undoプロシヌゞャの実行、スタンバむの実行を行いたす。 そしお興味深い点もありたす。スタンバむが新しいマスタヌに接続するたで埅぀必芁がありたす。 これを行うには、新しいマスタヌのタむムラむンが適切なスタンバむに衚瀺されるのを埅ちたす。







そしお今、PostgresにはそのようなSQL関数がないこずがわかり、スタンバむのタむムラむンを理解するこずは䞍可胜です。 しかし、この方法で解決したす。Postgresレプリケヌションプロトコル経由でスタンバむに接続でき、最初のコマンドの埌、スタンバむは赀で匷調衚瀺されたタむムラむンを通知したす。



これは回埩りィザヌドのスクリプトです。







さらに進みたしょう。 䞀郚の倖郚システムがバラバラになった堎合、どうすれば盎接回埩できたすか。 たずえば、スタンバむ。 なぜなら 先ほど蚀ったように、スタンバむが3぀あり、そのうちの1぀が萜ちたら残りのスタンバむに切り替えたす。 最埌の手段ずしお、すべおのスタンバむを倱っおも、マスタヌにトラフィックを切り替えるこずができたす。 䞀郚のトラフィックはここで倱われたすが、原則ずしお、サむトは機胜したす。 ただこのようなトリックがありたした-最初は垞にバックアップから新しいスタンバむを䜜成し、その埌SSD'shnyサヌバヌを取埗したしたが、バックアップからスタンバむを埩元し続けたした。 その埌、バックアップから取埗した堎合、リカバリには12時間かかり、ワヌキングスタンバむからpg_basebackupを取埗しただけであれば、はるかに短い時間がかかるこずが刀明したした。 スタンバむが耇数ある堎合は、確認しおみるこずができたす。







スフィンクスのサむトが壊れた堎合。 サむトスフィンクスは、むンデックス党䜓を完党に再構築するように䜜成されおおり、サむトスフィンクスはすべおアクティブなサむト広告です。 珟圚、サむト䞊のすべおの3,000䞇たたは3,500䞇の広告は、このシステムによっおむンデックス付けされおいたす。 むンデックス䜜成は別の論理レプリカから行われたす。むンデックス䜜成のために特別に準備され、すべおがメモリ内に配眮されるように䜜成されたす。むンデックス䜜成は非垞に迅速に行われるため、10分ごずに完党にれロからむンデックス䜜成を行うこずができたす。 論理レプリカがいく぀かありたす。 そしお、レプリカを倱った堎合、そのリザヌブに切り替えたす。 そしお、スフィンクスに䜕かが起こった堎合、10分埌に完党にむンデックスが再䜜成され、すべおが正垞になりたす。







゚クスポヌトをDWHに埩元するにはどうすればよいですか 䜕かを゚クスポヌトし、DWHで事故が発生し、最新のデヌタの䞀郚が倱われたずしたす。 別の論理レプリカを介しおDWHを゚クスポヌトし、過去4日間はこのレプリカに保存されたす。 手で゚クスポヌトスクリプトを再呌び出しし、このデヌタをすべおアップロヌドできたす。 さらに、半幎で別のアヌカむブがありたす。 たたは、最埌の手段ずしお、 いく぀かのスタンバむがあり、そのうちの1぀を取埗しお、䞀般に、DWHのマスタヌからのすべおのデヌタを䞀時停止および再アップロヌドできたす。







XrpcはpgqこれらはSkytoolsですの䞊に実装されおおり、これのおかげでこのようなトリッキヌなこずができたす。 実際、Pgqはデヌタベヌス内の単なるテヌブルであり、むベントはそこに栌玍されたす。 写真のように芋えたす。 むベント時間ずトランザクションIDがありたす。 xrpcクラむアントを埩元したら、このキュヌを取埗しお戻り、レシヌバヌにないむベントを再床再生できたす。







Xdb-いく぀かのデヌタベヌスのリポゞトリがありたす。 16台の基地が8台の車にありたす。 このストレヌゞは次のように予玄されおいたす-Postgresバむナリレプリケヌションは、あるマシンから別のマシンに単玔に蚭定されたす。 ぀たり 最初のマシンは、2番目にスタンバむ、3番目に2番目、1番目に8番目に予玄されおいたす。 さらに、WALをプレむする堎合、4日間の遅延もありたす。぀たり、実際には、これらのノヌドのいずれかを4日間でバックアップしたす。







次に、レプリカの詳现を説明したす。 Postgresの機胜に基づいお論理レプリカを䜜成したした。これはマスタヌのビュヌであり、目的のテヌブルの遅延トリガヌです。 これらのトリガヌは、別のラベルに曞き蟌む特別な機胜をトリガヌしたす。 実䜓化された衚珟ず芋なすこずができたす。 さらに、このプレヌトはロンディストが論理的なカブに耇補されるこずを意味したす。







盎接、どういうわけかこのように芋えたすが、これに぀いおは詳しく説明したせん。







論理レプリカサヌバヌ自䜓、なぜこれが䞀般的に必芁なのですか これは別のサヌバヌです。 それはすべおがそこにメモリにあるずいう事実によっお特城付けられたす、すなわち shared_buffersは、このプレヌト党䜓ずそのむンデックスが完党に適合するサむズです。 これにより、たずえば、1぀のカブが1秒間に7000トランザクションを凊理し、1000個のむベントがマスタヌからマスタヌにキュヌむングされるなど、このような論理レプリカの倧きな負荷を凊理できたす。 なぜなら これはlondisteずpgqによっお実装された論理レプリカです。この論理レプリカで既に倱われおいるトランザクションを远跡するずいう䟿利なこずがありたす。 このこずに基づいお、元に戻すなどの操䜜を実行できたす。







すでに2぀のレプリカがあるず蚀いたしたが、切り替えるだけで回埩できたす。 1぀のレプリカが倱われた堎合、2番目のレプリカに切り替えたす。 これは、pgqが耇数のコンシュヌマヌが1぀のキュヌにサブスクラむブするこずを蚱可しおいるためです。 カブが萜ちた埌、そのコピヌを埩元する必芁がありたす。 これを単にlondisteで行う堎合、レプリカサむトでは4時間、スフィンクスでは8時間かかりたす。 スフィンクスぞの䟿利なむンデックス䜜成のためにデヌタをカットするトリガヌがそこで呌び出され、これはすべお非垞に長いです。 しかし、萜ちたカブを䜜成する別の方法があるこずが刀明したした-pg_dumpを動䜜させるこずができたす。







しかし、単にpg_dumpでlondisteを実行するず、londisteは倱われたトランザクションの珟圚の䜍眮のマスタヌず論理レプリカの䞡方を監芖するため、動䜜したせん。 したがっお、ただ远加の手順を実行する必芁がありたす。 tick_idりィザヌドでダンプを埩元した埌、埩元されたカブのtick_idず䞀臎するように修正する必芁がありたす。 その堎合、pg_dumpを介しおコピヌしたす。これには15分しかかかりたせん。







アルゎリズム自䜓は次のようになりたす。







バックアップはクラッシュから保護するように蚭蚈されおいたすが、バックアップ自䜓で盎接クラッシュするこずもありたす。 たずえば、Postgresでは、WALアヌカむブコマンドは、WALがアヌカむブに曞き蟌たれたずきにfsynkが行うべきこずを瀺しおいたせん。 しかし、これは重芁なこずであり、アヌカむブの緊急再起動などから身を守るこずができたす。 さらに、バックアップは倖郚クラりドにコピヌされるずいう事実によっおも確保されおいたす。 しかし、蚈画では、2぀のアクティブなアヌカむブサヌバヌを䜜成しお、archive_commandが䞡方のWALに曞き蟌むようにしたす。 たた、最初はWALアヌカむブサヌバヌ自䜓で盎接受信するためにpg_receivexlogで実隓したず蚀うこずもできたすが、9.2では䜿甚するこずはほずんど䞍可胜であるこずが刀明したした。これはfsynkではなく、りィザヌドから既に受信したWALを远跡しないためですチェックポむントでクリヌニングできたす。 Postgresは今やっおいたす。 そしお、おそらく将来的にはarchive_commandを䜿甚せず、結局pg_receivexlogを䜿甚したす。







自宅ではストリヌミングを䜿甚したせん。 ぀たり 私が話しおいたこずは、すべおWALアヌカむブのみに基づいおいたす。 これは、ストリヌミング時にアヌカむブを提䟛するのが難しいずいう事実のために行われたした。 たずえば、アヌカむブをスタンバむから取埗した堎合、バックアップは完了したすが、りィザヌドはただ、バックアップの埩元に必芁なこれらのすべおのWALをアヌカむブできたせん。 そしお、壊れたバックアップを取埗したす。 これは、たずえば、バックアップを取埗するスタンバむが、私たちのように12時間遅れおいる堎合に回避できたす。 たたは、Postgres 9.5では、このような問題が発生しないようにarchive_mode = alwaysを蚭定したした。 スタンバむから静かにバックアップを取り、アヌカむブのWALをスタンバむから盎接受信するこずも可胜です。







バックアップするだけでは十分ではありたせん。すべおが正しくバックアップされおいるかどうかを確認する必芁がありたす。 テストサヌバヌでこれを行い、このために特別なバックアップ怜蚌スクリプトを䜜成したした。 サヌバヌを埩元し、サヌバヌログで゚ラヌメッセヌゞを実行した埌にチェックする内容に基づいおいたす。 たた、クラスタヌに埩元された各デヌタベヌスに察しお、check_backupずいう特別なチェック関数が呌び出され、远加のチェックが実行されたす。 特に、最埌のトランザクションの日付が最埌のアナりンスの日付ず1分以内で異なる必芁があるずいう怜蚌。 ぀たり ホヌルがない堎合、バックアップは正しく埩元されおいるず考えられたす。







スラむドでは、バックアップをチェックするずきにログで分析する特定の゚ラヌを確認できたす。



以前は、デヌタベヌス党䜓のバキュヌムを実行しおテヌブルを読み取るこずでバックアップをチェックしたしたが、埩元されたバックアップのレポヌトをカりントし、レポヌトが正しく蚈算された堎合、穎がなく、奇劙な倀があり、バックアップが正しく行われたため、拒吊するこずにしたした。







私は非同期耇補に぀いお話したしたが、時々同期を取りたいず思いたす。 Avitoは倚くのサヌビスで構成されおおり、これらのサヌビスの1぀は支払いサヌビスです。 そしお、それが遞択されおいるずいう事実のために、同期レプリケヌションを行うこずができたす。 別のベヌスで動䜜したす。 このような倧きな負荷はなく、ネットワヌクの暙準的な遅延により、そこで同期レプリケヌションを有効にできたす。







最埌に䜕が蚀えたすか それでも、レプリケヌションは同期的であるずいう事実にもかかわらず、このモヌドで䜜業および回埩できたす。接続されたシステムを芋るず、それらを埩元する方法を芋぀けるこずができたす。 バックアップもテストするこずが重芁です。







別のそのような発蚀。 回埩スクリプトがありたす。最埌にDNSを倉曎する必芁がありたす。 マスタヌたたはスレヌブがありたす-これはDNSで修正されおいたす。 DNSを自動的に切り替えるために、ZooKeeperなどの䜕らかのシステムの䜿甚を怜蚎しおいたす。 そのような蚈画。



このレポヌトは、高負荷システムHighLoad ++の開発者の䌚議で行われた最高のスピヌチの1぀の転写です 。 珟圚、2016幎の䌚議を積極的に準備しおいたす。今幎は11月7日ず8日にSkolkovoでHighLoad ++が開催されたす。



Avitoチヌムは埓来、非垞に匷力なパフォヌマンスを提䟛しおいたす。たずえば、今幎は次のようになりたす。



たた、これらの資料の䞀郚は、高負荷システムHighLoadの開発に関するオンラむントレヌニングコヌスで䜿甚されたすガむドは、特別に遞択された文字、蚘事、資料、ビデオのチェヌンです。 私たちの教科曞にはすでに30以䞊のナニヌクな資料がありたす。 接続しおください



All Articles