3 Improve Performance of PGPainless CLI with Nailgun
Paul Schaub edited this page 2023-05-08 14:44:31 +02:00

When executing a short-lived CLI application written in Java, a huge portion of the runtime is wasted on booting the JVM.

To fix this issue, nailgun can be used: Nailgun is a client, protocol, and server for running Java programs from the command line without incurring the JVM startup overhead. Programs run in the server (which is implemented in Java), and are triggered by the client (written in C), which handles all I/O.

To use nailgun to increase the performance of pgpainless-cli, the first thing you need is a Java 8 installation. This is because nailgun uses features from Java 8, which were removed in later releases.

Futher, you need to compile PGPainless using Java 8 to get a compatible jar file.

$ JAVA_HOME=$JAVA8_HOME gradle assemble
$ ls pgpainless-cli/build/libs/pgpainless-cli-XYZ-all.jar

Start the nailgun server

Simply execute the nailgun-server.jar on the Java 8 JVM:

$ $JAVA8_HOME/bin/java -jar nailgun-server.jar

Next, load the freshly built pgpainless-cli-XYZ-all.jar:

$ ng ng-cp /path/to/pgpainless-cli-XYZ-all.jar

Execute PGPainlessCLI calls

The syntax for calling pgpainless-cli only changes a little bit. Here is an example without and with using nailgun:

$ # WITHOUT nailgun
$ java -jar pgpainless-cli-XYZ-all.jar generate-key "Alice <alice@example.org>"

$ # WITH nailgun
$ ng org.pgpainless.cli.PGPainlessCLI generate-key "Alice <alice@example.org>"

As you can see, you now need to provide the name of the main class.

Results

On my machine, comparing the performance shows a drastic improvement!

$ time (repeat 100 {java -jar pgpainless-cli-1.5.1-all.jar generate-key > /dev/null;})                              
( repeat 100; do; java -jar pgpainless-cli-1.5.1-all.jar generate-key > ; done  167,06s user 9,14s system 216% cpu 1:21,42 total
$ # vs.
$ time (repeat 100 {ng org.pgpainless.cli.PGPainlessCLI generate-key > /dev/null;})
( repeat 100; do; ng org.pgpainless.cli.PGPainlessCLI generate-key > /dev/nul)  0,21s user 0,99s system 20% cpu 5,914 total