Tomcat JMX de la Connexion au serveur, mais ne peux pas trouver le MBean je veux

Je suis en train d'écrire un utilitaire client que pour vous connecter à Tomcat via JMX et de regarder l'état de la connexion de source de données.
J'ai mis la suite de VM arguments en $CATALINA_HOME/bin/setenv.chauve-souris et au redémarrage de Tomcat

set JAVA_OPTS=-Xms512M -Xmx1024M -XX:MaxPermSize=256M %JAVA_OPTS%
ensemble CATALINA_OPTS=-Dcom.soleil.de la gestion.jmxremote -Dcom.soleil.de la gestion.jmxremote.port=9004 -Dcom.soleil.de la gestion.jmxremote.authentifier=false -Dcom.soleil.de la gestion.jmxremote.ssl=false %CATALINA_OPTS%

Je ne suis pas très familier avec JMX donc, je suis juste en avoir un pour jouer avec elle pour passer le sens.
L'utilitaire que je suis en train d'écrire va être en cours d'exécution à l'extérieur de Tomcat. J'ai écrit le test suivant pour essayer d'accéder à la source de données Mbean objet dans Tomcat
mais pour quelque raison il n'est pas à la trouver.

    public class GuiMonitor {
      public static void main(String[] args){

       try{
        JMXServiceURL url = new JMXServiceURL(
             "service:jmx:rmi:///jndi/rmi://localhost:9004/jmxrmi");
            JMXConnector jmxc = JMXConnectorFactory.connect(url, null);

            final List<MBeanServer> servers = new LinkedList<MBeanServer>();

            servers.add(ManagementFactory.getPlatformMBeanServer());
            servers.addAll(MBeanServerFactory.findMBeanServer(null));

            System.out.println("MbeanServers " + servers.size()); 

            for(final MBeanServer server : servers){
              System.out.println("Server : " + server.getClass().getName());
             }

            MBeanServer mbsc = ManagementFactory.getPlatformMBeanServer();
            System.out.println(mbsc.queryMBeans(null, null));
            ObjectName on = new ObjectName("Catalina:type=DataSource,path=/appdb,host=localhost,class=javax.sql.DataSource,name=\"jdbc/appdb\"");
            System.out.println("ObjectName : " + on.toString());
            System.out.println(mbsc.getAttribute(on, "Catalina:type=DataSource,path=/appdb,host=localhost,class=javax.sql.DataSource,name=\"jdbc/appdb\""));

       } catch (Exception e) {
                 e.printStackTrace();
             }  
          }
         }

J'ai une page JSP que j'ai trouvé sur l'internet quand je le télécharge sur le répertoire webapps et l'exécuter, il affiche toutes les
MBeans dans Tomcat. L'objet string/nom que j'ai utilisé ci-dessus est venu du nom qui a été signalé à la fois la page jsp que j'ai utilisé et Jconsole de sorte qu'il n'existe pas.

La sortie du programme ci-dessus est illustré ci-dessous

     MbeanServers 2
Server : com.sun.jmx.mbeanserver.JmxMBeanServer
Server : com.sun.jmx.mbeanserver.JmxMBeanServer
[com.sun.management.OperatingSystem[java.lang:type=OperatingSystem], sun.management.MemoryPoolImpl[java.lang:type=MemoryPool,name=Tenured Gen], sun.management.MemoryPoolImpl[java.lang:type=MemoryPool,name=Perm Gen], java.util.logging.Logging[java.util.logging:type=Logging], sun.management.CompilationImpl[java.lang:type=Compilation], javax.management.MBeanServerDelegate[JMImplementation:type=MBeanServerDelegate], sun.management.MemoryImpl[java.lang:type=Memory], sun.management.MemoryPoolImpl[java.lang:type=MemoryPool,name=Survivor Space], sun.management.RuntimeImpl[java.lang:type=Runtime], sun.management.GarbageCollectorImpl[java.lang:type=GarbageCollector,name=Copy], sun.management.MemoryPoolImpl[java.lang:type=MemoryPool,name=Eden Space], sun.management.GarbageCollectorImpl[java.lang:type=GarbageCollector,name=MarkSweepCompact], sun.management.ThreadImpl[java.lang:type=Threading], sun.management.MemoryPoolImpl[java.lang:type=MemoryPool,name=Perm Gen [shared-ro]], sun.management.MemoryPoolImpl[java.lang:type=MemoryPool,name=Perm Gen [shared-rw]], sun.management.HotSpotDiagnostic[com.sun.management:type=HotSpotDiagnostic], sun.management.ClassLoadingImpl[java.lang:type=ClassLoading], sun.management.MemoryManagerImpl[java.lang:type=MemoryManager,name=CodeCacheManager], sun.management.MemoryPoolImpl[java.lang:type=MemoryPool,name=Code Cache]]
ObjectName : Catalina:type=DataSource,path=/appdb,host=localhost,class=javax.sql.DataSource,name="jdbc/appdb"
javax.management.InstanceNotFoundException: Catalina:type=DataSource,path=/appdb,host=localhost,class=javax.sql.DataSource,name="jdbc/appdb"
at com.sun.jmx.interceptor.DefaultMBeanServerInterceptor.getMBean(DefaultMBeanServerInterceptor.java:1094)
at com.sun.jmx.interceptor.DefaultMBeanServerInterceptor.getAttribute(DefaultMBeanServerInterceptor.java:662)
at com.sun.jmx.mbeanserver.JmxMBeanServer.getAttribute(JmxMBeanServer.java:638)
at com.bt.c21.c21mon.C21GuiMonitor.main(C21GuiMonitor.java:39)

