具有高数据量的清单应用程序的最佳数据库设计方法

时间:2018-07-05 23:20:49

标签: database database-design

对于我们的系统,清单定义为一组项目。每个项目都有两种可能的状态:正常或不正常(NOK)。在我们的应用程序中填写核对清单时,如果用户将某项标记为“ NOK”,则会显示可能的问题列表。然后,用户可以选择与当前清单项目相关的一个或多个问题。当用户未选择任何NOK选项时,我们认为该项目为OK。

项目示例: 一个项目示例为:冰淇淋 如果用户将此项目标记为NOK,则可能的选项列表可能是:

  • 融化

  • 不良品味

  • ...

此系统的数据库具有下表:

CHECKLIST_TEMPLATE:

用户可以回答的所有可能清单的模板都保存在该表中。用户可以自由创建或编辑任意数量的模板。

CHECKLIST_ITEMS:

在这里,我们关联哪些项目属于什么模板。一个项目只能属于一个模板,但是一个模板可以有多个项目。

CHECKLIST_ITEMS_NOK_OPTIONS:

在此表中,我们将NOK选项与清单项相关联。一个NOK选项只能属于一个项目,但是一个项目可以有多个NOK选项。

这些是使清单运行的基本表。我们还有另一组表格可以保存用户回答的清单:

CHECKLIST:

该表包含:用户回答的内容,模板和时间。该表中的每个条目都有其自己的唯一ID。

CHECKLIST_ANSWERS:

在此表中,我们将检查清单ID(来自CHECKLIST表)与NOK选项相关联。如果一个项目有5个NOK选项,我们会在此表中保存5个条目,告知用户在回答清单时是否选择了此NOK选项(更进一步,您将了解我们为什么使用此方法)。

现在是问题所在:

包含30个项目的清单,每个具有3个NOK选项的项目都将添加到CHECKLIST_ANSWERS表的90行中。该表目前每天增长10万行,我们担心表的大小。该表趋向于随着时间增长甚至更快。因此,下个月可能是每天12万条线(下个月可能是每天12万条线,到2018年底,我们估计此表将每天增加40万条线,到2019年底,每天2kk条线)... / p>

我们无法删除旧的清单,因为它们用于向客户生成一些报告。

重新创建已回答的清单

  

(进一步,您将了解我们为什么使用此方法)

我们选择保存每个NOK选项,因为用户可以编辑模板。因此,例如,他能够更改项目描述。这是一个危险的功能(也是必需的),因为如果用户更改了商品的含义,则可能会损害已经回答的清单。为了解决此问题并确保清单的完整性,当用户编辑项目时,我们在后端签入以检测项目的含义是否已更改。如果发生这种情况,则将禁用当前项目(及其所有选项),并自动创建另一个项目并将其与模板关联。这样可以确保将旧清单与旧项目相关联,并将新清单与新项目相关联。

如果用户也编辑NOK选项,则会发生相同的逻辑。

因此,对于用户回答的每个清单,我们需要知道当时模板中包含哪些项目。这就是为什么我们将所有项目的所有NOK选项都保存在CHECKLIST_ANSWERS表中的原因。通过简单的连接,我们可以重新创建用户在特定时刻回答的相同清单,同时考虑到哪些项目或NOK选项处于活动状态。

为解决桌子的快速增长,到目前为止,我们提供了4种可能的解决方案。其中两个假设我们将不会更改保存在CHECKLIST_ANSWERS表中的内容,而是继续保存所有NOK选项(无论是否选中)。另外两个正在考虑更改实现,而不是保存每个NOK选项并指出用户是否选择了该选项,而是仅保存 选定的选项。因此,如果该项正常,则表中将没有该项的条目。

解决方案在CHECKLIST_ANSWERS中保持相同的逻辑:

1-将当前CHECKLIST_ANSWERS表拆分为另外两个表

我们可以将当前的CHECKLIST_ANSWERS表分为两部分:CHECKLIST_ANSWERS_SELECTEDCHECKLIST_ANSWERS_NOT_SELECTED。此解决方案易于实现,但好处不是很大。大多数已回答的清单中有90%以上的NOK选项未被选中,因此CHECKLIST_ANSWERS_NOT_SELECTED表将继续保持快速增长。 2-按期间创建特定表

此方法背后的想法是,我们将CHECKLIST_ANSWERS表断开一段时间。因此,我们可以按年或月创建一个表。为了使SELECT变得容易,我们可以在视图(或函数)中封装创建答案清单的步骤,以验证清单日期并从正确的表中获取数据。

解决方案,将CHECKLIST_ANSWERS表更改为仅保存所选的NOK选项:

1-跟踪清单模板版本

每次编辑清单模板时,我们都可以保存每个项目和NOK选项的状态(如果确定还可以)。因此,当我们需要重新创建清单时,我们需要验证在回答清单时哪些项目和NOK选项处于活动状态。将清单日期与清单模板历史记录进行比较。除了可能增加的复杂性之外,我们还可以将此验证封装在视图(或函数)中。

2-制作完每个版本后,创建另一个清单模板

我们不必跟踪每个清单模板版本中哪些项目和NOK选项被(停用),我们可以简单地创建一个包含新项目和NOK选项的新清单模板。我们不喜欢这种解决方案,因为项目或NOK选项可能会频繁更改ID(即使项目文本保持不变),因此,例如,由于需要考虑NOK选项的所有不同ID。清单模板本身可以更改其唯一ID,但是只需创建高级清单模板即可轻松解决。因此,此高级模板一次只能具有一个低级别模板。无论如何,我们认为这种方法的好处并不能解决其问题。

现在,我们对走什么路感到困惑。如果我们确实重构表以仅保存检查表的选定NOK选项(如果该项目为OK,则该表中没有该项的条目),我们将失去简便的方法来重新创建已考虑活动项目和NOK选项的已回答检查表。值得吗?

我们也可以组合不同类别的解决方案,因此另一种可能的方法是:将当前CHECKLIST_ANSWERS表拆分为另外两个表  并且跟踪清单模板的版本。

处理这张快速增长的桌子的最佳方法是什么?也许我们错过了其他一些技巧?

1 个答案:

答案 0 :(得分:0)

为此使用一些无模式的数据库,例如MongoDB。将来您的检查列表可能会频繁增长或更改。建议您每次添加一个新的清单列表项时都不要在表中添加更多列,而是通过以下方式保持模式灵活使用No-sql解决方案。