CockroachDB プロセスが高 CPU を消費している場合——本例では 1 コアの 250% 超——OpenResty XRay は稼働中の Go サーバー上で CPU 時間の消費先を正確に特定します。再起動もコード変更も不要です。Go のガベージコレクションだけで CPU の約 13% を占め、その背後には kvcoord、Raft、sqlMux コンポーネントで大量の GC オブジェクトを割り当てるホットコードパスがあります。

本チュートリアルではこの後、OpenResty XRay が Go 実装の CockroachDB 内部で CPU 時間がどこに費やされているかを定量化し、Go 言語レベルの CPU フレームグラフを自動的に分析・解釈して、最も CPU を消費するコードパスを明らかにする方法を説明します。

問題:CockroachDB の高 CPU 使用率

CockroachDB は Go(golang)言語で書かれた分散データベースです。実行中の CockroachDB サーバーの CPU 時間がどのように配分されているかを分析します。

CPU 使用状況を確認するために top コマンドを使用します。このプロセスが 250% 以上の CPU を使用していることがわかります。

top コマンドで CockroachDB プロセスが 250% 以上の CPU を消費していることを表示

ps コマンドを実行してこのプロセスの詳細情報を確認します。このプロセスは、Linux ディストリビューションに付属する標準 CockroachDB バイナリ実行ファイルそのものです。

ps コマンドの出力で標準の CockroachDB バイナリプロセスであることを確認

Guided Analysis で最も CPU を消費する Go コードパスを特定する

OpenResty XRay を使用して、この未修正の CockroachDB プロセスをリアルタイムで分析します。再起動もコード変更も不要です。OpenResty XRay の Web コンソールを開き、分析対象のマシンが正しいことを確認して、「Guided Analysis」ページに移動します。

CockroachDB ホストを選択するための監視対象マシン一覧を表示した OpenResty XRay の Web コンソール

Guided Analysis ページで「High CPU Usage」の問題タイプを選び、「By Processes」を選択して、約 200% の CPU を消費している CockroachDB プロセス——先ほど top で確認したもの——を選びます。

高 CPU 分析のために約 200% の CPU を消費する CockroachDB プロセスを選択

アプリケーションのタイプと言語レベルは自動検出された「Go」のデフォルトのままにし、最大分析時間もデフォルトの 300 秒のままにして、分析を開始します。

CockroachDB の CPU 分析を開始する前に言語レベルを Go に設定

OpenResty XRay は稼働中のプロセスに対して複数回のサンプリングを実行します。この例では 2 回で十分なので、分析を停止します。

稼働中の CockroachDB プロセスに対して複数回の CPU サンプリングを実行する OpenResty XRay

自動生成された分析レポートを見ていきましょう。

OpenResty XRay が CockroachDB 向けに自動生成した CPU 分析レポート

これが分析対象の問題タイプ、「CPU」です。

診断された問題タイプが高 CPU 使用率であることを示す分析レポート

Go ランタイムのガベージコレクション(GC)が CPU 時間の約 13% を占めています。

Go ランタイムのガベージコレクションが CPU 時間の約 13% を消費していることを示すレポート

この Go コードパスで新しく作成された GC オブジェクトの数は、新規作成された GC オブジェクトの総数の約 25% を占めています。

新規作成された GC オブジェクト全体の約 25% を割り当てている Go コードパス

現在実行中のものは、RunAsyncTaskEx 関数内で作成された無名関数で、CockroachDB システム内のさまざまな非同期タスクのライフサイクルを管理するために使用されています。

CockroachDB の非同期タスクを管理する RunAsyncTaskEx が作成した無名関数内のホットパス

詳細を見るには「More」をクリックします。

RunAsyncTaskEx のホットコードパスの詳細ビュー

このホットコードパスは、Go レベルの GC オブジェクトメモリ分布フレームグラフから自動的に導き出されたものです。

