普通に自分が分かってなかったのでメモシリーズ
これはなに
-Xmx
オプションを指定する際に-J
をつけている。 -Dfoo.barなどのプロパティ指定にはつけたりつけなかったりしている- いつ
-J
をつけて、いつつけなくてよいのか、-J
の意味などをまとめる。
-J
の意味
-J
の意味1 javaコマンドのオプションである -J
“java -J” あたりでググるとコレがでてくる。 例: Javaアプリケーション メモ(Hishidama's Java-Application Memo)
これはjavacが使用するjavaコマンド(javacと同バージョンのjava)へのオプションを指定するものなので、Xmxの指定などの実行時のオプション設定には関係しない。
-J
の意味2 jarコマンドのオプションである -J
こちらもググってみると、
たとえば、
-J-Xms48m
と指定すると、スタートアップ・メモリーは48Mバイトに設定されます。
jar のように記載されている。
しかし「jarコマンド」はjarを作ったりjarの中身を一覧表示するためのコマンドであり、jarの実行(java -jar …)とは異なる物なのがポイントで、こちらもアプリケーション実行時に影響するオプションではない。
つまり jar -J-Xms48m
はjarを作る作業中にjvmが使うメモリを変更するオプションであるという意味になる。
-J
の意味3 scalaコマンド的な-J
scala -J-Xmx 2GB -Dfoo=bar baz.scala
みたいにjavaコマンドではなくscalaコマンドでアプリケーションを実行するときのオプション
scalaコマンドは結局モロモロの処理をした後javaコマンドを実行するものになっている。
ここでのポイントは-Jオプションをscalaコマンドに渡すと以下の2つを行ってくれるということ
つまり -J
の意味1 で述べたjavacうんぬんとは関係なく、scalaコマンドに -J
を渡すとjava側に渡してくれる機能がある( -J
という名前が被っているので混乱するが、全然違う機能)
scala/tool-unix.tmpl at c804289144c006e91a206ff12e94e5a39ac73a9f · scala/scala · GitHub
-J
の意味4 sbt-native-packager的な -J
こちらはscalaコマンドに似ている。
sbt-native-packagerが生成するスクリプトはモロモロの処理をしてjavaコマンドを実行する。
このとき -J
の意味2で述べたscalaコマンドの挙動を模した実装が行われており、scalaコマンドと同じように -J
をstripして、 -Xmx 1500m
にしてからjavaコマンドにわたすという形式になっている。
(scalaコマンドとは違いscala_argsには値が渡らない気がしているが未調査。気になる人は実装読んだりしてください)
sbt-native-packager/bash-template at master · sbt/sbt-native-packager · GitHub
-J
をつけないとどうなるかというと sbt-native-packager/bash-template at 1ee84811c3ce2048e2ea857aece3fbe563b8089e · sbt/sbt-native-packager · GitHub によりresidual_argsに入り sbt-native-packager/bash-template at 1ee84811c3ce2048e2ea857aece3fbe563b8089e · sbt/sbt-native-packager · GitHub でmainClassやappCommandの後に引数として渡されるようです。
まとめ
sbt-native-packagerを使う場合、jvmオプションは -J-Xmx 1500m
のようにする必要がある
これはscalaコマンドやsbt-native-packagerが独自実装しているshellスクリプトの機能でしかなく、jvmには-Jが削除された-Xmx 1500mだけが渡るようになっている。(-J-Xmxってなんか気持ち悪いなと思っていたけど-Jという文字列を機械的に削除すると考えれば割と理解しやすい)
この際使われる-J prefixはjavaコマンドについてググった時にでてくるjavacコマンドのオプションとは全く別物
おまけ
sbt-native-packagerを使う場合 -Dfoo=bar
はそのままjvmに渡される (sbt-native-packager/bash-template at 1ee84811c3ce2048e2ea857aece3fbe563b8089e · sbt/sbt-native-packager · GitHub) ので、
例えばエンコーディング指定であれば -Dfile.encoding=UTF-8
とすればよい。
が、 -J-Dfile.encoding=UTF-8
としても -J
が機械的に削除されてjvmに渡るので結局 -Dfile.encoding=UTF-8
となり、挙動はかわらない(はず)。