ホームページ  >  記事  >  バックエンド開発  >  tidb は Go 言語ですか?

tidb は Go 言語ですか?

青灯夜游
青灯夜游オリジナル
2022-12-02 18:24:176072ブラウズ

はい、TiDB は go 言語で書かれています。 TiDB は分散 NewSQL データベースであり、水平方向の柔軟な拡張、ACID トランザクション、標準 SQL、MySQL 構文、および MySQL プロトコルをサポートし、強力なデータ一貫性と高可用性機能を備えています。 TiDB アーキテクチャの PD は、キーがどの TiKV ノード上にあるかなど、クラスターのメタ情報を保存します。PD はクラスターのロード バランシングとデータ シャーディングも担当します。 PD は etcd を組み込むことでデータ分散とフォールト トレランスをサポートしており、PD は go 言語で書かれています。

tidb は Go 言語ですか?

このチュートリアルの動作環境: Windows 7 システム、GO バージョン 1.18、Dell G3 コンピューター。

重量級の Go 言語プロジェクトは数多くありますが、中国で最も強力な Go オープンソース プロジェクトはおそらく TiDB でしょう。 TiDB は分散データベースですが、多くの人はそれについて何も知らないかもしれません。今日はこのテーマについてお話しさせてください。

TiDB はシンプルなデザインで、公式 Web サイトとコードが非常に読みやすいため、分散データベースを学習するための最初のオープンソース プロジェクトです。

データベース、オペレーティングシステム、コンパイラを総称して三大システムと呼び、コンピュータソフトウェア全体の根幹とも言えます。

多くの人がデータベースを使用したことがありますが、データベース、特に分散データベースを実装した人はほとんどいません。データベースの実装原理と詳細を理解することは、一方では個人のスキルを向上させ、他のシステムの構築に役立ちますが、他方では、データベースを有効に活用することにも役立ちます。

1. TiDB の概要

TiDB は 分散型 NewSQL データベースです。水平方向の柔軟な拡張、ACID トランザクション、標準 SQL、MySQL 構文、および MySQL プロトコルをサポートし、強力なデータ整合性 高可用性機能を備えています。OLTP シナリオに適しているだけではありません。 OLAP シナリオ用ハイブリッド データベース

OLTP: オンライン トランザクション処理、オンライン トランザクション処理
OLAP: オンライン分析処理、オンライン 分析処理

  • MySQL 5.7 との高い互換性

TiDB は、MySQL 5.7 プロトコルである MySQL 5.7 と高い互換性があります。共通の機能と文法。 TiDB は MySQL の構文とプロトコルをサポートしていますが、TiDB は PingCAP チームによって完全に独立して開発された製品であり、MySQL に基づいて開発されたものではありません。

MySQL 5.7 エコシステムのシステム ツール (PHPMyAdmin、Navicat、MySQL Workbench、mysqldump、Mydumper、Myloader)、クライアントなどはすべて TiDB に適用できます。

TiDB は現在、トリガー、ストアド プロシージャ、カスタム関数、外部キーをサポートしていません。

  • 使いやすさ

TiDB は非常に使いやすく、TiDB クラスターを MySQL として使用できます。 MySQL をバックエンド ストレージ サービスとして使用するあらゆるアプリケーションで使用でき、基本的にアプリケーション コードを変更する必要はありません。同時に、最も一般的な MySQL 管理ツールを TiDB の管理に使用できます。

プログラミング言語が MySQL クライアント/ドライバーをサポートしている限り、TiDB を直接使用できます。

  • 分散トランザクションのサポート

1 か所に複数のノードがある場合でも、複数のデータセンターにまたがる場合でも、複数のノード上で、 TiDB は ACID 分散トランザクション をサポートします。

TiDB トランザクション モデルは、Google Percolator モデルからインスピレーションを受けており、本体は 2 フェーズ コミット プロトコル であり、いくつかの実用的な最適化が施されています。作られました。このモデルは、トランザクションの競合が検出されるように、各トランザクションに単調増加するタイムスタンプを割り当てる タイムスタンプ アサイナー に依存しています。 TiDB クラスターでは、PD がタイムスタンプ ディストリビュータ の役割を引き受けます。

TiDB は、MySQL のようなクロスデータベース トランザクションを満たすために XA をサポートする必要はありません。TiDO 独自の分散トランザクション モデルは、パフォーマンスと安定性の点で XA よりもはるかに優れているため、XA をサポートする必要はありません。

従来のスタンドアロン データベースと比較して、TiDB には次の利点があります:

  • 優れたスケーラビリティを備えた純粋な分散アーキテクチャ、柔軟なサポート拡張と縮小
  • SQL をサポートし、MySQL ネットワーク プロトコルを外部に公開し、ほとんどの MySQL 構文と互換性があり、ほとんどのシナリオで MySQL を直接置き換えることができます
  • デフォルトで高可用性をサポートします。いくつかのコピーに障害が発生した場合、データベース自体が自動的にデータ修復とフェイルオーバーを実行できます。これはビジネスには透過的です。
  • ACID トランザクションをサポートし、銀行振込などの強力な一貫性要件を持つ一部のシナリオに適しています
  • TiDB には、データ移行、同期、バックアップなどのさまざまなシナリオをカバーする豊富なツール チェーン エコシステムがあります。

