2016-03-30 12 views
1

Ich bin neu im frühling, überwintern, c3p0 & ehcache. Ich entwickle eine Anwendung vollständig mit Java-Konfiguration außer web.xml. Ich muss den Second-Level-Cache in meiner App verwenden. So habe ich folgenden Codefeder + überwintern + c3p0 + ehcache java konfiguration

import net.sf.ehcache.config.CacheConfiguration; 

import org.springframework.cache.CacheManager; 
import org.springframework.cache.annotation.CachingConfigurer; 
import org.springframework.cache.annotation.EnableCaching; 
import org.springframework.cache.ehcache.EhCacheCacheManager; 
import org.springframework.cache.interceptor.CacheErrorHandler; 
import org.springframework.cache.interceptor.CacheResolver; 
import org.springframework.cache.interceptor.KeyGenerator; 
import org.springframework.cache.interceptor.SimpleKeyGenerator; 
import org.springframework.context.annotation.Bean; 
import org.springframework.context.annotation.Configuration; 

@Configuration 
@EnableCaching 
public class CachingConfig implements CachingConfigurer{ 

    @Bean(destroyMethod="shutdown") 
    public net.sf.ehcache.CacheManager ehCacheManager() { 
     CacheConfiguration cacheConfiguration = new CacheConfiguration(); 
     cacheConfiguration.setName("myCacheName"); 
     cacheConfiguration.setMemoryStoreEvictionPolicy("LRU"); 
     cacheConfiguration.setMaxEntriesLocalHeap(1000); 

     net.sf.ehcache.config.Configuration config = new net.sf.ehcache.config.Configuration(); 
     config.addCache(cacheConfiguration); 

     return net.sf.ehcache.CacheManager.newInstance(config); 
    } 

    @Bean 
    @Override 
    public CacheManager cacheManager() { 
     return new EhCacheCacheManager(ehCacheManager()); 
    } 

    @Override 
    public CacheResolver cacheResolver() { 
     return null; 
    } 

    @Override 
    public CacheErrorHandler errorHandler() { 
     return null; 
    } 

    @Override 
    public KeyGenerator keyGenerator() { 
     return new SimpleKeyGenerator(); 
    } 

} 

In web.xml Ich habe es als

<context-param> 
    <param-name>contextConfigLocation</param-name> 
    <param-value> 
     ApplicationContextConfiguration 
     CachingConfig 
    </param-value> 
    </context-param> 

Mein ApplicationContextConfiguration ist

import java.beans.PropertyVetoException; 
import java.io.BufferedReader; 
import java.io.IOException; 
import java.io.InputStreamReader; 
import java.util.Properties; 

import org.springframework.context.annotation.Bean; 
import org.springframework.context.annotation.ComponentScan; 
import org.springframework.context.annotation.Configuration; 
import org.springframework.dao.annotation.PersistenceExceptionTranslationPostProcessor; 
import org.springframework.orm.jpa.JpaVendorAdapter; 
import org.springframework.orm.jpa.LocalContainerEntityManagerFactoryBean; 
import org.springframework.orm.jpa.vendor.HibernateJpaVendorAdapter; 
import org.springframework.transaction.annotation.EnableTransactionManagement; 

import com.mchange.v2.c3p0.ComboPooledDataSource; 


@Configuration 
@EnableTransactionManagement 
public class ApplicationContextConfiguration 
{ 
     @Bean 
     public LocalContainerEntityManagerFactoryBean entityManagerFactory() throws IOException { 
      LocalContainerEntityManagerFactoryBean entityManagerFactory = new LocalContainerEntityManagerFactoryBean(); 
      entityManagerFactory.setDataSource(pooledDataSource()); 
      entityManagerFactory.setPackagesToScan(new String[] { "*" });  
      JpaVendorAdapter vendorAdapter = new HibernateJpaVendorAdapter(); 
      entityManagerFactory.setJpaVendorAdapter(vendorAdapter); 
      entityManagerFactory.setJpaProperties(additionalProperties());  
      return entityManagerFactory; 
     } 

