MockCdmEntitySessionManager, MockCdmEntitySession, ICdmEntitySessionManager, ICdmEntitySession, CdmEntitySessionManager,
CdmEntitySession : added new load method with choice to update client object graph
TermServiceRequestExecutor : using cacher instead of cache
ICachedCommonService, CachedCommonServiceImpl, ProxyUtils : moved utility methods to utility class
CdmServiceRequestExecutor : updating client object graph when calling merge
EntityCacherDebugResult : corrections for output string
CdmTransientEntityCacher : corrected cache configuration, added load methods with update choice, added service cacher check before put
CacheLoader : checking in recursive call if collection and maps are already visited
CdmRemotingException : added constructor with exception as argument
CdmServiceCacher : corrected cache configuration and loading of entities from default cache
import java.util.UUID;
+import net.sf.ehcache.config.CacheConfiguration;
+import net.sf.ehcache.config.SizeOfPolicyConfiguration;
+
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Component;
import eu.etaxonomy.cdm.model.common.DefinedTermBase;
import eu.etaxonomy.taxeditor.remoting.cache.CacheLoader;
import eu.etaxonomy.taxeditor.remoting.cache.CdmTransientEntityCacher;
+import eu.etaxonomy.taxeditor.service.TermServiceRequestExecutor;
/**
* Class which uses CDM services to cache cdm entities
@Component
public class CdmServiceCacher extends CdmCacher{
- @Autowired
- ITermService termService;
+ @Autowired
+ ITermService termService;
- private CacheLoader cacheLoader;
+ private CacheLoader cacheLoader;
- @Override
- protected void setup() {
- DefinedTermBase.setCacher(this);
- CdmTransientEntityCacher.setDefaultCacher(this);
- cacheLoader = new CacheLoader(this);
- }
+ @Override
+ protected void setup() {
+ DefinedTermBase.setCacher(this);
+ CdmTransientEntityCacher.setDefaultCacher(this);
+ TermServiceRequestExecutor.setDefaultCacher(this);
+ cacheLoader = new CacheLoader(this);
+ }
+
+ @Override
+ protected CacheConfiguration getDefaultCacheConfiguration() {
+ // For a better understanding on how to size caches, refer to
+ // http://ehcache.org/documentation/configuration/cache-size
- @Override
- protected CdmBase findByUuid(UUID uuid) {
- CdmBase term = termService.findWithoutFlush(uuid);
- return cacheLoader.load(term, true);
+ SizeOfPolicyConfiguration sizeOfConfig = new SizeOfPolicyConfiguration();
+ sizeOfConfig.setMaxDepth(100);
+ sizeOfConfig.setMaxDepthExceededBehavior("abort");
- }
+ return new CacheConfiguration(DEFAULT_CACHE_NAME, 0)
+ .eternal(true)
+ .statistics(true)
+ .sizeOfPolicy(sizeOfConfig)
+ .overflowToOffHeap(false);
+
+ }
+
+ @Override
+ protected CdmBase findByUuid(UUID uuid) {
+ CdmBase term = termService.findWithoutFlush(uuid);
+ return load(term);
+ }
/* (non-Javadoc)
* @see eu.etaxonomy.cdm.model.ICdmCacher#isCachable(eu.etaxonomy.cdm.model.common.CdmBase)
}
+ /* (non-Javadoc)
+ * @see eu.etaxonomy.cdm.api.cache.CdmCacher#load(eu.etaxonomy.cdm.model.common.CdmBase)
+ */
+ @Override
+ public CdmBase load(CdmBase cdmEntity) {
+ CdmBase cachedCdmEntity = getFromCache(cdmEntity);
+ // NOTE : only when no cached cdm entity exists we
+ // load the entire sub-graph, which means that the
+ // sub-graph is never updated if the input
+ // cdm entity graph is newer
+ if(cachedCdmEntity == null && isCachable(cdmEntity)) {
+ cachedCdmEntity = cacheLoader.load(cdmEntity, true, false);
+ }
+ return cachedCdmEntity;
+ }
+
+
}
package eu.etaxonomy.taxeditor.remoting;
public class CdmRemotingException extends RuntimeException {
-
+
/**
- *
+ *
*/
private static final long serialVersionUID = -560332689478356360L;
super(message);
}
+ public CdmRemotingException(Exception exception) {
+ super(exception);
+ }
+
}
private final Cache cdmlibModelCache;
+ private final ICdmCacher cdmServiceCacher;
+
public CacheLoader(ICdmCacher cdmCacher) {
+ this(cdmCacher, null);
+ }
+
+ public CacheLoader(ICdmCacher cdmCacher, ICdmCacher cdmServiceCacher) {
this.cdmCacher = cdmCacher;
this.cdmlibModelCache = CdmRemoteCacheManager.getInstance().getCdmModelGetMethodsCache();
+ this.cdmServiceCacher = cdmServiceCacher;
}
}
@SuppressWarnings("unchecked")
- public <T extends Object> T load(T obj, boolean recursive) {
+ public <T extends Object> T load(T obj, boolean recursive, boolean update) {
if(obj == null) {
return null;
}
if(obj instanceof CdmBase) {
- return (T) load((CdmBase)obj, recursive);
+ return (T) load((CdmBase)obj, recursive, update);
} else if (obj instanceof Map) {
- return (T) load((Map<T,T>)obj, recursive);
+ return (T) load((Map<T,T>)obj, recursive, update);
} else if (obj instanceof Collection) {
- return (T) load((Collection<T>)obj, recursive);
+ return (T) load((Collection<T>)obj, recursive, update);
}
return obj;
}
@SuppressWarnings("unchecked")
- private <T extends Object> T loadRecursive(T obj, Set<CdmBase> alreadyVisitedEntities) {
+ private <T extends Object> T loadRecursive(T obj, Set<Object> alreadyVisitedEntities, boolean update) {
if(obj == null) {
return null;
}
if(obj instanceof CdmBase) {
- return (T) loadRecursive((CdmBase)obj, alreadyVisitedEntities);
+ return (T) loadRecursive((CdmBase)obj, alreadyVisitedEntities, update);
} else if (obj instanceof Map) {
- return (T) load((Map<T,T>)obj, alreadyVisitedEntities);
+ return (T) load((Map<T,T>)obj, alreadyVisitedEntities, update);
} else if (obj instanceof Collection) {
- return (T) load((Collection<T>)obj, alreadyVisitedEntities);
+ return (T) load((Collection<T>)obj, alreadyVisitedEntities, update);
}
return obj;
}
- public <T extends Object> Map<T,T> load(Map<T,T> map, boolean recursive){
- if(map == null) {
- return null;
- }
+ public <T extends Object> Map<T,T> load(Map<T,T> map, boolean recursive, boolean update){
+
if(isRecursiveEnabled && recursive) {
logger.info("---- starting recursive load for cdm entity map");
- Set<CdmBase> alreadyVisitedEntities = new HashSet<CdmBase>();
- Map<T,T> cachedMap = load(map, alreadyVisitedEntities);
+ Set<Object> alreadyVisitedEntities = new HashSet<Object>();
+ Map<T,T> cachedMap = load(map, alreadyVisitedEntities, update);
alreadyVisitedEntities.clear();
logger.info("---- ending recursive load for cdm entity map \n");
return cachedMap;
} else {
- return load(map, null);
+ return load(map, null, update);
}
}
- private <T extends Object> Map<T,T> load(Map<T,T> map, Set<CdmBase> alreadyVisitedEntities){
+ private <T extends Object> Map<T,T> load(Map<T,T> map, Set<Object> alreadyVisitedEntities, boolean update){
+ //map = (Map<T,T>)deproxy(map);
+
if(map == null || map.isEmpty()) {
return map;
}
Object[] result = new Object[ map.size() * 2 ];
Iterator<Map.Entry<T,T>> iter = map.entrySet().iterator();
int i=0;
+ // to avoid ConcurrentModificationException
+ alreadyVisitedEntities.add(map);
while ( iter.hasNext() ) {
Map.Entry<T,T> e = iter.next();
result[i++] = e.getKey();
for(i=0; i<result.length;i++) {
if(alreadyVisitedEntities == null) {
- result[i] = load(result[i], false);
+ result[i] = load(result[i], false, update);
} else {
- result[i] = loadRecursive(result[i], alreadyVisitedEntities);
+ result[i] = loadRecursive(result[i], alreadyVisitedEntities, update);
}
}
map.clear();
return map;
}
- public <T extends Object> Collection<T> load(Collection<T> collection, boolean recursive){
- if(collection == null) {
- return null;
- }
+ public <T extends Object> Collection<T> load(Collection<T> collection, boolean recursive, boolean update){
Collection<T> loadedCollection;
if(isRecursiveEnabled && recursive) {
logger.info("---- starting recursive load for cdm entity collection");
- Set<CdmBase> alreadyVisitedEntities = new HashSet<CdmBase>();
- Collection<T> cachedCollection = load(collection, alreadyVisitedEntities);
+ Set<Object> alreadyVisitedEntities = new HashSet<Object>();
+ Collection<T> cachedCollection = load(collection, alreadyVisitedEntities, update);
alreadyVisitedEntities.clear();
logger.info("---- ending recursive load for cdm entity collection \n");
loadedCollection = cachedCollection;
} else {
- loadedCollection = load(collection, null);
+ loadedCollection = load(collection, null, update);
}
return loadedCollection;
}
@SuppressWarnings("unchecked")
- private <T extends Object> Collection<T> load(Collection<T> collection, Set<CdmBase> alreadyVisitedEntities){
+ private <T extends Object> Collection<T> load(Collection<T> collection, Set<Object> alreadyVisitedEntities, boolean update) {
+
+
+
+ if(collection == null || collection.isEmpty()) {
+ return collection;
+ }
int length = collection.size();
Object[] result = new Object[length];
Iterator<T> collectionItr = collection.iterator();
int count = 0;
+ // to avoid ConcurrentModificationException
+ alreadyVisitedEntities.add(collection);
while(collectionItr.hasNext()) {
Object obj = collectionItr.next();
if(alreadyVisitedEntities == null) {
- result[count] = load(obj, false);
+ result[count] = load(obj, false, update);
} else {
- result[count] = loadRecursive(obj, alreadyVisitedEntities);
+ result[count] = loadRecursive(obj, alreadyVisitedEntities, update);
}
count++;
* @param uuid
* @param cdmEntity
*/
- public CdmBase load(CdmBase cdmEntity, boolean recursive) {
+ public CdmBase load(CdmBase cdmEntity, boolean recursive, boolean update) {
if(cdmEntity == null) {
return null;
}
if(cachedCdmEntity == cdmEntity) {
return cachedCdmEntity;
}
- return cachedCdmEntity;
+
}
CdmBase loadedCdmBase;
if(isRecursiveEnabled && recursive) {
logger.info("---- starting recursive load for cdm entity " + cdmEntity.getClass().getName() + " with id " + cdmEntity.getId());
- Set<CdmBase> alreadyVisitedEntities = new HashSet<CdmBase>();
- CdmBase cb = loadRecursive(cdmEntity, alreadyVisitedEntities);
+ Set<Object> alreadyVisitedEntities = new HashSet<Object>();
+ CdmBase cb = loadRecursive(cdmEntity, alreadyVisitedEntities, update);
alreadyVisitedEntities.clear();
logger.info("---- ending recursive load for cdm entity " + cdmEntity.getClass().getName() + " with id " + cdmEntity.getId() + "\n");
loadedCdmBase = cb;
private CdmBase load(CdmBase cdmEntity) {
logger.info("loading object of type " + cdmEntity.getClass().getName() + " with id " + cdmEntity.getId());
+ cdmEntity = (CdmBase)ProxyUtils.deproxy(cdmEntity);
+
// start by looking up the cdm entity in the cache
CdmBase cachedCdmEntity = cdmCacher.getFromCache(cdmEntity);
}
}
- private CdmBase loadRecursive(CdmBase cdmEntity, Set<CdmBase> alreadyVisitedEntities) {
+ private CdmBase loadRecursive(CdmBase cdmEntity, Set<Object> alreadyVisitedEntities, boolean update) {
CdmBase cachedCdmEntity = load(cdmEntity);
-
+ if(cdmServiceCacher != null && cdmServiceCacher.exists(cachedCdmEntity)) {
+ return cachedCdmEntity;
+ }
// we want to recursive through the cdmEntity (and not the cachedCdmEntity)
// since there could be new or deleted objects in the cdmEntity sub-graph
// this object will be either a CdmBase or a Collection / Map
// with CdmBase as the generic type
- CdmBase cdmEntityInSubGraph = getCdmBaseTypeFieldValue(cdmEntity, cachedCdmEntity, field, alreadyVisitedEntities);
+ CdmBase cdmEntityInSubGraph = getCdmBaseTypeFieldValue(cdmEntity, cachedCdmEntity, field, alreadyVisitedEntities, update);
if(cdmEntityInSubGraph != null) {
//checkForIdenticalCdmEntity(alreadyVisitedEntities, cdmEntityInSubGraph);
if(!alreadyVisitedEntities.contains(cdmEntityInSubGraph)) {
logger.info("recursive loading object of type " + cdmEntityInSubGraph.getClass().getName() + " with id " + cdmEntityInSubGraph.getId());
- loadRecursive(cdmEntityInSubGraph, alreadyVisitedEntities);
+ loadRecursive(cdmEntityInSubGraph, alreadyVisitedEntities, update);
} else {
logger.info("object of type " + cdmEntityInSubGraph.getClass().getName() + " with id " + cdmEntityInSubGraph.getId() + " already visited");
}
private CdmBase getCdmBaseTypeFieldValue(CdmBase cdmEntity,
CdmBase cachedCdmEntity,
String fieldName,
- Set<CdmBase> alreadyVisitedEntities) {
+ Set<Object> alreadyVisitedEntities,
+ boolean update) {
// this method attempts to make sure that for any two objects found in
// the object graph, if they are equal then they should also be the same,
CdmBase cdmEntityInSubGraph = null;
+ if(update) {
+ // making sure that the field in cached cdm entity is always
+ // up-to-date by setting to the value of the cdm entity being loaded
+ // the only exception to this is found below
+ field.set(cachedCdmEntity, o);
+ }
if(o != null
&& !ProxyFactory.isProxyClass(o.getClass())
&& !(o instanceof PersistentCollection) ) {
+
if(CdmBase.class.isAssignableFrom(o.getClass())) {
logger.info("found initialised cdm entity '" + fieldName + "' in object of type " + clazz.getName() + " with id " + cdmEntity.getId());
cdmEntityInSubGraph = (CdmBase)o;
-
-
CdmBase cachedCdmEntityInSubGraph = cdmCacher.getFromCache(cdmEntityInSubGraph);
- // making sure that the field in cached cdm entity is always
- // up-to-date by setting to the value of the cdm entity being loaded
- // the only execption to this is found below
- field.set(cachedCdmEntity, o);
-
// the only exception to updating the field to the latest value
// is the case where the field has been already initialised, cached and
logger.info("setting cached + real value to '" + fieldName + "' in object of type " + clazz.getName() + " with id " + cdmEntity.getId());
field.set(cachedCdmEntity, cachedCdmEntityInSubGraph);
field.set(cdmEntity, cachedCdmEntityInSubGraph);
+ } else {
+ // hack to stop the recursion, since the field value object in cdmEntity
+ // is the same as the field value object in cachedCdmEntity
+ cdmEntityInSubGraph = null;
}
- cdmEntityInSubGraph = null;
}
- } else if(o instanceof Map) {
- loadRecursive((Map)o, alreadyVisitedEntities);
- } else if(o instanceof Collection) {
- loadRecursive((Collection)o, alreadyVisitedEntities);
+ } else if(o instanceof Map && !alreadyVisitedEntities.contains(o)) {
+ loadRecursive((Map)o, alreadyVisitedEntities, update);
+ } else if(o instanceof Collection && !alreadyVisitedEntities.contains(o)) {
+ loadRecursive((Collection)o, alreadyVisitedEntities, update);
}
}
// we return the original cdm entity in the sub graph because we
return false;
}
+
public static boolean isRecursiveEnabled() {
return isRecursiveEnabled;
}
import java.util.Collection;
import java.util.List;
import java.util.Map;
+import java.util.UUID;
import net.sf.ehcache.Cache;
import net.sf.ehcache.Element;
import net.sf.ehcache.config.CacheConfiguration;
import net.sf.ehcache.config.SizeOfPolicyConfiguration;
import net.sf.ehcache.statistics.LiveCacheStatistics;
-import net.sf.ehcache.store.MemoryStoreEvictionPolicy;
import org.apache.log4j.Logger;
- public static enum CollectionType {
- SET,
- LIST,
- MAP;
-
- @Override
- public String toString() {
- return this.name().toLowerCase();
- }
- }
-
-
public CdmTransientEntityCacher(String cacheId, ICdmEntitySessionManager cdmEntitySessionManager) {
this.cacheId = cacheId;
cache = new Cache(getEntityCacheConfiguration(cacheId));
CdmRemoteCacheManager.getInstance().getDefaultCacheManager().addCache(cache);
- cacheLoader = new CacheLoader(this);
+
this.cdmEntitySessionManager = cdmEntitySessionManager;
+ CdmBase fromCache = cdmServiceCacher.getFromCache(UUID.fromString("462a7819-8b00-4190-8313-88b5be81fad5"));
+
+ cacheLoader = new CacheLoader(this, cdmServiceCacher);
}
SizeOfPolicyConfiguration sizeOfConfig = new SizeOfPolicyConfiguration();
sizeOfConfig.setMaxDepth(10000);
sizeOfConfig.setMaxDepthExceededBehavior("abort");
- // For a better understanding on how to size caches, refer to
- // http://ehcache.org/documentation/configuration/cache-size
- return new CacheConfiguration(cacheId, 500)
- .memoryStoreEvictionPolicy(MemoryStoreEvictionPolicy.LFU)
- //.eternal(true);
- // default ttl and tti set to 2 hours
- .timeToLiveSeconds(60*60*2)
- .timeToIdleSeconds(60*60*2)
- .statistics(true)
- .sizeOfPolicy(sizeOfConfig);
-
+ return new CacheConfiguration(cacheId, 0)
+ .eternal(true)
+ .statistics(true)
+ .sizeOfPolicy(sizeOfConfig)
+ .overflowToOffHeap(false);
}
return CdmRemoteCacheManager.getInstance().getDefaultCacheManager().getCache(cacheId);
}
- public <T extends Object> T load(T obj, boolean recursive) {
- return cacheLoader.load(obj, recursive);
+ public <T extends Object> T load(T obj, boolean update) {
+ return cacheLoader.load(obj, true, update);
}
- public <T extends Object> Map<T,T> load(Map<T,T> map, boolean recursive){
- return cacheLoader.load(map, recursive);
+ public <T extends Object> Map<T,T> load(Map<T,T> map, boolean update){
+ return cacheLoader.load(map, true, update);
}
- public <T extends Object> Collection<T> load(Collection<T> collection, boolean recursive){
- return cacheLoader.load(collection, recursive);
+ public <T extends Object> Collection<T> load(Collection<T> collection, boolean update){
+ return cacheLoader.load(collection, true, update);
}
- public CdmBase load(CdmBase cdmEntity, boolean recursive) {
- return cacheLoader.load(cdmEntity, recursive);
+ public CdmBase load(CdmBase cdmEntity, boolean update) {
+ return cacheLoader.load(cdmEntity, true, update);
}
public CdmModelFieldPropertyFromClass getFromCdmlibModelCache(String className) {
@Override
public void put(CdmBase cdmEntity) {
- CdmEntityCacheKey id = new CdmEntityCacheKey(cdmEntity);
- Element cachedCdmEntityElement = cdmServiceCacher.getCacheElement(cdmEntity.getUuid());
- if(cachedCdmEntityElement != null) {
+
+ CdmBase cachedCdmEntity = cdmServiceCacher.load(cdmEntity);
+ if(cachedCdmEntity != null) {
logger.info("Cdm Entity with id : " + cdmEntity.getId() + " already exists in permanent cache. Ignoring put.");
return;
}
+ CdmEntityCacheKey id = new CdmEntityCacheKey(cdmEntity);
getCache().put(new Element(id, cdmEntity));
}
public CdmBase getFromCache(CdmEntityCacheKey id) {
Element e = getCacheElement(id);
+
if (e == null) {
return null;
} else {
if(cachedCdmEntity == null) {
// ... then try the permanent cache
- cachedCdmEntity = cdmServiceCacher.load(cdmBase);
+ cachedCdmEntity = cdmServiceCacher.getFromCache(cdmBase);
}
return cachedCdmEntity;
}
public void dispose() {
- cache.removeAll();
- cache.flush();
+ cache.dispose();
CdmRemoteCacheManager.getInstance().getDefaultCacheManager().removeCache(cacheId);
}
return new CdmEntityCacheKey(entityClass, id);
}
+ /* (non-Javadoc)
+ * @see eu.etaxonomy.cdm.model.ICdmCacher#load(eu.etaxonomy.cdm.model.common.CdmBase)
+ */
+ @Override
+ public CdmBase load(CdmBase cdmEntity) {
+ return load(cdmEntity, true);
+ }
+
+ /* (non-Javadoc)
+ * @see eu.etaxonomy.cdm.model.ICdmCacher#isCachable(eu.etaxonomy.cdm.model.common.CdmBase)
+ */
+ @Override
+ public boolean isCachable(CdmBase cdmEntity) {
+ return true;
+ }
+
+ /* (non-Javadoc)
+ * @see eu.etaxonomy.cdm.model.ICdmCacher#exists(eu.etaxonomy.cdm.model.common.CdmBase)
+ */
+ @Override
+ public boolean exists(CdmBase cdmBase) {
+ return exists(generateKey(cdmBase));
+ }
+
}
import java.util.Map;
import java.util.Set;
+import net.sf.ehcache.Cache;
+
import org.apache.log4j.Logger;
import org.hibernate.collection.spi.PersistentCollection;
import org.hibernate.proxy.HibernateProxy;
import org.hibernate.proxy.LazyInitializer;
import org.springframework.util.ReflectionUtils;
+import eu.etaxonomy.cdm.api.cache.CdmCacher;
import eu.etaxonomy.cdm.model.common.CdmBase;
/**
CdmBase cb = (CdmBase) cei.getObject();
Object cbParent = cei.getParent().getObject();
+
+ sb.append(" - " + cei.getField().getName() + ":" + cb.getUserFriendlyTypeName() + "/" + cb.getId() +
+ " in entity " + cbParent.getClass().getCanonicalName());
+ if(cbParent instanceof CdmBase) {
+ sb.append(" with id : " + ((CdmBase)cbParent).getId());
+ }
+ sb.append(System.getProperty("line.separator"));
+ sb.append(" -- entity belongs to cache(s) : " + getCachesContainingEntity(cb));
+ sb.append(System.getProperty("line.separator"));
+
+
CdmEntityInfo dupCei = entry.getValue();
CdmBase dupCb = (CdmBase) dupCei.getObject();
Object dupCbParent = dupCei.getParent().getObject();
- sb.append(" - entity : " + cb.getUserFriendlyTypeName() + "/" + cb.getId() +
- " as member " + cei.getField().getName() +
- " of entity " + cbParent.getClass().getCanonicalName());
+ sb.append(" - " + dupCei.getField().getName() + ":" + dupCb.getUserFriendlyTypeName() + "/" + dupCb.getId() +
+ " in entity " + dupCbParent.getClass().getCanonicalName());
+ if(dupCbParent instanceof CdmBase) {
+ sb.append(" with id : " + ((CdmBase)dupCbParent).getId());
+ }
sb.append(System.getProperty("line.separator"));
- sb.append(" - duplicate entity : " + dupCb.getUserFriendlyTypeName() + "/" + dupCb.getId() +
- " as field " + dupCei.getField().getName() +
- " of entity " + dupCbParent.getClass().getCanonicalName());
+ sb.append(" -- entity belongs to cache(s) : " + getCachesContainingEntity(dupCb));
sb.append(System.getProperty("line.separator"));
sb.append("-----------");
}
sb.append(System.getProperty("line.separator"));
- sb.append(" - entity : " + cb.getUserFriendlyTypeName() + "/" + cb.getId() +
- " as field " + cei.getField().getName() +
- " of entity" + cbParent.getClass().getCanonicalName());
+ sb.append(" - " + cei.getField().getName() + ":" + cb.getUserFriendlyTypeName() + "/" + cb.getId());
+
+ if(cbParent instanceof CdmBase) {
+ sb.append(" of entity " + ((CdmBase)cbParent).getUserFriendlyTypeName());
+ } else {
+ sb.append(" of entity " + cbParent.getClass().getName());
+ }
}
}
sb.append(System.getProperty("line.separator"));
return sb.toString();
}
+ private String getCachesContainingEntity(CdmBase cdmEntity) {
+ Cache defaultCache = CdmRemoteCacheManager.getInstance().getDefaultCacheManager().getCache(CdmCacher.DEFAULT_CACHE_NAME);
+ String caches = "";
+ Object dce = defaultCache.get(cdmEntity.getUuid());
+ if(dce != null && dce == cdmEntity) {
+ caches = CdmCacher.DEFAULT_CACHE_NAME;
+ }
+ if(!caches.isEmpty()) {
+ caches += ", ";
+ }
+ Object cte = cacher.getFromCache(CdmTransientEntityCacher.generateKey(cdmEntity));
+ if(cte != null && cte == cdmEntity) {
+ caches += cacher.toString();
+ }
+ return caches;
+ }
+
private void debug(CdmBase cdmEntity, boolean recursive) {
if(cdmEntity == null) {
private CdmEntityInfo getDuplicate(Set<CdmEntityInfo> alreadyVisitedEntities, Object objectToCompare) {
- if(objectToCompare != null) {
+ if(objectToCompare != null ) {
for(CdmEntityInfo cei: alreadyVisitedEntities) {
if(objectToCompare.equals(cei.getObject()) && objectToCompare != cei.getObject()) {
return cei;
if(field != null) {
fieldName = field.getName();
}
+
if(object != null) {
+ String className = object.getClass().getName();
if(object instanceof HibernateProxy) {
LazyInitializer hli = ((HibernateProxy)object).getHibernateLazyInitializer();
if(hli.isUninitialized()) {
- label = "[HibernateProxy] " + fieldName;
+ className = "HibernateProxy";
} else {
- label = fieldName + "Object is a HibernateProxy, but initialised";
+ className = "InitialisedHibernateProxy";
}
+ label = "[" + className + "] " + fieldName;
} else if(object instanceof PersistentCollection) {
PersistentCollection pc = ((PersistentCollection)object);
if(!pc.wasInitialized()) {
- label = "[PersistentCollection] " + fieldName;
+ className = "PersistentCollection";
} else {
- label = fieldName + "Object is a PersistentCollection, but initialised";
+ className = "InitialisedPersistentCollection";
}
+ label = "[" + className + "] " + fieldName;
} else if(object instanceof Collection) {
- String className = object.getClass().getName();
label = "[" + className + "] " + fieldName + " : " + String.valueOf(((Collection)object).size());
} else if(object instanceof Map) {
- String className = object.getClass().getName();
+
label = "[" + className + "] " + fieldName + " : " + String.valueOf(((Map)object).size());
+ } else if(object instanceof CdmBase) {
+ label = "[" + className + ",id" + ((CdmBase)object).getId() + "] " + fieldName + " : " + object.toString();
} else {
- String className = object.getClass().getName();
label = "[" + className + "] " + fieldName + " : " + object.toString();
}
} else {
*/
package eu.etaxonomy.taxeditor.remoting.cache;
+import java.lang.reflect.Field;
import java.util.ArrayList;
import java.util.HashMap;
import java.util.HashSet;
import org.hibernate.collection.internal.PersistentSortedMap;
import org.hibernate.collection.internal.PersistentSortedSet;
import org.hibernate.collection.spi.PersistentCollection;
+import org.hibernate.proxy.HibernateProxy;
+import org.hibernate.proxy.LazyInitializer;
+import org.springframework.util.ReflectionUtils;
import eu.etaxonomy.cdm.model.common.PersistentMultiLanguageText;
import eu.etaxonomy.taxeditor.remoting.CdmRemotingException;
*/
public class ProxyUtils {
+
+
+ public static enum CollectionType {
+ SET,
+ LIST,
+ MAP;
+
+ @Override
+ public String toString() {
+ return this.name().toLowerCase();
+ }
+ }
+
+ public static Object getCollectionType(Object obj) {
+ if(obj != null) {
+ if(obj instanceof List) {
+ return CollectionType.LIST;
+ }
+ if(obj instanceof Set) {
+ return CollectionType.SET;
+ }
+ if(obj instanceof Map) {
+ return CollectionType.MAP;
+ }
+ throw new CdmRemotingException("Cannot get Collection Type for " + obj.getClass().getName());
+ }
+ return null;
+ }
+
public static Object getObject(PersistentCollection pc) {
if(pc != null) {
if(pc instanceof PersistentSet) {
return null;
}
+ public static CollectionField getCollectionField(PersistentCollection pc) {
+ if(pc != null) {
+ if(pc instanceof PersistentSet) {
+ return new CollectionField(new HashSet((Set)pc), CollectionType.SET);
+ }
+ if(pc instanceof PersistentSortedSet) {
+ return new CollectionField(new TreeSet((Set)pc), CollectionType.SET);
+ }
+ if(pc instanceof PersistentList) {
+ return new CollectionField(new ArrayList((List)pc), CollectionType.LIST);
+ }
+ if(pc instanceof PersistentMap || pc instanceof PersistentMultiLanguageText) {
+ return new CollectionField(new HashMap((Map)pc), CollectionType.MAP);
+ }
+ if(pc instanceof PersistentSortedMap) {
+ return new CollectionField(new TreeMap((Map)pc), CollectionType.MAP);
+ }
+ throw new CdmRemotingException("Cannot get Collection field for type " + pc.getClass().getName());
+ }
+ return null;
+ }
+
+ public static class CollectionField {
+ private final Object col;
+ private final CollectionType type;
+ public CollectionField(Object col, CollectionType type) {
+ this.col = col;
+ this.type = type;
+ }
+
+ public Object getCollection() {
+ return this.col;
+ }
+
+ public CollectionType getType() {
+ return this.type;
+ }
+ }
+
+
+ public static Object deproxy(Object o) {
+ if(o != null && o instanceof HibernateProxy) {
+ LazyInitializer hli = ((HibernateProxy)o).getHibernateLazyInitializer();
+ if(!hli.isUninitialized()) {
+ return ((HibernateProxy) o).getHibernateLazyInitializer().getImplementation();
+
+ }
+ }
+
+ if(o != null && o instanceof PersistentCollection) {
+ PersistentCollection pc = ((PersistentCollection)o);
+ if(pc.wasInitialized()) {
+ return ProxyUtils.getObject(pc);
+
+ }
+ }
+ return o;
+ }
+
+ public static void setRoleValueInOwner(Object owner, String role, Object value) {
+ if(role == null || role.isEmpty()) {
+ throw new CdmRemotingException("Role cannot be null or an empty string");
+ }
+
+ String fieldName = role.substring(role.lastIndexOf(".") + 1);
+
+ Field field = ReflectionUtils.findField(owner.getClass(), fieldName);
+
+ if(field == null) {
+ throw new CdmRemotingException("Field '" + fieldName
+ + "' not found when searching in class '" + owner.getClass() + "' and its supercalsses");
+ }
+
+ field.setAccessible(true);
+
+ try {
+ field.set(owner, value);
+ } catch (IllegalArgumentException e) {
+ throw new CdmRemotingException(e);
+ } catch (IllegalAccessException e) {
+ throw new CdmRemotingException(e);
+ }
+ }
+
}
*/
package eu.etaxonomy.taxeditor.service;
-import java.util.ArrayList;
-import java.util.HashMap;
-import java.util.HashSet;
-import java.util.List;
-import java.util.Map;
-import java.util.Set;
-import java.util.TreeMap;
-import java.util.TreeSet;
-
-import org.hibernate.collection.internal.PersistentList;
-import org.hibernate.collection.internal.PersistentMap;
-import org.hibernate.collection.internal.PersistentSet;
-import org.hibernate.collection.internal.PersistentSortedMap;
-import org.hibernate.collection.internal.PersistentSortedSet;
import org.hibernate.collection.spi.PersistentCollection;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Component;
import eu.etaxonomy.cdm.api.service.ICommonService;
import eu.etaxonomy.cdm.model.common.CdmBase;
-import eu.etaxonomy.cdm.model.common.PersistentMultiLanguageText;
-import eu.etaxonomy.taxeditor.remoting.CdmRemotingException;
-import eu.etaxonomy.taxeditor.remoting.cache.CdmTransientEntityCacher.CollectionType;
+import eu.etaxonomy.taxeditor.remoting.cache.ProxyUtils.CollectionField;
import eu.etaxonomy.taxeditor.session.ICdmEntitySessionManager;
/**
if(cdmEntity == null) {
throw new NullPointerException("CDM Entity of type " + clazz.getName() + " with id " + id + " is null.");
}
- return cdmEntitySessionManager.load(cdmEntity);
+ return cdmEntitySessionManager.load(cdmEntity, false);
} else {
return CdmBase.deproxy(commonService.find(clazz, id),clazz);
}
*/
@Override
public PersistentCollection initializeCollection(PersistentCollection col) {
- PersistentCollection pc = commonService.initializeCollection(col);
- return pc;
+ return commonService.initializeCollection(col);
}
@Override
public void updatePersistentCollection(CollectionField colf) {
if(cacheEnabled) {
- cdmEntitySessionManager.load(colf.getCollection());
+ cdmEntitySessionManager.load(colf.getCollection(), false);
}
}
return commonService.containsValue(col, element);
}
- @SuppressWarnings("rawtypes")
- @Override
- public CollectionField getCollectionField(PersistentCollection pc) {
- if(pc != null) {
- if(pc instanceof PersistentSet) {
- return new CollectionField(new HashSet((Set)pc), CollectionType.SET);
- }
- if(pc instanceof PersistentSortedSet) {
- return new CollectionField(new TreeSet((Set)pc), CollectionType.SET);
- }
- if(pc instanceof PersistentList) {
- return new CollectionField(new ArrayList((List)pc), CollectionType.LIST);
- }
- if(pc instanceof PersistentMap || pc instanceof PersistentMultiLanguageText) {
- return new CollectionField(new HashMap((Map)pc), CollectionType.MAP);
- }
- if(pc instanceof PersistentSortedMap) {
- return new CollectionField(new TreeMap((Map)pc), CollectionType.MAP);
- }
- throw new CdmRemotingException("Cannot get Collection field for type " + pc.getClass().getName());
- }
- return null;
- }
- public class CollectionField {
- private final Object col;
- private final CollectionType type;
- public CollectionField(Object col, CollectionType type) {
- this.col = col;
- this.type = type;
- }
-
- public Object getCollection() {
- return this.col;
- }
-
- public CollectionType getType() {
- return this.type;
- }
- }
if(rir == null) {
rir = super.doExecuteRequest(config, baos);
if(rir.getValue() != null && !rir.hasException()) {
- rir = new RemoteInvocationResult(cdmEntitySessionManager.load(rir.getValue()));
+ if(currentRemoteInvocation.getMethodName().equals("merge")) {
+ rir = new RemoteInvocationResult(cdmEntitySessionManager.load(rir.getValue(), true));
+ } else {
+ rir = new RemoteInvocationResult(cdmEntitySessionManager.load(rir.getValue(), false));
+ }
}
cache(currentRemoteInvocation, rir);
}
import org.hibernate.collection.spi.PersistentCollection;
import eu.etaxonomy.cdm.model.common.CdmBase;
-import eu.etaxonomy.taxeditor.service.CachedCommonServiceImpl.CollectionField;
+import eu.etaxonomy.taxeditor.remoting.cache.ProxyUtils.CollectionField;
/**
* @author cmathew
public boolean containsValue(PersistentCollection col, Object element);
- public CollectionField getCollectionField(PersistentCollection pc);
import java.util.Map;
import java.util.Set;
-import net.sf.ehcache.Cache;
-import net.sf.ehcache.Element;
-
+import org.apache.log4j.Logger;
import org.springframework.remoting.support.RemoteInvocation;
import org.springframework.remoting.support.RemoteInvocationResult;
-import eu.etaxonomy.cdm.api.cache.CdmCacher;
+import eu.etaxonomy.cdm.api.cache.CdmServiceCacher;
import eu.etaxonomy.cdm.model.common.DefinedTermBase;
import eu.etaxonomy.cdm.model.common.TermType;
public class TermServiceRequestExecutor extends CdmServiceRequestExecutor {
+ private static final Logger logger = Logger.getLogger(TermServiceRequestExecutor.class);
- private static Map<TermType, RemoteInvocationResult> termTypeMap = new
+ private static Map<TermType, RemoteInvocationResult> termTypeMap = new
HashMap<TermType, RemoteInvocationResult>();
+ private static CdmServiceCacher cdmServiceCacher;
+
+ public static void setDefaultCacher(CdmServiceCacher css) {
+ cdmServiceCacher = css;
+ }
@Override
public void cache(RemoteInvocation ri, RemoteInvocationResult rir) {
- if(ri.getMethodName().equals("listByTermType")) {
- if(ri.getArguments()[1] == null) {
- Set<DefinedTermBase> terms = new HashSet<DefinedTermBase>();
- if(rir.getValue() != null) {
- terms.addAll((List<DefinedTermBase>)rir.getValue());
- Cache defaultCache = CdmCacher.getDefaultCache();
- for(DefinedTermBase<?> term : terms) {
- defaultCache.put(new Element(term.getUuid(), term));
- }
- termTypeMap.put((TermType)ri.getArguments()[0], rir);
- }
-
- }
- }
-
+ if(cdmServiceCacher != null) {
+ if(ri.getMethodName().equals("listByTermType")) {
+ if(ri.getArguments()[1] == null) {
+ Set<DefinedTermBase> terms = new HashSet<DefinedTermBase>();
+ if(rir.getValue() != null) {
+ terms.addAll((List<DefinedTermBase>)rir.getValue());
+
+ for(DefinedTermBase<?> term : terms) {
+ cdmServiceCacher.put(term.getUuid(), term);
+ }
+ termTypeMap.put((TermType)ri.getArguments()[0], rir);
+ }
+
+ }
+ }
+ } else {
+ logger.info("Default CdmServiceCacher is null. Cannot cache terms");
+ }
}
import java.util.ArrayList;
import java.util.Arrays;
import java.util.Collection;
+import java.util.HashSet;
import java.util.List;
import java.util.Set;
import java.util.UUID;
}
+
/* (non-Javadoc)
- * @see eu.etaxonomy.taxeditor.session.ICdmEntitySession#load(T)
+ * @see eu.etaxonomy.taxeditor.session.ICdmEntitySession#load(java.lang.Object, boolean)
*/
@Override
- public <O extends Object> O load(O obj) {
- return cdmTransientEntityCacher.load(obj,true);
+ public <O extends Object> O load(O obj, boolean update) {
+ return cdmTransientEntityCacher.load(obj, update);
}
/* (non-Javadoc)
- * @see eu.etaxonomy.taxeditor.session.ICdmEntitySession#load(T)
+ * @see eu.etaxonomy.taxeditor.session.ICdmEntitySession#load(eu.etaxonomy.cdm.model.common.CdmBase, boolean)
*/
@Override
- public <T extends CdmBase> T load(T cdmBase) {
- return (T)cdmTransientEntityCacher.load(cdmBase,true);
+ public <T extends CdmBase> T load(T cdmBase, boolean update) {
+ return (T)cdmTransientEntityCacher.load(cdmBase, update);
}
+
@Override
public <T extends ICdmBase> void update(T cdmBase, Set<CdmBase> affectedObjects) {
- load(cdmBase);
addEvent(cdmBase, affectedObjects, EventType.UPDATE);
}
+ @Override
+ public <T extends ICdmBase> void update(T cdmBase, CdmBase affectedObject) {
+ Set<CdmBase> set = new HashSet<CdmBase>();
+ set.add(affectedObject);
+ addEvent(cdmBase, set, EventType.UPDATE);
+ }
+
+
@Override
public <T extends ICdmBase> void delete(T cdmBase, Set<CdmBase> affectedObjects) {
- for(CdmBase cb : affectedObjects) {
- load(cb);
- }
addEvent(cdmBase, affectedObjects, EventType.DELETE);
}
@Override
public <T extends ICdmBase> void delete(Set<T> cdmBases, Set<CdmBase> affectedObjects) {
- for(CdmBase cb : affectedObjects) {
- load(cb);
- }
addEvent(cdmBases, affectedObjects, EventType.DELETE);
}
* @see eu.etaxonomy.taxeditor.session.ICdmEntitySession#load(java.util.Collection)
*/
@Override
- public <T extends CdmBase> Collection<T> load(Collection<T> cdmBaseList) {
- return cdmTransientEntityCacher.load(cdmBaseList,true);
+ public <T extends CdmBase> Collection<T> load(Collection<T> cdmBaseList, boolean update) {
+ return cdmTransientEntityCacher.load(cdmBaseList, update);
}
/* (non-Javadoc)
*/
@Override
public void addEvent(ICdmBase cdmBase, Set<CdmBase> affectedObjects, EventType eventType) {
+ affectedObjects = (Set<CdmBase>) load(affectedObjects, true);
CdmDataChangeEvent cdce = CdmDataChangeEvent.NewInstance((CdmBase)cdmBase, affectedObjects, eventType);
CdmPostDataChangeObservableListener.getDefault().notifyObservers(cdce);
}
*/
@Override
public <T extends ICdmBase> void addEvent(Collection <T> cdmBases, Set<CdmBase> affectedObjects, EventType eventType) {
+ affectedObjects = (Set<CdmBase>) load(affectedObjects, true);
for(ICdmBase cdmBase : cdmBases) {
CdmDataChangeEvent cdce = CdmDataChangeEvent.NewInstance((CdmBase)cdmBase, affectedObjects, eventType);
CdmPostDataChangeObservableListener.getDefault().notifyObservers(cdce);
}
-
}
/* (non-Javadoc)
@Override
public <T extends CdmBase> T remoteLoad(IService<T> service, UUID uuid) {
T cdmBase = service.load(uuid);
- return load(cdmBase);
+ return load(cdmBase, false);
}
@Override
public <T extends CdmBase> T remoteLoad(IService<T> service, UUID uuid, List<String> propertyPaths) {
T cdmBase = service.load(uuid, propertyPaths);
- return load(cdmBase);
+ return load(cdmBase, false);
}
@Override
public <T extends CdmBase> UUID remoteSave(IService<T> service, T cdmBase) {
UUID uuid = service.save(cdmBase);
- load(cdmBase);
+ load(cdmBase,false);
return uuid;
}
*/
@Override
public <T extends CdmBase> T remoteUpdate(IService<T> service, T cdmBase) {
- //debug(cdmBase);
T mergedCdmBase = service.merge(cdmBase);
- //cdmTransientEntityCacher.clear();
- // FIXME:Remoting not really sure if we need to reload the new
- // merged object or can we keep using the old one
- //return load(mergedCdmBase);
-
return mergedCdmBase;
}
+
}
* @see eu.etaxonomy.taxeditor.session.ICdmEntitySessionManager#load(T)
*/
@Override
- public <T extends Object> T load(T obj) {
+ public <T extends Object> T load(T obj, boolean update) {
if(activeSession == null) {
return obj;
} else {
- return activeSession.load(obj);
+ return activeSession.load(obj, update);
}
}
* @see eu.etaxonomy.taxeditor.session.ICdmEntitySessionManager#load(T)
*/
@Override
- public <T extends CdmBase> T load(T cdmBase) {
+ public <T extends CdmBase> T load(T cdmBase, boolean update) {
if(activeSession == null) {
return cdmBase;
}
- return activeSession.load(cdmBase);
+ return activeSession.load(cdmBase, update);
}
+
/* (non-Javadoc)
* @see eu.etaxonomy.taxeditor.session.ICdmEntitySessionManager#load(java.util.Collection)
*/
@Override
- public <T extends CdmBase> Collection<T> load(Collection<T> cdmBaseList) {
+ public <T extends CdmBase> Collection<T> load(Collection<T> cdmBaseList, boolean update) {
if(activeSession == null) {
return cdmBaseList;
}
- return activeSession.load(cdmBaseList);
+ return activeSession.load(cdmBaseList, update);
}
+
+
}
public LiveCacheStatistics getCacheStatistics();
- public <O extends Object> O load(O obj);
+ public <O extends Object> O load(O obj, boolean update);
- public <T extends CdmBase> T load(T cdmBase);
+ public <T extends CdmBase> T load(T cdmBase, boolean update);
public <T extends CdmBase> EntityCacherDebugResult debug(T cdmBase);
public <T extends CdmBase> EntityCacherDebugResult debug();
- public <T extends CdmBase> Collection<T> load(Collection<T> cdmBaseList);
+ public <T extends CdmBase> Collection<T> load(Collection<T> cdmBaseList, boolean update);
public void setEntitiesAsLatest();
public boolean isActive();
+ /**
+ * @param cdmBase
+ * @param affectedObject
+ */
+ public <T extends ICdmBase> void update(T cdmBase, CdmBase affectedObject);
+
public abstract void bind(ICdmEntitySessionEnabled sessionOwner);
-// public abstract <T extends Object> T load(
-// ISessionEventListener sessionOwner, T obj);
- public abstract <T extends Object> T load(T obj);
+ public abstract <T extends Object> T load(T obj, boolean update);
-// public abstract <T extends CdmBase> T load(
-// ISessionEventListener sessionOwner, T cdmBase);
- public abstract <T extends CdmBase> T load(T cdmBase);
+ public abstract <T extends CdmBase> T load(T cdmBase, boolean update);
-// public abstract <T extends CdmBase> Collection<T> load(
-// ISessionEventListener sessionOwner, Collection<T> cdmBaseList);
- public abstract <T extends CdmBase> Collection<T> load(Collection<T> cdmBaseList);
+ public abstract <T extends CdmBase> Collection<T> load(Collection<T> cdmBaseList, boolean update);
- //public abstract void dispose(ICdmEntitySessionEnabled owner);
/**
* @return
* @see eu.etaxonomy.taxeditor.session.ICdmEntitySession#load(java.lang.Object)
*/
@Override
- public <O extends Object> O load(O obj) {
+ public <O extends Object> O load(O obj, boolean update) {
return obj;
}
* @see eu.etaxonomy.taxeditor.session.ICdmEntitySession#load(eu.etaxonomy.cdm.model.common.CdmBase)
*/
@Override
- public <T extends CdmBase> T load(T cdmBase) {
+ public <T extends CdmBase> T load(T cdmBase, boolean update) {
return cdmBase;
}
* @see eu.etaxonomy.taxeditor.session.ICdmEntitySession#load(java.util.Collection)
*/
@Override
- public <T extends CdmBase> Collection<T> load(Collection<T> cdmBaseList) {
+ public <T extends CdmBase> Collection<T> load(Collection<T> cdmBaseList, boolean update) {
return cdmBaseList;
}
return null;
}
+ /* (non-Javadoc)
+ * @see eu.etaxonomy.taxeditor.session.ICdmEntitySession#update(eu.etaxonomy.cdm.model.common.ICdmBase, eu.etaxonomy.cdm.model.common.CdmBase)
+ */
+ @Override
+ public <T extends ICdmBase> void update(T cdmBase, CdmBase affectedObject) {
+
+ }
+
+
}
}
@Override
- public <T> T load(T obj) {
+ public <T> T load(T obj, boolean update) {
return obj;
}
@Override
- public <T extends CdmBase> T load(T obj) {
+ public <T extends CdmBase> T load(T obj, boolean update) {
return obj;
}
@Override
- public <T extends CdmBase> Collection<T> load(Collection<T> cdmBaseList) {
+ public <T extends CdmBase> Collection<T> load(Collection<T> cdmBaseList, boolean update) {
return cdmBaseList;
}
return false;
}
+
}
import eu.etaxonomy.cdm.api.application.CdmApplicationRemoteConfiguration;
import eu.etaxonomy.taxeditor.remoting.CdmEagerLoadingException;
+import eu.etaxonomy.taxeditor.remoting.cache.ProxyUtils;
import eu.etaxonomy.taxeditor.service.ICachedCommonService;
-import eu.etaxonomy.taxeditor.service.CachedCommonServiceImpl.CollectionField;
/**
* Base class implementing {@link org.hibernate.collection.spi.PersistentCollection}
* @throws LazyInitializationException if we cannot initialize
*/
protected final void initialize(final boolean writing) {
- // In remoting we are sure that session is null
- // both when using property paths and switching off conversations
- if(session == null && remoting) {
- remoteInitialize();
- }
-
- if ( initialized ) {
- return;
- }
-
-
- withTemporarySessionIfNeeded(
- new LazyInitializationWork<Object>() {
- @Override
- public Object doWork() {
- session.initializeCollection( AbstractPersistentCollection.this, writing );
- return null;
- }
- }
- );
+ if ( initialized ) {
+ return;
+ }
+
+ // In remoting we are sure that session is null
+ // both when using property paths and switching off conversations
+ if(session == null && remoting) {
+ remoteInitialize();
+ } else {
+ withTemporarySessionIfNeeded(
+ new LazyInitializationWork<Object>() {
+ @Override
+ public Object doWork() {
+ session.initializeCollection( AbstractPersistentCollection.this, writing );
+ return null;
+ }
+ }
+ );
+ }
}
private void throwLazyInitializationExceptionIfNotConnected() {
throw new HibernateException("commonService not initialized (null)");
}
- PersistentCollection col = cachedCommonService.initializeCollection(this);
+ Object obj = ProxyUtils.deproxy(cachedCommonService.initializeCollection(this));
afterInitialize();
Class<?> clazz = getClass();
if (clazz != null) {
- CollectionField cf = cachedCommonService.getCollectionField(col);
- cachedCommonService.updatePersistentCollection(cf);
- Field field = clazz.getDeclaredField(cf.getType().toString());
+ //CollectionField cf = cachedCommonService.getCollectionField(col);
+ //cachedCommonService.updatePersistentCollection(cf);
+ Object collectionType = ProxyUtils.getCollectionType(obj);
+ Field field = clazz.getDeclaredField(collectionType.toString());
field.setAccessible(true);
- field.set(this, cf.getCollection());
+ field.set(this, obj);
+ ProxyUtils.setRoleValueInOwner(owner, role, obj);
+
}
} catch (Exception ex) {
throw new CdmEagerLoadingException(ex);