2009-09-24 48 views
1

我想要使用NHibernate有一个简单的一对多关系/层次结构。我想孤儿被自动删除,但是我目前的尝试都是由ObjectDeletedException引起的。我想知道如果有人能告诉我我做错了什么。NHibernate:简单删除孤儿场景不起作用

编辑:

我应该已经指定了我加载根美孚,然后除去孩子的会话之外,导致被孤立的一个或更多的孩子。当我在第二个会话中随后调用SaveOrUpdate(root)时发生异常。我如何纠正分离和修改的对象与数据库中持久化的对象之间的子项列表中的差异?

问题

示例代码看起来是这样的:

Foo foo = new Foo(); 
Foo child1 = new Foo(); 
Foo child2 = new Foo(); 

foo.Children.Add(child1); 
child1.Children.Add(child2); 

// session #1 
session.SaveOrUpdate(foo); 

// so far, so good 

// outside of any session 
foo.Children.Clear(); 

// session #2 
PutFoo(foo); // results in ObjectDeletedException 

对象正在持续:

class Foo 
{ 
    private IList<Foo> children = new List<Foo> children; 

    public virtual int Id { get; private set; } 
    public IList<Foo> Children 
    { 
     get { return children; } 
     set { children = value; } 
    } 
} 

的FluentNHibernate映射:

class FooMap : ClassMap<SyncDir> 
{ 
    public FooMap() 
    { 
     Id(x => x.Id); 
     base.HasMany(x => x.Children).Cascade.AllDeleteOrphan(); 
    } 
} 

用于保留一个对象的方法Foo类型:

void PutFoo(Foo foo) 
{ 
    using (var session = factory.OpenSession()) 
    using (var transaction = factory.BeginTransaction()) 
    { 
     session.SaveOrUpdate(foo); 
     transaction.Commit(); 
    } 
} 

回答

1

我总是这样做,是建立一种双向关系。

所以,这意味着孩子有一个参考他们的父母。 从集合中删除一个子项时,我也将对父项的引用设置为NULL。

在映射中,您还必须指出关系的'反向'结束。 我也从不在课堂外暴露'原样'的集合。

因此,我主要是做这样的:

public class Foo 
{ 
    private ISet<Bar> _bars = new HashSet<Bar>(); 

    public ReadOnlyCollection<Bar> Bars { get return new List<Bar>(_bars).AsReadOnly(); } 

    public void AddBar(Bar b) 
    { 
     b.Parent = this; 
     _bars.Add (b); 
    } 

    public void RemoveBar(Bar b) 
    { 
     b.Foo = null; 
     _bars.Remove (b); 
    } 
} 


public class Bar 
{ 
    public Foo Parent { get; set; } 
} 

然后,在映射我设置的集合“逆”端。 所以,这意味着在我的映射中(我仍然使用xml文件来指定映射),我在Foo类的Bars集合上设置了inverse = true属性。

+0

我添加了Parent和Add()/ Remove()方法,但在删除子项后,在根节点上调用SaveOrUpdate()时仍然收到异常。我应该提到我加载根,然后在会话外调用Remove()。只有在删除子项并从第二个会话中调用SaveOrUpdate()时,才会发生异常。 – anthony 2009-09-25 19:20:42