Java and Docker - JVM Runtime Basics
Tags: java, kotlin, docker, containers
Published: 2018-12-13 01:57:24

---
title: Java and Docker - JVM Runtime Basics
published: true
description: A brief overview of the things you should about the Java runtime when running your Java apps in docker container
tags: java, kotlin, docker, containers
---

This article originated on [zsiegel.com](https://zsiegel.com/2018/11/25/java-and-docker-runtime-basics)

As container deployments become increasingly common, it is important to understand how your application and runtime cooperate with various Linux container technologies.

Depending on your JVM target version, you may need to do a little extra work to ensure your Java runtime is aware of the processor and memory usage limits. If you are not careful, your application may have incorrect optimization or heuristics applied, potentially leading to performance issues and even crashes.

## Namespaces and Cgroups

First, if you need to brush up on the underlying Linux technologies that make Docker possible, you might want to read [Julia Evans](https://mobile.twitter.com/b0rk "Julia Evans on Twitter") excellent blog post [here](https://jvns.ca/blog/2016/10/10/what-even-is-a-container/ "Julia Evans - What even is a container: namespaces and cgroups").

With a basic understanding of [cgroups](https://en.wikipedia.org/wiki/Cgroups "Linux Cgroups") and [namespaces](https://en.wikipedia.org/wiki/Linux_namespaces "Linux namespaces") we can now turn our attention to ensuring our Java runtime is aware of these technologies. Here is what you need to know in order to ensure your Java runtime is aware of the memory and processor limits set on your containers.

## Java 7
Sadly there are no flags or features available in JDK 7 to provide container awareness. If you are running on JDK 7, you can tune your applications thread counts to reduce potential processor resource issues.

## Java 8
Java 8 has a few flags that can help the runtime operate in a more container aware manner. These updates were added in the Java 8 Update 131 release which has been available since April 18, 2017.

The update contains improved processor and memory container awareness, and allows for use of experimental VM flags to enable automatic heap adjustment. To unlock this capability simply add the following flags to your `java` command line options.

```bash
java -XX:+UnlockExperimentalVMOptions -XX:+UseCGroupMemoryLimitForHeap -jar app.jar
```

These experimental flags set the heap size based on the value specified in the container’s `sys/fs/cgroup/memory/memory.limit_in_bytes` file. You can check out the bug report and work related to this [here](https://bugs.openjdk.java.net/browse/JDK-8170888 "Experimental support for cgroup memory limits").

## Java 9 & 10
Oracle has signaled that JDK 9 and JDK 10 will be automatically container aware respecting both processor and memory limits. They are also providing manual overrides to allow for disabling or setting these limits manually. There are a number of tickets and work on these features can be tracked on the [OpenJDK Bug tracker](https://bugs.openjdk.java.net/projects/JDK/issues/JDK-8192936?filter=allopenissues%20%22OpenJDK%20Bug%20Tracker) which you can check out below.

- [JDK 10 Release Note: Improvements for Docker Containers](https://bugs.openjdk.java.net/browse/JDK-8196595 "JDK 10 Improvements for Docker Containers")
- [Docker memory limits](https://bugs.openjdk.java.net/browse/JDK-8170888 "Docker memory limits")
- [Docker processor limits](https://bugs.openjdk.java.net/browse/JDK-8140793 "Docker processor limits")

## Conclusion
There is still work to be done in order for the JVM to be fully aware of containerization, but so far excellent progress has been made and, more importantly, backported into JDK 8 in order to garner more feedback from the community. 

If you find yourself running your Java application in containers and need help check back here frequently for more updates as I start a new series of articles on running java apps with [Docker](https://www.docker.com/ "Docker") and [Kubernetes](https://kubernetes.io/ "Kubernetes").