つまり、TiDB は次のようなシナリオに適しています。特徴#

  • データ量が多くて 1 台のマシンに保存できない
  • シャーディングをしたくない、またはシャーディングをするのがめんどくさい
  • アクセス モードに明らかなホット スポットはない
  • #トランザクションが必要、強整合性が必要、災害復旧が必要
  • リアルタイム HTAP を望み、ストレージ リンクを削減する

5 つの主要な機能

  • ワンクリックで水平方向に拡大または縮小 TiDB のストレージとコンピューティングの分離アーキテクチャの設計のおかげで、コンピューティングはオンデマンドで実行でき、ストレージはそれぞれオンラインで拡張または縮小され、拡張または縮小のプロセスはアプリケーションの運用および保守担当者にとって透過的です。

  • 金融グレードの高可用性データは複数のコピーに保存され、データ コピーはトランザクション ログを同期します。 Multi-Raft プロトコルでは、大多数によって書き込まれた成功したトランザクションのみを送信できるため、強力なデータ一貫性が保証され、少数のレプリカの障害がデータの可用性に影響を与えることはありません。レプリカの地理的位置やレプリカの数などの戦略は、さまざまな耐災害性レベルの要件を満たすために必要に応じて構成できます。

  • リアルタイム HTAP 行ストレージ エンジン TiKV と列ストレージ エンジン TiFlash の 2 つのストレージ エンジンを提供します。マルチパス - Raft Learner プロトコルは TiKV からリアルタイムでデータをコピーし、行ストレージ エンジン TiKV と列ストレージ エンジン TiFlash の間の強力なデータ一貫性を確保します。 TiKV と TiFlash は、HTAP リソース分離の問題を解決するために、オンデマンドで異なるマシンに展開できます。

  • #クラウドネイティブ分散データベース

    クラウド向けに特別に設計された分散データベース。TiDB Operator Implement 導入を通じて利用可能パブリック クラウド、プライベート クラウド、ハイブリッド クラウドのツールと自動化。

  • MySQL 5.7 プロトコルおよび MySQL エコシステムとの互換性

    MySQL 5.7 プロトコル、MySQL 共通機能、MySQL エコシステムとの互換性, アプリケーションは、少量のコードを必要としたり変更したりすることなく、MySQL から TiDB に移行できます。アプリケーションがデータ移行を簡単に完了できるようにする豊富なデータ移行ツールを提供します。

#4 つのコア アプリケーション シナリオ

    一貫したデータのシナリオデータの一貫性、高い信頼性、高いシステム可用性、スケーラビリティ、災害復旧に対する高い要件を持つ金融業界
  • # ご存知のとおり、金融業界はデータの一貫性、高いシステム可用性、高いシステム可用性、拡張性、災害復旧に対する高い要件を持っています。信頼性、および高いシステムの可用性、拡張性、および災害復旧の要件が高くなります。従来のソリューションは、同じ都市にある 2 つのコンピュータ ルームがサービスを提供し、別の場所にある 1 つのコンピュータ ルームがデータ ディザスタ リカバリ機能を提供しますが、サービスは提供しません。このソリューションには、リソース使用率が低い、メンテナンス コストが高い、#RTO という欠点があります。 (目標復旧時間)

    RPO (目標復旧時点)

    では、企業が期待する価値を真に達成することはできません。 TiDB は、マルチコピー Multi-Raft プロトコルを使用して、さまざまなコンピュータ ルーム、ラック、およびマシンにデータをスケジュールします。一部のマシンに障害が発生した場合、システムは自動的に切り替わり、システムの RTO

    # 高いストレージ容量、スケーラビリティ、および同時実行要件を備えた大量のデータと同時実行性の高い OLTP シナリオ
  • # #ビジネスの急速な発展に伴い、データは爆発的な増加を示しています。データの爆発的な増加により、従来のスタンドアロン データベースではデータベースの容量要件を満たすことができません。実現可能な解決策は、サブデータベースとサブテーブル、または NewSQL を備えたミドルウェア製品を使用することです。それらの中で最もコスト効率が高いのは、TiDB などの NewSQL データベースです。 TiDB はコンピューティングとストレージの分離アーキテクチャを採用しており、コンピューティングとストレージをそれぞれ拡張および縮小できます。コンピューティングは最大 512 ノードをサポートし、各ノードは最大 1000 の同時実行をサポートし、クラスター容量は最大 PB レベルをサポートします。

    リアルタイム HTAP シナリオ
  • 5G、モノのインターネット、人工知能の急速な発展に伴い、企業 ますます多くのデータが生成され、その規模は数百 TB または PB レベルに達する可能性があります。従来のソリューションは、OLTP データベースを通じてオンライン オンライン トランザクションを処理し、ETL ツールを使用してデータを OLAP データベースに同期してデータ分析を行うことです。この処理ソリューションには、ストレージ コストが高い、リアルタイム パフォーマンスが低いなど、多くの問題があります。 TiDB は、バージョン 4.0 で列ストレージ エンジン TiFlash を導入し、行ストレージ エンジン TiKV と組み合わせて真の HTAP データベースを構築しました。ストレージ コストをわずかに増加させるだけで、オンライン トランザクション処理とリアルタイム データ分析を同じシステムで実行できます。 、企業のコストを大幅に節約します。

    データ集約と二次処理のシナリオ
  • 現在、ほとんどの企業のビジネスデータは統一された概要を持たずに異なるシステムに分散しており、ビジネスの発展に伴い、企業の意思決定レベルはタイムリーな意思決定を行うために全社の経営状況を把握する必要があります。 , そのため、さまざまなシステムに点在するデータを同一システムに集め、二次処理を行ってT 0 または T 1 レポートを生成する必要があります。従来の一般的なソリューションは、ETL Hadoop を使用してそれを完了することですが、Hadoop システムは複雑すぎて、運用と保守、ストレージのコストが高すぎてユーザーのニーズを満たすことができません。 Hadoop と比較すると、TiDB ははるかにシンプルです。ビジネスでは、ETL ツールまたは TiDB 同期ツールを通じてデータを TiDB に同期します。レポートは、SQL を通じて TiDB で直接生成できます。

