升级到 NHibernate 3.1 时 NHibernate 映射中断

发布于 2024-11-28 03:44:53 字数 3387 浏览 0 评论 0原文

我最近刚刚升级到 FluentNHibernate 1.2,它使用 NHibernate 3.1。升级后,我的一些旧映射无法正常工作。我一直很难弄清楚为什么,我想也许这里有人可以提供帮助。

我有 3 个课程:练习、练习和练习练习。一个练习可以有很多练习,而一个练习可以包含在很多练习中。 PracticeDrill 是连接它们的表,还包含一个 Order。这是我的 C# POCO:

public class PracticeDrill
{
    public virtual Practice Practice { get; set; }
    public virtual Drill Drill { get; set; }
    public virtual int Order { get; set; }
}

public class Practice
{
    public virtual Guid Id { get; set; }
    public virtual ICollection<PracticeDrill> Drills { get; set; }

    public Practice()
    {
        Drills = new List<PracticeDrill>();
    }
}

public class Drill
{
    public virtual Guid Id { get; set; }
}

这是我的映射文件的样子:

public class PracticeDrillMap : ClassMap<PracticeDrill>
{
    public PracticeDrillMap()
    {
        CompositeId()
            .KeyReference(x => x.Practice, "PracticeId")
            .KeyReference(x => x.Drill, "DrillId");
        Map(x => x.Order)
            .Column("[Order]")
            .Not.Nullable();
    }
}

public class PracticeMap : ClassMap<Practice>
{
    public PracticeMap()
    {
        Id(x => x.Id)
            .GeneratedBy.GuidComb();
        HasMany(x => x.Drills)
            .KeyColumn("PracticeId")
            .AsBag()
            .Inverse()
            .Cascade.AllDeleteOrphan();
    }
}

public class DrillMap : ClassMap<Drill>
{
    public DrillMap()
    {
        Id(x => x.Id)
            .GeneratedBy.GuidComb();
    }
}

这之前允许我创建/删除引用 Drills 的实践。现在,当我尝试删除练习时,我收到以下异常:

{System.Collections.Generic.KeyNotFoundException: The given key was not present in the dictionary.    
at System.ThrowHelper.ThrowKeyNotFoundException()    
at System.Collections.Generic.Dictionary`2.get_Item(TKey key)    
at NHibernate.Engine.StatefulPersistenceContext.RemoveEntity(EntityKey key) in d:\CSharp\NH\NH\nhibernate\src\NHibernate\Engine\StatefulPersistenceContext.cs:line 444    
at NHibernate.Action.EntityDeleteAction.Execute() in d:\CSharp\NH\NH\nhibernate\src\NHibernate\Action\EntityDeleteAction.cs:line 87    
at NHibernate.Engine.ActionQueue.Execute(IExecutable executable) in d:\CSharp\NH\NH\nhibernate\src\NHibernate\Engine\ActionQueue.cs:line 136    
at NHibernate.Engine.ActionQueue.ExecuteActions(IList list) in d:\CSharp\NH\NH\nhibernate\src\NHibernate\Engine\ActionQueue.cs:line 126    
at NHibernate.Engine.ActionQueue.ExecuteActions() in d:\CSharp\NH\NH\nhibernate\src\NHibernate\Engine\ActionQueue.cs:line 174    
at NHibernate.Event.Default.AbstractFlushingEventListener.PerformExecutions(IEventSource session) in d:\CSharp\NH\NH\nhibernate\src\NHibernate\Event\Default\AbstractFlushingEventListener.cs:line 241    
at NHibernate.Event.Default.DefaultFlushEventListener.OnFlush(FlushEvent event) in d:\CSharp\NH\NH\nhibernate\src\NHibernate\Event\Default\DefaultFlushEventListener.cs:line 19    
at NHibernate.Impl.SessionImpl.Flush() in d:\CSharp\NH\NH\nhibernate\src\NHibernate\Impl\SessionImpl.cs:line 1472    
at NHibernate.Transaction.AdoTransaction.Commit() in d:\CSharp\NH\NH\nhibernate\src\NHibernate\Transaction\AdoTransaction.cs:line 187    
at GoldMedalSquared.Toolbox.Data.NHibernate.RepositoryBase`1.WrapInTransaction(ISession session, Action query) in C:\Work\primary\trunk\Toolbox\Data.NHibernate\RepositoryBase.cs:line 42}

有什么建议吗?

I just recently upgraded to FluentNHibernate 1.2 which uses NHibernate 3.1. After upgrading some of my old mappings are not working. I've been having a hard time figuring out why, I thought maybe someone here could help.

I have 3 classes, Practice, Drill, and PracticeDrill. A Practice has many Drills and a Drill can be in many Practices. PracticeDrill is the table that joins them and also includes an Order. Here are my C# POCOs:

public class PracticeDrill
{
    public virtual Practice Practice { get; set; }
    public virtual Drill Drill { get; set; }
    public virtual int Order { get; set; }
}

public class Practice
{
    public virtual Guid Id { get; set; }
    public virtual ICollection<PracticeDrill> Drills { get; set; }

    public Practice()
    {
        Drills = new List<PracticeDrill>();
    }
}

public class Drill
{
    public virtual Guid Id { get; set; }
}

Here is what my mapping files look like:

public class PracticeDrillMap : ClassMap<PracticeDrill>
{
    public PracticeDrillMap()
    {
        CompositeId()
            .KeyReference(x => x.Practice, "PracticeId")
            .KeyReference(x => x.Drill, "DrillId");
        Map(x => x.Order)
            .Column("[Order]")
            .Not.Nullable();
    }
}

public class PracticeMap : ClassMap<Practice>
{
    public PracticeMap()
    {
        Id(x => x.Id)
            .GeneratedBy.GuidComb();
        HasMany(x => x.Drills)
            .KeyColumn("PracticeId")
            .AsBag()
            .Inverse()
            .Cascade.AllDeleteOrphan();
    }
}

public class DrillMap : ClassMap<Drill>
{
    public DrillMap()
    {
        Id(x => x.Id)
            .GeneratedBy.GuidComb();
    }
}

This previously allowed me to Create/Delete Practices that referenced Drills. Now when I try to Delete a practice I get the following exception:

{System.Collections.Generic.KeyNotFoundException: The given key was not present in the dictionary.    
at System.ThrowHelper.ThrowKeyNotFoundException()    
at System.Collections.Generic.Dictionary`2.get_Item(TKey key)    
at NHibernate.Engine.StatefulPersistenceContext.RemoveEntity(EntityKey key) in d:\CSharp\NH\NH\nhibernate\src\NHibernate\Engine\StatefulPersistenceContext.cs:line 444    
at NHibernate.Action.EntityDeleteAction.Execute() in d:\CSharp\NH\NH\nhibernate\src\NHibernate\Action\EntityDeleteAction.cs:line 87    
at NHibernate.Engine.ActionQueue.Execute(IExecutable executable) in d:\CSharp\NH\NH\nhibernate\src\NHibernate\Engine\ActionQueue.cs:line 136    
at NHibernate.Engine.ActionQueue.ExecuteActions(IList list) in d:\CSharp\NH\NH\nhibernate\src\NHibernate\Engine\ActionQueue.cs:line 126    
at NHibernate.Engine.ActionQueue.ExecuteActions() in d:\CSharp\NH\NH\nhibernate\src\NHibernate\Engine\ActionQueue.cs:line 174    
at NHibernate.Event.Default.AbstractFlushingEventListener.PerformExecutions(IEventSource session) in d:\CSharp\NH\NH\nhibernate\src\NHibernate\Event\Default\AbstractFlushingEventListener.cs:line 241    
at NHibernate.Event.Default.DefaultFlushEventListener.OnFlush(FlushEvent event) in d:\CSharp\NH\NH\nhibernate\src\NHibernate\Event\Default\DefaultFlushEventListener.cs:line 19    
at NHibernate.Impl.SessionImpl.Flush() in d:\CSharp\NH\NH\nhibernate\src\NHibernate\Impl\SessionImpl.cs:line 1472    
at NHibernate.Transaction.AdoTransaction.Commit() in d:\CSharp\NH\NH\nhibernate\src\NHibernate\Transaction\AdoTransaction.cs:line 187    
at GoldMedalSquared.Toolbox.Data.NHibernate.RepositoryBase`1.WrapInTransaction(ISession session, Action query) in C:\Work\primary\trunk\Toolbox\Data.NHibernate\RepositoryBase.cs:line 42}

Any suggestions?

如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。

扫码二维码加入Web技术交流群

发布评论

需要 登录 才能够评论, 你可以免费 注册 一个本站的账号。

评论(1

酒儿 2024-12-05 03:44:53

您映射了 ICollection;仅使用一个外键 (.KeyColumn("PracticeId")) 进行练习,但它实际上有一个复合键。因此 NH 无法通过 PracticeDrill 的 id 对其进行微调。

整个映射有点奇怪。为什么使用参考类?如果确实有必要,为什么要使用复合键呢?

You mapped ICollection<PracticeDrill> Drills with only one foreign key (.KeyColumn("PracticeId")), but it actually has a composite key. Therefore NH can't fine the PracticeDrill by its id.

The whole mapping is a bit strange. Why using a reference class? If it is really necessary, why using a composite key?

~没有更多了~
我们使用 Cookies 和其他技术来定制您的体验包括您的登录状态等。通过阅读我们的 隐私政策 了解更多相关信息。 单击 接受 或继续使用网站,即表示您同意使用 Cookies 和您的相关数据。
原文