ホットコードパスの推定に用いられた Go レベルの GC オブジェクト割り当てフレームグラフ

フレームグラフを拡大します。

拡大した CockroachDB の Go GC オブジェクト割り当てフレームグラフ

さらにクリックして拡大します。

さらに拡大した CockroachDB の Go GC 割り当てフレームグラフ

このホットコードパスは、kvcoord パッケージ、

ホットコードパスの一部として kvcoord パッケージを強調したフレームグラフ

Raft プロトコル、

ホットコードパスのうち Raft プロトコル部分を強調したフレームグラフ

sqlMux コンポーネントの 3 つの主要部分で構成されています。

ホットコードパスのうち sqlMux コンポーネントを強調したフレームグラフ

kvcoord/dist_sender をクリックして拡大します。

拡大した kvcoord/dist_sender コードパスのフレームグラフ

kvcoord は CockroachDB のキー値コーディネーターモジュールで、並行アクセスとデータの一貫性を処理します。複数の kvclient インスタンス間の並行操作を調整し、データの正確性と一貫性を確保する役割を担っています。

CockroachDB の CPU フレームグラフ内の kvcoord キー値コーディネーターのフレーム

Start 関数をクリックして拡大します。

拡大した Raft の Start 関数のフレームグラフ

Raft は CockroachDB が使用する分散コンセンサスプロトコルで、データのレプリケーションと障害耐性を実現するために使用されます。CockroachDB は分散データベースアーキテクチャを採用しており、複数の kvserver ノードが協調して高可用性とスケーラビリティを提供しています。

CockroachDB のフレームグラフ内でデータレプリケーションを担う Raft プロトコルのフレーム

sqlMux 関数に進みます。

拡大した sqlMux 関数のフレームグラフ

sqlMux は CockroachDB のノード上で SQL リクエストのルーティングと多重化を処理するために使用されます。

フレームグラフ内で SQL リクエストのルーティングと多重化を行う sqlMux のフレーム

これらは GC オブジェクトを最も多く割り当てている他のコードパスです。

CockroachDB で GC オブジェクトを最も多く割り当てているその他のコードパス

これは 2 番目の GC オブジェクト割り当てパスです。

CockroachDB で 2 番目に大きい GC オブジェクト割り当てパス

CockroachDB の SQL レイヤーにある makeExecPlan() 関数は、クエリ実行プランを作成します。

CockroachDB の SQL レイヤーでクエリ実行プランを構築する makeExecPlan()

3 番目の GC オブジェクト割り当てパスを見てみましょう。

CockroachDB で 3 番目に大きい GC オブジェクト割り当てパス

列データストリームを処理する際、nextAdapter() の呼び出しも多数の GC オブジェクトを作成します。

列データストリームの処理中に多数の GC オブジェクトを割り当てる nextAdapter()

これは 4 番目の GC オブジェクト割り当てパスです。

CockroachDB で GC オブジェクトを割り当てる 4 番目の Go コードパス

execStmt 関数も実行過程で多数の GC オブジェクトを作成します。

クエリ実行中に多数の GC オブジェクトを割り当てる execStmt 関数

GC オブジェクトの回収が CPU 時間の約 10% を占めています。

GC オブジェクトの回収が CPU 時間の約 10% を占めていることを示すレポート

自動 CPU 分析とレポート

OpenResty XRay は、オンラインプロセスを自動的に監視し、分析レポートを表示することもできます。

オンラインプロセスを自動的に監視しレポートを表示する OpenResty XRay

「Insights」ページに切り替えます。

CockroachDB の自動分析レポートを一覧表示する Insights ページ

「Insights」ページでは、日次および週次のレポートを確認することができます。

Insights ページ上の日次および週次の CPU 分析レポート

したがって、「Guided Analysis」機能を必ずしも使用する必要はありません。もちろん、「Guided Analysis」はアプリケーションの開発やデモンストレーションに非常に有用です。

