Skip to main content

Extending the NetBeans Tutorial JSF-JPA-Hibernate Application, Part 3 - Enabling JMX Monitoring on Hibernate v3 & Ehcache 1.3.0

Posted by maxpoon on June 27, 2007 at 11:21 AM PDT

Background

This is the continuation from the previous article "Extending the NetBeans Tutorial JSF-JPA-Hibernate Application, Part 2 - Enabling JMX Monitoring on Hibernate v3 and Ehcache 1.3, on HibernateTutorialApp" where we continue with (3) and (4) of the following :

  1. Configuring HibernateTutorialApp/HibernateTravelPOJO to use Ehcache 1.3.0
  2. Configuring HibernateTutorialApp/HibernateTravelPOJO to enable JMX monitoring on Hibernate and Ehcache
  3. Configuring SimpleJpaHibernateApp to use Ehcache 1.3.0
  4. Configuring SimpleJpaHibernateApp to enable JMX monitoring on Hibernate and Ehcache

 

(3) Configuring SimpleJpaHibernateApp to use Ehcache 1.3.0

The configurations for SimpleJpaHibernateApp, created with the NetBeans tutorial "Using Hibernate With the Java Persistence API", to use Ehcache 1.3.0 are similar to those of "Configuring HibernateTutorialApp/HibernateTravelPOJO to use Ehcache 1.3.0" , except :

  • SimpleJpaHibernateApp is directly configured to use Hibernate (Hibernate-3.2.2, or above, e.g. Hibernate-3.2.4sp1) and Ehcache-1.3.0
  • persistence.xml and hibernate.cfg.xml (cache related configurations  highlighted in bold), and ehcache.cfg.xml as shown :
Code Listing 3.1 - persistence.xml for SimpleJpaHibernateApp
<?xml version="1.0" encoding="UTF-8"?>

<persistence version="1.0" xmlns="http://java.sun.com/xml/ns/persistence"
    xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
    xsi:schemaLocation="http://java.sun.com/xml/ns/persistence
    http://java.sun.com/xml/ns/persistence/persistence_1_0.xsd">


  <persistence-unit name="SimpleJpaHibernateAppPU" transaction-type="JTA">

    <provider>org.hibernate.ejb.HibernatePersistence</provider>

    <jta-data-source>jdbc/sample</jta-data-source>

    <class>simpleJpaHibernateApp.entities.ProductCode</class>

    <class>simpleJpaHibernateApp.entities.Product</class>

    <class>simpleJpaHibernateApp.entities.Manufacturer</class>

    <properties>

      <property name=
        "hibernate.ejb.classcache.simpleJpaHibernateApp.entities.ProductCode"
          value="read-write"/>


      <property name=
        "hibernate.ejb.classcache.simpleJpaHibernateApp.entities.Product"
          value="read-write"/>


      <property name=
        "hibernate.ejb.classcache.simpleJpaHibernateApp.entities.Manufacturer"
          value="read-write"/>


      <property name="hibernate.ejb.cfgfile" value="/hibernate.cfg.xml"/>

    </properties>

  </persistence-unit>

</persistence>

 

Code Listing 3.2 - hibernate.cfg.xml for SimpleJpaHibernateApp
<?xml version='1.0' encoding='utf-8'?>

<!DOCTYPE hibernate-configuration PUBLIC

  "-//Hibernate/Hibernate Configuration DTD 3.0//EN"


  "http://hibernate.sourceforge.net/hibernate-configuration-3.0.dtd">



