Advertisement
graywatson

JMXServer

Dec 5th, 2011
990
0
Never
Not a member of Pastebin yet? Sign Up, it unlocks many cool features!
Java 4.16 KB | None | 0 0
  1. package com.mprew.commons.jmx;
  2.  
  3. import java.io.IOException;
  4. import java.lang.management.ManagementFactory;
  5. import java.net.InetSocketAddress;
  6. import java.net.MalformedURLException;
  7. import java.net.Socket;
  8. import java.net.SocketAddress;
  9. import java.rmi.NoSuchObjectException;
  10. import java.rmi.registry.LocateRegistry;
  11. import java.rmi.registry.Registry;
  12. import java.rmi.server.UnicastRemoteObject;
  13. import java.util.HashMap;
  14.  
  15. import javax.management.remote.JMXConnectorServer;
  16. import javax.management.remote.JMXConnectorServerFactory;
  17. import javax.management.remote.JMXServiceURL;
  18.  
  19. /**
  20.  * JMX server connection for main to self publish itself via RMI.
  21.  *
  22.  * @author gwatson
  23.  */
  24. public class JmxServer {
  25.  
  26.     private Registry rmiRegistry;
  27.     private final int port;
  28.     private JMXConnectorServer connector;
  29.  
  30.     public JmxServer(int port) {
  31.         this.port = port;
  32.     }
  33.  
  34.     /**
  35.      * Start our JMX service.
  36.      */
  37.     public synchronized void start() throws MprewJmxException {
  38.         startRmiRegistry();
  39.         startJmxService();
  40.     }
  41.  
  42.     /**
  43.      * Start the RMI registry.
  44.      */
  45.     private void startRmiRegistry() throws MprewJmxException {
  46.         if (!isRegistryCreated()) {
  47.             createRegistry();
  48.         }
  49.     }
  50.  
  51.     /**
  52.      * Start our JMX service.
  53.      */
  54.     private void startJmxService() throws MprewJmxException {
  55.         if (connector != null) {
  56.             return;
  57.         }
  58.         JMXServiceURL url = null;
  59.         String urlString = "service:jmx:rmi://localhost:" + (port + 1) + "/jndi/rmi://:" + port + "/jmxrmi";
  60.         try {
  61.             url = new JMXServiceURL(urlString);
  62.         } catch (MalformedURLException e) {
  63.             throw new MprewJmxException("Malformed service url created " + urlString, e);
  64.         }
  65.         try {
  66.             connector =
  67.                     JMXConnectorServerFactory.newJMXConnectorServer(url, new HashMap<String, Object>(),
  68.                             ManagementFactory.getPlatformMBeanServer());
  69.         } catch (IOException e) {
  70.             throw new MprewJmxException("Could not make our Jmx connector server", e);
  71.         }
  72.         try {
  73.             connector.start();
  74.         } catch (IOException e) {
  75.             try {
  76.                 // try to start the rmi service again
  77.                 createRegistry();
  78.                 connector.start();
  79.             } catch (Exception ignored) {
  80.                 // ignore exception
  81.             }
  82.             connector = null;
  83.             throw new MprewJmxException("Could not start our Jmx connector server", e);
  84.         }
  85.     }
  86.  
  87.     private boolean isRegistryCreated() {
  88.         /**
  89.          * After a ton of trial and error, we determined that making the connection to the port is the only reliable way
  90.          * to see if there is an existing registry on the port. Although there is a
  91.          * {@link LocateRegistry#getRegistry(int)} method, there is no easy way to detect if the registry that is in
  92.          * place is a stub or not. Sometimes it is a stub delegating to a real registry and other times it is an empty
  93.          * stub. We also had problems where the registry would be closed but the socket is still open and not closed by
  94.          * the finalizer yet.
  95.          *
  96.          * NOTE: this could be in a different VM or on the way down in unit tests in which case may need to create the
  97.          * registry later.
  98.          */
  99.         Socket socket = new Socket();
  100.         SocketAddress sockAddr = new InetSocketAddress(port);
  101.         try {
  102.             socket.connect(sockAddr);
  103.             // try to connect, if it works then don't start the registry again
  104.             return true;
  105.         } catch (IOException e) {
  106.             // if we get an exception then create a new registry
  107.         } finally {
  108.             try {
  109.                 socket.close();
  110.             } catch (IOException e) {
  111.                 // ignored
  112.             }
  113.         }
  114.         return false;
  115.     }
  116.  
  117.     private void createRegistry() throws MprewJmxException {
  118.         try {
  119.             rmiRegistry = LocateRegistry.createRegistry(port);
  120.         } catch (IOException e) {
  121.             throw new MprewJmxException("Unable to create RMI registry on port " + port, e);
  122.         }
  123.     }
  124.  
  125.     /**
  126.      * Close the JMX server.
  127.      */
  128.     public synchronized void close() throws MprewJmxException {
  129.         if (connector != null) {
  130.             try {
  131.                 connector.stop();
  132.             } catch (IOException e) {
  133.                 throw new MprewJmxException("Could not stop our Jmx connector server", e);
  134.             } finally {
  135.                 connector = null;
  136.             }
  137.         }
  138.         if (rmiRegistry != null) {
  139.             try {
  140.                 UnicastRemoteObject.unexportObject(rmiRegistry, true);
  141.             } catch (NoSuchObjectException e) {
  142.                 // oh well, we tried
  143.             } finally {
  144.                 rmiRegistry = null;
  145.             }
  146.         }
  147.     }
  148. }
  149.  
  150.  
Advertisement
Add Comment
Please, Sign In to add comment
Advertisement