アプリケーションの開発やデモに用いる Guided Analysis のビュー

よくある質問

なぜ CockroachDB の CPU 使用率が高いのか?

今回の分析では、Go のガベージコレクションが主なコストでした。GC 自体が CPU 時間の約 13% を占め、GC オブジェクトの回収がさらに約 10% を占めています。大量のオブジェクト割り当ては、kvcoord キー値コーディネーター、Raft レプリケーションプロトコル、sqlMux SQL リクエスト多重化器といったホットコードパス、および SQL レイヤーの makeExecPlan()nextAdapter()execStmt() 関数に由来しています。ご自身のクラスターでは高 CPU の原因が異なる場合があるため、稼働中のプロセスをプロファイリングすることが CPU 時間の消費先を確実に知る方法です。

CockroachDB で最も CPU を消費しているコードを見つけるには?

稼働中の CockroachDB プロセスに対して OpenResty XRay の「Guided Analysis」を実行し、プロセス単位で「High CPU Usage」を選び、数回サンプリングさせます。Go 言語レベルの CPU および GC オブジェクト割り当てのフレームグラフを生成し、関数レベルまで最もホットなコードパスを自動的に推定します。再起動もコード変更も不要です。

再起動や pprof なしで CockroachDB の CPU をプロファイリングできますか?

はい。OpenResty XRay は未修正の稼働中の CockroachDB バイナリを直接分析するため、Go の pprof エンドポイントを有効にしたり、デバッグフラグを渡したり、サーバーを再起動したりする必要はありません。これにより、本番ノードがトラフィックを処理し続けている状態でも、CockroachDB の高 CPU 使用率を安全に診断できます。

OpenResty XRay について

OpenResty XRay動的トレーシング製品であり、実行中のアプリケーションを自動的に分析して、パフォーマンスの問題、動作の問題、セキュリティの脆弱性を解決し、実行可能な提案を提供いたします。基盤となる実装において、OpenResty XRay は弊社の Y 言語によって駆動され、Stap+、eBPF+、GDB、ODB など、様々な環境下で複数の異なるランタイムをサポートしております。

著者について

章亦春(Zhang Yichun)は、オープンソースの OpenResty® プロジェクトの創始者であり、OpenResty Inc. の CEO および創業者です。

章亦春(GitHub ID: agentzh)は中国江蘇省生まれで、現在は米国ベイエリアに在住しております。彼は中国における初期のオープンソース技術と文化の提唱者およびリーダーの一人であり、Cloudflare、Yahoo!、Alibaba など、国際的に有名なハイテク企業に勤務した経験があります。「エッジコンピューティング」、「動的トレーシング」、「機械プログラミング」 の先駆者であり、22 年以上のプログラミング経験と 16 年以上のオープンソース経験を持っております。世界中で 4000 万以上のドメイン名を持つユーザーを抱えるオープンソースプロジェクトのリーダーとして、彼は OpenResty® オープンソースプロジェクトをベースに、米国シリコンバレーの中心部にハイテク企業 OpenResty Inc. を設立いたしました。同社の主力製品である OpenResty XRay動的トレーシング技術を利用した非侵入型の障害分析および排除ツール)と OpenResty Edge(マイクロサービスおよび分散トラフィックに最適化された多機能ゲートウェイソフトウェア)は、世界中の多くの上場企業および大企業から高い評価を得ております。OpenResty 以外にも、章亦春は Linux カーネル、Nginx、LuaJITGDBSystemTapLLVM、Perl など、複数のオープンソースプロジェクトに累計 100 万行以上のコードを寄与し、60 以上のオープンソースソフトウェアライブラリを執筆しております。

翻訳

英語版の原文と日本語訳版(本文)をご用意しております。読者の皆様による他の言語への翻訳版も歓迎いたします。全文翻訳で省略がなければ、採用を検討させていただきます。心より感謝申し上げます!