<hibernate-configuration>


  <session-factory>



    <!-- SQL dialect -->

    <property name="hibernate.dialect">
        org.hibernate.dialect.DerbyDialect</property>




    <!-- Debug logging of SQL statements -->

    <property name="hibernate.show_sql">true</property>



    <!-- Cache Configurations -->

    <!-- Using net.sf.ehcache.hibernate.SingletonEhCacheProvider instead of

         net.sf.ehcache.hibernate.EhCacheProvider ensures the same instance
         of CacheManager is referred to by both Hibernate and our JMX Agent


         simpleJpaHibernateApp.agents.jmxAgent. (Thanks to Greg Luck!)  -->

    <property name="hibernate.cache.provider_class">

        net.sf.ehcache.hibernate.SingletonEhCacheProvider</property>

    <property name="hibernate.cache.provider_configuration">

        /ehcache.cfg.xml</property>

    <property name="hibernate.cache.use_minimal_puts">false</property>

    <property name="hibernate.cache.use_query_cache">true</property>

    <property name="hibernate.cache.use_second_level_cache">true</property>

    <property name="hibernate.cache.use_structured_entries">true</property>



    </session-factory>


</hibernate-configuration>

 

Coding Listing 3.3 - ehcache.cfg.xml for SimpleJpaHibernateApp
<?xml version="1.0" encoding="UTF-8"?>

<ehcache xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"

         xsi:noNamespaceSchemaLocation="ehcache.xsd">

  <diskStore path="java.io.tmpdir"/>

  <defaultCache

    maxElementsInMemory="10000"

    eternal="false"

    timeToIdleSeconds="120"

    timeToLiveSeconds="120"

    overflowToDisk="true"

    diskPersistent="true"

    diskExpiryThreadIntervalSeconds="120"

    memoryStoreEvictionPolicy="LRU"

  />
  <cache name="simpleJpaHibernateApp.entities.ProductCode"
         maxElementsInMemory="300"
         eternal="true"
         overflowToDisk="false"
  />
  <cache name="simpleJpaHibernateApp.entities.Product"
         maxElementsInMemory="300"
         eternal="true"
         overflowToDisk="false"
  />
  <cache name="simpleJpaHibernateApp.entities.Manufacturer"
         maxElementsInMemory="300"
         eternal="true"
         overflowToDisk="false"
  />
  <cache name="simpleJpaHibernateApp.entities.ProductCode.productCollection"
         maxElementsInMemory="300"
         eternal="true"
         overflowToDisk="false"
  />
  <cache name="simpleJpaHibernateApp.entities.Manufacturer.productCollection"
         maxElementsInMemory="300"
         eternal="true"
         overflowToDisk="false"
  />

</ehcache>

 

(4) Configuring SimpleJpaHibernateApp to enable JMX monitoring on Hibernate and Ehcache

After being configured to use Ehcache 1.3.0 as shown in "Configuring SimpleJpaHibernateApp to use Ehcache 1.3.0" above, the SimpleJpaHibernateApp can also be extended to enable JMX monitoring, e.g. on Hibernate and Ehcache used, similar to "Configuring HibernateTutorialApp/HibernateTravelPOJO to enable JMX monitoring on Hibernate and Ehcache" in previous article.

Step 4.1 - Create JMX Agent with Hibernate and Ehcache MBeans Registration Codes

Similar to Step 2.1 in "Configuring HibernateTutorialApp/HibernateTravelPOJO to enable JMX monitoring on Hibernate and Ehcache", we need to create the JMX Agent which registers the Hibernate and Ehcache MBeans to enable JMX monitoring on them.  However, there are a few small but important differences here...

(A) To register Hibernate's MBean, we still need the following codes :

    // Enable Hibernate JMX Statistics

    StatisticsService statsMBean = new StatisticsService();

    statsMBean.setSessionFactory(sessionFactory);

    statsMBean.setStatisticsEnabled(true);

    mbs.registerMBean(statsMBean, on);

i.e. we need to get Hibernate SessionFactory from our JPA execution environment (which uses the implementation-independent JPA PersistentUnit and the associated EntityMangerFactory instead) to enable JMX monitoring on Hibernate, by (also used by the NetBeans Tutorial "NetBeans Wiki - UsingHibernateWithJPA") :

  • Session session = (Session) em.getDelegate();

