产品属性的数据库架构

时间:2010-04-16 15:54:53

标签: database-design entity-attribute-value

正如那么多人,我正在寻找Products /Product Properties数据库架构。我正在使用Ruby on Rails和(思考)Sphinx进行分面搜索。

要求:

  • 添加新产品类型及其选项不应要求更改数据库架构
  • 使用Sphinx支持分面搜索。

我遇到的解决方案:
See Bill Karwin's answer

选项1:单表继承

真的不是一个选择。该表将包含许多列的方法。

选项2:类表继承

Ruby on Rails在启动时缓存数据库模式,这意味着每当引入新类型的产品时都会重新启动。如果您有一个可用的产品目录,这可能意味着数百个表。

选项3:序列化LOB

杀死能够在没有繁重的应用程序逻辑的情况下进行分面搜索。

选项4:实体 - 属性 - 值

出于测试目的,EAV工作正常。然而,随着您添加越来越多的选项(例如,当某个选项增加价格或交付时间时),它很快就会变得混乱和维护地狱。


我应该选择哪种方式?还有哪些其他解决方案?我忽略了一颗银弹(哈)吗?

1 个答案:

答案 0 :(得分:2)

IMO,类表继承和EAV的组合以及一些严格的限制将是最好的方法。

EAV就像毒品一样:数量少且情况狭窄,它们可能是有益的;太多会杀了你。 EAV作为模式的主要部分将失败。没有问题。但是,作为良好数据库模式的补充,如果您实施适当的限制,它们将非常有用。

使用EAV的主要规则是,您永远不会编写包含'[AttributeCol] = 'Attribute'的查询。换句话说,您永远不能过滤,排序,限制范围,也不能将特定属性放在报表或表单的任何位置。它只是一个数据袋,可以完全在报表上或列表中的屏幕上吐出。事实上,我已经看到人们将此功能实现为Xml列。

如果您能够维持此限制,则可以将EAV结构添加到类表继承设计中,作为允许用户仅为存储目的向产品添加一组属性的方法。当他们想要使用属性执行任何一个verboten任务时,它必须成为第一类列,并且所有这些都需要。

关键在于执法。如果您认为您不能合理地执行或让其他开发人员对EAV结构的使用强制执行此限制,那么跳过它可能是有意义的。但是,如果您可以强制执行此限制,它可以解决人们想要添加大量属性仅用于存储和跟踪目的的问题。