/** * Licensed to the Apache Software Foundation (ASF) under one * or more contributor license agreements. See the NOTICE file * distributed with this work for additional information * regarding copyright ownership. The ASF licenses this file * to you under the Apache License, Version 2.0 (the * "License"); you may not use this file except in compliance * with the License. You may obtain a copy of the License at * * http://www.apache.org/licenses/LICENSE-2.0 * * Unless required by applicable law or agreed to in writing, * software distributed under the License is distributed on an * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY * KIND, either express or implied. See the License for the * specific language governing permissions and limitations * under the License. */ package org.apache.cxf.management.jmx; import java.io.IOException; import java.rmi.registry.LocateRegistry; import java.util.Map; import java.util.logging.Level; import java.util.logging.Logger; import javax.management.MBeanServer; import javax.management.MBeanServerFactory; import javax.management.remote.JMXConnectorServer; import javax.management.remote.JMXConnectorServerFactory; import javax.management.remote.JMXServiceURL; import org.apache.cxf.common.logging.LogUtils; /** * Deal with the MBeanServer Connections * */ public final class MBServerConnectorFactory { public static final String DEFAULT_SERVICE_URL = "service:jmx:rmi:///jndi/rmi://localhost:9913/jmxrmi"; private static final Logger LOG = LogUtils.getL7dLogger(MBServerConnectorFactory.class); private static MBeanServer server; private static String serviceUrl = DEFAULT_SERVICE_URL; private static Map<String, ?> environment; private static boolean threaded; private static boolean daemon; private static JMXConnectorServer connectorServer; private static class MBServerConnectorFactoryHolder { private static final MBServerConnectorFactory INSTANCE = new MBServerConnectorFactory(); } private static class MBeanServerHolder { private static final MBeanServer INSTANCE = MBeanServerFactory.createMBeanServer(); } private MBServerConnectorFactory() { } private int getURLLocalHostPort(String url) { int portStart = url.indexOf("localhost") + 10; int portEnd; int port = 0; if (portStart > 0) { portEnd = indexNotOfNumber(url, portStart); if (portEnd > portStart) { final String portString = url.substring(portStart, portEnd); port = Integer.parseInt(portString); } } return port; } private static int indexNotOfNumber(String str, int index) { int i = 0; for (i = index; i < str.length(); i++) { if (str.charAt(i) < '0' || str.charAt(i) > '9') { return i; } } return -1; } public static MBServerConnectorFactory getInstance() { return MBServerConnectorFactoryHolder.INSTANCE; } public void setMBeanServer(MBeanServer ms) { server = ms; } public void setServiceUrl(String url) { serviceUrl = url; } public void setEnvironment(Map<String, ?> env) { environment = env; } public void setThreaded(boolean fthread) { threaded = fthread; } public void setDaemon(boolean fdaemon) { daemon = fdaemon; } public void createConnector() throws IOException { if (server == null) { server = MBeanServerHolder.INSTANCE; } // Create the JMX service URL. JMXServiceURL url = new JMXServiceURL(serviceUrl); // if the URL is localhost, start up an Registry if (serviceUrl.indexOf("localhost") > -1 && url.getProtocol().compareToIgnoreCase("rmi") == 0) { try { int port = getURLLocalHostPort(serviceUrl); try { LocateRegistry.createRegistry(port); } catch (Exception ex) { // the registry may had been created LocateRegistry.getRegistry(port); } } catch (Exception ex) { LOG.log(Level.SEVERE, "CREATE_REGISTRY_FAULT_MSG", new Object[]{ex}); } } // Create the connector server now. connectorServer = JMXConnectorServerFactory.newJMXConnectorServer(url, environment, server); if (threaded) { // Start the connector server asynchronously (in a separate thread). Thread connectorThread = new Thread() { public void run() { try { connectorServer.start(); } catch (IOException ex) { LOG.log(Level.SEVERE, "START_CONNECTOR_FAILURE_MSG", new Object[]{ex}); } } }; connectorThread.setName("JMX Connector Thread [" + serviceUrl + "]"); connectorThread.setDaemon(daemon); connectorThread.start(); } else { // Start the connector server in the same thread. connectorServer.start(); } if (LOG.isLoggable(Level.INFO)) { LOG.info("JMX connector server started: " + connectorServer); } } public void destroy() throws IOException { connectorServer.stop(); if (LOG.isLoggable(Level.INFO)) { LOG.info("JMX connector server stopped: " + connectorServer); } } }