And, in our case for SimpleJpaHibernateApp, it is followed by :

  • SessionFactory sessionFactory = session.getSessionFactory();

to get SessionFactory as in Code Listing 4.1 (additional MBeans registration codes in bold) below.

(B) Also, we would like to modify the init() method to take EntityMangerFactory from the calling context, to get the Hibernate SessionFactory for registering Hibernate statsMBean.

Code Listing 4.1 - SimpleJpaHibernateApp's JmxAgent.java
/*

 * JmxAgent.java

 *

 */



package simpleJpaHibernateApp.agents;



import java.lang.management.ManagementFactory;

import javax.management.MBeanServer;

import javax.management.ObjectName;

import javax.persistence.EntityManagerFactory;

import javax.persistence.EntityManager;

import net.sf.ehcache.CacheManager;

import net.sf.ehcache.management.ManagementService;

import org.hibernate.Session;

import org.hibernate.SessionFactory;

import org.hibernate.jmx.StatisticsService;



/**

 * JMX agent (singleton) for monitoring Hibernate and Ehcache

 * in SimpleJpaHibernateApp, which uses:

 * <ul>

 * <li>JavaServer Faces (JSF) web-tier</li>

 * <li>Java Persistence API (JPA) persistence</li>

 * <li>Hibernate Core (3.2.4 sp1) and Hibernate EntityManager (3.3.1)</li>

 * <li>Ehcache 1.3.0</li>

 * </ul>

 *

 * @author Max Poon (maxpoon@dev.java.net)

 */

public class JmxAgent {

   

  private EntityManager em;

  private Session session;

  private SessionFactory sf;

   

  /**

   * Instantiate, register MBeans, enable Hibernate & Ehcache JMX Statistics

   * @param emf javax.persistence.EntityManagerFactory to be passed in

   *            from the invoking context (instead of creating it here

   *            which is expensive operation)

   */

  public void init(EntityManagerFactory emf) throws Exception {



    try {

      // Create EntityManager from EntityManagerFactory passed in

      // from the invoking context

      em = emf.createEntityManager();

           

      // Get Hibernate Session and SessionFactory from EntityManager

      // *Important* for registering the Hibernate SessionFactory

      //  with org.hibernate.jmx.StatisticsService later on

      //  to enable JMX monitoring of Hibernate statistics

      session = (Session) em.getDelegate();

      sf = session.getSessionFactory();

    } catch (Exception ex) {

      ex.printStackTrace();

    } finally {

      em.close();

    }



    ObjectName on = new ObjectName
        ("Hibernate:type=statistics,application=SimpleJpaHibernateApp");




    // Enable Hibernate JMX Statistics

    StatisticsService statsMBean = new StatisticsService();

    statsMBean.setSessionFactory(sf);

    statsMBean.setStatisticsEnabled(true);

    mbs.registerMBean(statsMBean, on);

    /*
     * Enable Ehcache JMX Statistics


     * Use CacheManager.getInstance() instead of new CacheManager()

     * as net.sf.ehcache.hibernate.SingletonEhCacheProvider is used

     * to ensure reference to the same CacheManager instance as used

     * by Hibernate

     */

    CacheManager cacheMgr = CacheManager.getInstance();

    ManagementService.registerMBeans
        (cacheMgr, mbs, true, true, true, true);


  }

   

  /**

   * Returns an agent singleton.

   */

  public synchronized static JmxAgent getDefault(EntityManagerFactory emf)
      throws Exception {


    if(singleton == null) {

      singleton = new JmxAgent();

      singleton.init(emf);

    }

    return singleton;

  }

   

  public MBeanServer getMBeanServer() {

    return mbs;

  }

 

  // Platform MBeanServer used to register your MBeans

  private final MBeanServer mbs = ManagementFactory.getPlatformMBeanServer();

   

  // Singleton instance

  private static JmxAgent singleton;

}

 

