First MicroProfile.io application using Java Module System
Embrace the JPMS power with MicroProfile.io applications
Update
Sample application migrated to use JDK 11.
MicroProfile.io
Eclipse MicroProfile project is growing fast, it has a lot of supporters and compatible implementations.
I see it as a new way to package enterprise Java Enterprise applications that already leverage of existing Java Specifications (JSRs) and want to be compatible with different platforms, specially ready for running in Cloud.
It also aims to reduce the gap between community feedback and release of new features.
I would like to mention that in addition of well know MicroProfile implementations like Payara Micro, WildFly Swarm, TomEE and Websphere Liberty, there's also Hammock, which I'll use in this post.
Hammock is an open-source project that allows the creation of CDI based microservices using Microprofile.io specification and additional starter modules such as JPA (Hibernate/EclipseLink/OpenJPA), Security (JWT, Keycloak), Messaging (Artemis/RabbitMQ) or your own starter module, just like Spring Boot does, but in a CDI way.
Currently in development version 2.2 supports most of MicroProfile.io 1.3 capabilities.
First MicroProfile.io JPMS application
There're few ways to start using Hammock, the easiest one is to add the following maven dependency.
Personally, as I want to ensure my application dependencies are thin I prefer to use the DIY way, adding each module individually (CDI, REST, JSON), so I can choose which implementation of CDI, REST and JSON I’ll use.
It also helps us to fix JPMS comparability issues that I found during the implementation of (my) first MicroProfile.io JPMS application (I have not heard of any other on the internet).
As usual, I already explained in previous post Upgrade to Java 10 now! Why not? in which I only add module-info.java and deal with application dependencies to start using module system.
The problem
Java Module System (JPMS) is still recent and thirdparty libraries and frameworks are trying to catch up to support modularization, so we will need a few tweaks, like preventing two JARs with the same package names conflicts in the classpath (that was already a hidden problem, because you know, API changes and first class on classpath wins).
With JPMS, it prevents two modules (or automatic modules) to export the same package.
Solution
The sample application is a basic Hello World JAX-RS resource using JSON-B.
With the following module descriptor:
View the Maven project descriptor (pom.xml) to see the dependencies and plugins declarations.
Results
The total size of this example application is around 12mb
and the startup time of the whole application is around 1s
in my machine.
Also the maximum memory usage (RSS) of the JVM was 133mb
in my tests.
Note: The maximum heap size used in tests was -Xmx128m.
Put Things Together using JLink and Docker
Following the same approach of previous post Create a Cloud Native Image using Java Modules I can create a minimal JVM to run the application and generate a Docker image.
The resulting was an amazing 54.3mb
Docker image with only minimal JRE and application modules.
If you look carefully, you will notice that a patch-module
was added in the command line in order to hack JPMS and remove java.desktop
module dependency. We really don't need Swing/AWT classes here!
I was only able to achieve that using my new pet project LiteBeans, a java.beans package patch and alternative API implementation used to remove java.desktop module requirement on JDK 9 and up.
Conclusion
The CDI is the new glue and Docker the new hammer.
Finally, you can find the source in this repository: panga/hammock-jpms
Also the instructions to build and run are available in the README.