     @Bean 
     public ComboPooledDataSource pooledDataSource() throws IOException{ 
      ComboPooledDataSource dataSource = new ComboPooledDataSource(); 
      Properties properties = new Properties(); 

      BufferedReader input = new BufferedReader (new InputStreamReader (getClass().getResourceAsStream("/config/hibernate.properties"))); 
      properties.load(input); 
      try { 
       dataSource.setDriverClass(properties.getProperty("hibernate.connection.driver_class")); 
      } catch (PropertyVetoException e) { 
       e.printStackTrace(); 
      } 
      dataSource.setJdbcUrl(properties.getProperty("hibernate.connection.url")); 
      dataSource.setUser(properties.getProperty("hibernate.connection.username")); 
      dataSource.setPassword(properties.getProperty("hibernate.connection.password")); 

      dataSource.setMaxPoolSize(Integer.parseInt(properties.getProperty("hibernate.c3p0.max_size"))); 
      dataSource.setMinPoolSize(Integer.parseInt(properties.getProperty("hibernate.c3p0.min_size"))); 
      dataSource.setCheckoutTimeout(Integer.parseInt(properties.getProperty("hibernate.c3p0.timeout"))); 
      dataSource.setMaxStatements(Integer.parseInt(properties.getProperty("hibernate.c3p0.max_statements"))); 
      dataSource.setIdleConnectionTestPeriod(Integer.parseInt(properties.getProperty("hibernate.c3p0.idle_test_period"))); 
      dataSource.setAcquireIncrement(Integer.parseInt(properties.getProperty("hibernate.c3p0.acquire_increment"))); 

      return dataSource; 
     } 

     @Bean 
     public PersistenceExceptionTranslationPostProcessor exceptionTranslation(){ 
      return new PersistenceExceptionTranslationPostProcessor(); 
     } 

     Properties additionalProperties() throws IOException { 
      Properties properties = new Properties(); 
      Properties hibernateProperties = new Properties();   
      BufferedReader input = new BufferedReader (new InputStreamReader (getClass().getResourceAsStream("/config/hibernate.properties")));     
      hibernateProperties.load(input);   
      properties.setProperty("hibernate.dialect", hibernateProperties.getProperty("hibernate.dialect")); 
      return properties; 
     } 

} 

Wenn ich zu laufen versuchen, erhalte ich folgende Fehler

org.hibernate.cache.NoCacheRegionFactoryAvailableException: Second-level cache is used in the application, but property hibernate.cache.region.factory_class is not given, please either disable second level cache or set correct region factory class name to property hibernate.cache.region.factory_class (and make sure the second level cache provider, hibernate-infinispan, for example, is available in the classpath). 

I verstanden, dass ich hinzufügen muss

<property name="hibernate.cache.region.factory_class">net.sf.ehcache.hibernate.EhCacheRegionFactory</property> 

aber nicht sicher, wo und wie Sie es über Java-Konfiguration hinzufügen. Kann hier bitte jemand helfen.

Muss ich außerdem Folgendes hinzufügen?

<property name="hibernate.cache.provider_class">org.hibernate.cache.EhCacheProvider</property> 
<property name="hibernate.cache.use_second_level_cache">true</property> 
<property name="hibernate.cache.use_query_cache">true</property> 
+0

Wird Ihre Anwendung derzeit mit dem Second-Level-Cache ausgeführt? Ich meine, können Sie die Entitäten ohne Second-Level-Cache speichern und abrufen? Und warum willst du 'CachingConfigurer' verwenden? weil das nichts mit dem Second-Level-Cache von Hibernate zu tun hat, auf den Sie sich beziehen? –

+0

@Madhusudana Reddy Sunnapu - ja ich bin in der Lage, ohne Second-Level-Cache –

Antwort

1

Unter der Annahme, dass Sie die Einheiten abrufen können, und Sie wollen nur Second Level Cache aktivieren:

Fügen Sie die folgenden Eigenschaften in Ihrer vorhandenen additionalProperties() Methode.

properties.setProperty("hibernate.cache.region.factory_class", "org.hibernate.cache.ehcache.SingletonEhCacheRegionFactory"); 
properties.setProperty("hibernate.cache.use_second_level_cache", "true"); 
properties.setProperty("hibernate.cache.use_query_cache", "true"); 

und auf der entity Sie Second Level Cache Platz @Cache Anmerkung auf dieser Entität ex aktivieren: @Cache(usage=CacheConcurrencyStrategy.READ_WRITE)

Sie CachingConfig Klasse entfernen können, dass nichts mit der Aktivierung des Cache zweiter Ebene für Hibernate zu tun hat.

+0

Dankeschön es funktioniert für mich –