著者: Zhang Kai@aliyun、Chen Weiting@Intel、Zhou Yuan @Intel
序章
Apache Celeborn (Incubating) は、Alibaba Cloud によって Apache に提供された汎用リモート シャッフル サービスであり、ビッグ データ コンピューティング エンジンのパフォーマンス/安定性/弾力性を向上させることを目的としており、運用シナリオで広く使用されています。Gluten は、Intel のオープンソース エンジン アクセラレーション プロジェクトであり、Spark Java エンジンをネイティブ エンジン (Velox、ClickHouse、Arrow など) に置き換えることによって Spark エンジンを高速化することを目的としています。過去の期間にわたって、Gluten コミュニティと Celeborn コミュニティは相互に協力し、Celeborn を Gluten に統合することに成功しました。これについては、この記事で紹介します。
Gluten: Spark をネイティブ エンジンに置き換える
Gluten プロジェクトは、Apache Spark ベースのデータ読み込みシナリオにおける CPU コンピューティングのボトルネックを解決することを目的としています。IO テクノロジーの向上、特に SSD や 10 ギガビット ネットワーク カードの普及に伴い、CPU コンピューティングのボトルネックが徐々にパフォーマンスを制限する主な要因になってきました。ただし、JVM が提供する最適化機能が C++ などの他のネイティブ言語に比べて少ないため、JVM に基づいて CPU 命令を最適化することは比較的困難です。
この問題を解決するために、オープン ソース コミュニティの一部の成熟したローカル エンジン (ClickHouse や Velox など) は、パフォーマンスに大きな利点をもたらす優れたベクトル化実行機能を備えています。ただし、これらのエンジンは通常、Spark エコシステムから分離されているため、すでに Spark コンピューティング フレームワークに大きく依存しており、多額の運用、メンテナンス、移行コストを支払う余裕がないユーザーにとっては、十分に使いやすいものではありません。Gluten プロジェクトの目標は、Spark ユーザーが移行することなく、これらの成熟したネイティブ エンジンのパフォーマンス上の利点を享受できるようにすることです。
Gluten プロジェクトは、Spark プラグイン メカニズムを使用してクエリ プランをインターセプトし、実行のためにローカル エンジンに送信します。これにより、Spark 自体が十分に効率的ではない実行パスがスキップされます。このプロジェクトは、Velox、ClickHouse、Apache Arrow などの複数のネイティブ エンジンをバックエンドとしてサポートしています。ネイティブ エンジンが処理できない操作の場合、Gluten は Spark の通常の実行パスにフォールバックします。スレッド モデルに関しては、Gluten は JNI 呼び出しライブラリの形式を使用して、Spark エグゼキューター タスク スレッドのローカル コードを直接呼び出し、複雑なスレッド モデルの導入を回避します。
メモリ管理に関しては、Gluten はローカル メモリと JVM メモリを統合的に管理し、ローカル メモリ プールとタスク メモリ マネージャーを通じてメモリを割り当てることができます。メモリが不足すると、メモリを解放するためにオーバーフロー操作がトリガーされます。さらに、Gluten は、Celeborn などの市場で人気のあるサードパーティの RemoteShuffleService に接続するための完全なカラム型 Shuffle メカニズムと統合 API インターフェイスも提供し、データ変換のオーバーヘッドを回避してサービスを提供します。
さまざまなローカル エンジンと互換性を持たせるために、Gluten は、Spark フレームワークと基礎となるエンジンの間のブリッジとして明確な JNI インターフェイスを定義します。これらのインターフェイスは、リクエストの配信、データ送信、機能の検出に使用されます。開発者は、これらのインターフェイスを実装し、Gluten を使用して Spark とローカル エンジンの統合を完了するための対応するセマンティック要件を満たすだけで済みます。さらに、Shim レイヤーも、Spark のさまざまなバージョンに適応してサポートするために、Spark のアーキテクチャ設計で予約されています。
グルテン柱状シャッフル
Shuffle自体はSparkのパフォーマンスを左右する重要な部分ですが、ここでは多重シリアル化/デシリアライズ、ネットワーク送信、ディスクの読み書きなどを導入するので、高いパフォーマンスを実現するためにボトルネックにならないようにします。Native Engine はデータを一時的に保存するために Columnar データ構造を使用するため、単純に Spark の行データ モデルベースの Shuffle を使用する場合、データ列変換のリンクは Shuffle Write ステージで導入され、データ行転送は Shuffle Write ステージで導入されます。シャッフルリードステージ データの流れをスムーズにするため。ただし、行を列に、または列を行に変換するコストは低くありません。したがって、Gluten は、ここでの変換オーバーヘッドを回避するために、完全な Columnar Shuffle メカニズムを提供する必要があります。カラムナ シャッフル実装層に特有のもので、主にシャッフル データの書き込みとシャッフル データの読み取りの 2 つの部分に分かれています。
カラムナシャッフル書き込み
ネイティブ Spark と同様に、Columnar Shuffle の目的は、現在の DAG によって生成された一時データをディスクに書き込むことです。データは次のステージで読み取られる必要があります。また、メモリが不十分な場合のスピル操作をサポートする必要もあります。クエリの堅牢性を確保することを優先します。Spark との主な違いは次のとおりです。
- Spark はデフォルトで行ベースの形式を使用してデータを保存し、Gluten のシャッフルは列形式を使用してデータを保存します。
- 現在の実装はシリアル化用の Arrow 形式に基づいており、カスタム圧縮形式をサポートしています。カラムナ形式を使用することで、最適化のための SIMD 命令を簡単に導入できます。
- Spark はデフォルトでソートベースのシャッフルを使用しますが、Gluten はデフォルトでハッシュベースのシャッフルを使用します
- ソートベースのシャッフルは、ハッシュベースのアルゴリズムよりも複雑ではありませんが、より多くのメモリを必要とし、小さなファイルに関する多くの問題が発生します。グルテンでハッシュ ベースのシャッフルを実装する場合、ソート ベースのシャッフルの設計の一部も参照し、小さなファイルが多すぎる場合の影響を軽減します。
TPC-H Like Scale Factor 6TB のテスト シナリオでは、列指向シャッフル書き込みにより、ネイティブ Spark の行ベースのシャッフルと比較して、シャッフル サイズを約12%削減できます。
カラムナシャッフル読み取り
Columnar Shuffle 読み取りを実装する場合、Gluten は Spark の netty ベースのシャッフル転送メカニズムを再利用し、ディスクに書き込まれたシャッフル ファイルを読み取り、reducer にデシリアライズするための対応するデシリアライザーを提供するだけで済みます。Spark では netty や kryo などのソフトウェア スタックが多数導入されており、その結果、リデューサーの読み取り時にメモリ コピーが重複してしまいますが、Gluten では、ソフトウェアのオーバーヘッドを削減するためにゼロ コピーの最適化も行っています。
Celeborn: ローカル シャッフルの制限を解決
グルテンのローカルシャッフルの制限
上の図は、Gluten Columnar Shuffle の主要なプロセスを示しています。ハッシュベースのシャッフル、ネイティブ パーティショナー、ゼロ コピーなどの設計がその高いパフォーマンスの鍵となります。ただし、Gluten は Spark のローカル Shuffle フレームワークに従っており、次のような大きな制限があります。
-
シャッフル データの保存に大容量のローカル ディスクに依存すると、ストレージとコンピューティングの分離アーキテクチャを適用できない一方で、「ステートフル」コンピューティング ノードを時間内にスケールダウンできないため、困難になります。クラウドネイティブ アーキテクチャと低いリソース使用率との互換性を実現します。
-
シャッフル書き込み メモリが不足している場合にディスクにスピルし、追加のディスク I/O を追加します。
-
シャッフル読み取りでは、多数のネットワーク接続と大量のディスクのランダム読み取りが行われるため、安定性とパフォーマンスが低下します。
著名人紹介
Apache Celeborn (Incubating) は、比較的成熟した汎用リモート シャッフル サービスであり、ビッグ データ エンジンのローカル シャッフルの安定性、パフォーマンス、弾力性の問題を十分に解決できます。詳細については、巻末の索引を参照してください。記事[1][2][3][4]。Apache Celeborn コミュニティと Gluten コミュニティは、一定期間にわたって相互に協力し、Celeborn を Gluten に統合することに成功し、Native Spark が Cloud Native をより適切に受け入れることができるようになりました。次に、Gluten がどのように Celeborn と統合されるかを紹介します。
グルテン + セレボルン
全体的なデザイン
Celeborn を統合する Gluten の設計目標は、Gluten Columnar Shuffle と Celeborn Remote Shuffle のコア設計を同時に維持し、両方の利点を重ね合わせることです。
上の図は、Gluten+Celeborn Columnar Shuffle の全体的な設計を示しています: Shuffle Writer はネイティブ パーティショナーを再利用し、ローカル IO をインターセプトして代わりに Celeborn クラスターにプッシュします。Celeborn クラスターはデータの再編成 (同じパーティションのデータの集約) と複数のバックアップを実行します。Shuffle Reader特定の Celeborn ワーカーでデータを順次読み取り、列バッチに逆シリアル化します。この設計は、Gluten Columnar Shuffle の高性能設計を維持するだけでなく、Celeborn のリモート ストレージ、データ再編成、およびマルチコピー機能を最大限に活用します。
具体的には、Gluten と Celeborn の統合は、主に、次に紹介する、対応する ShuffleManager、ShuffleWriter、および ShuffleReader の実装です。
セレボーンシャッフルマネージャー
CelebornShuffleManager は Spark ShuffleManager インターフェイスを継承しており、Celeborn に接続された Gluten の ShuffleManager として、主に次の作業を行います。
-
シャッフルを Celeborn に登録し、失敗した場合は Gluten のローカル Columnar Shuffle にフォールバックします。
-
Celeborn クラスターとの接続を確立し、Celeborn Shuffle クライアントを初期化します。
-
CelebornShuffleWriter を取得するための getWriter メソッドを提供します。
-
CelebornShuffleReader を取得するための getReader メソッドを提供します。
セレボーンシャッフルライター
CelebornShuffleWriter は Gluten Columnar Shuffle と一致しており、どちらもハッシュベースの Shuffle を採用しています。その中心的な機能は、Gluten のネイティブ パーティショナーを再利用し、ディスク IO 操作 (スピル、シャッフル ファイルの書き込み) を Celeborn クラスターへのプッシュに置き換えることです。主なプロセスは次のとおりです。
-
CelebornPartitionPusher を JNI 経由でネイティブ モジュールに渡し、ネイティブ モジュールがデータを Celeborn クラスターにプッシュできるようにします。
-
ネイティブ パーティショナーを再利用して、Gluten Columnar Shuffle と一貫して列データを分割します。
-
Spiller を GlutenMemoryConsumer に登録すると、Spark がメモリ不足を検出して Spill をトリガーしたときに、Celeborn SDK を通じてデータを Celeborn クラスターにプッシュできるため、追加のディスク IO が回避されます。
-
ネイティブ モジュールでは、すべてのデータがパーティション化されると、ファイルの書き込み操作は、Celeborn SDK を介して Celeborn クラスターにプッシュされることで置き換えられます。
CelebornShuffleReader
CelebornShuffleReader は、Celeborn クラスターとの接続を確立して、Shuffle データを読み取ります。CelebornColumnarBatchSerializer を Gluten 側に実装し、deserializeStream メソッドを通じて InputStream の逆シリアル化プロセスをカスタマイズし、最後にさらなる処理のために逆シリアル化された ColumnarBatch を Gluten に渡します。上の 2 つの図の比較から、ローカル Shuffle の Reducer は複数のファイルからデータを読み取るのに対し、Celeborn Reducer は 1 つの Worker からのみ読み取る必要があり、ランダム読み取りがシーケンシャル読み取りに変換されることがわかります。ネットワーク接続数が乗数関係から 1 に変更され、線形関係が改善され、シャッフル読み取りのパフォーマンスが向上します。
性能試験
Celeborn は、ディスク リソースが制限されている場合に最高のパフォーマンスを発揮します。SDD 環境、フル HDD 環境、制限付き HDD 環境の 3 つのハードウェア環境をテストしました。全体的な結論は、SDD 環境では、Gluten + Celeborn Columnar Shuffle のパフォーマンスは Gluten のローカル Columnar Shuffle のパフォーマンスと同等であり、フル HDD 環境および制限付き HDD 環境では、Gluten + Celeborn Columnar Shuffle のパフォーマンスは 8% と 12 です。 Gluten のローカル Columnar Shuffleよりもそれぞれ% 高い値です。
フルHDD環境
展開方法:CelebornクラスタとYarnクラスタが混在します。
ハードウェア環境: 1 x マスター (64 vCPU、256 GiB) 5 x ワーカー (40 vCPU、176 GiB、15 x 7300GB HDD)
スパークバージョン: 3.3.1
ベンチマーク:3T TPCDS
以下の図は、Gluten の Top20 と比較した Gluten+Celeborn の高速化率を示しています。
次の図は、完全な TPCDS の時間の比較であり、全体で 8% の増加が見られます。
制約のある HDD 環境
展開方法:CelebornクラスタとYarnクラスタが混在します。
ハードウェア環境: 1 x マスター (64 vCPU、256 GiB) 5 x ワーカー (40 vCPU、176 GiB、2 x 7300GB HDD)
スパークバージョン: 3.3.1
ベンチマーク:3T TPCDS
以下の図は、Gluten の Top20 と比較した Gluten+Celeborn の高速化率を示しています。
次の図は、完全な TPCDS の時間の比較であり、全体的に12%増加しています。
SSD環境
最終的に、すべてのディスクを SSD に交換しましたが、Gluten+Celeborn は、追加のマシン リソースを消費することなく、Gluten と比較してパフォーマンスが1.2%向上し、パフォーマンスは基本的に同じでした。
要約する
この記事では、Gluten プロジェクトの背景と目標、および Apache Spark ベースのデータ読み込みシナリオにおける CPU コンピューティングのボトルネックを解決する方法について紹介します。Gluten は、Spark プラグイン メカニズムを使用して、実行のためにクエリ プランをローカル エンジンに送信します。これにより、Spark 自体が十分に効率的ではない実行パスをスキップします。このプロジェクトはバックエンドとして複数のローカル エンジンをサポートし、Columnar Shuffle 設計を導入し、ローカル メモリと JVM メモリを統合された方法で管理します。さらに、Gluten は Celeborn をリモート シャッフル サービスとして統合しており、Celeborn はプッシュ シャッフルの設計を採用しており、リモート ストレージ、データの再編成、メモリ キャッシュ、および複数のコピーの設計を通じて、Gluten Shuffle のパフォーマンスと安定性がさらに向上するだけでなく、また、グルテンの弾力性も向上し、クラウド ネイティブをよりよく受け入れることができます。
私たちのオープンソース プロジェクトに参加してコードを貢献することを歓迎します。私たちのプロジェクトは次の場所にあります
グルテン: https://github.com/oap-project/gluten
セレボーン: https://github.com/apache/incubator-celeborn
セレボーンユーザー交流ネイルグループ: 41594456
参照
[1] https://developer.aliyun.com/article/779686
[2] https://developer.aliyun.com/article/857757
[3] https://developer.aliyun.com/article/891951
[4] https://developer.aliyun.com/article/1153123
iQIYIクライアント「ホワイト」TV、バックグラウンドでフルスピードでアップロード. Deepin はApple M1 スレッドに適応するためにAsahi Linuxを使用 . 7月のリスト: C++がCを追い越そうとしており、JavaScriptがトップ6に入る Visual Studio Code 1.80リリース、ターミナルピクチャ機能をサポート ChatGPT トラフィックはバックグラウンドとフロントエンドの中間で 10% 減少し 、長い間 CURD に悩まされ、Koala Form 7 月のデータベースランキング: Oracle が急上昇、 世界のデスクトップブラウザ市場シェアランキングで再びトップに躍り出、Safari は引き続きトップにしっかりと座った二位