开发者

NHibernate - KeyNotFoundException: The given key was not present in the dictionary

Update:开发者_C百科 I have fixed this issue

I have the following block of code which should ultimately update a record

if (session.Contains(entity))
{
    session.Evict(entity);
}

which errors on Session.Evict(entity) with a KeyNotFoundException, and the following message:

The given key was not present in the dictionary.

Am I misunderstanding something? I assume if session.Contains(entity) is true, then the key should exist and therefore session.Evict() should work as expected?

Stack trace is as follows:

System.Collections.Generic.KeyNotFoundException : The given key was not present in the dictionary.

at System.Collections.Generic.Dictionary`2.get_Item(TKey key)
at NHibernate.Engine.StatefulPersistenceContext.RemoveEntity(EntityKey key)
at NHibernate.Event.Default.DefaultEvictEventListener.OnEvict(EvictEvent event)
at NHibernate.Impl.SessionImpl.FireEvict(EvictEvent evictEvent)
at NHibernate.Impl.SessionImpl.Evict(Object obj)
at Core.Repository.NHibernate.Repository.NoIdRepository`1.Update(T entity) in NoIdRepository.cs: line 26
at Core.Tests.Repository.NHibernate.Repository.TestInstanceVersionRepository.Test_Saving_Data() in TestInstanceVersionRepository.cs: line 63 


It turns out that the Equals() method was comparing incorrectly, it was checking the equality of an additional property on the object which was not part of the composite key.

i.e.

return obj != null
                   && obj is InstanceVersion
                   && this.Instance.Id == ((InstanceVersion)obj).Instance.Id
                   && this.Version == ((InstanceVersion)obj).Version
                   && this.DefaultEntry == ((InstanceVersion)obj).DefaultEntry;

Where DefaultEntry is a property .


It may be an issue of how NH identifies the entity. It may use a different method to find the entity in Contains as in Evict.

If you use a composite ID, it uses instances of the entity itself as key type, unless you implemented another class which represents the composite id. Equals and GetHashCode are additionally important to compare the composite key. It needs to compare the properties of the key.

To find the actual reason, you could debug the NH code, or at least take a look into the stack trace (paste it to your question).


to my understanding and guess, if the PK of your entity is 0 your entity does not need to be Evicted because is not linked yet to the data storage.

If so, you could check ID != 0 in && with the session.Contains.

0

上一篇:

下一篇:

精彩评论

暂无评论...
验证码 换一张
取 消

最新问答

问答排行榜