您将如何设计数据库以允许用户定义的架构

时间:2009-05-28 23:52:33

标签: sql-server database entity-framework schema entity-attribute-value

如果你必须创建一个类似的应用程序 - 比如说一个博客应用程序,那么创建数据库模式就相对简单了。你必须创建一些表,tblPosts,tblAttachments,tblCommets,tblBlaBla ......就是这样(好吧,我知道,这有点简化,但你理解我的意思)。

如果您有一个应用程序,您希望允许用户在运行时定义部分模式,该怎么办?假设您要构建一个用户可以记录任何类型数据的应用程序。一个用户想要记录他的工作时间(startTime,endTime,项目ID,描述),下一个想要收集烹饪食谱,其他人可能是股票报价,他们的婴儿的每周体重,他们花在食物上的每月费用,他们的结果最喜欢的足球队或你能想到的任何东西。

您如何设计数据库来保存所有非常不同类型的数据?您是否会创建一个可以包含所有类型数据的通用模式,是否可以创建反映用户数据模式的新表,或者您是否有另外一个好主意可以做到这一点?

如果重要:我必须使用SQL Server / Entity Framework

9 个答案:

答案 0 :(得分:11)

我们再试一次。

如果您希望他们能够创建自己的架构,那么为什么不使用,哦,我不知道,CREATE TABLE语句来构建架构。你有一个完整的船,功能齐全,功能强大的数据库,可以做一些惊人的事情,如定义模式和存储数据。为什么不使用它?

如果您打算做一些临时属性,那么肯定。

但如果是“全权委托,他们可以做任何他们想做的事情”,那就让他们吧。

他们必须知道SQL吗?嗯,不。那是你的UI任务。您作为工具和应用程序设计人员的工作是隐藏用户的实现。如果你想要关系,那么现在列出的字段,线条和箭头等等。无论如何。

多年来,人们一直在制作“最终用户”,“简单”的数据库工具。

“如果他们想要添加列怎么办?”然后添加一个列,数据库就是这样做的,至少是最好的。如果没有,请创建新表,复制旧数据,删除旧数据。

“如果他们想要删除列怎么办?”往上看。如果您的列无法删除,请将其从用户的逻辑视图中删除,以使其看起来已删除。

“如果他们有数十亿行数据怎么办?”然后他们有数十亿行数据和操作比他们拥有1行数据的时间长了11亿次。如果他们有数十亿行数据,他们可能不应该使用你的系统。

“在数据库上实施数据库”的魅力使我望而却步。

“我这里有Oracle,我怎样才能提供更少的功能,让用户慢一点?”

哎呀,我不知道。

答案 1 :(得分:10)

您无法预测其数据要求的复杂程度。 Entity-Attribute-Value是许多程序员使用的典型解决方案,但它可能就足够了,例如,如果用户的数据通常用多个表建模。

我将用户的自定义数据序列化为XML或YAML或JSON或类似的半结构化格式,并将其保存在文本BLOB中。

您甚至可以创建倒排索引,以便在BLOB中的属性中查找特定值。请参阅http://bret.appspot.com/entry/how-friendfeed-uses-mysql(该技术适用于任何RDBMS,而不仅仅是MySQL)。

另请考虑使用SolrMongoDB等文档存储。这些技术不需要符合关系数据库约定。您可以在运行时向任何文档添加新属性,而无需重新定义架构。但这是一种权衡 - 没有架构意味着你的应用程序不能依赖整个集合中类似的文档/行。


我是实体 - 属性 - 价值反模式的批评者。

我在我的书SQL Antipatterns: Avoiding the Pitfalls of Database Programming中写过关于EAV问题的文章。

这是一个SO答案,我在其中列出了Entity-Attribute-Value的一些问题:“Product table, many kinds of products, each product has many parameters。”

这是我前几天发布的关于EAV问题的更多讨论的博客:“EAV FAIL。”

请务必阅读此博客“Bad CaRMa”,了解如何尝试使完全灵活的数据库几乎摧毁公司。

答案 2 :(得分:5)

我会选择混合实体 - 属性 - 值模型,所以像Antony的回复一样,你有EAV表,但你也有默认列(和类属性),它们将永远存在。

以下是great article关于你的用途:)

作为补充说明,我在几天内使用Linq2Sql敲除了这种方法的原型,这是一个可行的解决方案。鉴于您已经提到了实体框架,我将看一下版本4及其POCO support,因为这将是一种注入混合EAV模型而不会污染您的EF模式的好方法。

答案 3 :(得分:3)

从表面上看,自定义用户数据的无架构或面向文档的数据库(如CouchDBSimpleDB听起来很理想。但是,如果除了SQL和EF之外你不能使用任何东西,我认为这没有多大帮助。

答案 4 :(得分:3)

我不熟悉实体框架,但我倾向于实体 - 属性 - 值(http://en.wikipedia.org/wiki/Entity-Attribute-Value_model)数据库模型。

因此,不是动态创建表格和列,您的应用程序将创建属性(或属性集合),然后您的最终用户将完成值。

但是,正如我所说,我不知道实体框架应该为您做什么,它可能不会让您采用这种方法。

答案 5 :(得分:1)

不是批评性评论,但它可能有助于节省您的一些时间来指出这是唐吉诃德圣杯类型问题之一。 50多年来,人们一直渴望建立一个用户友好的数据库设计界面。

我能想到的唯一准成功的是1. Excel(和它的前辈),2。Filemaker(原始的,不是它现在的味道),和3.(可能,但是怀疑地)访问。请注意,前两个基本上只限于一个表。

如果我们的集体传统智慧能够帮助你打破障碍,我会感到惊讶。但它会很精彩。

答案 6 :(得分:1)

而不是重新实现sqlservers“CREATE TABLE”语句,这是多年前由可能比你或我更好的程序员团队完成的,为什么不以有限的方式向用户公开SQLSERVER - 让他们以有限的方式创建自己的架构,并利用SQLServer的强大功能来正确完成。

答案 7 :(得分:0)

我只是给他们一份SQL Server Management Studio,然后说“疯了!”为什么要在车轮内重新发明轮子?

答案 8 :(得分:0)

看看这个post你可以做到但是这是一项艰苦的工作:)如果性能不是一个问题,xml解决方案也可以工作,虽然这也很多工作。