2013-09-05 49 views
2

DELETE語句與SAME TABLE REFERENCE約束條件 「FK_AuthCategories_Parent」衝突。衝突發生在數據庫「MyDB」中, 表「dbo.AuthCategories」, 列'ParentID'。使用LINQ to SQL簡單級聯刪除自引用表

如果我嘗試在具有自引用FK的PARENTID我得到上面,我需要基本上首先除去孩子的誤差(即它試圖刪除有子父項表中刪除一切這打破了FK)。

var dc = from c in db.AuthCategories 
     select c; 
db.AuthCategories.DeleteAllOnSubmit(dc); 
db.SubmitChanges(); 

是否有一個簡單的LINQ to SQL查詢,它將在處理級聯刪除時刪除表中的所有內容?

  • 不想使用SQL服務器端解決方案如觸發器或ON DELETE CASCADE
  • 需要使用LINQ到SQL,不是EF
  • 希望它儘可能的簡單,單班輪如果可能的話

這裏的表結構:

[Table(Name = "AuthCategories")] 
public class AuthCategory 
{ 
    [Column(IsPrimaryKey = true, IsDbGenerated = true)] 
    public int ID { get; set; } 

    [Column] 
    public string Name { get; set; } 

    [Column] 
    private int? ParentID { get; set; } 
    private EntityRef<AuthCategory> parent; 
    [Association(IsForeignKey = true, ThisKey = "ParentID")] 
    public AuthCategory Parent 
    { 
     get { return parent.Entity; } 
     set { parent.Entity = value; } 
    } 
} 

回答

2

好吧,咖啡踢,這個工程:

添加一個孩子的IEnumerable的類:

private EntitySet<AuthCategory> children = new EntitySet<AuthCategory>(); 
[Association(Storage = "children", OtherKey = "ParentID")] 
public IEnumerable<AuthCategory> AuthCatChildren 
{ 
    get { return children; } 
} 
public IEnumerable<AuthCategory> Children 
{ 
    get { return (from x in AuthCatChildren select x).AsEnumerable(); } 
} 

現在你可以通過while環路先刪除兒童:

// Loop, Deleting all rows with no children (which would delete childless parents and nested grandchild/children) 
int loop = 1; 
while (loop > 0) 
{ 
    var dbList = from c in db.AuthCategories.ToList() 
        where c.Children.Count() == 0 
        select c; 
    loop = dbList.Count(); 
    db.AuthCategories.DeleteAllOnSubmit(dbList); 
    db.SubmitChanges(); 
} 
+0

L2S沒有原生支持自引用級聯刪除 - 出於好奇,爲什麼你不想使用ON_DELETE_CASCADE?當您的表中有一百萬行時,該刪除代碼將如何執行? –

+0

那麼,你*可以使用'ON_DELETE_CASCADE',但是這個循環提供了更多的控制權/可以擴展到只刪除某些父母/孩子,而不是強制吹散所有東西。 –

+0

夠公平的,儘管我仍然認爲只要你走過幾百行就會撞牆! –