Un couple de questions

  • Est l'URL correcte? Je sais que le numéro de port est correct, mais je ne suis pas sûr du nom du service. Le nom de service "jmxrmi" je suis à l'aide de l'URL est juste celui que j'ai vu dans l'un des exemples que j'ai été à la recherche sur.

J'ai le sentiment que c'est la connexion à un autre MBeanServer. Je soupçonne que cela parce que si vous chercher à la sortie de mbsc.queryMBeans(null, null), il n'y a rien de spécifique à tomcat. Ce service de nom dois-je utiliser pour l'instance de Tomcat?

  • Si l'URL est correcte, alors est le nom de service toujours jmxrmi? Et pourquoi n'est-il pas de trouver le "Catalina:type=source de données,path=/base de données d'applications,host=localhost class=javax.sql.Source de données,nom=\"jdbc/base de données d'applications\" entrée"?

  • J'ai vu beaucoup d'exemples de la façon de le faire et de plus utiliser une autre méthode pour obtenir le MbeanServer. Quelques exemples que j'ai vu sont

    ManagementFactory.getPlatformMBeanServer()
    MBeanServerFactory.findMBeanServer(null)
    getMBeanServerConnection()

  • Comme mentionné précédemment, l'utilité, je suis en train d'écrire est une activité normale de l'application java qui sera exécuté à l'extérieur de tomcat. Est-il une autre configuration que j'ai raté? J'ai été à la recherche sur plusieurs exemples et la majorité parlent de la création d'MBeans et il y a généralement des références à des Auditeurs. Comme je ne suis pas en créer un nouveau Mbeans mais seulement de lire les valeurs de celles existantes, dois-je configurer un auditeur?

Modifier

Il semble que getPlatformMbeanServer() ne retourne pas la bonne Instance de la JVM. J'ai essayé les

MBeanServerConnection conn = jmxc.getMBeanServerConnection(); 
System.out.println("Query2  : " + conn.queryMBeans(null, null)); 

Et ce n'retour de certains Tomcat de valeurs spécifiques. Mais je suis toujours incapable d'obtenir le jdbc/base de données d'applications de la source de données.

krtek - je ne vais pas être en mesure d'utiliser la Console JMX que j'ai l'intention de tout faire manuellement avec l'intention de les automatiser.

Edit 2

Ok, j'ai compris ce que je faisais mal. D'abord j'ai été de tenter de récupérer les valeurs que

MBeanServerConnection conn = jmxc.getMBeanServerConnection(); 
ObjectName on = new ObjectName("Catalina:type=DataSource,path=/appdb,host=localhost,class=javax.sql.DataSource,name=\"jdbc/appdb\"");
mbsc.getAttribute(on, "Catalina:type=DataSource,path=/appdb,host=localhost,class=javax.sql.DataSource,name=\"jdbc/appdb\""));

Ci-dessus est incorrecte, car le deuxième paramètre pour mbsc.getAttribute est censé être l'attribut dans le Mbean pas le nom de la Chaîne.

Cela m'a donné l'corriger les valeurs d'attribut

MBeanServerConnection conn = jmxc.getMBeanServerConnection(); 
ObjectName on = new ObjectName("Catalina:type=DataSource,path=/appdb,host=localhost,class=javax.sql.DataSource,name=\"jdbc/appdb\"");
mbsc.getAttribute(on, "numIdle")

Et j'ai aussi changé le MBeanServer j'ai été à l'aide de getPlatformMbeanServer() pour getMBeanserverConnection(). Je dois avouer que je n'ai pas très bien compris la différence, parce que depuis Tomcat est en cours d'exécution sur la même JVM que celui retourné par getPlatformMbeanServer(). Ça veut dire que getPlatformMbeanServer() ne retourne que le soleil spécifique Mbeans? et getMBeanserverConnection() comprendra à la fois?

Grâce

Il suffit de noter à la dernière phrase: Tomcat est certainement pas en cours d'exécution dans la même JVM, il tourne dans le même PC, mais sur les différentes JVM. Et la différence est simple: jmxc.getMBeanServerConnection() retourne une instance de serveur JMX à partir d'une connexion à distance (le Tomcat de la JVM). ManagementFactory.getPlatformMBeanServer() renvoie le serveur JMX du local de la JVM.
Salut Krtek - locaux de la JVM à-dire la JVM où l'application que je suis utilise pour se connecter au serveur Tomcat est en cours d'exécution?
Oui, exactement 🙂

OriginalL'auteur ziggy | 2011-01-05