用户为应用程序定义的数据模式
User defined data schemas for applications
我想编写一个允许用户定义他们自己的数据库模式的应用程序。用户使用 DSL(生物实验)提供定义,并在此基础上生成 oop/entity 关系模型。后端应该是 RDBMS,例如 Postgres。
最好的方法是什么?
我能想到两种可能的方法:
- 将类型映射到 SQL table 就像您在编写基于 Django 或 Hibernate 的应用程序时所做的那样。然后对象映射到 table 行。
- 描述 "type" table 中的类型和另一个 table 中的对象。
人们通常在这里做什么?对于 1.,权限管理等可以交给 rdbms。然而,如何才能在这里跟踪更改并允许回滚?
谁能指出我的最佳做法?
最佳实践在很大程度上取决于应用程序的特定需求。例如,如果您正在为精通技术且值得信赖的用户编写应用程序生成器,则选项 1 是合适的。例如,PeopleSoft Application Designer 就采用了这种方法。跟踪更改并允许回滚是很棘手的,因为您无法回滚诸如删除的列之类的东西。您可以使用自定义审计 table 编写一些复杂的安排来跟踪所做的事情,以及使其可逆的逻辑。但是您仍然会丢失该删除列的数据。如果存储不是问题,您可以为每个更改制作 table 的备份副本,回滚将简单地恢复该备份。但是这样一来,您可能会丢失在更改和回滚之间添加到 table 的数据。
另一方面,如果您正在创建的更像是一个调查生成器,那么我已经做了一些类似于选项 2 的事情。保留一个元数据 table 来显示 "record"是。记录本身实际上存储在两个 tables - parent 和 child 中。父 table 标识记录,但所有字段都作为键值对存储在子 table 中。您可以完全灵活地存储您想要的任何内容,而且您永远不必为动态更改数据库模式而烦恼。您甚至可以保留元数据的历史版本,这样您就可以随时引用历史记录而不会丢失数据。
有很多选择,实际上比您提供的要多得多。
不要执行选项 1 动态创建 tables/schemas 真的很奇怪,除非您正在编写通用数据库客户端,如 TOAD 或 RAD 工具。这听起来不像是你想要构建的,但如果只是使用现有的一个。当然,您可以动态创建所有 类、映射信息和脚本,但目的是什么?无论如何,你必须使用反射来使用它们,因为它们在你编写程序时不存在。
不要使用 RDBMS RDBMS 背后的想法是它或多或少有一个固定的模式。如果这不符合您的需要,请不要这样做。使用更有活力的东西。像 MongoDb 这样的 NoSql 数据库可能会满足您的需要。如果回滚真的很重要,您可以使用 git 存储库作为后端。
也许它是一个数据仓库? 你说的是 "experiments"。因此,如果您必须存储测量值,这可能就是这样:测量值和它们将具有它们所属的类型和实验……有点像选项 2。要了解更多信息,您可能需要查找 "star schemas"
我想编写一个允许用户定义他们自己的数据库模式的应用程序。用户使用 DSL(生物实验)提供定义,并在此基础上生成 oop/entity 关系模型。后端应该是 RDBMS,例如 Postgres。
最好的方法是什么?
我能想到两种可能的方法:
- 将类型映射到 SQL table 就像您在编写基于 Django 或 Hibernate 的应用程序时所做的那样。然后对象映射到 table 行。
- 描述 "type" table 中的类型和另一个 table 中的对象。
人们通常在这里做什么?对于 1.,权限管理等可以交给 rdbms。然而,如何才能在这里跟踪更改并允许回滚?
谁能指出我的最佳做法?
最佳实践在很大程度上取决于应用程序的特定需求。例如,如果您正在为精通技术且值得信赖的用户编写应用程序生成器,则选项 1 是合适的。例如,PeopleSoft Application Designer 就采用了这种方法。跟踪更改并允许回滚是很棘手的,因为您无法回滚诸如删除的列之类的东西。您可以使用自定义审计 table 编写一些复杂的安排来跟踪所做的事情,以及使其可逆的逻辑。但是您仍然会丢失该删除列的数据。如果存储不是问题,您可以为每个更改制作 table 的备份副本,回滚将简单地恢复该备份。但是这样一来,您可能会丢失在更改和回滚之间添加到 table 的数据。
另一方面,如果您正在创建的更像是一个调查生成器,那么我已经做了一些类似于选项 2 的事情。保留一个元数据 table 来显示 "record"是。记录本身实际上存储在两个 tables - parent 和 child 中。父 table 标识记录,但所有字段都作为键值对存储在子 table 中。您可以完全灵活地存储您想要的任何内容,而且您永远不必为动态更改数据库模式而烦恼。您甚至可以保留元数据的历史版本,这样您就可以随时引用历史记录而不会丢失数据。
有很多选择,实际上比您提供的要多得多。
不要执行选项 1 动态创建 tables/schemas 真的很奇怪,除非您正在编写通用数据库客户端,如 TOAD 或 RAD 工具。这听起来不像是你想要构建的,但如果只是使用现有的一个。当然,您可以动态创建所有 类、映射信息和脚本,但目的是什么?无论如何,你必须使用反射来使用它们,因为它们在你编写程序时不存在。
不要使用 RDBMS RDBMS 背后的想法是它或多或少有一个固定的模式。如果这不符合您的需要,请不要这样做。使用更有活力的东西。像 MongoDb 这样的 NoSql 数据库可能会满足您的需要。如果回滚真的很重要,您可以使用 git 存储库作为后端。
也许它是一个数据仓库? 你说的是 "experiments"。因此,如果您必须存储测量值,这可能就是这样:测量值和它们将具有它们所属的类型和实验……有点像选项 2。要了解更多信息,您可能需要查找 "star schemas"