【Kubernetes Novice Tokyo #2】コンテナで動作する Java アプリケーションのイメージサイズを小さくする方法

【Kubernetes Novice Tokyo #2】コンテナで動作する Java アプリケーションのイメージサイズを小さくする方法

44b799f91cc48e38c5fe9f5d9c5ecc61?s=128

Takaichi00

June 30, 2020
Tweet

Transcript

  1. 2.

    自己紹介 @Takaichi00 tomoaki.takaichi.5 ・髙市 智章(タカイチ トモアキ) ・Java / Node でのシステム開発

    ・CI / CD ・Container / k8s ・アジャイル開発実践 共著: クリーンなコードへの SonarQube即効活用術 http://u0u0.net/RSvx
  2. 3.

    ❏ コンテナで動作する SpringBoot の Docker イメージを小さ くさせたい場合、以下のことを実施する ❏ Alpine Linux

    ベースのイメージを利用する ❏ Custom Runtime とマルチステージビルドを利用する 要約 AdoptOpenJDK AdoptOpenJDK-Alpine Custom Runtime 436 MB 358 MB 85.5 MB
  3. 4.

    ❏ The Twelve-Factor App の IX. 廃棄容易性 では、プロセ スは素早く起動/終了ができることが求められている ❏

    コンテナ実行時、k8s のノード上に使用する Docker イ メージがない場合は、外部からイメージをダウンロードす る必要がある ❏ Docker イメージを小さくすることは、素早いスケールと デプロイを可能にするためにも重要な要素の一つ なぜ Docker のイメージサイズを小さくするか
  4. 5.

    ❏ SpringBoot で Hello World を返す REST API を用意 ❏

    公式の AdoptOpenJDK が提供する Docker イメージ上で起 動する SpringBoot をコンテナで動作させる
  5. 6.

    ❏ 公式が提供する Ubuntu ベースの AdoptOpenJDK Docker イメージ を利用して build すると

    Docker のイメージサイズ は 436MB になった (※ SpringBoot の jar ファイルは 16.5MB) SpringBoot をコンテナで動作させる $ docker build -t demo-official-openjdk:latest .
  6. 7.

    ❏ 公式の AdoptOpenJDK は Alpine Linux 上で Java が実 行できる

    Docker イメージも提供している ❏ Alpine Linux ベースの Docker イメージを利用するだけ でもコンテナサイズは 358 MB まで小さくすることができ た (※ SpringBoot の jar ファイルは 16.5MB) Alpine Linux ベースのイメージを利用する $ docker build -t demo-official-openjdk-alpine:latest .
  7. 8.

    ❏ Java9 から追加されたモジュールシステムを利用すること で、ある jar を起動するのに必要最低限な Java の実行環 境 (Custom

    Runtime) を構築できる ❏ 公式が提供する AdoptOpenJDK の代わりに、作成した必 要最低限な Java の実行環境 (Custom Runtime)を利用す ることで容量を削減することができる Custom Runtime を作成する AdoptOpenJDK SpringBoot jar Custom Runtime SpringBoot jar >
  8. 9.

    Custom Runtime を作成する ❏ jdeps コマンドで SpringBoot の起動に必要な依存モ ジュールを調べる ※

    jdeps コマンドは jar に含まれる jar を再帰的に解析はしないため、 SpringBoot を解析する場合は実行可 能 jar を展開して手動で解析する必要 がある (今回の発表のは本質ではない ため詳しくは以下を参照) SpringBootのdockerイメージを必要最小限に絞りたい (2019年9月版) https://www.m3tech.blog/entry/2019/09/13/110000 get-springboot-module.sh
  9. 10.

    Custom Runtime を作成する ❏ jdeps コマンドで SpringBoot の起動に必要な依存モ ジュールを調べる 実行結果

    実行コマンド (前ページの ShellScript を実行) java.base,java.desktop,java.instrument,java.management.rmi,java.namin g,java.prefs,java.scripting,java.security.jgss,java.sql,jdk.httpserver,jdk. unsupported ./get-springboot-module.sh demo-0.0.1-SNAPSHOT.jar 11
  10. 11.

    ❏ jlink コマンドで必要なモジュールだけを含んだ Java の実 行環境 (Custom Runtime) を作成する Custom

    Runtime を作成する jlink --strip-debug --no-header-files --no-man-pages --compress=2 --module-path $JAVA_HOME \ --add-modules java.base,java.desktop,java.instrument,java.management.rmi,java.naming,java.prefs,java.scri pting,java.security.jgss,java.sql,jdk.httpserver,jdk.unsupported \ --output jre-min 実行コマンド
  11. 12.

    ❏ マルチステージビルドを利用すれば、あるステージの生成 物を別のステージにコピーすることができる ❏ Custom Runtime を作成するステージと、作成した Custom Runtime 上で

    SpringBoot を起動するステージ に分ける マルチステージビルドを利用して Custom Runtime 上で SpringBoot を起動する Custom Runtime Custom Runtime SpringBoot jar COPY adoptopenjdk/openjdk11:alpine as java-builder alpine:3.12.0 jlink create
  12. 13.

    ❏ Dockerfile の構成は次の通り マルチステージビルドを利用して Custom Runtime 上で SpringBoot を起動する 1.

    Custom Runtime を生成するステージ 2. 生成した Custom Runtime を使って SpringBoot を起動するステージ ~ 中略 (Alpine Linux 上で Java を起動するために必要な設定) ~ Custom Runtime の作成 前のステージで作成した Custom Runtime をコピー
  13. 14.

    ❏ 最初のステージで Custom Runtime を作成し、それを次 のステージにコピーすることで Custom Runtime 上で SpringBoot

    が起動する Docker イメージを作成できる ❏ このように build した Docker イメージは、85.5MB とサ イズが削減されていることがわかる マルチステージビルドを利用して Custom Runtime 上で SpringBoot を起動する $ docker build -t demo-custom-runtime:latest . AdoptOpenJDK AdoptOpenJDK-Alpine Custom Runtime 436 MB 358 MB 85.5 MB
  14. 15.

    ❏ コンテナで動作する SpringBoot の Docker イメージを小 さくする場合、以下のことを実施する ❏ Alpine Linux

    ベースのイメージを利用する ❏ Custom Runtime とマルチステージビルドを利用する まとめ AdoptOpenJDK AdoptOpenJDK-Alpine Custom Runtime 436 MB 358 MB 85.5 MB
  15. 16.

    参考資料 ❏ Spring Boot の Docker Image を小さくする方法 ❏ https://qiita.com/Takaichi00/items/517132e01c844d426c09

    ❏ サンプルコード (Github) ❏ https://github.com/Takaichi00/java-container-build-sample