2011-04-05 10 views
35

मुझे जेएमएक्स का उपयोग कर लोकहोस्ट जेवीएम पर जावा प्रोग्राम से कनेक्ट होना चाहिए। दूसरे शब्दों में मैं लोकहोस्ट पर जावा प्रोग्राम कॉन्फ़िगर करने के लिए जेएमएक्स क्लाइंट विकसित करना चाहता हूं।जेएमएक्स का उपयोग कर लोकहोस्ट जेवीएम पर जावा प्रोग्राम से कैसे जुड़ें?

  • JConsole का उपयोग करने की अनुशंसा न करें! जेकोनसोल उपयुक्त नहीं है क्योंकि यह सामान्य जेएमएक्स क्लाइंट है और मुख्य कार्यक्रम प्रदर्शन पर नकारात्मक प्रभाव पड़ता है।

  • ओरेकल साइट पर नमूने RMIConnector और होस्ट: पोर्ट पैराम का उपयोग करते हैं लेकिन मुझे नहीं पता: जहां jmx पोर्ट सेट करना चाहिए?

  • जेकोनसोल में पीआईडी ​​द्वारा जावा प्रक्रियाओं से जुड़ने का विकल्प है। लेकिन मुझे जेएमएक्स एपीआई में कोई विधि नहीं मिली है जिसमें पीआईडी ​​इनपुट पैरामीटर है।

+1

दोनों मुख्य कार्यक्रम और JMX ग्राहक स्टैंड-अलोन कार्यक्रमों (जावा SE) कर रहे हैं। – mjafari

+0

यह भी देखें http://www.pongasoft.com/blog/yan/entry/connecting_to_a_local_vm/ –

उत्तर

56

हम अपने जेएमएक्स सर्वर से प्रोग्रामेटिक रूप से कनेक्ट करने के लिए निम्न की तरह कुछ उपयोग करते हैं।

-Dcom.sun.management.jmxremote 
-Dcom.sun.management.jmxremote.authenticate=false 
-Dcom.sun.management.jmxremote.port=1234 
-Dcom.sun.management.jmxremote.ssl=false 

एक विशेष पते के लिए बाध्य करने के लिए आप निम्न वीएम तर्क जोड़ने की आवश्यकता होगी: आपको निम्न तर्क की तरह कुछ के साथ अपने सर्वर चलाना चाहिए

-Djava.rmi.server.hostname=A.B.C.D 

तो फिर आप अपने सर्वर से कनेक्ट कर सकते हैं निम्नलिखित की तरह JMX ग्राहक कोड का उपयोग:

String host = "localhost"; // or some A.B.C.D 
int port = 1234; 
String url = "service:jmx:rmi:///jndi/rmi://" + host + ":" + port + "/jmxrmi"; 
JMXServiceURL serviceUrl = new JMXServiceURL(url); 
JMXConnector jmxConnector = JMXConnectorFactory.connect(serviceUrl, null); 
try { 
    MBeanServerConnection mbeanConn = jmxConnector.getMBeanServerConnection(); 
    // now query to get the beans or whatever 
    Set<ObjectName> beanSet = mbeanConn.queryNames(null, null); 
    ... 
} finally { 
    jmxConnector.close(); 
} 

हम भी कोड है कि प्रोग्राम के वीएम तर्कों के बाहर एक विशेष बंदरगाह के लिए खुद को प्रकाशित कर सकते हैं लेकिन यह है कि अधिक फू है आपको लगता है की तुलना में मुझे लगता है।


"पीआईडी ​​द्वारा" जोड़ने के संदर्भ में, आप के रूप में तक मुझे पता है जावा भूमि से यह करने के लिए Java6 उपयोग करने की आवश्यकता। मैंने निम्नलिखित कोड का उपयोग नहीं किया है लेकिन ऐसा लगता है कि यह काम करता है।

List<VirtualMachineDescriptor> vms = VirtualMachine.list(); 
for (VirtualMachineDescriptor desc : vms) { 
    VirtualMachine vm; 
    try { 
     vm = VirtualMachine.attach(desc); 
    } catch (AttachNotSupportedException e) { 
     continue; 
    } 
    Properties props = vm.getAgentProperties(); 
    String connectorAddress = 
     props.getProperty("com.sun.management.jmxremote.localConnectorAddress"); 
    if (connectorAddress == null) { 
     continue; 
    } 
    JMXServiceURL url = new JMXServiceURL(connectorAddress); 
    JMXConnector connector = JMXConnectorFactory.connect(url); 
    try { 
     MBeanServerConnection mbeanConn = connector.getMBeanServerConnection(); 
     Set<ObjectName> beanSet = mbeanConn.queryNames(null, null); 
     ... 
    } finally { 
     jmxConnector.close(); 
    } 
} 

