⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 defaultrefresheventlistener.cs

📁 NHibernate NET开发者所需的
💻 CS
字号:
using System;
using System.Collections;
using log4net;
using NHibernate.Cache;
using NHibernate.Engine;
using NHibernate.Impl;
using NHibernate.Persister.Entity;
using NHibernate.Type;
using NHibernate.Util;

namespace NHibernate.Event.Default
{
	/// <summary> 
	/// Defines the default refresh event listener used by hibernate for refreshing entities
	/// in response to generated refresh events. 
	/// </summary>
	[Serializable]
	public class DefaultRefreshEventListener : IRefreshEventListener
	{
		private static readonly ILog log = LogManager.GetLogger(typeof(DefaultRefreshEventListener));

		public virtual void OnRefresh(RefreshEvent @event)
		{
			OnRefresh(@event, IdentityMap.Instantiate(10));
		}

		public virtual void OnRefresh(RefreshEvent @event, IDictionary refreshedAlready)
		{
			IEventSource source = @event.Session;

			if (source.PersistenceContext.ReassociateIfUninitializedProxy(@event.Entity))
				return;

			object obj = source.PersistenceContext.UnproxyAndReassociate(@event.Entity);

			if (refreshedAlready.Contains(obj))
			{
				log.Debug("already refreshed");
				return;
			}

			EntityEntry e = source.PersistenceContext.GetEntry(obj);
			IEntityPersister persister;
			object id;

			if (e == null)
			{
				persister = source.GetEntityPersister(null, obj); //refresh() does not pass an entityName
				id = persister.GetIdentifier(obj, source.EntityMode);
				if (log.IsDebugEnabled)
				{
					log.Debug("refreshing transient " + MessageHelper.InfoString(persister, id, source.Factory));
				}
				EntityKey key = new EntityKey(id, persister, source.EntityMode);
				if (source.PersistenceContext.GetEntry(key) != null)
				{
					throw new PersistentObjectException("attempted to refresh transient instance when persistent instance was already associated with the Session: " + 
						MessageHelper.InfoString(persister, id, source.Factory));
				}
			}
			else
			{
				if (log.IsDebugEnabled)
				{
					log.Debug("refreshing " + MessageHelper.InfoString(e.Persister, e.Id, source.Factory));
				}
				if (!e.ExistsInDatabase)
				{
					throw new HibernateException("this instance does not yet exist as a row in the database");
				}

				persister = e.Persister;
				id = e.Id;
			}

			// cascade the refresh prior to refreshing this entity
			refreshedAlready[obj] = obj;
			new Cascade(CascadingAction.Refresh, CascadePoint.BeforeRefresh, source).CascadeOn(persister, obj, refreshedAlready);

			if (e != null)
			{
				EntityKey key = new EntityKey(id, persister, source.EntityMode);
				source.PersistenceContext.RemoveEntity(key);
				if (persister.HasCollections)
					new EvictVisitor(source).Process(obj, persister);
			}

			if (persister.HasCache)
			{
				CacheKey ck = new CacheKey(id, persister.IdentifierType, persister.RootEntityName, source.EntityMode, source.Factory);
				persister.Cache.Remove(ck);
			}

			EvictCachedCollections(persister, id, source.Factory);

			string previousFetchProfile = source.FetchProfile;
			source.FetchProfile = "refresh";
			object result = persister.Load(id, obj, @event.LockMode, source);
			source.FetchProfile = previousFetchProfile;

			UnresolvableObjectException.ThrowIfNull(result, id, persister.EntityName);
		}

		// Evict collections from the factory-level cache
		private void EvictCachedCollections(IEntityPersister persister, object id, ISessionFactoryImplementor factory)
		{
			EvictCachedCollections(persister.PropertyTypes, id, factory);
		}

		private void EvictCachedCollections(IType[] types, object id, ISessionFactoryImplementor factory)
		{
			for (int i = 0; i < types.Length; i++)
			{
				if (types[i].IsCollectionType)
				{
					factory.EvictCollection(((CollectionType)types[i]).Role, id);
				}
				else if (types[i].IsComponentType)
				{
					IAbstractComponentType actype = (IAbstractComponentType)types[i];
					EvictCachedCollections(actype.Subtypes, id, factory);
				}
			}
		}
	}
}

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -