Montag, Januar 27, 2020

JMX-MBean-Registrierung mit Spring auf eine eigenständige JVM

Folgenden verschiedene Beispiel-Konfigurationen aus der Spring-Dokumentation sowie einige Foren im Internet, meine Anwendung, die Kontext-Datei sieht wie folgt aus:

<beans>
    <bean id="dH" class="abc.def.ghi.DH">
        <constructor-arg>
            <value>0</value>
        </constructor-arg>
        <property name="num" value="100"/>
    </bean>
    <bean class="org.springframework.jmx.export.MBeanExporter" lazy-init="false">
            <property name="beans">
              <map>
                    <entry key="bean:name=dH1" value-ref="dH"/>
              </map>
            </property>
    </bean>
    <bean class="org.springframework.jmx.support.MBeanServerFactoryBean"/>
</beans>

Bin ich mit diesem ohne container und auf der Ebene JVM. Ich bin in der Lage, eine Verbindung zu meinem Prozess über JConsole aber die MBean nicht zeigen, bis. Allerdings registrieren die bean programmatisch stellt es erfolgreich.

MBeanServer mbeanServer = ManagementFactory.getPlatformMBeanServer();
DH dh = new DH(0);
mbeanServer.registerMBean(dh, new ObjectName("bean:name=dH1"));

Habe ich versucht, das Spiel mit der Spring-Konfiguration, ohne Erfolg. Ich denke die Bohne ist nicht die Registrierung, um die bereits laufende MBean-server zugänglich von ManagementFactory.getPlatformMBeanServer().
Irgendwelche Ideen zu dem Problem?

InformationsquelleAutor Monis Iqbal | 2012-02-06

