栏目分类:
子分类:
返回
名师互学网用户登录
快速导航关闭
当前搜索
当前分类
子分类
实用工具
热门搜索
名师互学网 > IT > 面试经验 > 面试问答

驱逐相关集合以及上级实体

面试问答 更新时间: 发布时间: IT归档 最新发布 模块sitemap 名妆网 法律咨询 聚返吧 英语巴士网 伯小乐 网商动力

驱逐相关集合以及上级实体

这是一个老问题。在插入,更新或删除集合引用的实体时,有一种方法可以挂入hibernate状态以驱逐集合缓存。我已经提供了hibernate的修复程序。该修复程序计划用于Hibernate 4.3.0.Beta5,并将由以下属性激活:

hibernate.cache.auto_evict_collection_cache=true

只要未实现此修复程序,您就可以通过自己向SessionFactory和SessionFactoryServiceRegistry注册CollectionCacheInvalidator的方法来注入驱逐逻辑。

import javax.persistence.OneToMany;import java.io.Serializable;import java.util.HashMap;import java.util.Map;import java.util.Set;import my.own.library.BeanInformationFromClass;import my.own.library.PropertyInformationFromClass;import org.apache.commons.lang.StringUtils;import org.apache.log4j.Logger;import org.hibernate.engine.spi.SessionFactoryImplementor;import org.hibernate.event.service.spi.EventListenerRegistry;import org.hibernate.event.spi.EventSource;import org.hibernate.event.spi.EventType;import org.hibernate.event.spi.PostInsertEvent;import org.hibernate.event.spi.PostInsertEventListener;import org.hibernate.event.spi.PreDeleteEvent;import org.hibernate.event.spi.PreDeleteEventListener;import org.hibernate.event.spi.PreUpdateEvent;import org.hibernate.event.spi.PreUpdateEventListener;import org.hibernate.persister.collection.CollectionPersister;import org.hibernate.persister.entity.EntityPersister;import org.hibernate.persister.entity.Joinable;import org.hibernate.service.spi.SessionFactoryServiceRegistry;public class CollectionCacheInvalidator        implements PostInsertEventListener, PreDeleteEventListener, PreUpdateEventListener {    private static final Logger LOGGER = Logger.getLogger( CollectionCacheInvalidator.class );    private Map<String, String> mappedByFieldMapping;    public void integrate(SessionFactoryImplementor sf, SessionFactoryServiceRegistry registry) {        EventListenerRegistry eventListenerRegistry = registry.getService( EventListenerRegistry.class );        eventListenerRegistry.appendListeners( EventType.POST_INSERT, this );        eventListenerRegistry.appendListeners( EventType.PRE_DELETE, this );        eventListenerRegistry.appendListeners( EventType.PRE_UPDATE, this );        mappedByFieldMapping = new HashMap<String, String>();        Map<String, CollectionPersister> persiters = sf.getCollectionPersisters();        if ( persiters != null ) { for ( CollectionPersister collectionPersister : persiters.values() ) {     if ( !collectionPersister.hasCache() ) {         continue;     }     if ( !(collectionPersister instanceof Joinable) ) {         continue;     }     String oneToManyFieldName = collectionPersister.getNodeName();     EntityPersister ownerEntityPersister = collectionPersister.getOwnerEntityPersister();     Class ownerClass = ownerEntityPersister.getMappedClass();     // Logic to get the mappedBy attribute of the oneToMany annotation.     BeanInformationFromClass bi = new BeanInformationFromClass( ownerClass );     PropertyInformationFromClass prop = bi.getProperty( oneToManyFieldName );     oneToMany oneToMany = prop.getAnnotation( OneToMany.class );     String mappedBy = null;     if ( oneToMany != null && StringUtils.isNotBlank( oneToMany.mappedBy() ) ) {         mappedBy = oneToMany.mappedBy();     }     mappedByFieldMapping.put( ((Joinable) collectionPersister).getName(), mappedBy ); }        }    }    @Override    public void onPostInsert(PostInsertEvent event) {        evictCache( event.getEntity(), event.getPersister(), event.getSession(), null );    }    @Override    public boolean onPreDelete(PreDeleteEvent event) {        evictCache( event.getEntity(), event.getPersister(), event.getSession(), null );        return false;    }    @Override    public boolean onPreUpdate(PreUpdateEvent event) {        evictCache( event.getEntity(), event.getPersister(), event.getSession(), event.getOldState() );        return false;    }    private void evictCache(Object entity, EntityPersister persister, EventSource session, Object[] oldState) {        try { SessionFactoryImplementor factory = persister.getFactory(); Set<String> collectionRoles = factory.getCollectionRolesByEntityParticipant( persister.getEntityName() ); if ( collectionRoles == null || collectionRoles.isEmpty() ) {     return; } for ( String role : collectionRoles ) {     CollectionPersister collectionPersister = factory.getCollectionPersister( role );     if ( !collectionPersister.hasCache() ) {         continue;     }     if ( !(collectionPersister instanceof Joinable) ) {         continue;     }     String mappedBy = mappedByFieldMapping.get( ((Joinable) collectionPersister).getName() );     if ( mappedBy != null ) {         int i = persister.getEntitymetamodel().getPropertyIndex( mappedBy );         Serializable oldId = null;         if ( oldState != null ) {  oldId = session.getIdentifier( oldState[i] );         }         Object ref = persister.getPropertyValue( entity, i );         Serializable id = null;         if ( ref != null ) {  id = session.getIdentifier( ref );         }         if ( id != null && !id.equals( oldId ) ) {  evict( id, collectionPersister, session );  if ( oldId != null ) {      evict( id, collectionPersister, session );  }         }     }     else {         LOGGER.debug( "Evict CollectionRegion " + role );         collectionPersister.getCacheAccessStrategy().evictAll();     } }        }        catch (Exception e) { LOGGER.error( "", e );        }    }    private void evict(Serializable id, CollectionPersister collectionPersister, EventSource session) {        LOGGER.debug( "Evict CollectionRegion " + collectionPersister.getRole() + " for id " + id );        collectionPersister.getCacheAccessStrategy().evict(     session.generateCacheKey(  id,  collectionPersister.getKeyType(),  collectionPersister.getRole()     )        );    }}


转载请注明:文章转载自 www.mshxw.com
本文地址:https://www.mshxw.com/it/376001.html
我们一直用心在做
关于我们 文章归档 网站地图 联系我们

版权所有 (c)2021-2022 MSHXW.COM

ICP备案号:晋ICP备2021003244-6号