Project

General

Profile

Download (5.56 KB) Statistics
| Branch: | Tag: | Revision:
1
package eu.etaxonomy.cdm.api.cache;
2

    
3
import java.util.UUID;
4

    
5
import org.apache.log4j.Logger;
6
import org.springframework.beans.factory.annotation.Autowired;
7

    
8
import eu.etaxonomy.cdm.model.ICdmUuidCacher;
9
import eu.etaxonomy.cdm.model.common.CdmBase;
10
import net.sf.ehcache.Cache;
11
import net.sf.ehcache.CacheManager;
12
import net.sf.ehcache.Element;
13
import net.sf.ehcache.config.CacheConfiguration;
14
import net.sf.ehcache.config.CacheConfiguration.CacheEventListenerFactoryConfiguration;
15
import net.sf.ehcache.store.MemoryStoreEvictionPolicy;
16

    
17
/**
18
 * CDM Entity Cacher class based on EhCache.
19
 * The cacher allows null values to be cached.
20
 *
21
 * @author cmathew
22
 *
23
 * @param <T>
24
 */
25

    
26
public abstract class CdmCacher implements ICdmUuidCacher {
27

    
28
    public static final Logger logger = Logger.getLogger(CdmCacher.class);
29

    
30
    @Autowired
31
    public CacheManager cacheManager;
32

    
33
    public static final String DEFAULT_CACHE_NAME = "defaultCache"; //TODO compare with CacheConfiguration where the name for the default cache is 'default', Why another name here?
34

    
35
    /**
36
     * Constructor which initialises a singleton {@link net.sf.ehcache.CacheManager}
37
     *
38
     */
39
    public CdmCacher() {
40
        init();
41
    }
42

    
43
    /**
44
     * Initialises an empty singleton {@link net.sf.ehcache.CacheManager} and
45
     * sets itself as the cacher object in specific CDM Entity objects.
46
     *
47
     */
48
    private void init() {
49
        setup();
50
    }
51

    
52
    protected abstract void setup();
53

    
54
    /**
55
     * Returns the singleton default cache manager.
56
     * @param conf
57
     *
58
     * @return
59
     */
60
    public void addCacheManager(CacheManager cacheManager) {
61

    
62
        if(this.cacheManager == null){
63
            this.cacheManager = cacheManager;
64
        } else {
65
            logger.error("There is already a CacheManager configured.");
66
        }
67
    }
68

    
69
    /**
70
     * Returns the default cache configuration.
71
     *
72
     * @return
73
     */
74
    protected CacheConfiguration getDefaultCacheConfiguration() {
75
        CacheEventListenerFactoryConfiguration factory;
76
        // For a better understanding on how to size caches, refer to
77
        // http://ehcache.org/documentation/configuration/cache-size
78

    
79
        CacheConfiguration cc = new CacheConfiguration(DEFAULT_CACHE_NAME, 500)
80
                .memoryStoreEvictionPolicy(MemoryStoreEvictionPolicy.LFU)
81
                .eternal(false)
82
                // default ttl and tti set to 2 hours
83
                .timeToLiveSeconds(60*60*2)
84
                .timeToIdleSeconds(60*60*2)
85
                .statistics(true);
86

    
87
        return cc;
88
    }
89

    
90
    /**
91
     * Returns the default cache
92
     *
93
     * @return
94
     */
95
    public Cache getDefaultCache() {
96
        Cache defaultCache = cacheManager.getCache(DEFAULT_CACHE_NAME);
97
        if(defaultCache == null) {
98
            // Create default cache
99
            cacheManager.addCache(DEFAULT_CACHE_NAME);
100
            defaultCache = cacheManager.getCache(DEFAULT_CACHE_NAME);
101
            //FIXME write test to check if default config as defined in EhCacheConfiguration is being used
102
        }
103
        return defaultCache;
104
    }
105

    
106
    /**
107
     * Gets the cache element corresponding to the given {@link java.util.UUID}
108
     *
109
     * @param uuid
110
     * @return
111
     */
112
    public Element getCacheElement(UUID uuid) {
113
        return getDefaultCache().get(uuid);
114
    }
115

    
116
    @Override
117
    public  void put(UUID uuid, CdmBase cdmEntity) {
118
        CdmBase cachedCdmEntity = getFromCache(uuid);
119
        if(cachedCdmEntity == null) {
120
            getDefaultCache().put(new Element(uuid, cdmEntity));
121
        }
122
    }
123

    
124
    @Override
125
    public CdmBase load(UUID uuid) {
126
        Element e = getCacheElement(uuid);
127

    
128
        CdmBase cdmEntity;
129
        if (e == null) {
130
            // nothing in the cache for "key" (or expired) ... re-load the entity
131
            cdmEntity = findByUuid(uuid);
132
            // currently default cache is a non-null cache
133
            // We would like to have the possibility to put null values in the cache,
134
            // but we need to first distinguish between real null values and null values
135
            // returned by the service is the type of class does not match
136
            if(cdmEntity != null) {
137
                put(uuid, cdmEntity);
138
            }
139
        } else {
140
            // there is a valid element in the cache, however getObjectValue() may be null
141
            cdmEntity = (CdmBase)e.getObjectValue();
142
        }
143
        return cdmEntity;
144
    }
145

    
146

    
147
    @Override
148
    public  CdmBase getFromCache(UUID uuid) {
149
        Element e = getCacheElement(uuid);
150
        if (e == null) {
151
            return null;
152
        } else {
153
            return(CdmBase)e.getObjectValue();
154
        }
155
    }
156

    
157
    @Override
158
    public CdmBase getFromCache(CdmBase cdmBase) {
159
        return getFromCache(cdmBase.getUuid());
160
    }
161

    
162

    
163
    @Override
164
    public void put(CdmBase cdmEntity) {
165
        if(cdmEntity != null) {
166
            put(cdmEntity.getUuid(), cdmEntity);
167
        }
168
    }
169

    
170
    @Override
171
    public abstract CdmBase load(CdmBase cdmEntity);
172

    
173

    
174
    @Override
175
    public boolean exists(UUID uuid) {
176
        return getCacheElement(uuid) != null;
177
    }
178

    
179
    @Override
180
    public boolean exists(CdmBase cdmBase) {
181
        if(cdmBase != null) {
182
            return exists(cdmBase.getUuid());
183
        }
184
        return false;
185

    
186
    }
187

    
188
    @Override
189
    public boolean existsAndIsNotNull(UUID uuid) {
190
        Element e = getCacheElement(uuid);
191
        CdmBase cdmEntity;
192
        if (e != null) {
193
            return e.getObjectValue() != null;
194
        }
195
        return false;
196
    }
197

    
198
    /**
199
     * Finds CDM Entity by uuid
200
     *
201
     * @param uuid
202
     * @return
203
     */
204
    protected abstract CdmBase findByUuid(UUID uuid);
205

    
206
}
(1-1/2)