Step 4.2 Modify JSF Managed Beans to initiate JMX Agent

Unlike the HibernateTravelPOJO application, there is no HibernateUtil.java-like object for getting Hibernate Session in SimpleJpaHibernateApp.  One solution is to initiate JmxAgent during the 1st retrieval of EntityManager in following JSF managed beans / controllers :

  • simpleJpaHibernate.controllers.ProductController
  • simpleJpaHibernate.controllers.ProductCodeController
  • simpleJpaHibernate.controllers.ManufacturerController

e.g. as shown in Code Listing 4.2 for simpleJpaHibernate.controllers.ProductController :

Code Listing 4.2 - ProductController.java modified to initiate JmxAgent if needed
/*

 * ProductController.java

 *

 */



package simpleJpaHibernateApp.controller;



import java.util.ArrayList;
import java.util.Collection;
import java.util.List;
import javax.annotation.Resource;
 ....


import simpleJpaHibernateApp.agents.JmxAgent;

import simpleJpaHibernateApp.entities.Manufacturer;

import simpleJpaHibernateApp.entities.Product;

import simpleJpaHibernateApp.entities.ProductCode;



/**
 * This version of ProductController uses JPA query with SQL joint
 * to retrieve all Products associated with a given ProductCode
 * indicated by its ID 'selectedProdCode'.
 * This shows simple code modification to get additional behaviour.
 *
 * @author Max Poon (maxpoon@dev.java.net)
 */


public class ProductController {

   

    /** Creates a new instance of ProductController */

    public ProductController() { }

   

    private Product product;

    private ProductCode selectedProductCode;

    private String selectedProdCode;

    private DataModel model;

   

    @Resource

    private UserTransaction utx;

   

    @PersistenceUnit(unitName = "SimpleJpaHibernateAppPU")

    private EntityManagerFactory emf;



    private EntityManager getEntityManager() {

        initJMX();

        return emf.createEntityManager();

    }

   

    // Initiate JMX if needed

    void initJMX() {

        try {

            JmxAgent.getDefault(emf);

        } catch (Exception ex) {

            ex.printStackTrace();

        }

    }

    ...

    ...

Similar modifications should also be done for :

