2013-05-14 44 views
1

我有這些類:ForeignKeyAttribute不工作MVC3 EF5

public class SystemRequirements : DbEntity 
{ 
    public string OS {get;set;} 
} 

public class Application : DbEntity 
{ 
    public string Name {get;set;} 

    public virtual SystemRequirements MinimumSystemRequirements {get;set;} 
    public Guid MinimumSystemRequirementsId {get;set;} 

    public virtual SystemRequirements RecommendedSystemRequirements {get;set;} 
    public Guid RecommendedSystemRequirementsId {get;set;} 
} 

我得到了一個錯誤說:Introducting外鍵約束可能會導致循環或多個級聯路徑。

DbEntity是一個包含主鍵的抽象類。 [Key] public Guid Id {get;set;}

於是,我改變Application到:

public class Application : DbEntity 
{ 
    public string Name {get;set;} 

    public virtual SystemRequirements MinimumSystemRequirements {get;set;} 
    [ForeignKey("MinimumSystemRequirements")] 
    public Guid MinimumSystemRequirementsId {get;set;} 

    public virtual SystemRequirements RecommendedSystemRequirements {get;set;} 
    [ForeignKey("RecommendedSystemRequirements")] 
    public Guid RecommendedSystemRequirementsId {get;set;} 
} 

所以我的問題是,爲什麼不這項工作?我甚至試過在SystemRequirements中提到Application,那沒用?

請不要在拼寫錯誤時翻譯這篇文章。我的代碼在VS上很好,我複製並粘貼,而不是輸出。

回答

0

Heyyyyy好消息。我找到了問題!

我還記得,早在天(兩個月前),我被告知,要想在代碼第一次使用Attributes使Cascade On Delete你必須這樣做:

public Guid CascadeOnId {get;set;} 
public virtual Cascade CascadeOn {get;set;} 

不過之前我就知道,我總是使用此:

public virtual Cascade CascadeOff {get;set;} 

的原因,我發現了循環刪除,是因爲第一個例子將刪除硬盤驅動器,如果它存在,但硬盤驅動器必須始終存在於它的第二個實例,例如:

public Guid FirstCascadeId {get;set;} 
public virtual Cascade FirstCascade {get;set;} 

public Guid SecondCascadeId {get;set;} 
public virtual Cascade SecondCascade {get;set;} 

因此,實體框架令人擔憂的是,如果您刪除級聯實體,則必須刪除其關聯的父級,在刪除父級時必須刪除所有關聯的級聯。這是週期開始的地方。我希望我有某種意義。

爲了將Cascade On Delete了,你不能指定有關虛擬一個Guid標識。因此,爲了使上述工作,您可以使用:

public virtual Cascade FirstCascade {get;set;} 
public virtual Cascade SecondCascade {get;set;} 

您可以在第一Cascade On Delete轉,如果你想,只要確保其中一人還沒有得到它,它工作得很好:)

我找到了答案,通過使用模式,然後再讓我頭上一個巨大的發光燈泡:P

+0

有趣的是,你有這方面的一些文件,你可以鏈接到? – 2013-05-15 13:42:13

+0

不,我只記得做這一切,試一試它很容易設置,我使用的模型'計算機'和'Hdd' 「計算機」必須引用(導航屬性)到'Hdd',然後佈局'Computer'就像我的回答 – 2013-05-15 14:59:50

+0

中的場景一樣,我發現你也可以使Id屬性爲空,永遠不會意識到這一點。仍然有外鍵協會的好處,但我更喜歡顯式(流暢)映射,而不是依賴這些隱藏的功能。 – 2013-05-15 21:42:32

0

SystemRequirements可能需要具有MinimumSystemRequirementsIDRecommendedSystemRequirmentsID字段。我對EF FK關係的理解是,它會查看您稱爲FK的Element的值的模型,然後將其用於鏈接。

試試這個:

public class SystemRequirements : DbEntity 
{ 
    public string OS {get;set;} 
    public Guid MinimumSystemRequirementsId {get;set;} 
    public Guid RecommendedSystemRequirementsId {get;set;} 
} 
+0

我認爲我得到了虛擬類和ID都連接在一起 – 2013-05-14 15:19:43

+0

你必須在'Application'模型虛擬和FK也是如此,但FK只是'指向'SystemRequirements中使用的值......想象它像兩個表......你ar e試圖設置一個外鍵,它需要指向另一個表中的一個鍵......我知道你在所有DbEntity中都有'id',但是我的經驗要求FK匹配模型中的字段我是試圖link..thus'MinimumSystemRequirementsId'和'RecommendedSystemRequirementsId' – 2013-05-14 17:57:30

+0

所以你說要添加FK到SystemRequirements類或修改DbEntity – 2013-05-14 18:11:25

0

你必須告訴EF(至少)ApplicationSystemRequirements之間的關聯的一個已經沒有級聯刪除,例如:

modelBuilder.Entity<Application>().HasRequired(a => a.MinimumSystemRequirements) 
    .WithMany().HasForeignKey(a => a.MinimumSystemRequirementsId) 
    .WillCascadeOnDelete(false); 

(在上下文的過載爲OnModelCreating)。

+0

我更喜歡流利的api的屬性 – 2013-05-14 18:09:04

+0

沒有相當於這個的屬性:( – 2013-05-14 18:10:32

+0

你需要HasRequired?因爲我不需要任何必需的東西在我正在做的。 – 2013-05-15 08:35:47