#2. すぐに始めましょう

TiDB は分散システムです。最も基本的な TiDB テスト クラスターは、通常、2 つの TiDB インスタンス、3 つの TiKV インスタンス、3 つの PD インスタンス、およびオプションの TiFlash インスタンスで構成されます。

TiUP Playground を使用すると、上記の基本的なテスト クラスターをすばやく構築できます。手順は次のとおりです:

  • step1. TiUP をダウンロードしてインストールします。

    curl --proto '=https' --tlsv1.2 -sSf https://tiup-mirrors.pingcap.com/install.sh | sh
インストールが完了すると、次のように表示されます:

Successfully set mirror to https://tiup-mirrors.pingcap.com
Detected shell: bash
Shell profile:  /home/user/.bashrc
/home/user/.bashrc has been modified to add tiup to PATH
open a new terminal or source /home/user/.bashrc to use it
Installed path: /home/user/.tiup/bin/tiup
===============================================
Have a try:     tiup playground
===============================================
  • step2. グローバル環境変数を宣言します。

    source ${your_shell_profile}

    source /home/user/.bashrc
  • step3. 現在のセッションで次のコマンドを実行してクラスターを開始します。

    tiup playground
  • ステップ4、確認。 [

    MySQL と同じように TiDB を使用できるようになりました]

    #新开启一个 session 以访问 TiDB 数据库。
    #使用 TiUP client 连接 TiDB:
    tiup client
    #也可使用 MySQL 客户端连接 TiDB
    mysql --host 127.0.0.1 --port 4000 -u root
    #通过 http://127.0.0.1:9090 访问 TiDB 的 Prometheus 管理界面。
    #通过 http://127.0.0.1:2379/dashboard 访问 TiDB Dashboard 页面,默认用户名为 root,密码为空。
    #通过 http://127.0.0.1:3000 访问 TiDB 的 Grafana 界面,默认用户名和密码都为 admin。

##3. TiDB アーキテクチャの原則 ##コア設計の観点から見ると、TiDB 分散データベースはアーキテクチャ全体を複数のモジュールに分割し、各モジュールが相互に通信して完全な TiDB システムを形成します。対応するアーキテクチャ図は次のとおりです。

tidb は Go 言語ですか?

TiDB サーバーは、SQL 関連ロジックの処理、SQL ステートメントのキーへの変換、およびデータの検索を担当します。具体的には、TiKV です。 TiDB 自体はステートレスであり、データを保存せず、計算のみを行います。 TiDB は Go 言語で書かれています。 [関連する推奨事項:
    Go ビデオ チュートリアル
  • ]

    PD
  • PD には、どの TiKV ノードがキーであるかなど、クラスターのメタ情報が保存されます。がオンになっており、PD はクラスターのロード バランシングとデータ シャーディングも担当します。 PD は etcd を組み込むことでデータ分散とフォールト トレランスをサポートします。 PD は Go 言語で書かれています。

    TiKV サーバー
  • TiKV は、トランザクションを提供する分散型 Key-Value ストレージ エンジンです。Google Spanner と HBase に基づいて設計されていますが、基盤となるものからは分離されています。複雑な HDFS。 RocksDB を通じてキーと値の値をロ​​ーカル ディスクに保存し、Raft プロトコルを使用してレプリケーションを行い、データの整合性と災害復旧を維持します。 TiKV は Rust 言語で書かれています。

