Предоставление статистики Hibernate (кеш) через JMX с помощью Spring в Tomcat - PullRequest
2 голосов
/ 09 мая 2011

Сбор статистики Hibernate / Ehcache и предоставление ее через JMX в настройках на основе Spring кажется простым.В Интернете есть много ресурсов, которые помогают, например, http://snippets.dzone.com/posts/show/11159

Однако все эти статьи предполагают, что одна из них работает с какой-то фабрикой сеансов Hibernate.Я не - мои сущности аннотированы JPA, и я использую javax.persistence.EntityManager.Если бы я развертывал в контейнер Java EE, я мог бы получить фабрику сеансов Hibernate через JNDI, как описано здесь http://internna.blogspot.com/2007/08/hibernate-statistics-in-enterprise-5.html, но я на Tomcat ...

Как это сделатьэтот?Я еще не нашел решение.

Если бы у меня была ссылка на Ehcache CacheManager, я мог бы попробовать что-то вроде:

<context:mbean-server />
<bean class="net.sf.ehcache.management.ManagementService" init-method="init">
  <constructor-arg ref="..myCacheManager.."/>
  <constructor-arg ref="mbeanServer"/>
  <constructor-arg value="true"/>
  <constructor-arg value="true"/>
  <constructor-arg value="true"/>
  <constructor-arg value="true"/>
</bean>

Поскольку менеджер кэша создаетсяHibernate (т.е. это не бин Spring) не будет работать.Я попытался заменить эту ссылку на

<constructor-arg><bean id="cacheManager" class="net.sf.ehcache.CacheManager" factory-method="getInstance"/></constructor-arg>

, надеясь, что каким-то образом поймаю нужный экземпляр.Также не будет работать, поскольку это фактически создаст новый экземпляр диспетчера кэша.

Ответы [ 6 ]

3 голосов
/ 21 мая 2011

Я недавно создал пример веб-приложения на основе Spring, которое очень четко включает JMX для последних версий Spring, Hibernate и Ehcache.

Имеются примеры как для доступа на основе EntityManager, так и для доступа к DAO (включая транзакции!).Также показано, как сделать внедрение на основе аннотаций, чтобы избежать необходимости использовать xml-конфигурацию Spring для bean-компонентов.Существует даже пример сервлета на основе SpringMVC с использованием аннотаций.По сути, это версия довольно мощного сервера приложений на базе Spring, работающего поверх любого механизма сервлетов.

Пока не задокументировано, но я скоро к этому вернусь.Взгляните на файлы конфигурации и исходный код, и это должно быть довольно ясно.

Мотивация этого заключается в том, что я устал от всех сумасшедших постов в блоге с 50 различными способами настройки и, наконец, создал единый простой источник, из которого люди могут работать.Он работает на github, поэтому не стесняйтесь раскошелиться на проект и делать с ним все, что захотите.

https://github.com/lookfirst/fallback

2 голосов
/ 30 августа 2013

Вы можете фактически открыть любой CacheManager, используя Spring Expression Language .

<bean id="hibernateCacheManagement" class="net.sf.ehcache.management.ManagementService" init-method="init" >
    <constructor-arg value="#{T(net.sf.ehcache.CacheManager).getCacheManager('CACHE_NAME')}"/>
    <constructor-arg><ref bean="mbeanServer"/></constructor-arg>
    <constructor-arg value="true"/>
    <constructor-arg value="true"/>
    <constructor-arg value="true"/>
    <constructor-arg value="true"/>
</bean>

Где CACHE_NAME - это имя кэша, настроенного в файле ehcache.xml.

<ehcache name="CACHE_NAME">
    ...
</ehcache>
2 голосов
/ 10 мая 2011

JPA EntityManager предоставляет базовый сеанс Hibernate, так что вы можете получить на его Factory:

   public static Session getHibernateSession(EntityManager entityManager) {
        Session session;
        if (entityManager.getDelegate() instanceof EntityManagerImpl) {
            EntityManagerImpl entityManagerImpl = (EntityManagerImpl) entityManager.getDelegate();
            session = entityManagerImpl.getSession();
        } else {
            session = (Session) entityManager.getDelegate();
        }

        return session;
    }

Затем вы можете использовать эту сессию для включения статистики , как мы это делали в RHQ проекте

1 голос
/ 12 января 2013

Я закончил писать следующий класс

HibernateStatisticsJmxРегистрация

import javax.management.JMException;
import javax.management.MBeanServer;
import javax.management.ObjectName;
import javax.persistence.EntityManagerFactory;