  • simpleJpaHibernate.controllers.ProductCodeController
  • simpleJpaHibernate.controllers.ManufacturerController

Then recompile SimpleJpaHibernateApp with the above configurations and checked that it is working fine getting also the web interface and functionalities as those in "Extending the NetBeans Tutorial JSF-JPA-Hibernate Application, Part 1 - Co-ordinating Query Views Based on Parameter Passing from JSF View to Managed Bean".

Step 4.3 - Use JConsole to Observe JMX Statistics

Similar to Step 2.3 in "Configuring HibernateTutorialApp/HibernateTravelPOJO to enable JMX monitoring on Hibernate and Ehcache", start JConsole and connect to JVM running GlassFish (indicated by "com.sun.enterprise.server.PELaunch" in JConsole) and observe the following real-time JMX information collected.

Starting with the "Listing ProductCodes" page :

Figure 4.3.1 - "Listing ProductCodes" page of SimpleJpaHibernateApp

Figure 4.3.2 - JConsole showing Hibernate Entity Names, Queries, 2nd Level Cache Regions, and related statistics

Figure 4.3.3 - JConsole showing Ehcache Statistics on ProductCode, with 6 cache miss for the 6 ProductCode instances retrieved

Click on "SW" page on "Listing ProductCodes" page to get the following, then click on "List of Product with this Product Code" to get the next screen shown in Figure 4.3.7.

Figure 4.3.4 - "Detail of ProductCode" page of SimpleJpaHibernateApp for ProdCode="SW"

Figure 4.3.5 - JConsole showing Hibernate Statistics being updated as compared to Figure 4.3.2

Figure 4.3.6 - JConsole showing Ehcache Statistics for ProductCode updated (with 2 more cache misses and 7 more cache hits) as compared to Figure 4.3.3

Figure 4.3.7 - "Listing Products" page of SimpleJpaHibernateApp for ProdCode="SW"

Figure 4.3.8 - JConsole showing Hibernate Statistics being updated as compared to Figure 4.3.5

Figure 4.3.9 - JConsole showing Ehcache Statistics for ProductCode updated, with 1 more (ProductCode where ProdCode="SW") cache hit as compared to Figure 4.3.6

Figure 4.3.10 - JConsole showing Ehcache Statistics for Product, with 8 new retrieval, i.e. cache misses, for the 8 Product instances where ProdCode="SW" as shown in Figure 4.3.7

Step 4.4 - Modify ProductController to Enable Collection Cache

The SimpleJpaHibernateApp is extended in "Extending the NetBeans Tutorial JSF-JPA-Hibernate Application, Part 1 - Co-ordinating Query Views Based on Parameter Passing from JSF View to Managed Bean" and the above steps, to demonstrate easy modification to achieve JSF query views co-ordination and then JMX monitoring.  The ProductCode-to-Product entity 'navigation' and retrieval are done by JPA Query with SQL joint and parameter binding as shown in Code Listing 4.4.1, instead of one-to-many entity mapping and entity collection retrieval.  Hence, collection cache are not used as observed previously from the Hibernate JMX cache statistics on collection cache.

Coding Listing 4.4.1 - simpleJpaHibernateApp.controllers.ProductController#getProducts() - using JPA Query with SQL joint and parameter binding
/**
 * This version of ProductController uses JPA query with SQL joint
 * to retrieve all Products associated with a given ProductCode
 * indicated by its ID 'selectedProdCode'.
 * This shows simple code modification to get additional behaviour.
 *
 * @author Max Poon (maxpoon@dev.java.net)
 */
public class ProductController {
  ...
  public DataModel getProducts() {


     EntityManager em = getEntityManager();

     try{

        Query q;

        if (selectedProdCode != null && selectedProdCode.length() != 0) {

           q = em.createQuery("select object(o) from Product as o " +

               "where o.productCode.prodCode = :selectedProdCode")

               .setParameter("selectedProdCode", selectedProdCode);

        } else {

           q = em.createQuery("select object(o) from Product as o");

        }

        q.setMaxResults(batchSize);

        q.setFirstResult(firstItem);

        model = new ListDataModel(q.getResultList());

        return model;

     } finally {

        em.close();

     }

  }

  ...

  public int getItemCount() {
     EntityManager em = getEntityManager();
     try{
        Query q;
        if (selectedProdCode != null && selectedProdCode.length() != 0) {
           q = em.createQuery("select count(o) from Product as o " +

               "where o.productCode.prodCode = :selectedProdCode")

               .setParameter("selectedProdCode", selectedProdCode);
        } else {
           q = em.createQuery("select count(o) from Product as o");
        }
        int count = ((Long) q.getSingleResult()).intValue();
        return count;
     } finally {
        em.close();
     }
  }
  ...

An alternative to the above is to get the ProductCode entity class using the selectedProdCode string :

  • ProductCode productCode = em.find(ProductCode.class, selectedProdCode);

Then for ProductController.getProducts(), retrieve all the associated Product's from ProductCode.getProductonCollection() using one-to-many association :

  • productList = (List<Product>) productCode.getProductCollection();

For ProductController.getItemCount(),

