[英]Entity Framework 6 with POCO Using Only Some Classes
我在另一個VS項目中使用了多個相互關聯的類,例如:
namespace MyOtherProject
{
public class A {
public string Name {get;set;}
}
public class B {
public int Value {get;set;}
public A Child {get;set;}
}
}
現在,我想首先在EF中將這些類用作POCO用於代碼。 但是,我不需要數據庫中的所有類,而只需要其中一些。 所以我創建了一個上下文:
public class MyContext : DbContext
{
public MyContext () : base("MyContext ")
{
}
public DbSet<B> Bs { get; set; }
protected override void OnModelCreating(DbModelBuilder modelBuilder)
{
modelBuilder.Conventions.Remove<PluralizingTableNameConvention>();
}
}
當我嘗試運行項目時,出現此錯誤:
System.Data.Entity.ModelConfiguration.ModelValidationException:在模型生成期間檢測到一個或多個驗證錯誤:MyProject.A:名稱:模式中的每個類型名稱都必須是唯一的。 類型名稱“ A”已經定義。
請注意,錯誤中的名稱空間與類A的定義不同,因為我的類A是在另一個(共享)項目中定義的。 相反,名稱空間是上下文之一。
您可能已經省略了DbSet和DbSet語句,它的工作原理相同。 實體框架將隱式包括它們,因為學生實體引用了注冊實體,而注冊實體引用了課程實體。
我的假設(未確認)是EF看到B引用了A但沒有類型A的數據集,因此它在內部生成了一個類A,然后突然發現有兩個此類。
任何人都知道確切的問題是什么,我該怎么做才能解決它? 我有太多我並不需要的類,所以我不想為我擁有的每個類創建數據集。
首先,從DbSet<Type1>
獲取所有通用類型參數( Type1
, Type2
...)。 然后,應檢查每種類型的內部屬性類型,即對其他類型的引用(作為直接鏈接或通過ICollection
集),-如果此內部類型在第一個tableTypes集合中不存在,我們將忽略它們。
protected override void OnModelCreating(DbModelBuilder modelBuilder)
{
//other stuff.....
Func<Type, bool> genericFilter = x => typeof(IEnumerable).IsAssignableFrom(x) && x.GenericTypeArguments.Length == 1;
//All types of your context tables
var tablesTypes = GetType().GetProperties()
.Where(x => genericFilter(x.PropertyType))
.Select(x => x.PropertyType.GenericTypeArguments.First());
var namespaces2ignore = new List<string> { "Namespace2Ignore1", "Namespace2Ignore2" };
var toIgnore = new List<Type>();
foreach (var type in tablesTypes)
//Ignore internal types, which not exist at tablesTypes
toIgnore.AddRange(type.GetProperties()
.Select(x => genericFilter(x.PropertyType) ? x.PropertyType.GenericTypeArguments.First() : x.PropertyType)
.Where(x => !tablesTypes.Contains(x) && namespaces2ignore.Contains(x.Namespace)
/*or as you suggested: && typeof(A).Assembly == x.Assembly*/
).ToList());
modelBuilder.Ignore(toIgnore);
}
如果要在特定對類型屬性上添加條件,可以執行以下操作:
foreach (var type in tablesTypes)
foreach(var prop in type.GetProperties()
.Select(x => new { type = genericFilter(x.PropertyType) ? x.PropertyType.GenericTypeArguments.First() : x.PropertyType, prop = x })
.Where(x => !tablesTypes.Contains(x.type) && namespaces2ignore.Contains(x.type.Namespace)
).ToList())
if(!(type == typeof(TestType) && prop.prop.Name == "Test"))
toIgnore.Add(prop.type);
現在將不會排除類型為TestType
名稱為“ Test”的TestType
。
聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.