2018-03-26  Java プログラミング

アプリケーション配布用に小さなJREを作る

Java 9 の新機能 Project Jigsaw プロジェクト ジグソー Java に待望のモジュール機能が追加されました。

Jigsaw によるモジュール化は自作アプリケーションやサードパーティー製ライブラリの依存関係の解決に役立つだけではありません。Java の標準クラスライブラリも複数のモジュールに分割され 必要なモジュールのみで構成された小さな Java Runtime Environment 実行環境 を作成できるようになりました。

この小さな JRE を作る機能はモジュール対応していない Java 8 以前の アプリケーションでも利用することができます。

JRE が小さくなればアプリケーションにバンドルするのも容易になりますね。Project Jigsaw を使って小さな JRE を作成する手順をまとめました。

JDKを用意する

まずは JDK を用意しましょう。

JDK 9 JDK 10 Oracle の下記サイトからダウンロードすることができます。

インストーラーを使ってインストールするか もしくは JDK アーカイブを単に展開した場合は jdk-9.0.4\bin などを PATH に追加して Java コマンド群を使えるようにしておいてください。

サンプルプログラムを作る

はじめに簡単なサンプルプログラムを作っておきましょう。お馴染みの Hello, World!! をコンソールに表示するだけのプログラムです。以下のソースコードを HelloWorld.java というファイル名で保存します。

HelloWorld.java
public class HelloWorld { public static void main(String[] args) { System.out.println("Hello, World!!"); } }

HelloWorld.java を保存したフォルダーに移動して javac コマンドでコンパイルします。

コマンドプロンプト
C:¥>javac HelloWorld.java

これで HelloWorld.class ができました。次は jar コマンドを使って実行可能 JAR ファイルを作成します。

コマンドプロンプト
C:¥>jar --create --file hello.jar --main-class HelloWorld HelloWorld.class

これで 実行可能 JAR ファイル hello.jar ができました。さっそく 実行してみます。

コマンドプロンプト
C:¥>java -jar hello.jar Hello, World!!

上手くいきました。

次は この hello.jar を実行するのに必要な小さな JRE を作成していきます。

jdepsで依存モジュールを調べる

jdeps コマンドを使うとアプリケーション JAR ファイル が依存しているモジュールを調べることができます。

サンプルプログラム hello.jar の依存モジュールを調べる場合は以下のように --list-deps オプションを付けて実行します。

コマンドプロンプト
C:¥>jdeps --list-deps hello.jar java.base

hello.jar が依存しているモジュールは java.base だけであることが分かります。複数のモジュールに依存している場合は複数行表示されます

jlinkに依存モジュールを指定して小さなJREを作る

hello.jar が依存しているモジュールが java.base であることが分かったので 次に java.base のみの JRE を作ります。これには jlink というコマンドを使います。

以下のように引数を指定して jlink を実行します。

コマンドプロンプト
C:¥>jlink --compress=2 --module-path "C:¥jdk-9.0.4¥jmods" --add-modules java.base --output jre-min
引数      説明
–compress=2JRE を圧縮するオプションです。
–module-pathモジュールが格納されているパスを指定します。JDK を展開すると jmods というフォルダーがあるのでそのパスを指定します。このフォルダーの中に java.base.jmod java.sql.jmod java.xml.jmod など様々なモジュールが格納されています。
–add-modulesjdeps で調べたモジュール名を指定します。今回は java.base だけですが モジュールが複数ある場合はカンマで区切って並べます。
–outputJRE を出力するパスを指定します。

他のオプションは jlink --help で確認することができます。

これで jre-min というフォルダーが作成されます。これが hello.jar を実行するために作成した小さな JRE です。

サイズは 24MB になっています。この jre-min フォルダーを ZIP 圧縮するとさらに 15MB まで小さくなりました。これならアプリケーションに Java 実行環境をバンドルするのも難しくないですね。

小さなJREでアプリケーションを実行してみる

本当に これで Java アプリケーションが実行できるのでしょうか? 新しいコマンドプロンプトを起動して確認してみましょう。できれば Java コマンド群に PATH が通っていないほうが分かりやすいです。

はじめに このコマンドプロンプトから Java 実行環境が見えていないことを確認します。誤って作業に使用した JDK でアプリケーションが実行されないようにするためです。

コマンドプロンプト
C:¥>java 'java' は、内部コマンドまたは外部コマンド、 操作可能なプログラムまたはバッチ ファイルとして認識されていません。

このコマンドプロンプトでは java コマンドが見つからないので 他の Java 実行環境が使われることはありません。次に 作成した jre-min\bin PATH を通します。

コマンドプロンプト
C:¥>PATH=C:¥jre-min¥bin;%PATH%

サンプルプログラムを実行します。

コマンドプロンプト
C:¥>java -jar hello.jar Hello, World!!

無事に動きましたね! hello.jarjre-min をバンドルして配布すれば Java をインストールしていない環境でもアプリケーションが実行できます。

もっと簡単なバッチファイルを!

jdeps で依存モジュールを確認してから jlink で小さな JRE を作る 同じ手順を繰り返していると次第に面倒になってきますよね。この jdeps jlink を使った手順を自動化するバッチファイル create-jre.bat を作ってみました。

上記 ZIP ファイルをダウンロード 展開して中に入っている create-jre.bat sed.exe PATH の通った場所に配置します。Java コマンド群にも PATH を通す必要がありますので create-jre.bat sed.exe JDK bin フォルダーにコピーしてしまうのが簡単だと思います。

あとは Java コマンド群に PATH が通ったコマンドプロンプトで以下のコマンドを実行するだけです。

コマンドプロンプト
C:¥>create-jre hello.jar

これで hello.jar を実行するのに必要な小さな JRE ができます。使用した JDK のバージョンを含む jre-9.0.4.min のような JRE フォルダーが出力されます

小さな JRE Minimized JRE を作成する手順は以上です。

この JRE 縮小手順は モジュール化していない Java 8 以前のアプリケーションにも適用できますので Java 9 Java 10 を見送って長期サポートの Java 11 待ちという開発者にも是非試してみていただきたい機能です。

最終更新日 2024-12-13
この記事を共有しませんか?
ブックマーク ポスト