PDスケジュールのベストプラクティス
このドキュメントでは、PDスケジューリングの原則と戦略を、一般的なシナリオを通してアプリケーション開発を容易にするために詳しく説明します。このドキュメントは、TiDB、TiKV、PDの基本的な知識と、以下のコアコンセプトを理解していることを前提としています。
注記:
このドキュメントはTiDB 3.0を対象としています。一部の機能は以前のバージョン(2.x)ではサポートされていませんが、基盤となるメカニズムは同様であるため、このドキュメントは引き続きリファレンスとしてご利用いただけます。
PDスケジュールポリシー
このセクションでは、スケジューリング システムに関連する原則とプロセスについて説明します。
スケジュール作成プロセス
スケジュール設定プロセスには通常、次の 3 つのステップがあります。
情報を収集する
各 TiKV ノードは、次の 2 種類のハートビートを定期的に PD に報告します。
StoreHeartbeat: ディスク容量、使用可能なstorage、読み取り/書き込みトラフィックなど、ストアの全体的な情報が含まれます。RegionHeartbeat: 各リージョンの範囲、ピア分布、ピアステータス、データ量、読み取り/書き込みトラフィックなど、リージョンの全体的な情報が含まれます。
PD はスケジュール決定のためにこの情報を収集し、復元します。
演算子を生成する
さまざまなスケジューラが、次の点を考慮して、独自のロジックと要件に基づいてオペレーターを生成します。
- 異常な状態(切断、ダウン、ビジー、容量不足)にあるピアをストアに追加しないでください。
- 異常な状態の領域のバランスをとらない
- リーダーを保留中のピアに転送しないでください
- リーダーを直接削除しないでください
- さまざまなリージョンピアの物理的な分離を破壊しない
- ラベルプロパティなどの制約に違反しない
実行演算子
演算子を実行するための一般的な手順は次のとおりです。
生成されたオペレータは、まず
OperatorControllerによって管理されるキューに参加します。OperatorControllerオペレータをキューから取り出し、設定に基づいて一定の同時実行数で実行します。このステップでは、各オペレータステップを対応するリージョンリーダーに割り当てます。オペレータは「終了」または「タイムアウト」としてマークされ、キューから削除されます。
負荷分散
リージョンは、負荷分散を実現するために、主にスケジューラbalance-leaderとbalance-regionに依存しています。どちらのスケジューラも、クラスター内のすべてのストアにリージョンを均等に分散することを目標としていますが、それぞれの重点は異なります。スケジューラbalance-leaderリージョンリーダーと連携してクライアントからの受信リクエストのバランスを取り、スケジューラbalance-region各リージョンピアと連携してstorage負荷を再分配し、storage容量不足などの例外を回避します。
balance-leaderとbalance-region同様のスケジュール プロセスを共有します。
- リソースの可用性に応じて店舗を評価します。
balance-leaderまたはbalance-region、高スコアの店舗から低スコアの店舗へ、リーダーまたは同僚を継続的に異動させます。
しかし、それぞれの評価方法は異なります。1 balance-leaderストア内のリーダーに対応するすべての領域サイズの合計を使用しますが、 balance-regionの方法は比較的複雑です。各ノードの具体的なstorage容量に応じて、 balance-regionの評価方法は以下のようになります。
- 十分なstorageがある場合のデータ量に基づいて(ノード間でデータ分散のバランスをとるため)。
- storageが不足している場合は、使用可能なstorageに基づいて割り当てます (異なるノード上のstorageの可用性のバランスをとるため)。
- どちらの状況も当てはまらない場合は、上記の 2 つの要因の加重合計に基づきます。
ノードによってパフォーマンスが異なる場合があるため、ストアごとにロードバランシングの重みを設定することもできます。1とregion-weight leader-weightリーダー重みとリージョン重みを制御します(どちらもデフォルトは「1」です)。例えば、あるストアのleader-weight 「2」に設定すると、スケジューリングが安定した後、そのノードのリーダー数は他のノードの約2倍になります。同様に、あるストアのleader-weight 「0.5」に設定すると、そのノードのリーダー数は他のノードの約半分になります。
ホットリージョンのスケジュール
ホットリージョンのスケジューリングにはhot-region-scheduler使用します。TiDB v3.0以降では、このプロセスは次のように実行されます。
ストアから報告された情報に基づいて、一定期間内に特定のしきい値を超える読み取り/書き込みトラフィックを判別し、ホット領域をカウントします。
負荷分散と同様の方法でこれらの領域を再分配します。
ホット書き込み領域の場合、 hot-region-scheduler領域ピアとリーダーの両方の再配布を試行します。ホット読み取り領域の場合、 hot-region-scheduler領域リーダーのみを再配布します。
クラスタトポロジの認識
クラスタトポロジの認識により、PDはリージョンのレプリカを可能な限り分散させることができます。これにより、TiKVは高可用性と災害復旧能力を確保します。PDはバックグラウンドですべてのリージョンを継続的にスキャンします。リージョンの分散が最適ではないと判断された場合、ピアを置き換えてリージョンを再分散するためのオペレーターを生成します。
リージョン分散をチェックするコンポーネントはreplicaCheckerです。これは、無効にできないことを除いてスケジューラに似ています。 replicaChecker location-labelsの設定に基づいてスケジュールします。たとえば、 [zone,rack,host]クラスターの 3 層トポロジを定義します。PD は、最初にリージョン ピアを異なるゾーンにスケジュールしようとします。ゾーンが不十分な場合は (たとえば、3 つのレプリカに対して 2 つのゾーン)、またはラックが不十分な場合は異なるホストにスケジュールしようとします。
スケールダウンと障害回復
スケールダウンとは、コマンドを使用してストアをオフラインにし、「オフライン」としてマークするプロセスを指します。PDは、スケジュールに従ってオフラインノード上のリージョンを他のノードに複製します。障害復旧は、ストアに障害が発生し、復旧できない場合に適用されます。この場合、対応するストアに分散されたピアを持つリージョンのレプリカが失われる可能性があり、PDは他のノードでレプリカを補充する必要があります。
スケールダウンと障害回復のプロセスは基本的に同じです。1 replicaChecker異常な状態にあるリージョン ピアを見つけ、異常なピアを正常なストア上の新しいピアに置き換える演算子を生成します。
リージョンの統合
リージョンマージとは、隣接する小領域をマージするプロセスを指します。これは、データ削除後に多数の小領域や空の領域によって不要なリソース消費が発生するのを防ぐのに役立ちます。リージョンマージはmergeCheckerによって実行され、 replicaCheckerと同様の方法で処理されます。PDはバックグラウンドですべての領域を継続的にスキャンし、連続する小領域が見つかった場合に演算子を生成します。
具体的には、新しく分割されたリージョンがsplit-merge-interval (デフォルトでは1h ) 以上の値で存在する場合、次の条件が同時に発生すると、このリージョンはリージョンのマージ スケジュールをトリガーします。
このリージョンのサイズは
max-merge-region-sizeの値より小さいです。v8.4.0 以降、デフォルト値は 20 MiB から 54 MiB に変更されます。新しいデフォルト値は、新規に作成されたクラスターにのみ自動的に適用されます。既存のクラスターには影響しません。このリージョンのキーの数が
max-merge-region-keys未満です。v8.4.0 以降、デフォルト値は 200000 から 540000 に変更されます。新しいデフォルト値は、新規に作成されたクラスターにのみ自動的に適用されます。既存のクラスターには影響しません。
クエリのスケジュールステータス
スケジューリングシステムの状態は、メトリクス、pd-ctl、ログを通じて確認できます。このセクションでは、メトリクスとpd-ctlの使用方法について簡単に説明します。詳細はPDモニタリングメトリクスとPD Control参照してください。
オペレーターのステータス
Grafana PD/Operatorページには、次のようなオペレーターに関するメトリックが表示されます。
- スケジュールオペレータ作成:オペレータ作成情報
- オペレータ完了時間: 各オペレータが消費した実行時間
- オペレータステップの所要時間: オペレータステップで消費される実行時間
次のコマンドで pd-ctl を使用して演算子をクエリできます。
operator show: 現在のスケジュールタスクで生成されたすべての演算子を照会しますoperator show [admin | leader | region]: 演算子をタイプ別に照会する
残高ステータス
Grafana PD/統計- バランスページには、次のような負荷分散に関するメトリックが表示されます。
- 店舗リーダー/地域スコア: 各店舗のスコア
- 店舗リーダー/地域数: 各店舗のリーダー/地域の数
- 利用可能な店舗: 各店舗で利用可能なstorage
pd-ctl のストア コマンドを使用して、各ストアの残高ステータスを照会できます。
ホットリージョンステータス
Grafana PD/統計- ホットスポットページには、次のようなホット リージョンに関するメトリックが表示されます。
- ホットライト領域のリーダー/ピア分布: ホットライト領域におけるリーダー/ピア分布
- ホットリード領域のリーダー分布: ホットリード領域におけるリーダー分布
次のコマンドで pd-ctl を使用してホット リージョンのステータスを照会することもできます。
hot read: ホットリード領域を照会するhot write: ホット書き込み領域を照会するhot store: 店舗別にホットリージョンの分布を照会するregion topread [limit]: 読み取りトラフィックが最も多い領域を照会しますregion topwrite [limit]: 書き込みトラフィックが最も多い領域を照会する
リージョンの健康
Grafana PD/クラスタ/リージョンのヘルスパネルには、異常な状態にあるリージョンに関するメトリックが表示されます。
領域チェック コマンドを使用して pd-ctl を使用すると、異常状態にある領域のリストを照会できます。
region check miss-peer: 十分なピアがない領域を照会するregion check extra-peer: 追加のピアを持つ領域を照会するregion check down-peer: ダウンしているピアがあるリージョンを照会するregion check pending-peer: 保留中のピアがある領域を照会します
制御スケジューリング戦略
pd-ctl を使用すると、以下の3つの側面からスケジューリング戦略を調整できます。詳細はPD Controlを参照してください。
スケジューラを手動で追加/削除する
PDはpd-ctlを介してスケジューラを動的に追加および削除することをサポートしています。例:
scheduler show: システムで現在実行中のスケジューラを表示しますscheduler remove balance-leader-scheduler: バランスリーダースケジューラを削除(無効化)するscheduler add evict-leader-scheduler 1: ストア 1 のすべてのリーダーを削除するスケジューラを追加します。
オペレータを手動で追加/削除する
PDはpd-ctlを介してオペレータを直接追加または削除することもできます。例:
operator add add-peer 2 5: ストア5のリージョン2にピアを追加するoperator add transfer-leader 2 5:リージョン2のリーダーをストア5に移行しますoperator add split-region 2:リージョン2を均等なサイズで2つの領域に分割しますoperator remove 2:リージョン2で現在保留中の演算子を削除します
スケジュールパラメータを調整する
pd-ctl のconfig showコマンドを使用してスケジュール設定を確認し、 config set {key} {value}を使用して値を調整できます。一般的な調整には以下が含まれます。
leader-schedule-limit: 転送リーダーのスケジュールの同時実行を制御するregion-schedule-limit: ピアスケジュールの追加/削除の同時実行を制御するenable-replace-offline-replica: ノードをオフラインにするスケジュールを有効にするかどうかを決定しますenable-location-replacement: 領域の分離レベルを処理するスケジュールを有効にするかどうかを決定しますmax-snapshot-count: 各ストアのスナップショットの送受信の最大同時実行数を制御します
一般的なシナリオにおけるPDスケジューリング
このセクションでは、いくつかの一般的なシナリオを通じて PD スケジューリング戦略のベスト プラクティスについて説明します。
リーダー/地域が均等に分布していない
PDの評価メカニズムでは、異なるストアのリーダー数とリージョン数だけでは負荷分散状況を完全に反映できないと判断されます。そのため、TiKVの実際の負荷やstorage使用量から、負荷の不均衡が発生しているかどうかを確認する必要があります。
リーダー/地域が均等に分散されていないことを確認したら、さまざまな店舗の評価を確認する必要があります。
各店舗のスコアが近い場合、PDはリーダー/地域が均等に分布していると誤って認識している可能性があります。考えられる理由は次のとおりです。
- 負荷の不均衡を引き起こすホットリージョンがあります。この場合、 ホットリージョンのスケジュールに基づいてさらに分析する必要があります。
- 空きリージョンや小さなリージョンが多数存在するため、ストア間のリーダー数に大きな差が生じ、 Raftストアへの負荷が高くなります。このような状況では、 地域の統合スケジューリングが適しています。
- ハードウェアおよびソフトウェア環境は店舗によって異なります。リーダー/リージョンの配分を制御するには、 負荷分散参考にして
leader-weightとregion-weightの値を調整してください。 - その他の不明な理由。ただし、
leader-weightとregion-weightの値を調整することで、リーダー/リージョンの配分を制御できます。
異なるストア間で評価に大きな差がある場合は、オペレータ関連の指標、特にオペレータの生成と実行に注目して調査する必要があります。主な状況としては、以下の2つが挙げられます。
オペレーターは正常に生成されているが、スケジュール処理が遅い場合は、次のことが考えられます。
- スケジューリング速度は、負荷分散を目的としてデフォルトで制限されています。1 または
region-schedule-limit値を大きくしても、通常のサービスに大きな影響はありません。また、leader-schedule-limitおよびmax-snapshot-countで指定された制限max-pending-peer-count適切に緩和することもできます。 - 他のスケジューリングタスクが同時に実行されているため、バランシングの速度が低下しています。この場合、バランシングが他のスケジューリングタスクよりも優先される可能性がある場合は、他のタスクを停止するか、速度を制限することができます。例えば、バランシングの実行中に一部のノードをオフラインにすると、両方の操作でクォータ
region-schedule-limitが消費されます。このような場合、スケジューラの速度を制限してノードを削除するか、enable-replace-offline-replica = false設定して一時的に無効にすることができます。 - スケジューリングプロセスが遅すぎます。原因を確認するには
RemovePeerOperatorステップの所要時間メトリックを確認してください。通常、スナップショットの送受信を伴わないステップ(TransferLeaderPromoteLearner)は数ミリ秒で完了するはずですが、スナップショットを伴うステップ(AddLearnerやAddPeerなど)は数十秒で完了すると予想されます。所要時間が明らかに長すぎる場合は、TiKVの高負荷またはネットワークのボトルネックが原因である可能性があり、詳細な分析が必要です。
- スケジューリング速度は、負荷分散を目的としてデフォルトで制限されています。1 または
PDは対応するバランシングスケジューラを生成できません。考えられる原因は次のとおりです。
- スケジューラが有効化されていません。例えば、対応するスケジューラが削除されているか、制限が「0」に設定されている可能性があります。
- その他の制約。例えば、システム内の制約
evict-leader-scheduler、リーダーが対応する店舗に移行できない、あるいはラベルプロパティが設定されているため、一部の店舗がリーダーを拒否するといった状況です。 - クラスタトポロジによる制約。例えば、3つのデータセンターにまたがる3つのレプリカを持つクラスタでは、レプリカ分離のため、各リージョンの3つのレプリカが異なるデータセンターに分散されます。これらのデータセンター間でストア数が異なる場合、スケジューリングは各データセンター内ではバランスの取れた状態になりますが、グローバルではバランスが取れません。
ノードをオフラインにするのは遅い
このシナリオでは、関連するメトリックを通じて演算子の生成と実行を調べる必要があります。
オペレーターは正常に生成されたが、スケジュール プロセスが遅い場合は、次の理由が考えられます。
- スケジューリング速度はデフォルトで制限されています。1 または
replica-schedule-limit値を大きく調整できます。同様に、leader-schedule-limitとmax-snapshot-countmax-pending-peer-countを緩和することも検討できます。 - 他のスケジューリングタスクが同時に実行され、システム内のリソースを奪い合っています。解決策はリーダー/地域が均等に分布していないを参照してください。
- 単一ノードをオフラインにすると、処理対象となるリージョンリーダー(レプリカ3台構成の場合、約1/3)が削除対象ノードに分散されます。そのため、処理速度はこの単一ノードによるスナップショット生成速度によって制限されます。移行リーダーに手動で
evict-leader-scheduler追加することで、処理速度を上げることができます。
対応する演算子の生成に失敗した場合、考えられる理由は次のとおりです。
- オペレータが停止しているか、
replica-schedule-limit"0" に設定されます。 - リージョン移行に適したノードが存在しません。例えば、同じラベルの置き換えノードの利用可能な容量が20%未満の場合、PDはそのノードのstorage不足を回避するためにスケジューリングを停止します。このような場合、ノードを追加するか、データを削除してスペースを解放する必要があります。
ノードをオンラインにするのは遅い
現在、ノードのオンライン化はバランスリージョンメカニズムを通じてスケジュールされています。トラブルシューティングについてはリーダー/地域が均等に分布していない参照してください。
暑い地域は均等に分布していない
ホット リージョンのスケジュールの問題は、通常、次のカテゴリに分類されます。
ホット領域は PD メトリックを通じて観察できますが、スケジュール速度が追いつかず、ホット領域を時間内に再分配できません。
解決策:
hot-region-schedule-limit値を大きくし、他のスケジューラの制限クォータを減らして、ホットリージョンのスケジューリングを高速化します。または、hot-region-cache-hits-threshold値を小さくして、PD がトラフィックの変化に敏感になるように調整することもできます。単一のリージョンにホットスポットが形成されています。例えば、小さなテーブルが大量のリクエストによって集中的にスキャンされている場合などです。これはPDメトリクスからも検出できます。単一のホットスポットを分散させることはできないため、このようなリージョンを分割するには、手動で
split-region演算子を追加する必要があります。TiKV関連のメトリクスから、一部のノードの負荷が他のノードよりも著しく高くなっており、これがシステム全体のボトルネックとなっています。現在、PDはトラフィック分析のみでホットスポットをカウントしているため、特定のシナリオではPDがホットスポットを特定できない可能性があります。例えば、一部のリージョンでポイントルックアップリクエストが集中している場合、トラフィック内では検出しにくいものの、高いQPSが主要モジュールのボトルネックにつながる可能性があります。
解決策:まず、特定のビジネスに基づいてホットリージョンが形成されるテーブルを特定します。次に、
scatter-range-schedulerのスケジューラを追加して、このテーブルのすべてのリージョンを均等に分散させます。TiDBは、この操作を簡素化するためのHTTP APIインターフェースも提供しています。詳細はTiDB HTTP APIを参照してください。
リージョンのマージが遅い
低速スケジューリングと同様に、リージョンマージの速度は、 merge-schedule-limitとregion-schedule-limit設定によって制限されているか、リージョンマージスケジューラが他のスケジューラと競合している可能性が高くなります。具体的な解決策は次のとおりです。
メトリクスからシステム内に多数の空き領域があることが分かっている場合は、
max-merge-region-sizeとmax-merge-region-keys小さな値に調整することでマージを高速化できます。これは、マージプロセスにはレプリカの移行が含まれるため、マージする領域が小さいほどマージが高速になるためです。マージ演算子が既に高速に生成されている場合は、プロセスをさらに高速化するために、patrol-region-intervalを10msに設定できます(TiDB v5.3.0以降では、この設定項目のデフォルト値は10msです)。これにより、CPU消費量は増加しますが、領域スキャンが高速化されます。多数のテーブルが作成され、その後空になっています(切り捨てられたテーブルを含む)。分割テーブル属性が有効になっている場合、これらの空のリージョンは結合できません。この属性を無効にするには、以下のパラメータを調整してください。
TiKV:
split-region-on-table~falseに設定します。パラメータを動的に変更することはできません。PD: PD Controlを使用して、クラスターの状況に応じて必要なパラメータを設定します。
- クラスターにTiDBインスタンスがなく、
key-typeの値がrawまたはtxnに設定されているとします。この場合、PDはenable-cross-table-merge settingの値に関係なく、テーブル間でリージョンをマージできます。key-typeパラメータは動的に変更できます。
config set key-type txn- クラスターにTiDBインスタンスがあり、
key-typeの値がtableに設定されているとします。この場合、PDはenable-cross-table-mergeの値がtrueに設定されている場合にのみ、テーブル間でリージョンをマージできます。key-typeパラメータは動的に変更できます。
config set enable-cross-table-merge true変更が有効にならない場合は、 FAQ - TiKV/PD 用に変更された
toml構成が有効にならないのはなぜですか?を参照してください。注記:
配置ルールを有効にした後、デコードの失敗を回避するために
key-typeの値を適切に切り替えます。- クラスターにTiDBインスタンスがなく、
v3.0.4およびv2.1.16以前では、特定の状況(主にテーブルの削除後)において、リージョンのapproximate_keys不正確になり、キー数がmax-merge-region-keysの制約に違反することがあります。この問題を回避するには、 max-merge-region-keysより大きな値に調整してください。
TiKVノードのトラブルシューティング
TiKV ノードに障害が発生した場合、PD はデフォルトで、対応するノードを 30 分後 (構成項目max-store-down-timeでカスタマイズ可能) にダウン状態に設定し、関係するリージョンのレプリカを再調整します。
実用的には、ノード障害が回復不可能と判断された場合は、直ちにオフラインにすることができます。これにより、PDはすぐに別のノードにレプリカを補充し、データ損失のリスクを軽減します。一方、ノードが回復可能と判断されたものの、30分以内に回復できない場合は、タイムアウト後にレプリカの不必要な補充とリソースの浪費を回避するために、一時的にmax-store-down-time大きく調整することができます。
TiDB v5.2.0 では、TiKV に低速 TiKV ノード検出のメカニズムが導入されました。このメカニズムは、TiKV 内のリクエストをサンプリングすることで、1 から 100 までのスコアを算出します。スコアが 80 以上の TiKV ノードは低速としてマークされます。スコアにevict-slow-store-scheduler加算することで、低速ノードを検出してスケジュールすることができます。低速と検出された TiKV が 1 つだけで、低速スコアが上限(デフォルトでは 80)に達した場合、このノードのLeaderは排除されます(スコアevict-leader-schedulerの場合と同様)。
注記:
Leaderの排除は、PDがTiKVの低速ノードにスケジューリング要求を送信し、TiKVが受信したスケジューリング要求を順次実行することで実現されます。低速I/Oなどの要因により、低速ノードでは要求が蓄積され、一部のリーダーは遅延した要求が処理されるまでLeaderの排除要求を処理できない場合があります。その結果、Leaderの排除にかかる時間が全体的に長くなります。したがって、
evict-slow-store-scheduler有効にする場合は、この状況を緩和するためにstore-io-pool-sizeも有効にすることをお勧めします。