मैंने भी SimpleJMX package के लेखक जो यह आसान एक JMX सर्वर प्रारंभ और दूरदराज के ग्राहकों के लिए सेम प्रकाशित करने के लिए बनाता है।

// create a new server listening on port 8000 
JmxServer jmxServer = new JmxServer(8000); 
// start our server 
jmxServer.start(); 
// register our lookupCache object defined below 
jmxServer.register(lookupCache); 
jmxServer.register(someOtherObject); 
// stop our server 
jmxServer.stop(); 

यह रूप में अच्छी तरह लेकिन अभी यह पीआईडी ​​द्वारा प्रक्रियाओं को खोजने के लिए किसी भी तंत्र नहीं है एक ग्राहक इंटरफ़ेस है - (6/2012 में) केवल होस्ट/पोर्ट संयोजन समर्थित हैं।

+1

धन्यवाद ग्रे! क्या आप (या अन्य लोग) मेरे दूसरे प्रश्न का उत्तर दे सकते हैं (पीआईडी ​​का उपयोग कर स्थानीय जेएमएक्स कनेक्टिंग)? – mjafari

+0

अगर किसी कारण से कनेक्टर एड्रेस शून्य है, तो आप एजेंट को डायनामिक रूप से लोड करने का प्रयास कर सकते हैं। देखें http://www.pongasoft.com/blog/yan/entry/connecting_to_a_local_vm/ –

+0

आपके पास लाइन में संकलन समस्या है: jmxConnector.close(); – shlomi33

3
List<VirtualMachineDescriptor> vm = new ArrayList<VirtualMachineDescriptor>(); 
     jvmList = new JVMListManager(); 

     vm = jvmList.listActiveVM(); 

     for (VirtualMachineDescriptor vmD : vm) 
     { 
      try 
      { 

      //importFrom is taking a process ID and returning a service url in a String Format 
      String ServiceUrl = ConnectorAddressLink.importFrom(Integer.parseInt(vmD.id().trim())); 
      JMXServiceURL jmxServiceUrl = new JMXServiceURL(ServiceUrl); 

      jmxConnector = JMXConnectorFactory.connect(jmxServiceUrl, null); 
      con = jmxConnector.getMBeanServerConnection(); 
      CompilationMXBean compMXBean = ManagementFactory.newPlatformMXBeanProxy(con 
        , ManagementFactory.COMPILATION_MXBEAN_NAME 
        , CompilationMXBean.class); 
      }catch(Exception e) 
      { 
      //Do Something 
      } 
     } 


protected List listActiveVM() { 
    List<VirtualMachineDescriptor> vm = VirtualMachine.list(); 

    return vm; 
} 

इस प्रक्रिया को आप को पढ़ने के लिए कोशिश कर रहे हैं के लिए JVM स्टार्टअप पर jmxremote तर्क का उपयोग करने की आवश्यकता है। स्टार्टअप पर jmxremote तर्क पास किए बिना इसे करने में सक्षम होने के लिए। आपको संलग्न एपीआई (केवल जावा 6 और उच्चतर का उपयोग करने वाले कार्यक्रमों के लिए लागू होना होगा।

4

स्पष्टीकरण के लिए, यदि आप केवल स्थानीय जेएमएक्स आंकड़े प्राप्त करने में रुचि रखते हैं, तो आपको दूरस्थ एपीआई का उपयोग करने की आवश्यकता नहीं है। बस उपयोग करें java.lang.management.ManagementFactory:

MemoryMXBean memoryMXBean = ManagementFactory.getMemoryMXBean(); 
memoryMXBean.getHeapMemoryUsage().getMax(); 
... 

List<MemoryPoolMXBean> beans = ManagementFactory.getMemoryPoolMXBeans(); 
... 
1

सरल साधन:

import javax.management.Attribute; 
import javax.management.AttributeList; 
import java.lang.management.ManagementFactory; 
import javax.management.MBeanServer; 
import javax.management.ObjectName; 

// set a self JMX connection 
MBeanServer mBeanServer = ManagementFactory.getPlatformMBeanServer(); 
// set the object name(s) you are willing to query, here a CAMEL JMX object 
ObjectName objn = new ObjectName("org.apache.camel:context=*,type=routes,name=\"route*\""); 
Set<ObjectName> objectInstanceNames = mBeanServer.queryNames(objn, null); 
for (ObjectName on : objectInstanceNames) { 
    // query a number of attributes at once 
    AttributeList attrs = mBeanServer.getAttributes(on, new String[] {"ExchangesCompleted","ExchangesFailed"}); 
    // process attribute values (beware of nulls...) 
    // ... attrs.get(0) ... attrs.get(1) ... 
} 
संबंधित मुद्दे