2015-10-20 114 views
2

使用複雜類型的默認列命名約定使用下劃線。這意味着其類型定義的那樣:實體框架的複雜類型的列命名約定

[ColmplexType] 
public class Contact 
{ 
    string Email {get;set;} 
    string Post {get;set;} 
} 

public EntityN 
{ 
    //... 
    public Contact Contact {get;set;} 
} 

,我們會得到一個名爲列這樣的方式

Contact_Email nvarchar(max) 
Contact_Post nvarchar(max) 

我們當然可以配置各列名分別使用ColumnAttribute或Context.Properties映射,但我們是否有是否有可能創建命名約定並因此爲currnet類型配置所有名稱?

對於一些複雜的類型,我寧願在所有的人的名字和屬性使用CammelCase,決不會用undersore連接不提財產的名稱(「聯繫方式」)的。

討論:

這一工程(創建特定表的配置信息)

public class CustomComplexTypeAttributeConvention : ComplexTypeAttributeConvention 
    { 
     public override void Apply(ConventionTypeConfiguration configuration, ComplexTypeAttribute attribute) 
     { 
      Properties().Where(pi => pi.DeclaringType == typeof(Contact)) 
       .Configure(p => p.HasColumnName(p.ClrPropertyInfo.Name) 
      ); 
      base.Apply(configuration, attribute); 
     } 
    } 

和OnModelCreating

modelBuilder.Conventions.AddBefore<ComplexTypeAttributeConvention>(new CustomComplexTypeAttributeConvention()); 

它的工作原理,但我不知道它是一個正確的方式編碼: 1),那麼「AddBefore」按預期工作(我不想刪除默認行爲調查r,只是想覆蓋一個案例的默認行爲)? 2)將「自定義代碼」放入Apply方法或構造函數的最佳選擇是哪裏。

斷點和ComplexTypeAttributeConvention的拆卸帶來了一個想法,我們不越權「默認」的命名慣例,而是通過「所有類型的所有屬性」利用「循環」。

這看起來像最堅實的解決方案,但它仍然是一個「黑客」(它不覆蓋默認的「下劃線」約定,但模擬「ColumnAttribute」的禮物):

public class BriefNameForComplexTypeConvention<T> : Convention 
    { 
     public BriefNameForComplexTypeConvention() 
     { 
      Properties().Where(pi => pi.DeclaringType == typeof(T)) 
       .Configure(p => p.HasColumnName(p.ClrPropertyInfo.Name) 
      ); 
     } 
    } 
    // ... 
    modelBuilder.Conventions.Add(new BriefNameForComplexTypeConvention<Contact>()); 
+0

我認爲這是錯誤的屬性修改 - 看EF源代碼,這只是將類型標記爲ComplexTypes(以及Complex TypeDiscoveryConvention)。我們應該尋找的是構建的ColumnName的複合類型 –

+1

這似乎是一個壞主意的慣例。這將打破,例如,EntityFramework.MappingAPI,其派生屬性名稱從命名,如「CONTACT_EMAIL」一欄,將其轉換爲一個屬性搜索,如「Contact.Email」。如果聯繫人或電子郵件不同,它將無法找到對象上的屬性,並且映射將失敗。這也是包含下劃線的屬性或列的問題。按照慣例,最好不要使用複雜類型的列名。 – Triynko

回答

3

我從來這樣做過,但它是值得一試的ComplexTypeAttributeConvention,你可以刪除默認之一,添加自定義一個DbModelBuilder.Conventions

public class CustomComplexTypeAttributeConvention : ComplexTypeAttributeConvention { 
    public CustomComplexTypeAttributeConvention(){ 
     Properties().Configure(p => p.HasColumnName(p.ClrPropertyInfo.Name)); 
    } 
} 

protected override void OnModelCreating(DbModelBuilder modelBuilder){ 
    modelBuilder.Conventions.Remove<ComplexTypeAttributeConvention>(); 
    modelBuilder.Conventions.Add(new CustomComplexTypeAttributeConvention()); 
    //... 
} 
+0

謝謝。有用。但是我還有一些尚未解決的問題,你能爲我解釋一下嗎? –

+0

我也都體現了原ComplexTypeAttributeConvention類......並沒有發現默認的「強調」的行爲呢?可能你知道它隱藏在哪裏嗎? –

+1

@RomanPokrovskij有關ComplexTypeAttributeConvention的文檔非常有限。我認爲刪除默認並添加自定義之一在我的代碼是好的。因爲自定義的***從默認的繼承***而不會覆蓋任何事物。它只是通過'Properties()'(它是'Convention'的成員)來配置屬性。我認爲我們可以在'Apply'方法中做很多事情(我們可能仍然需要使用'Properties()')。我不知道爲什麼,但我看到一些其他人爲自定義'Convention'編寫代碼就是這樣做的。 –