tidb は Go 言語ですか?

1. TiDB データベースのストレージ - TiKV サーバーTiDB ストレージモデル、トランザクションを備えた分散 KV エンジン[

グローバルに順序付けされた分散 Key-Value エンジン

] の階層構造と、マルチコピー フォールト トレランスを実現する方法。 ストレージ ノードTiKV サーバー

: データの保存を担当します。外部から見ると、TiKV はトランザクションを提供する分散型 Key-Value ストレージ エンジンです。データを格納するための基本単位はリージョンであり、各リージョンはキー範囲 (StartKey から EndKey までの左閉および右開の範囲) のデータを格納する責任を負い、各 TiKV ノードは複数のリージョンを担当します。 TiKV の API は、KV キーと値のペア レベルで分散トランザクションのネイティブ サポートを提供し、デフォルトで SI (スナップショット分離) の分離レベルを提供します。これは、SQL レベルでの分散トランザクションに対する TiDB のサポートの中核でもあります。 TiDB の SQL レイヤーは SQL 解析を完了すると、SQL 実行プランを TiKV API への実際の呼び出しに変換します。したがって、データは TiKV に保存されます。さらに、TiKV 内のデータは自動的に複数のコピー (デフォルトでは 3 つのコピー) を維持し、高可用性と自動フェイルオーバーを自然にサポートします。

TiFlash: TiFlash は特別なタイプのストレージ ノードです。通常の TiKV ノードとは異なり、TiFlash 内ではデータが列形式で保存され、その主な機能は分析シナリオを高速化することです。

TiKVデータを保存するには、データが失われておらず、データが良好であることを確認する必要があります→Raft プロトコル。さらに、次の問題を考慮する必要があります:

1. データセンター間の災害復旧をサポートできますか?

2. 書き込み速度は十分ですか?

3. データを保存した後、読みやすいですか?

4. 保存したデータを変更するにはどうすればよいですか?同時変更をサポートするにはどうすればよいですか?
5. 複数のレコードをアトミ​​ックに変更するにはどうすればよいですか?

TiKV プロジェクトは、上記の問題をうまく解決します。では、
TiKV のような高性能で信頼性の高い巨大な (分散型) マップを実装するにはどうすればよいでしょうか?

  • TiKV は、Key-Value ペアを格納する巨大なマップです。
  • このマップ内のキーと値のペアは、キーのバイナリ順序に従って順序付けされます。つまり、特定のキーの位置をシークし、継続的に Next メソッドを呼び出して、より大きなキーを取得できます。この Key よりも昇順で並べた Key-Value。

Raft と RocksDB

TiKV はデータ レプリケーションに Raft を使用します。各データ変更は Raft ログとして記録されます。Raft のログレプリケーション機能により、グループのほとんどのノードにデータが安全かつ確実に同期されます。

