【发布时间】:2016-07-08 21:00:45
【问题描述】:
我有一个旧数据库,其中包含一些使用Polymorphic Associations 设计的表。通过多态关联,我的意思是根据ObjectType 列,这些表可以是不同表的子表。
例子:
-
Documents表有DocumentID(身份主键)、一些其他列和两个称为ObjectType和ObjectID的特殊列。 - 如果
ObjectType='STUDENT',ObjectID指向Students表。 - 如果
ObjectType='TEACHER'、ObjectID指向Teachers表等。
这类似于this design(如“无外键方法”中所述)或this one(描述为反模式)。显然,这些列没有外键约束(AFAIK 没有数据库允许这种关系)。
我正在使用实体框架 6(使用 Fluent API 的代码优先)编写一个新的数据访问层,它应该与现有代码并排工作。由于这种数据库结构已部署到数百个不同的客户(每个客户都有不同的代码库和不同的数据库定制),因此修改现有表的结构不是一种选择。
我的问题是:如何将这些多态关联映射到我的 EF 代码优先模型中?
编辑:似乎我试图在错误的实体上设计类层次结构。我的理解是,我有很多“GenericChildTables”(如 Documents)应该指向一个(不存在的)实体,该实体将具有复合键 ObjectType+ObjectID。然后我尝试创建新实体(我们称之为“BusinessObject”)并将我的核心实体(学生、教师等)映射为该 BusinessObject 的子类型。
这种设计可能完全是错误的,而且可能完全不可能,因为我正在创建的这个新表 (BusinessObject) 依赖于 StudentID/TeacherID 等,因此它不可能是这些表的父级。使用一些丑陋的解决方法,我可以将 BusinessObject 创建为每个核心实体的单个子对象,并将这些 BusinessObjects 映射到多态表,它确实可以工作,但设计完全错误。
然后我看到Gert Ardold's question 并意识到应该被设计为类层次结构的不是学生/教师/等(分组为一个通用实体),而是这些子表中的每一个,其中根据ObjectType 鉴别器持有不同的子类型 - 这些类型应该被拆分为子类型。 在下面我自己的答案中查看我的解决方案。
【问题讨论】:
-
Here 是我如何使用数据库优先完成的,但也描述了我如何无法将其移植到代码优先。
-
@GertArnold 你试过这样的gist.github.com/mauriciolobo/40a4fc6017539c79135bf62f57ee80f1 吗?
-
不,这不是正确的模型(两个外键)。
-
@GertArnold 这是朋友对我问题的回复,但我不确定它是否有效。您的设计为我指明了正确的方向,我刚刚发布了一个答案,它现在似乎正在工作。如果我正确理解了您的代码,我想问题是 OwnerId 应该从基类(注释)中删除,并且仅是派生类的一部分。
标签: sql-server entity-framework entity-framework-6 polymorphic-associations