2 Kommentare

  1. 12

    Neben der Definition einer MBeanServerFactory bean (als Nicholas bereits in Ihrer Antwort) mit …

    <bean class="org.springframework.jmx.support.MBeanServerFactoryBean">
        <property name="locateExistingServerIfPossible" value="true" />
    </bean>

    … Sie sagen müssen, die MBeanExporter was zu verwalten:

    Wenn eine bean implementiert eine der JMX-management-Schnittstellen, MBeanExporter können registrieren Sie sich einfach den MBean mit dem server durch seine automatische Erkennung Prozess.

    Wenn eine bean nicht implementieren Sie eine der JMX-management-Schnittstellen, MBeanExporter erstellen die management-Informationen mithilfe der mitgelieferten MBeanInfoAssembler.

    Vorausgesetzt, Ihr abc.def.ghi.DH Klasse keine Implementierung der JMX-Schnittstelle, versuchen Sie, die Definition Ihrer MBeanExporter als:

    <bean class="org.springframework.jmx.export.MBeanExporter" lazy-init="false">
        <property name="assembler">
            <bean
                class="org.springframework.jmx.export.assembler.MethodNameBasedMBeanInfoAssembler"
            >
                <property name="managedMethods">
                    <list>
                        <value>getNum</value>
                    </list>
                </property>
            </bean>
        </property>
        <property name="beans">
            <map>
                <entry key="bean:name=dH1" value-ref="dH"/>
            </map>
        </property>
    </bean>

    Blick auf das OpenJDK 7, update 2 build 21 DefaultMBeanServerInterceptor.java Quelle, Linie 898 schafft eine DynamicMBean für regelmäßige Objekte:

    DynamicMBean mbean = Introspector.makeDynamicMBean(object);

    Habe ich noch nicht ausgetestet, aber ich Wette mbeanServer.registerMBean(dh, new ObjectName("bean:name=dH1")) schließlich fordert DefaultMBeanServerInterceptor.registerObject() werden, wodurch eine DynamicMBean für Sie und ordnungsgemäß registriert Ihren standard JavaBean Eigenschaften‘ setter und Getter.


    Hier sind einige test-Dateien, die Arbeit mit Spring Framework 3.0.5 und die Oracle HotSpot Java 1.6.0_24. Nachdem Sie Ihr CLASSPATH Umgebungsvariable, führen Sie einfach javac *.java und java Main und verwenden VisualVM (oder eine ähnliche Anwendung) zu verbinden, um die Ausführung von java-Anwendung, um den registrierten MBeans.

    ac.xml:

    <?xml version="1.0" encoding="UTF-8"?>
    <beans
        xmlns="http://www.springframework.org/schema/beans"
        xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
        xsi:schemaLocation="http://www.springframework.org/schema/beans
            http://www.springframework.org/schema/beans/spring-beans.xsd"
        default-lazy-init="true"
    >
        <bean id="test" class="Test" />
        <bean class="org.springframework.jmx.support.MBeanServerFactoryBean">
            <property name="locateExistingServerIfPossible" value="true" />
        </bean>
        <bean class="org.springframework.jmx.export.MBeanExporter" lazy-init="false">
            <property name="assembler">
                <bean
                    class="org.springframework.jmx.export.assembler.MethodNameBasedMBeanInfoAssembler"
                >
                    <property name="managedMethods">
                        <list>
                            <value>getVal</value>
                            <value>setVal</value>
                        </list>
                    </property>
                </bean>
            </property>
            <property name="beans">
                <map>
                    <entry key="bean:name=Test" value-ref="test"/>
                </map>
            </property>
        </bean>
    </beans>

    Test.java:

    public class Test {
        private String val = "";
        public String getVal() {
            return val;
        }
        public void setVal(String v) {
            val = v;
        }
    }

    Main.java:

    import org.springframework.context.ApplicationContext;
    import org.springframework.context.support.ClassPathXmlApplicationContext;
    public class Main {
        public static void main(final String[] args) {
            ApplicationContext ac = new ClassPathXmlApplicationContext("ac.xml");
            try {
                Thread.sleep(1000 * 60 * 5);
            } catch (final Throwable t) {}
        }
    }
    • Vielen Dank für Graben diese aus @Dan. Bei der Spring-context geladen ist, oder sogar die dh wird mit dem Kontext der Introspector-line ist auch nicht ausgeführt. Allerdings registrieren die Bohnen manuell tut, rufen Sie die gleiche Linie. Ich glaube nicht, dass Frühling ist zu registrieren versucht die bean mit diesen Konfigurationen. Irgendwas muss fehlen…
    • Dies funktioniert für mich mit Spring 3.0.5 und eine einfache JavaBean mit einer Eigenschaft getter/setter; kann ich eine Verbindung zu meinem einfachen test-app mit VisualVM und finden Sie die test-MBean, die registriert wurde, mithilfe der MBeanExporter bean-definition, die ich zur Verfügung gestellt. Versuchen Sie brechen Ihr Szenario sich auf eine einfache form bekommen, dass die Arbeit, dann bauen Sie wieder auf, was Sie derzeit haben und sehen, wo Ihr Problem liegt.
    • Mit Spring 3.1.0 ich habe versucht, mit Ihnen bereitgestellte XML -, mit-und ohne -Dcom.Sonne.management.jmxremote als Programm-option, noch kein Glück. Ich bin be-der Zusammenhang in folgender Weise: BeanFactory factory = new XmlBeanFactory(neue ClassPathResource(„/application-context.xml“)); und dann laden die beabsichtigte MBean als: Fabrik.getBean(DH.class); ich weiß, das klingt naiv, aber gibt es eine Möglichkeit passen wir unsere komplette XMLs und einfache Programm-Struktur?
    • Tausend Dank @Dan. Es war die Art, wie die Bohnen wurden immer initialisiert :|. Ich war mit BeanFactory in der Erwägung, dass mit der Datei ApplicationContext hat den trick.
    • Diese Antwort hat mich gerettet heute. +1 und danke.
  2. 2

    Das Problem mit dem MBeanServerFactoryBean.

    Aus der javadoc:

    Standardmäßig MBeanServerFactoryBean wird immer erstellen Sie eine neue
    MBeanServer auch wenn man bereits läuft. Die
    MBeanServerFactoryBean versuchen, zu finden eine laufende MBeanServer erste,
    setzen Sie den Wert von „locateExistingServerIfPossible“ – Eigenschaft
    „true“.

    Versuchen, diese config:

    <bean class="org.springframework.jmx.support.MBeanServerFactoryBean">
        <property name="locateExistingServerIfPossible" value="true" />
    </bean>

    =================================================

    Versuchen Sie, den MBeanServer in der Ausführer bean:

    <bean class="org.springframework.jmx.export.MBeanExporter" lazy-init="false">
        <property name="beans">
            <map>
                    <entry key="bean:name=dH1" value-ref="dH" />
                </map>
            </property>
            <property name="server" ref="MBeanServer" />
    </bean>
    <bean id="MBeanServer" class="org.springframework.jmx.support.MBeanServerFactoryBean">
        <property name="locateExistingServerIfPossible" value="true" />
    </bean>

    ========================================================================

    Ok, nehmen wir mal den brute-force-Ansatz und dem Erwerb der Plattform MBeanServer direkt:

    <bean class="org.springframework.jmx.export.MBeanExporter" lazy-init="false">
        <property name="beans">
            <map>
                    <entry key="bean:name=dH1" value-ref="dH" />
                </map>
            </property>
            <property name="server">
                <bean id="MBeanServer" class="java.lang.management.ManagementFactory" factory-method="getPlatformMBeanServer"/>
            </property>
    </bean>
    • Ich habe bereits versucht es @Nikolaus. Versuchte wieder zu, ohne Glück..
    • kein Glück mit, dass auch..
    • Vielen Dank für die Vorschläge, @Nikolaus. Aber versuchen Sie beide nicht registrieren, die MBeans als gut.

Kostenlose Online-Tests