import org.hibernate.SessionFactory;
import org.hibernate.ejb.HibernateEntityManagerFactory;
import org.hibernate.jmx.StatisticsService;
import org.springframework.beans.factory.annotation.Autowired;

/**
 * Provides code to register Hibernate's statistics bean with a JMX MBean server. Assumes that both
 * the MBeanServer and the EntityManagerFactory are available as Spring-managed beans. Note that
 * while registering this class enables the collection of statistics even if that was previously
 * disabled.
 * <p>
 * May become obsolete once <a href="https://hibernate.onjira.com/browse/HHH-6034">HHH-6034</a> is
 * implemented. Even if not the confusing situation abround the meanwhile deprecated
 * {@link StatisticsService} should be clear then.
 */
@SuppressWarnings({"deprecation", "javadoc" })
public class HibernateStatisticsJmxRegistration {

  @Autowired
  private EntityManagerFactory entityManagerFactory;

  @Autowired
  private MBeanServer mbeanServer;

  private ObjectName objectName;

  private String jmxObjectName = "org.hibernate:name=HibernateStatistics";

  /**
   * Registers the statistics MBean that wraps a Hibernate session factory. The bean is registered
   * under the name provided by {@link HibernateStatisticsJmxRegistration#getJmxObjectName()}.
   *
   * @throws JMException if anything fails..
   * @see HibernateStatisticsJmxRegistration#unregister()
   */
  public void register() throws JMException {
    final SessionFactory sessionFactory = ((HibernateEntityManagerFactory) entityManagerFactory).getSessionFactory();

    objectName = new ObjectName(jmxObjectName);

    final StatisticsService statsMBean = new StatisticsService();
    statsMBean.setSessionFactory(sessionFactory);
    statsMBean.setStatisticsEnabled(true);
    mbeanServer.registerMBean(statsMBean, objectName);
  }

  /**
   * Unregisters the MBean that was registered.
   *
   * @throws JMException if the de-registration fails
   * @see HibernateStatisticsJmxRegistration#register()
   */
  public void unregister() throws JMException {
    mbeanServer.unregisterMBean(objectName);
  }

  /**
   * Override the default JMX object name. Obviously you need to call this method before
   * registration for it to have any effect. The string must comply to the rules described in
   * {@link ObjectName}. Suggested is {@code <domain>:name=<name>}.
   *
   * @param jmxObjectName the name to use during registration
   */
  public void setJmxObjectName(String jmxObjectName) {
    this.jmxObjectName = jmxObjectName;
  }
}

Пружинная конфигурация

<!-- Setting up Ehcache manager for various caches (offer facade, images). -->
<bean id="ehCacheManager" class="org.springframework.cache.ehcache.EhCacheManagerFactoryBean">
  <property name="configLocation" value="classpath:ehcache.xml" />
</bean>  
<ehcache:annotation-driven cache-manager="ehCacheManager" />

<!-- Exposing cache statistics through JMX. -->
<context:mbean-server />
<bean class="net.sf.ehcache.management.ManagementService" init-method="init">
  <constructor-arg ref="ehCacheManager"/>
  <constructor-arg ref="mbeanServer"/>
  <constructor-arg value="true"/>
  <constructor-arg value="true"/>
  <constructor-arg value="true"/>
  <constructor-arg value="true"/>
</bean>    
<bean class="HibernateStatisticsJmxRegistration"
      init-method="register" destroy-method="unregister" />
0 голосов
/ 12 июня 2015

Очень хорошо, но это тоже работает, где (угадайте, что) mbeanServer - это имя компонента MBean Server, а entityManagerFactory - это имя компонента EntityManagerFactory:

<bean id="managementService-ehcache-hibernate"
    class="net.sf.ehcache.management.ManagementService"
    init-method="init"
    destroy-method="dispose">

    <constructor-arg value="#{T(org.springframework.security.util.FieldUtils).getFieldValue(@entityManagerFactory.cache.unwrap(T(org.hibernate.cache.spi.RegionFactory)),'manager')}"/>
    <constructor-arg ref="mbeanServer"/>
    <constructor-arg index="2" value="true"/>
    <constructor-arg index="3" value="true"/>
    <constructor-arg index="4" value="true"/>
    <constructor-arg index="5" value="true"/>
</bean>
0 голосов
/ 09 мая 2011

Spring предоставляет в JMX только его компоненты, но вы можете программно экспортировать ресурс через MBeanExporter.

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...