TiKV はデータをディスクに直接書き込むことを選択しませんが、データを RocksDB に保存します。RocksDB は特定のデータのランディングを担当します。 [RocksDB は、非常に優れたオープンソースのスタンドアロン ストレージ エンジン です。 】

tidb は Go 言語ですか?

Raft 整合性アルゴリズムを使用することにより、データは TiKV ノード間で複数のコピーにコピーされ、ノードに障害が発生した場合のデータのセキュリティが確保されます。

実際には、内部では、TiKV はレプリケーション ログ ステート マシン (ステート マシン) モデルを使用してデータをレプリケートします。書き込みリクエストの場合、データはリーダーに書き込まれ、リーダーはコマンドをログの形式でフォロワーにコピーします。クラスター内の大部分のノードがこのログを受信すると、ログはコミットされ、それに応じてステート マシンが変更されます。

リージョンの概念

KV システムの場合、複数のマシンにデータを分散するための典型的なソリューションが 2 つあります。1 つはキーによるハッシュです。ハッシュ値に応じて対応するストレージノードを選択する方法と、レンジを分割して、ある連続したキーをストレージノードに保存する方法とがあります。 範囲クエリをサポートするために 、TiKV は 2 番目の方法を選択しました。 Key-Value 空間全体を多くのセグメントに分割しました。各セグメントは一連の連続したキーであり、各セグメントを と呼びます。リージョンであり、各リージョンに保存されるデータが特定のサイズを超えないようにします(このサイズは構成可能で、現在のデフォルトは96MBです)。各領域は、StartKey から EndKey までの左閉および右開の間隔で記述することができます。

tidb は Go 言語ですか?

#データをリージョンに分割した後、

2 つの重要な作業を行います:

  • # #リージョンを単位として使用し、クラスター内のすべてのノードにデータを分散し、各ノードで提供されるリージョンの数がほぼ同じになるようにしてください。

    データはキーに従って多数のリージョンに分割されており、各リージョンのデータは 1 つのノードにのみ保存されます。私たちのシステムには、クラスター内のすべてのノードにリージョンをできるだけ均等に分散する役割を担うコンポーネント [PD] があり、

    一方でストレージ容量の水平方向の拡張を実現します

    (新しいノードを追加した後、リージョンは他のノードは自動的にスケジュールされます)、 一方、負荷分散も実現されます (あるノードに多くのデータがあり、他のノードに少ないデータがあるという状況は発生しません)。同時に、上位層のクライアントが必要なデータに確実にアクセスできるようにするために、システムのコンポーネント [PD] はノード上のリージョンの分布も記録します。キーがどのリージョンにあるか、およびそのリージョンが現在どのノードにあるかをクエリします。

  • Raft のレプリケーションとメンバー管理をリージョンで実行します。

    TiKV はリージョン単位でデータをレプリケートします。つまり、リージョンのデータは複数のコピーを保存し、各コピーはレプリカと呼ばれます。レプリカはデータの一貫性を維持するために Raft を使用します (最後に Raft について説明しました)。リージョン内の複数のレプリカは異なるノードに保存され、Raft グループを形成します。 1 つのレプリカはこのグループのリーダーとして機能し、もう 1 つのレプリカはフォロワーとして機能します。すべての読み取りと書き込みはリーダーを通じて実行され、リーダーはフォロワーにコピーされます。

    リージョンを理解すると、次の図が理解できるはずです。

tidb は Go 言語ですか?

データはリージョンで作成されます。分散とレプリケーションにより、特定の災害耐性機能を備えた分散 KeyValue システムが得られるため、データの損失やディスク障害によるデータ損失を心配する必要がなくなります。

MVCC2 つのクライアントが同時にキーの値を変更した場合、MVCC がない場合、データはロックする必要があります。分散シナリオでは、パフォーマンスとデッドロックの問題が発生する可能性があります。 TiKV の MVCC 実装は、Key の後に Version を追加することで実装されます。

对于同一个 Key 的多个版本,把版本号较大的放在前面,版本号小的放在后面。这样当用户通过一个 Key + Version 来获取 Value 的时候,可以将 Key 和 Version 构造出 MVCC 的 Key,也就是 Key-Version。然后可以直接 Seek(Key-Version),定位到第一个大于等于这个 Key-Version 的位置。

#简单来说,没有 MVCC 之前,可以把 TiKV 看做这样的
Key1 -> Value
Key2 -> Value
……
KeyN -> Value
#有了 MVCC 之后,TiKV 的 Key 排列是这样的:
Key1-Version3 -> Value
Key1-Version2 -> Value
Key1-Version1 -> Value
……
Key2-Version4 -> Value
Key2-Version3 -> Value
Key2-Version2 -> Value
Key2-Version1 -> Value
……
KeyN-Version2 -> Value
KeyN-Version1 -> Value
……

GC

TiDB 的事务的实现采用了 MVCC(多版本并发控制)机制,当新写入的数据覆盖旧的数据时,旧的数据不会被替换掉,而是与新写入的数据同时保留,并以时间戳来区分版本。Garbage Collection (GC) 的任务便是清理不再需要的旧数据。

  • GC整体流程

一个 TiDB 集群中会有一个 TiDB 实例被选举为 GC leader,GC 的运行由 GC leader 来控制。

GC 会被定期触发。每次 GC 时,首先,TiDB 会计算一个称为 safe point 的时间戳,接下来 TiDB 会在保证 safe point 之后的快照全部拥有正确数据的前提下,删除更早的过期数据。每一轮 GC 分为以下三个步骤

step1:“Resolve Locks” 【清理锁】阶段会对所有 Region 扫描 safe point 之前的锁,并清理这些锁。

step2:“Delete Ranges” 【删除区间】阶段快速地删除由于 DROP TABLE/DROP INDEX 等操作产生的整区间的废弃数据。

step3:“Do GC”【进行GC清理】阶段每个 TiKV 节点将会各自扫描该节点上的数据,并对每一个 key 删除其不再需要的旧版本。

默认配置下,GC 每 10 分钟触发一次,每次 GC 会保留最近 10 分钟内的数据(即默认 GC life time 为 10 分钟,safe point 的计算方式为当前时间减去 GC life time)。如果一轮 GC 运行时间太久,那么在一轮 GC 完成之前,即使到了下一次触发 GC 的时间也不会开始下一轮 GC。另外,为了使持续时间较长的事务能在超过 GC life time 之后仍然可以正常运行,safe point 不会超过正在执行中的事务的开始时间 (start_ts)。

2、TiDB数据库的计算——TiDB Server

从 SQL 的角度了解了数据是如何存储,以及如何用于计算。

TiDB 在 TiKV 提供的分布式存储能力基础上,构建了兼具优异的交易处理能力与良好的数据分析能力的计算引擎。

TiDB Server:SQL 解析层,对外暴露 MySQL 协议的连接 endpoint,负责接受客户端的连接,执行 SQL 解析和优化,最终生成分布式执行计划。TiDB 层本身是无状态的,实践中可以启动多个 TiDB 实例,通过负载均衡组件(如 LVS、HAProxy 或 F5)对外提供统一的接入地址,客户端的连接可以均匀地分摊在多个 TiDB 实例上以达到负载均衡的效果。TiDB Server 本身并不存储数据,只是解析 SQL,将实际的数据读取请求转发给底层的存储节点 TiKV(或 TiFlash)。

SQL映射KV

可以将关系模型简单理解为 Table 和 SQL 语句,那么问题变为如何在 KV 结构上保存 Table 以及如何在 KV 结构上运行 SQL 语句。 SQL 和 KV 结构之间存在巨大的区别,那么如何能够方便高效地进行映射,就成为一个很重要的问题。一个好的映射方案必须有利于对数据操作的需求。

tidb は Go 言語ですか?

分布式SQL运算

首先我们需要将计算尽量靠近存储节点,以避免大量的 RPC 调用。其次,我们需要将 Filter 也下推到存储节点进行计算,这样只需要返回有效的行,避免无意义的网络传输。最后,我们可以将聚合函数、GroupBy 也下推【计算下推】到存储节点,进行预聚合,每个节点只需要返回一个 Count 值即可,再由 tidb-server 将 Count 值 Sum 起来【并行算子】。 这里有一个数据逐层返回的示意图:

tidb は Go 言語ですか?

实际上 TiDB 的 SQL 层要复杂的多,模块以及层次非常多,下面这个图【SQL引擎架构】列出了重要的模块以及调用关系:

tidb は Go 言語ですか?

SQL クエリを返す簡単なプロセス: ユーザーの SQL リクエストは tidb-server に直接送信されるか、ロード バランサ経由で送信されます。tidb-server は MySQL プロトコル パケットを解析し、リクエストの内容を取得してから、構文分析の実行 クエリ プランの作成と最適化、データの取得と処理のためのクエリ プランの実行。すべてのデータは TiKV クラスターに保存されるため、このプロセスでは tidb-server が tikv-server と対話してデータを取得する必要があります。最後に、tidb-server はクエリ結果をユーザーに返す必要があります。

SQL 実行プロセス

TiDB では、入力されたクエリ テキストから最終的な実行プランの実行結果までのプロセスを次の図に示します。

tidb は Go 言語ですか?

パーサーが元のクエリ テキストを解析し、簡単な合法性を検証した後、TiDB は最初にクエリに論理的に同等の変更をいくつか加えます——クエリ ロジックの最適化
これらの同等の変更により、このクエリは論理実行プランでの処理が容易になります。同等の変更が完了すると、TiDB は元のクエリと同等のクエリ プラン構造を取得し、データ分散とオペレーターの特定の実行コストに基づいて最終的な実行プランを取得します - クエリの物理的な最適化
同時に、TiDB が PREPARE ステートメントを実行するときに、TiDB が実行計画を生成するコストを削減するためにキャッシュを有効にすることを選択できます (実行計画キャッシュ)。

3. TiDB データベースのスケジューリング - PD サーバー

PD (配置ドライバー) は TiDB クラスターの管理モジュールであり、次の役割も果たします。クラスター データのリアルタイム スケジューリング。

スケジューリング シナリオ

PD (配置ドライバー) サーバー: TiDB クラスター全体のメタ情報管理モジュール、ストレージを担当します。各 TiKV ノードとクラスターのトポロジー全体のリアルタイム データ分散を提供し、TiDB ダッシュボード管理および制御インターフェイスを提供し、分散トランザクションにトランザクション ID を割り当てます。 PD はメタ情報を保存するだけでなく、TiKV ノードからリアルタイムに報告されるデータ配信状況に基づいて、特定の TiKV ノードにデータ スケジューリング コマンドを発行する、クラスター全体の「頭脳」とも言えます。さらに、PD 自体は少なくとも 3 つのノードで構成され、高可用性を提供します。奇数の PD ノードを展開することをお勧めします。

スケジュール要件

最初のカテゴリ: 分散型高可用性ストレージ システムとして、満たさなければならない要件には次のものが含まれます。 : [ディザスタリカバリ機能]

  • コピー数は増減できません。
  • レプリカは、トポロジに応じて異なる属性を持つマシンに分散する必要があります。
  • ノードのダウンタイムまたは異常が発生した場合、災害復旧を自動的かつ合理的に迅速に実行できます。

#2 番目のカテゴリ: 優れた分散システムとして、考慮する必要がある事項は次のとおりです。: [より高く合理的なリソース使用率、優れたスケーラビリティ]

    クラスター全体でリーダーの均等な分布を維持します。
  • 各ノードのストレージ容量を均一に維持します。
  • アクセス ホットスポットの均等な分散を維持します。
  • オンライン サービスへの影響を避けるために、負荷分散の速度を制御します。
  • ノードを手動でオンライン/オフラインにするなど、ノードのステータスを管理します。
これらのニーズを満たすためには、各ノードのステータス、各 Raft グループの情報、ビジネス アクセス操作の統計など、十分な情報を収集する必要があります。を設定する必要があり、PD はこれらの情報とスケジューリング戦略に従っていくつかのポリシーを設定し、前述のニーズを可能な限り満たすスケジューリング計画を作成する必要があります。

スケジューリング操作

スケジューリングの基本操作とは、スケジューリング ポリシーを満たす目的を指します。上記のスケジュール要件は、次の 3 つの操作に整理できます。

    コピーの追加
  • コピーの削除
  • Raft の異なるコピー間にリーダー ロールを配置します。グループ転送 (移行)
Raft プロトコルは、3 つのコマンド

AddReplicaRemoveReplicaTransferLeader# を通じて上記 3 つをサポートできます。 ## 基本的な操作。 TiKV ストアのステータスは、具体的には、アップ、切断、オフライン、ダウン、および廃棄に分類されます。各ステータスの関係は次のとおりです。

スケジュール戦略

  • リージョンのコピー数は正しいです。
  • Raft グループ内の複数のコピーは同じ場所にありません。
  • コピーはストア間で均等に分配されます。
  • リーダーの数はストア間で均等に配分されます。
  • アクセス ホットスポットの数はストア間で均等に分散されます。
  • 各ストアが占有する保管スペースはほぼ均等です。
  • オンライン サービスへの影響を避けるために、スケジュール速度を制御します。

スケジューリング実装

PD は、ストア [つまり、TiKV ノード] またはリーダーのハートビート パケットを通じて継続的に情報を収集し、全体の情報を取得します。 PD はクラスタの詳細データを取得し、この情報とスケジューリング ポリシーに基づいてスケジューリング操作シーケンスを生成します。リージョン リーダーからハートビート パケットを受信するたびに、PD はこのリージョンに対して実行する操作があるかどうかを確認します。 PD は、ハートビート パケットのメッセージを受信すると、必要な操作をリージョン リーダーに返し、実行結果を後続のハートビート パケットで監視します。なお、ここでの運用はリージョンリーダーへの提案であり、実行されることを保証するものではなく、実行するか否か、いつ実行するかはリージョンリーダーの現状に応じて自ら判断するものとします。

5. TiDB のベスト プラクティス

TiDB のベスト プラクティスは、その実装原則と密接に関連しています。最初にいくつかの基本的な実装メカニズムを理解することをお勧めします。 Raft、分散トランザクション、データ シャーディング、ロード バランシング、SQL から KV へのマッピング スキーム、セカンダリ インデックスの実装方法、分散実行エンジンが含まれます。

Raft

Raft は、強力な整合性データ レプリケーション保証を提供できる整合性プロトコルであり、TiDB の最下層は Raft を使用してデータを同期します。 。各書き込みでは、成功を外部に返す前に大部分のコピーに書き込む必要があるため、たとえ少数のコピーが失われたとしても、システム内で最新のデータが確保されます。たとえば、コピーが最大 3 つある場合、2 つのコピーへの書き込みはそれぞれ成功したとみなされ、コピーが 1 つだけ失われた場合でも、残っている 2 つのコピーのうち少なくとも 1 つは最新のデータを持つことになります。

同様に 3 つのコピーを保存するマスター/スレーブ同期方式と比較すると、Raft 方式は、書き込み遅延が最も遅いコピーではなく 2 つの最も速いコピーに依存するため、より効率的です。したがって、Raft 同期を使用すると、複数の場所に住むことが可能になります。 2 か所に 3 つのセンターがある一般的なシナリオでは、データの整合性を確保するために、各書き込みはローカル データ センターと近くのデータ センターでのみ成功する必要があり、3 つのデータ センターすべてで成功する必要はありません。

分散トランザクション

TiDB は完全な分散トランザクションを提供し、トランザクション モデルは Google Percolator に基づいて最適化されています。

  • オプティミスティック ロック

    TiDB のオプティミスティック トランザクション モデルは、実際に送信されたときにのみ競合検出を実行します。競合がある場合は、再試行する必要があります。このモデルは、再試行前の操作は無効であり、繰り返す必要があるため、深刻な競合があるシナリオでは比較的非効率的になります。極端な例として、データベースをカウンターとして使用すると、アクセスの同時実行性が比較的高い場合、深刻な競合が発生し、多数の再試行が発生したり、タイムアウトが発生したりすることがあります。ただし、アクセス競合がそれほど深刻でない場合は、楽観的ロック モデルの方が効率的です。深刻な競合が発生するシナリオでは、悲観的ロックを使用するか、Redis にカウンターを配置するなど、システム アーキテクチャ レベルで問題を解決することをお勧めします。

  • 悲観的ロック

    TiDB の悲観的トランザクション モード、悲観的トランザクションの動作は基本的に MySQL と同じで、実行フェーズ中にロックされます (先着順)。 、競合を回避するために、特定の状況下で再試行すると、競合が多いトランザクションの成功率を確保できます。悲観的ロックは、select for update を通じて事前にデータをロックするシナリオも解決します。ただし、ビジネス シナリオ自体の競合が少ない場合は、楽観的ロックのパフォーマンスがより有利になります。

  • トランザクション サイズ制限

    分散トランザクションには 2 段階のコミットが必要であり、最下層にも Raft レプリケーションが必要であるため、トランザクションが非常に大きい場合、送信プロセスはこれは遅く、以下の Raft コピー プロセスをブロックします。システムがスタックするのを防ぐために、トランザクションのサイズを制限しました [1 つのトランザクションに含まれる SQL ステートメントは 5,000 個以下 (デフォルト)]。

データの断片化

TiKV は、キーの範囲に従って基になるデータを自動的に断片化します。各リージョンはキーの範囲であり、StartKey から EndKey までの左閉および右開の間隔です。リージョン内の Key-Value の総数が一定の値を超えると、自動的に分割されます。この部分はユーザーには透過的です。

ロード バランシング

PD は、TiKV クラスター全体のステータスに基づいてクラスターの負荷をスケジュールします。スケジューリングはリージョン単位で、PDで設定したポリシーをスケジューリングロジックとして使用し、自動で完了します。

KV 上の SQL

TiDB は、SQL 構造を KV 構造に自動的にマップします。簡単に言えば、TiDB は次の操作を実行します:

  • データ行は KV にマップされ、キーはプレフィックスとして TableID を使用して構築され、行 ID はサフィックスになります。
  • インデックスは次のようにマップされます。 KV の場合、キーは TableID IndexID で構築されます。 プレフィックスを構築し、インデックス値を使用してサフィックスを構築します。

テーブル内のデータまたはインデックスは次のようになります。同じプレフィックスなので、TiKV キー空間では、これらの Key-Value は隣接する位置になります。そして、書き込み量が多くテーブルに集中している場合、特に継続的に書き込まれるデータ内の一部のインデックス値も連続している場合(更新時間、時間とともに増加するフィールドなど)、書き込みホットスポットが発生します。 、いくつかのリージョンに書き込みホットスポットが形成され、システム全体のボトルネックになります。同様に、すべてのデータ読み取り操作が狭い範囲 (連続したデータの数万行または数十万行など) に集中している場合、データ アクセス ホットスポットが発生する可能性があります。

セカンダリ インデックス

TiDB は完全なセカンダリ インデックスをサポートしており、グローバル インデックスであり、インデックスを通じて多くのクエリを最適化できます。セカンダリ インデックスを上手に利用する場合、それはビジネスにとって非常に重要です。MySQL での多くの経験が TiDB にもそのまま当てはまります。ただし、TiDB には注意が必要な独自の特性もいくつかあります。このセクションでは主に次の点について説明します。 TiDB でセカンダリ インデックスを使用する場合の注意事項。

  • セカンダリ インデックスは多いほど良いです。

  • 識別度 [カーディナリティ] が比較的大きい列にインデックスを作成する方が適切です。複数のクエリ条件がある場合は、結合されたインデックスを選択し、左端のプレフィックスの原則に注意を払うことができます。

  • インデックスによるクエリとテーブルの直接スキャンの違い。

  • #クエリの同時実行性。

    データは多くのリージョンに分散しているため、TiDB はクエリを同時に実行します。同時実行数が高すぎると大量のシステム リソースが消費されるため、デフォルトの同時実行数は比較的控えめです。

    OLTP タイプのクエリの場合、多くの場合、大量のデータが関与しないため、同時実行性が低くてもすでにニーズを満たすことができます。

    OLAP タイプのクエリの場合、多くの場合、より高度な同時実行性が必要になります。

    したがって、TiDB は、システム変数によるクエリの同時実行の調整をサポートしています。 [tidb_distsql_scan_concurrency、tidb_index_lookup_size、tidb_index_lookup_concurrency、tidb_index_serial_scan_concurrency など]

  • インデックスによる結果の順序を保証します。 [インデックスはデータのフィルタリングに使用するだけでなく、データの並べ替えにも使用できます。まず、インデックスの順序で行 ID が取得され、次に行の返された順序で行の内容が返されます。 ID: これにより、返された結果がインデックス列に従って確実に配置されます。 ]

  • は逆インデックス作成もサポートしています。 [現在の速度は逐次スキャンより遅く、通常は 20% 遅くなります。データが頻繁に変更され、バージョンが多い場合はさらに遅くなります。可能であれば、インデックスの逆スキャンを避けることをお勧めします]

プログラミング関連の知識の詳細については、

プログラミング ビデオをご覧ください。 !

以上がtidb は Go 言語ですか?の詳細内容です。詳細については、PHP 中国語 Web サイトの他の関連記事を参照してください。

声明:
この記事の内容はネチズンが自主的に寄稿したものであり、著作権は原著者に帰属します。このサイトは、それに相当する法的責任を負いません。盗作または侵害の疑いのあるコンテンツを見つけた場合は、admin@php.cn までご連絡ください。