Merge branch 'develop' into remoting-4.0
[taxeditor.git] / eu.etaxonomy.taxeditor.cdmlib / src / main / java / eu / etaxonomy / taxeditor / remoting / cache / CdmRemoteCacheManager.java
index b8998c221d14378179e14a0c055d6ffe31b4411a..84f88c24fb3c51a19b1d4d70bb0e12aa271b2f2e 100644 (file)
 package eu.etaxonomy.taxeditor.remoting.cache;
 
-import java.io.InputStream;
-import java.util.HashSet;
-import java.util.Set;
-
 import net.sf.ehcache.Cache;
 import net.sf.ehcache.CacheException;
 import net.sf.ehcache.CacheManager;
 import net.sf.ehcache.config.CacheConfiguration;
 import net.sf.ehcache.config.SizeOfPolicyConfiguration;
 
-import org.springframework.core.io.ClassPathResource;
-import org.springframework.core.io.Resource;
+import org.apache.log4j.Logger;
 
 
 public class CdmRemoteCacheManager {
 
-       private CacheManager cdmlibModelCacheManager;
+    private static final Logger logger = Logger.getLogger(CdmRemoteCacheManager.class);
 
-       private static CdmRemoteCacheManager cdmRemoteCacheManager = null;
 
-       private final Set<CdmTransientEntityCacher> transientEntityCachers = new HashSet<CdmTransientEntityCacher>();
+    private Cache cdmlibModelCache;
 
-    public static final Resource CDMLIB_CACHE_MANAGER_CONFIG_RESOURCE =
-            new ClassPathResource("cdmlib-ehcache.xml");
+    private static CdmRemoteCacheManager cdmRemoteCacheManager = null;
 
-    public static final String CDM_MODEL_CACHE_MGR_NAME = "cdmlibModelCacheManager";
     public static final String CDM_MODEL_CACHE_NAME = "cdmModelGetMethodsCache";
 
+    private static Thread initThread;
+
+    private static boolean cacheInitialised = false;
 
     public enum CdmCacheManagerType {
-       CDMLIB_MODEL,
-       DEFAULT
+        CDMLIB_MODEL,
+        DEFAULT
     }
 
     public static CdmRemoteCacheManager getInstance(){
-       if(cdmRemoteCacheManager == null) {
-               cdmRemoteCacheManager = new CdmRemoteCacheManager();
-       }
-       return cdmRemoteCacheManager;
+
+        if(cdmRemoteCacheManager == null) {
+            cdmRemoteCacheManager = new CdmRemoteCacheManager();
+        }
+        return cdmRemoteCacheManager;
     }
     private CdmRemoteCacheManager() {
 
 
-       try {
-               // NOTE:Programmatically creating the cache manager may solve the problem of
-               //      recreating data written to disk on startup
-               //      see https://stackoverflow.com/questions/1729605/ehcache-persist-to-disk-issues
-               //String cacheFilePath = CDMLIB_CACHE_MANAGER_CONFIG_RESOURCE.getFile().getAbsolutePath();
-               InputStream in = this.getClass().getClassLoader().getResourceAsStream("cdmlib-ehcache.xml");
+        try {
+            // NOTE:Programmatically creating the cache manager may solve the problem of
+            //      recreating data written to disk on startup
+            //      see https://stackoverflow.com/questions/1729605/ehcache-persist-to-disk-issues
+            //String cacheFilePath = CDMLIB_CACHE_MANAGER_CONFIG_RESOURCE.getFile().getAbsolutePath();
+            //InputStream in = this.getClass().getClassLoader().getResourceAsStream("cdmlib-ehcache.xml");
 
             SizeOfPolicyConfiguration sizeOfConfig = new SizeOfPolicyConfiguration();
             sizeOfConfig.setMaxDepth(1000);
             sizeOfConfig.setMaxDepthExceededBehavior("abort");
 
-               CacheConfiguration modelcc = new CacheConfiguration(CDM_MODEL_CACHE_NAME, 0)
+            CacheConfiguration modelcc = new CacheConfiguration(CDM_MODEL_CACHE_NAME, 0)
             .eternal(true)
             .statistics(true)
             .sizeOfPolicy(sizeOfConfig)
             .overflowToOffHeap(false);
 
-               Cache modelCache = new Cache(modelcc);
+            cdmlibModelCache = new Cache(modelcc);
+
+            CacheManager.create().addCache(cdmlibModelCache);
+            initCdmModelCache(cdmlibModelCache);
 
-                       cdmlibModelCacheManager = CacheManager.create(CDM_MODEL_CACHE_MGR_NAME);
-                       cdmlibModelCacheManager.addCache(modelCache);
+        } catch (CacheException e) {
+            throw new CdmClientCacheException(e);
+        }
 
-               } catch (CacheException e) {
-                       throw new CdmClientCacheException(e);
-               }
+    }
+
+    private void initCdmModelCache(final Cache cache) {
+
+        initThread = new Thread() {
+            @Override
+            public void run(){
+                synchronized (cdmlibModelCache) {
+                    CdmModelCacher cmdmc = new CdmModelCacher();
+                    cmdmc.cacheGetterFields(cache);
+                    cacheInitialised = true;
+                    logger.info("Initialisation of CDM getter fields complete");
+                    cdmlibModelCache.notify();
+                }
+            }
+
+        };
+        initThread.start();
+    }
 
+    public Cache getCdmModelGetMethodsCache(){
+        //Note : Even though we synchronize this method, the cache can be simply
+        //       retrieved using CacheManager.create().getCache(CDM_MODEL_CACHE_NAME)
+        //       in which case the cache may not be fully initialised
+        synchronized (cdmlibModelCache) {
+            while(!cacheInitialised) {
+                try {
+                    logger.info("Waiting for initialisation of CDM getter fields to complete ...");
+                    cdmlibModelCache.wait();
+                } catch (InterruptedException e) {}
+            }
+        }
+        logger.info("CDM getter fields cache initialised");
+        return cdmlibModelCache;
     }
 
-       public Cache getCdmModelGetMethodsCache(){
-               return cdmlibModelCacheManager.getCache(CDM_MODEL_CACHE_NAME);
-       }
-
-       public CacheManager getCdmModelGetMethodsCacheManager() {
-           return cdmlibModelCacheManager;
-       }
-
-       public CacheManager getDefaultCacheManager() {
-           return CacheManager.create();
-       }
-
-       public void shutdown(CdmCacheManagerType ccmt) {
-               CacheManager cm;
-               switch(ccmt) {
-               case CDMLIB_MODEL:
-                       cdmlibModelCacheManager.shutdown();
-                       break;
-               case DEFAULT:
-                       cm = CacheManager.create();
-                       cm.shutdown();
-                       break;
-               default:
-                       //do nothing
-               }
-       }
+    public static void removeEntityCaches() {
+        CacheManager cm = CacheManager.create();
+        String[] cacheNames = CacheManager.create().getCacheNames();
+        for(String cacheName : cacheNames) {
+            if(!cacheName.equals(CDM_MODEL_CACHE_NAME)) {
+                cm.removeCache(cacheName);
+            }
+        }
+    }