Criteria
Today, almost all of our Java applications are running containerized. So the goal is to find a good base image that meets typical cloud-native requirements:
- Image-Size: The size of the base image should be as small as possible to speed up the pull and push process to the registry. Also, a smaller image usually results in fewer dependencies.
- Security: In an ideal world, a base image should have no security vulnerabilities. This is only possible if the base image contains as few dependencies as possible. Therefore, it might make sense to set these two requirements.
- JRE only: At runtime, our Java applications no longer need the full Java Development Kit (it is already developed and built at this point). So we only need the Java Runtime Environment (JRE) for our base image.
- Alpine flavour: Normally, the Alpine base images are quite small. Therefore, they generally contain fewer dependencies than other Linux variants.
- Easy to use in CI-Pipeline: Developers are lazy, me too. That’s why I would be happy to have an official Maven image to build the application inside a CI pipeline with the same Java as in my base image.
Test Results
The following list gives an overview of the Java images I identified and the results according to the above criteria:
Name | Image | Compressed Size | Alpine | JRE | Maven |
---|---|---|---|---|---|
Adoptium Eclipse Temurin | eclipse-temurin:17-jre-alpine |
58 MB | |||
Azul Zulu / Zing | azul/zulu-openjdk-alpine:17-jre |
66 MB | |||
BellSoft Liberica JDK | bellsoft/liberica-openjre-alpine-musl:17 |
49 MB | |||
IBM Semeru Runtime | ibm-semeru-runtimes:open-17-jre |
89 MB | |||
Amazon Corretto | amazoncorretto:17-alpine-jdk |
185 MB | |||
Microsoft Build of OpenJDK | mcr.microsoft.com/openjdk/jdk:17-mariner |
168 MB | |||
Red Hat OpenJDK | registry.access.redhat.com/ubi8/openjdk-17 |
137 MB | |||
GraalVM | ghcr.io/graalvm/graalvm-ce:ol9-java17 |
409 MB |
These Java variants are not published directly under the official maven
Docker repository. Instead, they are published under csanchez/maven
. Nevertheless, both docker repositories are provided by the same upstream GitHub repository.
The heavily used AdoptOpenJDK base image with Java 8 and Java 11 is now obsolete and has been transferrred to the „Adoptium Eclipse Temurin“ project.
Security Risks & Vulnerabilities
I also checked all these images for security risks using two different image scanners:
The results are summarized in the following list (as of November 10, 2022):
Name | Image | Trivy | XRay |
---|---|---|---|
Adoptium Eclipse Temurin | eclipse-temurin:17-jre-alpine |
Total: 1 (UNKNOWN: 0, LOW: 0, MEDIUM: 0, HIGH: 1, CRITICAL: 0) | Total: 9 (UNKNOWN: 0, LOW: 0, MEDIUM: 2, HIGH: 7, CRITICAL: 0) |
Azul Zulu / Zing | azul/zulu-openjdk-alpine:17-jre |
Total: 0 (UNKNOWN: 0, LOW: 0, MEDIUM: 0, HIGH: 0, CRITICAL: 0) | Total: 9 (UNKNOWN: 0, LOW: 0, MEDIUM: 2, HIGH: 7, CRITICAL: 0) |
BellSoft Liberica JDK | bellsoft/liberica-openjre-alpine-musl:17 |
Total: 0 (UNKNOWN: 0, LOW: 0, MEDIUM: 0, HIGH: 0, CRITICAL: 0) | Total: 7 (UNKNOWN: 0, LOW: 0, MEDIUM: 2, HIGH: 5, CRITICAL: 0) |
IBM Semeru Runtime | ibm-semeru-runtimes:open-17-jre |
Total: 17 (UNKNOWN: 0, LOW: 13, MEDIUM: 4, HIGH: 0, CRITICAL: 0) | Total: 10 (UNKNOWN: 0, LOW: 7, MEDIUM: 3, HIGH: 0, CRITICAL: 0) |
Amazon Corretto | amazoncorretto:17-alpine-jdk |
Total: 0 (UNKNOWN: 0, LOW: 0, MEDIUM: 0, HIGH: 0, CRITICAL: 0) | Total: 7 (UNKNOWN: 0, LOW: 0, MEDIUM: 2, HIGH: 5, CRITICAL: 0) |
Microsoft Build of OpenJDK | mcr.microsoft.com/openjdk/jdk:17-mariner |
Total: 10 (UNKNOWN: 0, LOW: 2, MEDIUM: 2, HIGH: 4, CRITICAL: 2) | Total: 46 (UNKNOWN: 0, LOW: 5, MEDIUM: 28, HIGH: 8, CRITICAL: 5) |
Red Hat OpenJDK | registry.access.redhat.com/ubi8/openjdk-17 |
Total: 88 (UNKNOWN: 0, LOW: 44, MEDIUM: 44, HIGH: 0, CRITICAL: 0) | Total: 111 (UNKNOWN: 0, LOW: 38, MEDIUM: 59, HIGH: 11, CRITICAL: 3) |
GraalVM | ghcr.io/graalvm/graalvm-ce:ol9-java17 |
Total: 7 (UNKNOWN: 0, LOW: 0, MEDIUM: 1, HIGH: 6, CRITICAL: 0) | Total: 0 (UNKNOWN: 0, LOW: 0, MEDIUM: 0, HIGH: 0, CRITICAL: 0) |
Conclusion
For a new project based on Java, I would first choose the Adoptium Eclipse Temurin project. The image is tiny, meets all my criteria and has almost no vulnerable security holes. Also, the official Maven image supports this Java version, which is a perfect match for me.
Nevertheless, other Java vendors are also quite interesting. Especially if you use Spring and the official image plugin for Maven and Gradle, you end up with the BellSoft Liberica JDK by default.
This blog post is intended to make you aware that you should not just randomly select a Java base image. Instead, you should define some basic criteria based on your use case and choose the Docker image that fits best.