9

我正计划创建我的应用程序并为模型使用 ORM,但问题是,数据库的一部分使用实体-属性-值表。

我非常喜欢 Doctrine ORM,但我不知道是否有可能创建看起来像任何普通学说实体的类,而实际上连接到的表是 EAV 样式。

是否可以在这方面使用 Doctrine,如果可以,如何使用?

4

2 回答 2

5

绝对有可能:

有这样的关系:对象(一对多)-> AttributeValue -> 多对一-> AttributeType

于 2013-01-14T23:19:20.923 回答
2

鉴于EAVentity ,如何建立和attribute使用学说之间的关系似乎是显而易见的。在最复杂的情​​况下,我们处理多对多关系。

所以假设我们想将一个属性映射Name到一个实体User。假设一个用户只有一个名字并且每个名字都属于一个用户,这个链接可以使用一对一关系存档

attribute但是如何建模和之间的关系value?问题是值可以是不同的类型,甚至需要不同数量的字段来保存它们的信息。

考虑属性namephone_number。虽然名称可能由字符串表示,但电话号码可能需要一个整数。或者甚至需要在单独的字段中不仅有号码而且还需要区号。

因为 EAV 需要非常灵活的值表示,所以不可能将它们全部存储在数据库表的同一字段中(忽略 blob、数据序列化等)。因此,大多数 EAV 实现使用不同的表来表示不同的值类型。

为了达到这种灵活性,学说特征继承映射。它基本上允许您扩展学说实体。这样做你discriminator为你的实体的每个子类型指定一个:

/**
  * @Entity
  * @InheritanceType("JOINED")
  * @DiscriminatorColumn(name="value_type", type="string")
  * @DiscriminatorMap({"name" = "Name", "phone" = "PhoneNumber"})
*/
class Value
{
// ...
}

/** @Entity */
class Name extends Value
{
// ...
}

/** @Entity */
class PhoneNumber extends Value
{
// ...
}

该类Value为所有值提供通用实现,即 id。每个子类(即NamePhoneNumber)通过它们的特定值扩展这些公共值,例如附加字段。

  • @DiscriminatorColumn定义了父关系中存储值类型的列。
  • 教义使用将@DiscriminatorMap类型从 映射@DiscriminatorColumn到这些类之一。

attribute和之间的关系value可以指定给父类。然后从属性调用值将获取所有类型的值,这些值可以在运行时使用例如instanceof进行过滤(和处理)。

于 2015-10-21T21:46:06.477 回答