Docker JVM メモリ使用量の表示

Docker JVM メモリ使用量の表示

1. Docker コンテナのホスト マシンに入り、指定されたイメージを実行しているコンテナ ID (結果の最初の列) を表示します。

docker ps | grep myImageName (または docker ps | grep java)

2. コンテナを入力します。

docker exec -it コンテナID sh

3. top コマンドを直接入力します。

トップ

pid、vsz、cpu、コマンドなど、コンテナの基本的な使用情報を確認できます。 (ctrl+c または q、トップを終了)

4. より具体的な JVM メモリ使用量を表示します。

トップ -m

このうち、vsz: Virtual Memory Size、仮想メモリのサイズは、スワップメモリ​​や共有ライブラリメモリなど、プロセスがアクセスできるすべてのメモリを示します。

rss: 常駐セット サイズ (常駐メモリ セット サイズ) は、プロセスが RAM 内で占有するメモリの量を示します。SWAP 内で占有される仮想メモリは含まれません。スタックとヒープ内の完全なメモリを含め、メモリ内の共有ライブラリのメモリ サイズも含まれます。

SHR: 共有メモリ、共有メモリ。

補充:

ps -ef | grep java または docker top container id を実行して、pid に関する情報を表示します。

ps aux | grep java。

top -p pid です。

RSSは Resident Set Size の略で、プロセスに割り当てられたメモリ サイズを示します。

RSSは、スワップ パーティションに入るメモリは含まれません。

RSSは共有ライブラリが占有するメモリが含まれます (共有ライブラリがメモリ内にある限り)

RSSは割り当てられたすべてのスタック メモリとヒープ メモリが含まれます。

VSZプロセスによって割り当てられた仮想メモリを表します。

VSZは、スワップに入るものや共有ライブラリによって占有されるメモリなど、プロセスがアクセス可能なすべてのメモリが含まれます。

VSZRW: Baidu では具体的な意味はわかりませんでしたが、最初に要求された仮想メモリのサイズのことだと思います。

docker stats コンテナ名または docker stats コンテナ ID の場合、結果は次のようになります。

コンテナ CPU % メモリ使用量 / メモリ制限 % ネット I/O ブロック I/O PID
 

補足: Docker コンテナ化における JVM パラメータの調整

1. JVMヒープメモリ設定

Docker コンテナで実行されている Java サービスで、メモリ オーバーフロー例外がいくつか発生しました。実際、これは Java プログラムの Docker コンテナ化と大きく関係しています。 Java と Docker は相性がよくありません。Docker はメモリと CPU の制限を設定できますが、これは最下層の Linux cgroup テクノロジを通じて実装されますが、Java JVM はそれを自動的に検出できません。

この問題は、Java の Xmx フラグを使用してヒープ メモリのサイズを手動で指定するか、JDK の上位バージョンで提供される JVM フラグを使用することで解決できます。

質問:

Java 8 の古いバージョン (アップデート 131 より前のバージョン) の場合、JVM の使用可能なメモリと CPU 数は、Docker で使用できる使用可能なメモリと CPU 数とは異なります。

たとえば、Docker コンテナは 1 GB に制限されていますが、古いバージョンの Java はこの制限を認識できません。ビジネスが拡大すると、JVM はより多くのメモリを要求するため、この制限をはるかに超える可能性があります。しかし、メモリが多すぎると、Docker はアクションを起こしてコンテナ内の Java プロセスを強制終了しますが、これは明らかに望ましいことではありません。

現在、私たちの本番環境では Java 8 を使用しています。この問題は、-Xmx を使用してヒープ メモリ サイズを制限することで解決できます。ただし、実際には 2 つの制限があります。1 つは Docker コンテナのメモリ制限であり、もう 1 つは JVM ヒープ メモリの制限です。

解決:

この前提には、Java プログラムの Dockerfile サポートが必要です。

# adoptopenjdk/openjdk8 からの初期イメージ
# jar パッケージ名はプロジェクト名-バージョン番号に変更する必要がありますが、app.jar は変更しません。ADD example-sun-1.0.jar app.jar
# JVM 起動パラメータを設定する ENV JVM_ARGS=${JVM_ARGS}
エクスポーズ8080
# ENTRYPOINT java を起動するための jvm パラメータ設定を最適化 ${JVM_ARGS} -Djava.security.egd=file:/dev/./urandom -jar app.jar

具体的には、k8sのdeployment.yamlデプロイメントファイル内の環境変数envに次のパラメータを追加すると、JVMの起動時にロードされます。

- 名前: JVM_ARGS
 値: -Xmx1024m -Xms512m

Xmx1024m #JVMヒープメモリの最大値を設定する

-Xms512m #JVMヒープメモリの最小値を設定します

ここでは、最小ヒープメモリを 512m、最大ヒープメモリを 1024m に設定しています。ヒープメモリを調整するときは、単に増やすのではなく、過剰なメモリ使用量の原因とコードの問題がないか慎重に分析してください。

Java 9のより高いバージョン(8u131+)を搭載したJVMは、より良いソリューションを提供します。