  • count = productCode.getProductCollection().size();

as shown in Code Listing 4.4.2 below :

Coding Listing 4.4.2 - simpleJpaHibernateApp.controllers.ProductController#getProducts() and getItemCount() - using JPA Entity Collection, e.g. to show use of Hibernate Collection Cache in additional to Class Caching
/**
 * This version of ProductController uses entity collection for
 * retrieving all Products associated with a given ProductCode
 * indicated by its ID 'selectedProdCode' to show JMX monitoring
 * on collection cache in additional to entity class cache
 *
 * @author Max Poon (maxpoon@dev.java.net)
 */
public class ProductController {
  ...
  public DataModel getProducts() {


    EntityManager em = getEntityManager();

    try{

      List<Product> productList;

      if (selectedProdCode != null && selectedProdCode.length() != 0) {

        ProductCode productCode = em.find(ProductCode.class, selectedProdCode);

        productList = (List<Product>) productCode.getProductCollection();

      } else {

        Query q = em.createQuery("select object(o) from Product as o");

        q.setMaxResults(batchSize);

        q.setFirstResult(firstItem);

        productList = (List<Product>) q.getResultList();

      }

      model = new ListDataModel(productList);

      return model;

    } finally {

      em.close();

    }

  }
  ...
  public int getItemCount() {
    EntityManager em = getEntityManager();
    try{
      int count;
      if (selectedProdCode != null && selectedProdCode.length() != 0) {
        ProductCode productCode = em.find(ProductCode.class, selectedProdCode);

        count = productCode.getProductCollection().size();

      } else {
        Query q = em.createQuery("select count(o) from Product as o");
        count = ((Long) q.getSingleResult()).intValue();
      }
      return count;
    } finally {
      em.close();
    }
  ...

The entity class ProductCode.java is also required to further enable collection cache on ProductCode.productCollection (similarly for  Manufacturer.productCollection in Manufacturer.java) :

Code Listing 4.4.3 - ProductCode.java with Hibernate @Cache Annotation to enable Entity Class Cache on ProductCode and Collection Cache on ProductCode.productionCollection
/*

 * ProductCode.java

 *

 */



package simpleJpaHibernateApp.entities;



import java.io.Serializable;

import java.util.Collection;

import javax.persistence.CascadeType;

import javax.persistence.Column;

import javax.persistence.Entity;

import javax.persistence.Id;

import javax.persistence.NamedQueries;

import javax.persistence.NamedQuery;

import javax.persistence.OneToMany;

import javax.persistence.Table;
import org.hibernate.annotations.Cache;

import org.hibernate.annotations.CacheConcurrencyStrategy;


/**

 * Entity class ProductCode, adding Hibernate Annotations to enable
 *  Entity Class Cache on ProductCode, and
 *  Collection Cache on ProductCode.
productCollection

 *

 * @author Max Poon (maxpoon@dev.java.net)

 */

@Entity

@Table(name = "PRODUCT_CODE")

@NamedQueries( {
  ......

} )

@Cache(usage = CacheConcurrencyStrategy.READ_WRITE)
public class ProductCode implements Serializable {



    @Id

    @Column(name = "PROD_CODE", nullable = false)

    private String prodCode;



    @Column(name = "DISCOUNT_CODE", nullable = false)

    private char discountCode;



    @Column(name = "DESCRIPTION")

    private String description;



    @OneToMany(cascade = CascadeType.ALL, mappedBy = "productCode")

    @Cache(usage = CacheConcurrencyStrategy.READ_WRITE)

    private Collection<Product> productCollection;


    ......

After recompiling SimpleJpaHibernateApp and invoking its "Listing Products" page for ProdCode="SW" (Figure 4.3.7), the JMX statistics collected by JConsole are shown :

* Hibernate JMX statistics in Figure 4.4.1

* Ehcache JMX statistics

  • Class Cache for simpleJpaHibernateApp.entities.ProductCode, in Figure 4.4.2
  • Class Cache for simpleJpaHibernateApp.entities.Product, in Figure 4.4.3
  • Collection Cache simpleJpaHibernateApp.entities.ProductCode.productionCollection, in Figure 4.4.4

 

Figure 4.4.1 - JConsole showing Hibernate JMX statistics, on SimpleJpaHibernateApp using @Cache Annotation (to enable Collection Cache), as compared to Figure 4.3.8 for SimpleJpaHibernateApp using JPA Query

Figure 4.4.2 - JConsole showing Ehcache JMX Class Cache Statistics for ProductCode, on SimpleJpaHibernateApp using @Cache Annotation to enable Collection Cache, as compared to Figure 4.3.9 for SimpleJpaHibernateApp using JPA Query

Figure 4.4.3 - JConsole showing Ehcache JMX Class Cache Statistics for Product, on SimpleJpaHibernateApp using @Cache Annotation to enable Collection Cache, as compared to Figure 4.3.10 for SimpleJpaHibernateApp using JPA Query

Figure 4.4.4 - JConsole showing Ehcache JMX Collection Cache Statistics for ProductCode.productCollection, on SimpleJpaHibernateApp using @Cache Annotation to enable Collection Cache (Collection Cache not used in SimpleJpaHibernateApp using JPA Query)

Resulting from the above JMX statistics collected on Hibernate and Ehcache, an indicative comparison of cache and query statistics for the same use case can be tabulated, e.g. for the mentioned case of querying all the 6 Product's associated with ProductCode where ProdCode="SW", showing the following major observations :

  • Querying using entity collection causes slightly more entity loading (28 vs 29) but, at the same time, more utilisation of entity class cache and Hibernate 2nd level cache
    • (2ndLevelCacheHit of 2 vs 109, for the respective cases)
  • Querying using entity collection improves query by :
    • requiring more simple query (compare the different QueryExecutionMaxTimeQueryString's)
    • reducing time of the longest query execution (QueryExecutionMaxTime from 181 ms to 60 ms)
    • reducing number of queries required (QueryExecutionCount from 27 to 20)

 

  Using JPA Query
with SQL Joint
Using Entity Collection
& Collection Cache
Hibernate JMX Statistics    
Entity Load Count 28 29
2nd Level Cache Hit 2 109
2nd Level Cache Miss 1 2
2nd Level Cache Put 28 30
Query Execution Count 27 20
Query Execution Max Time (ms) 181 60
Query Execution Max Time Query String select count(o)
from Product as o where o.productCode.prodCode
= :selectProdCode;
select object(o)
from Product as o;
Ehcache JMX Statistics    
ProductCode Cache Hit / Miss 3 / 13 8 / 16
Product Cache Hit / Miss 0 / 8 48 / 8
ProductCode.productCollection Cache Hit / Miss Not Available 6 / 2

Notes:

  • Relative values of QueryExecutionMaxTime may differ slightly in different testing environments and value above are just the results collected during my testings.
  • The new structure of the SimpleJpaHibernateApp application shown as NetBeans Projects is included for reference :
Figure 4.4.5 - New Structure of SimpleJpaHibernateApp NetBeans Project

 

Summary

To summarise, the above shows :

  • ways of extending JSF-Hibernate applications to enable JMX monitoring on its Java object/relational persistence (Hibernate v3) and cache (Ehcache 1.3.0) implementations, for both Hibernate v3 and JPA-with-Hibernate applications
  • an example (using SimpleJpaHibernateApp) of how JMX statistics enable comparison of query execution and cache utilisation for application providing same functionalities but using different implementation strategies

Note: While only JMX statistics for Java object/relational persistence (Hibernate v3) and cache (Ehcache 1.3.0) implementations are discussed above, application-specific JMX statistics can also be gathered by building custom JMX MBeans, e.g. as shown in the NetBeans tutorial "Getting Started with JMX Monitoring in NetBeans IDE 5.0".

Acknowledgements

Special thanks to Greg Luck for his collaboration in the configuration of HibernateTravelPOJO and SimpleJpaHibernateApp to enable JMX monitoring on Ehcache 1.3.0  released earlier in June 11, 2007.

Resources

Note: All the 3 application source packages can either be opened and compiled in NetBeans 5.5 or above, or compiled by Ant 1.6.5 or above.

Related Topics >>