---
title: "Monitor Java with JMX"
url: "/articles/monitor-java-with-jmx"
type: article
date: 2012-08-02
updated: 2014-05-15
---

# Monitor Java with JMX

#  Monitor Java with JMX 

 By

 [  Ben Chavet   ](/about/ben-chavet) 

 August 2, 2012

  

JMX is a great way to monitor and manage any java application. Information about things like heap memory usage, garbage collection rate, and any custom data that the application supports can be retrieved. It is easy to enable and can be secured for remote access.

## Enable JMX

By default, JMX is not enabled because it does introduce a security risk if not configured correctly. In order to enable it, a few flags need to be added to the command-line string that starts the application. This location varies by application as well as by platform and installation method. A typical tomcat installation has a $JAVA\_OPTS variable that can be set in the supplied catalina.sh for things like this, which will be used here for demonstration purposes.

To enable JMX with no security options, use the following. Port 1616 is specified here, but there is no "standard" JMX port, so any unused port can be used.

`JAVA_OPTS="${JAVA_OPTS} -Dcom.sun.management.jmxremote -Dcom.sun.management.jmxremote.port=1616"<br></br>JAVA_OPTS="${JAVA_OPTS} -Dcom.sun.management.jmxremote.authenticate=false -Dcom.sun.management.jmxremote.ssl=false"  `

Restart tomcat, and that's it! JMX is now ready to be queried. Fire up jconsole to see the statistics

`jconsole localhost:1616<br></br>  `

## Security

The configuration above is really only safe for use in a secured network environment with no access to the JMX port from the outside. Anyone that has access to the open port has full access to the JMX subsystem listening there, and a simple port scan is all it takes to find it. To combat this, JMX provides security by means of SSL encryption as well as authentication via username/password or a client-side SSL certificate. Using a client-side SSL certificate is generally viewed as the more secure option, so that is what is demonstrated here.

Two java keystores and truststore pairs are required in order to use JMX over SSL with client-side certificate authentication. One pair to allow the client to trust the application, and the other to allow the application to trust the client. A keystore holds a private key and public certificate that identifies one side of the connection. A truststore holds a list of trusted public certificates which allows communication with whatever service has the matching private keys.

First, create the keystore and truststore for the application, tomcat in this case.

`keytool -genkey -alias tomcat -keyalg RSA -validity 365 -keystore tomcat.keystore -storepass password -keypass password -dname "CN=Ben Chavet, OU=DevOps, O=Lullabot, L=Des Moines, S=IA, C=US"<br></br>keytool -genkey -alias tomcat -keyalg RSA -validity 365 -keystore tomcat.truststore -storepass trustword -keypass trustword -dname "CN=Ben Chavet, OU=DevOps, O=Lullabot, L=Des Moines, S=IA, C=US"  `

And do the same for the JMX client, jconsole in this case.

`keytool -genkey -alias jconsole -keyalg RSA -validity 365 -keystore jconsole.keystore -storepass password -keypass password -dname "CN=Ben Chavet, OU=DevOps, O=Lullabot, L=Des Moines, S=IA, C=US"<br></br>keytool -genkey -alias jconsole -keyalg RSA -validity 365 -keystore jconsole.truststore -storepass trustword -keypass trustword -dname "CN=Ben Chavet, OU=DevOps, O=Lullabot, L=Des Moines, S=IA, C=US"  `

Then, export the public certificates from the keystores

`keytool -export -alias tomcat -keystore tomcat.keystore -file tomcat.cer -storepass password<br></br>keytool -export -alias jconsole -keystore jconsole.keystore -file jconsole.cer -storepass password  `

Finally, import the certificates into the truststores. Again, this allows the application (tomcat) to trust the client (jconsole), and vice-versa.

`keytool -import -alias jconsole -file jconsole.cer -keystore tomcat.truststore -storepass trustword -noprompt<br></br>keytool -import -alias tomcat -file tomcat.cer -keystore jconsole.truststore -storepass trustword -noprompt  `

Now, copy the tomcat keystore and truststore to the tomcat server, and modify the startup options to use it

`JAVA_OPTS="${JAVA_OPTS} -Dcom.sun.management.jmxremote -Dcom.sun.management.jmxremote.port=1616"<br></br>JAVA_OPTS="${JAVA_OPTS} -Dcom.sun.management.jmxremote.authenticate=false -Dcom.sun.management.jmxremote.ssl=true"<br></br>JAVA_OPTS="${JAVA_OPTS} -Djavax.net.ssl.keyStore=/path/to/tomcat.keystore -Djavax.net.ssl.keyStorePassword=password"<br></br>JAVA_OPTS="${JAVA_OPTS} -Djavax.net.ssl.trustStore=/path/to/tomcat.truststore -Djavax.net.ssl.trustStorePassword=trustword"<br></br>JAVA_OPTS="${JAVA_OPTS} -Dcom.sun.management.jmxremote.ssl.need.client.auth=true"  `

Restart tomcat for these options to take effect, and then connect with jconsole using

`jconsole -J-Djavax.net.ssl.keyStore=/path/to/jconsole.keystore -J-Djavax.net.ssl.keyStorePassword=password -J-Djavax.net.ssl.trustStore=/path/to/jconsole.truststore -J-Djavax.net.ssl.trustStorePassword=trustword tomcathost:1616<br></br>  `

The connection between the JMX client and the application is now encrypted, securely authenticated, and safe to use on any network, including the Internet.

## References

- http://docs.oracle.com/javase/1.5.0/docs/guide/security/jsse/JSSERefGuide.html#CreateKeystore
- http://docs.oracle.com/javase/1.5.0/docs/guide/management/agent.html#SSL\_enabled

 Published in:

- [  Drupal Development   ](/topics/drupal-development)
- [  Performance and Scalability   ](/topics/performance-and-scalability)
- [  System Administration   ](/topics/system-administration)

 

   You must have JavaScript enabled to use this form.

## Get in touch with us

### Tell us about your project. We'd love to hear from you!

 First Name  

 Last Name  

 Your email address  

 Your organization  

 How you heard about us  

 Tell us more 

     Leave this field blank