JVM フラグを使用します: -XX:+UnlockExperimentalVMOptions -XX:+UseCGroupMemoryLimitForHeap

JVM に Linux の cgroup 構成をチェックするよう強制します。実際、Docker は Linux の cgroup テクノロジを使用して、メモリなどのコンテナ リソースを制限します。これで、アプリケーションが Docker によって設定された制限 (たとえば 1G) に達すると、JVM はこの制限を認識し、GC 操作を試行します。

gc 後もメモリ制限を超えている場合は、JVM は OutOfMemoryException をスローするなど、必要な処理を実行します。つまり、JVM は Docker のこれらの設定を認識できます。

2. GCログ出力とOOM自動ダンプ

プログラムの実行中に、GC ログを出力してトラブルシューティングを容易にすることもできます。同時に、Java OutOfMemory 例外が発生した場合は、ヒープ メモリをダンプしてトラブルシューティングを容易にすることができます。次のパラメータを設定します。

- 名前: JVM_ARGS
 値: -Xmx1536m -Xms512m -XX:+HeapDumpOnOutOfMemoryError -XX:HeapDumpPath=/logs/my-heap-dump.hprof -Xloggc:/logs/gc.log -XX:+PrintGCDetails -XX:+PrintGCDateStamps

パラメータの意味:

# メモリオーバーフローが発生したときにメモリファイルを自動的にダンプします -XX:+HeapDumpOnOutOfMemoryError
############## ダンプ ファイルのアドレスをサービス印刷ログ フォルダー/ログ (マウント済み) として指定します。
-XX:HeapDumpPath=/logs/my-heap-dump.hprof
############# 印刷サービス gc log-Xloggc:/logs/gc.log
# 詳細なGCログを出力 -XX:+PrintGCDetails
# 出力タイムスタンプをフォーマットします 2020-09-17T19:45:05.680+0800
-XX:+PrintGCDateStamps

上記は私の個人的な経験です。参考になれば幸いです。また、123WORDPRESS.COM を応援していただければ幸いです。間違いや不備な点がありましたら、遠慮なくご指摘ください。

以下もご興味があるかもしれません:
  • JVM の概要: メモリ構造 (ヒープ、メソッド領域)
  • JFR を使用したメモリ リークの解決に関する JVM の簡単な説明
  • Huawei の技術専門家が JVM メモリ モデルを説明 (コレクション)
  • JConsoler を使って Tomcat の JVM メモリを監視する方法を説明します

<<:  CSSをインポートする方法に関する詳細な洞察の要約

>>:  XHTMLはHTMLのいくつかの廃止された要素を使用しなくなりました

推薦する

アイデアを通じてプロジェクトをDockerにパッケージ化する方法

多くの友人が、Docker でプロジェクトを実行する方法をずっと知りたがっていました。今日は、自分の...

SQL 実践演習: オンライン モール データベースの製品カテゴリ データ操作

オンラインショッピングモールデータベース - 商品カテゴリデータ操作(I)プロジェクトの説明電子商取...

VC6.0をWIN10にインストールすると使用できない問題の解決方法

VC6.0は確かに古すぎるVC6.0は昔の開発ツールです。現在のwin10では対応していません。しか...

PXEを使用してCentOS7.6を自動的にインストールする方法の詳細なチュートリアル

1. 需要ベースには 300 台の新しいサーバーがあり、CentOS7.6 オペレーティング システ...

発生したブラウザの互換性の問題と解決策(推奨)について

序文:先週の日曜日、先輩から3ページ作るのを手伝って欲しいと頼まれました。データのやり取りなどはなく...

React コンポーネントのコンストラクタとスーパーの知識ポイントのまとめ

1. Reactでクラス宣言する際のヒント 上記のように、Child クラスは class キーワー...

Jenkins を使用した Vue プロジェクトのワンクリック パッケージングと公開の実装

目次Jenkinsのインストールインストールポート番号を変更します(デフォルトのポートは8080です...

Ubuntuデュアルシステムが起動時に停止する問題の解決方法の詳細な説明

起動時に Ubuntu デュアル システムが停止する問題の解決方法 (Ubuntu 16.04 およ...

Windows に異なる (2 つの) バージョンの MySQL データベースをインストールする詳細なチュートリアル

1. 原因: SQL ファイルをインポートする必要があるのですが、インポートできません。この文を実行...

Dockerコンテナの操作手順の概要と詳細説明

1. コンテナを作成して実行するdocker run -it --rm centos:latest ...

Nginx 仮想ホストを構成する 3 つの方法 (ドメイン名に基づく)

Nginx は、IP ベースの仮想ホスト構成、ポート ベースの仮想ホスト構成、ドメイン名ベースの仮...

ページにデータを表示するReactメソッド

目次親コンポーネントリストボックスリストコンポーネントボタンコンポーネント PageButton昨年...

Vue は左右のスライド効果のサンプルコードを実装します

序文個人の実際の開発で使用した効果問題を、今後の開発やレビューに役立てるためにまとめています。他の人...

GET POSTの違い

1. Get はサーバーからデータを取得するために使用され、Post はサーバーにデータを渡すために...