EF5 Code first TPH Mapping error using DBSet.Find()
在首先使用Entity Framework 5代码并按表分层结构时。
这与存储库和工作单元结合在一起(尝试了几种实现方式)。
我遇到以下错误:
(34,10) : error 3032: Problem in mapping fragments starting at lines 19, 34:EntityTypes T, T are being mapped to the same rows in table T. Mapping conditions can be used to distinguish the rows that these types are mapped to.
我已使用以下指南解决了此问题:
实体框架4.3-TPH映射和迁移错误
当使用所有记录的常规查找时,此方法有效,然后没有错误。
使用
使用
请问有人有解决此问题的方法吗?
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 | public class TDataContext : DbContext { // Models public abstract class BaseTrackable { public DateTime DateModified { get; set; } } public abstract class ParentClass : BaseTrackable { public int ParentId { get; set; } public string ParentString { get; set; } } public class Foo : ParentClass { public string FooString { get; set; } } public class Bar : ParentClass { public string BarString { get; set; } } // Configuration public class ParentConfiguration : EntityTypeConfiguration<ParentClass> { public ParentConfiguration() { ToTable("Parent"); } } public class FooConfiguration : EntityTypeConfiguration<Foo> { public FooConfiguration() { Map(m => m.Requires("FooIndicator").HasValue(true)); } } public class BarConfiguration : EntityTypeConfiguration<Bar> { public BarConfiguration() { Map(m => m.Requires("BarIndicator").HasValue(true)); } } public DbSet<ParentClass> Parent { get; set; } protected override void OnModelCreating(DbModelBuilder modelBuilder) { modelBuilder.Configurations .Add(new ParentConfiguration()) .Add(new FooConfiguration()) .Add(new BarConfiguration()); } } public class Controller { TDataContext _context = new TDataContext(); // Repository function public T GetById< T >(object id) where T : class { var dbset = _context.Set< T >(); return dbset.Find(id); } public IQueryable<TDataContext.Foo> GetFiltered(Expression<Func<TDataContext.Foo, bool>> filter) { var dbset = _context.Set<TDataContext.Foo>(); return dbset.Where(filter); } // Final call // Which fails.. public TDataContext.Foo Get(int id) { return this.GetById<TDataContext.Foo>(id); } // This works... public TDataContext.Foo GetWhere(int id) { return this.GetFiltered(f => f.ParentId == id).FirstOrDefault(); } } |
会不会更好
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 | public class FooConfiguration : EntityTypeConfiguration<Foo> { public FooConfiguration() { Map(m => m.Requires("Type").HasValue("Foo")); } } public class BarConfiguration : EntityTypeConfiguration<Bar> { public BarConfiguration() { Map(m => m.Requires("Type").HasValue("Bar"); } } |
通过这种方式,FooConfiguration不需要了解任何有关BarConfiguration的知识,反之亦然。从EF 4.3迁移到5.0时遇到了这个问题,我认为发生了变化的是在EF 5.0中区分数据库列不可为空。我认为它们不可为空更有意义,并且一般而言,对每个派生类型只使用一个discrimanotor列,而不是对每个类型使用一个列(如EF 4.3中那样)会更好。
-斯坦
找到了可以部分解决我的问题的东西...
在表中添加另一个指标时,没有更多错误,例如:
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 | public class FooConfiguration : EntityTypeConfiguration<Foo> { public FooConfiguration() { Map(m => { m.Requires("FooIndicator").HasValue(true); m.Requires("BarIndicator").HasValue<short>(1); }); } } public class BarConfiguration : EntityTypeConfiguration<Bar> { public BarConfiguration() { Map(m => { m.Requires("BarIndicator").HasValue(true); m.Requires("FooIndicator").HasValue<short>(0); }); } } |