I am about to file a bug but wanted to run this by the experts first. Let's say there is a User entity class that declares 20 lazy collections much like so:
@OneToMany( mappedBy = "owner")
@Cascade({CascadeType.REMOVE, CascadeType.DELETE_ORPHAN})
@LazyCollection(LazyCollectionOption.TRUE)
@BatchSize(size = 1000)
@Cache(usage = CacheConcurrencyStrategy.TRANSACTIONAL)
public Set<CustomSpace> getCustomSpaces()
In Hibernate 3.3.1.GA if I load ~1000 User entities from second level cache
(w/o accessing any of the collections), I'll end up spending 5x time assembling
cache entries vs. actually loading de-hydrated state from the cache provider
(profiler snapshot attached). Most of the time is spent eagerly assembling
CollectionTypes, all of which may or may not be needed during a given Session.
So, basically, I'm being penalized for merely declaring OneToMany's. Currently,
the only way to avoid this penalty - as far as I can tell - is to complicate
the domain model by introducing some number of new entities that will be
OneToOne to User; and redistributing collection declarations amongst those. But
even that may not help: what if services using the domain model access a
variety of collections at different times? IMO a much more scalable approach
would be to:
* stash serialized states representing collection properties during
assembleCacheEntry
* call CollectionType.assemble lazily when collection property field is
actually accessed (a la lazy properties)
Fwiw, a post covering the above in a little more detail can be found here:
https://forum.hibernate.org/viewtopic.php?p=2412263#p2412263
-nikita
Merged callees
+-------------------------------------------------------------------------------------------------------------------------------------------------------------+----------------+-----------------+--------------------+
|
Name
| Time (ms) | Own Time (ms) | Invocation Count |
+-------------------------------------------------------------------------------------------------------------------------------------------------------------+----------------+-----------------+--------------------+
|
+---org.hibernate.event.def.DefaultLoadEventListener.loadFromSecondLevelCache(LoadEvent,
EntityPersister, LoadEventListener$LoadType) | 2,390
100 % | 0 | 999 |
| |
|
| | |
|
+---org.hibernate.event.def.DefaultLoadEventListener.assembleCacheEntry(CacheEntry,
Serializable, EntityPersister, LoadEvent) | 1,796
75 % | 15 | 999 |
| | |
|
| | |
| | +---org.hibernate.cache.entry.CacheEntry.assemble(Object, Serializable,
EntityPersister, Interceptor, EventSource)
| 1,546 65 % | 0 | 999 |
| | | |
|
| | |
| | | +---org.hibernate.cache.entry.CacheEntry.assemble(Serializable[],
Object, Serializable, EntityPersister, Interceptor, EventSource)
| 1,546 65 % | 31 | 999 |
| | | |
|
| | |
| | | +---org.hibernate.type.TypeFactory.assemble(Serializable[], Type[],
SessionImplementor, Object)
| 1,250 52 % | 0 | 999 |
| | | | |
|
| | |
| | | | +---org.hibernate.type.CollectionType.assemble(Serializable,
SessionImplementor, Object)
| 1,109 46 % | 31 | 10,998 |
| | | | | |
|
| | |
| | | | | +---org.hibernate.type.CollectionType.resolveKey(Serializable,
SessionImplementor, Object)
| 875 37 % | 0 | 10,998 |
| | | | | | |
|
| | |
| | | | | |
+---org.hibernate.type.CollectionType.getCollection(Serializable,
SessionImplementor, Object) |
875 37 % | 78 | 10,998 |
| | | | | | |
|
| | |
| | | | | |
+---org.hibernate.engine.StatefulPersistenceContext.addUninitializedCollection(CollectionPersister,
PersistentCollection, Serializable) | 343 14 % | 0 |
10,998 |
| | | | | | |
|
| | |
| | | | | |
+---org.hibernate.engine.loading.LoadContexts.locateLoadingCollection(CollectionPersister,
Serializable) | 203 8 % |
31 | 10,998 |
| | | | | | |
|
| | |
| | | | | |
+---org.hibernate.type.CollectionType.getPersister(SessionImplementor)
| 62 3 % |
15 | 10,998 |
| | | | | | |
|
| | |
| | | | | |
+---org.hibernate.engine.CollectionKey.<init>(CollectionPersister,
Serializable, EntityMode) |
62 3 % | 15 | 10,998 |
| | | | | | |
|
| | |
| | | | | |
+---org.hibernate.type.SetType.instantiate(SessionImplementor,
CollectionPersister, Serializable) |
46 2 % | 15 | 10,499 |
| | | | | | |
|
| | |
| | | | | | +---org.hibernate.impl.SessionImpl.getPersistenceContext()
|
31 1 % | 15 | 10,998 |
| | | | | | |
|
| | |
| | | | | |
+---org.hibernate.type.CollectionType.initializeImmediately(EntityMode)
| 31 1 % |
31 | 10,998 |
| | | | | | |
|
| | |
| | | | | | +---org.hibernate.impl.SessionImpl.getEntityMode()
|
15 1 % | 15 | 10,998 |
| | | | | |
|
| | |
| | | | |
+---org.hibernate.type.CollectionType.getPersister(SessionImplementor)
| 109 5 %
| 15 | 10,998 |
| | | | | |
|
| | |
| | | | | +---org.hibernate.type.AbstractType.assemble(Serializable,
SessionImplementor, Object)
| 93 4 % | 31 | 10,998 |
| | | | |
|
| | |
| | | | +---org.hibernate.type.AbstractType.assemble(Serializable,
SessionImplementor, Object)
| 140 6 % | 46 | 16,489 |
| | | |
|
| | |
| | |
+---org.hibernate.persister.entity.AbstractEntityPersister.setPropertyValues(Object,
Object[], EntityMode) | 265 11 %
| 0 | 999 |
| | |
|
| | |
| |
+---org.hibernate.persister.entity.AbstractEntityPersister.afterInitialize(Object,
boolean, SessionImplementor) | 62
3 % | 0 | 999 |
| | |
|
| | |
| | +---org.hibernate.type.TypeFactory.deepCopy(Object[], Type[], boolean[],
Object[], SessionImplementor) |
46 2 % | 15 | 999 |
| | |
|
| | |
| | +---org.hibernate.impl.SessionImpl.instantiate(EntityPersister,
Serializable)
| 31 1 % | 0 | 999 |
| | |
|
| | |
| | +---org.hibernate.engine.Versioning.getVersion(Object[],
EntityPersister)
| 31 1 % | 31 | 999 |
| | |
|
| | |
| |
+---org.hibernate.engine.TwoPhaseLoad.addUninitializedCachedEntity(EntityKey,
Object, EntityPersister, LockMode, boolean, Object, SessionImplementor) |
31 1 % | 0 | 999 |
| | |
|
| | |
| |
+---org.hibernate.event.def.DefaultPostLoadEventListener.onPostLoad(PostLoadEvent)
| 15
1 % | 15 | 999 |
| | |
|
| | |
| | +---org.hibernate.impl.SessionFactoryImpl.getEntityPersister(String)
|
15 1 % | 15 | 999 |
| |
|
| | |
| +---org.hibernate.cache.jbc2.entity.TransactionalAccess.get(Object, long)
|
359 15 % | 0 | 999 |
| |
|
| | |
| +---org.hibernate.cache.entry.StructuredCacheEntry.destructure(Object,
SessionFactoryImplementor)
| 218 9 % | 15 | 999 |
| |
|
| | |
| +---org.hibernate.cache.CacheKey.<init>(Serializable, Type, String,
EntityMode, SessionFactoryImplementor)
| 15 1 % | 0 | 999 |
+-------------------------------------------------------------------------------------------------------------------------------------------------------------+----------------+-----------------+--------------------+
Generated by YourKit Java Profiler 8.0.7 May 26, 2009 10:51:14 AM
_______________________________________________ hibernate-dev mailing list [email protected] https://lists.jboss.org/mailman/listinfo/hibernate-dev
