用于处理数据库的反模式

哈Ha!我向您介绍我的文章“数据库:反模式”的翻译

如果存储数据,这是应用程序的关键部分。您可以轻松,快速地在新的约会网站上修复错误修复程序,以便来自北德克萨斯州的农民乔终于可以阅读他的笔友的最后一条消息,并发现她喜欢秃头男人。但是上帝禁止您丢失或破坏用户数据。

图片
硅谷,第2季,第8集

但是,许多开发人员并未完全理解这个简单的事实。我已经多年没有成为专业的程序员了,但是我已经看到使用数据库的人犯了很多很多错误。

这就是那些马上浮现在脑海的东西。

缺乏备份


图片

“备份”是我们许多人都同意但不遵守的规则(例如“不要扎根”或“系好安全带”)之一,希望坏事发生在别人而不是我们身上。

顺便说一句,如果您不测试从备份中恢复,则可以假定您根本没有备份。从别人的错误中学习
换句话说,在这五种备份技术中,没有一种可靠地工作或没有配置。最后,我们从6个小时前进行的备份中还原了数据。
通过GitLab.com,我们在6个小时内丢失了数据库数据(问题,合并请求,用户,评论,摘要等)。

NoSQL


您的用户 碰巧看到成人内容太多,而他们却经常观看,数据量太大或负载太大,关系数据库无法处理。NoSQL技术发挥作用时就是这种情况。像Google这样的软件巨头对这种第一手资料很熟悉。

但是您不是Google几百个千兆字节不是“大数据”,但每天1000条注释不是“高负载”。PostgreSQL很可能足以容纳您的数据。请参阅:它甚至支持JSON并可以对其进行索引

来吧,您是否真的想为不需要的功能而牺牲一个可靠的结构,而面对它却永远不需要?您不会成为新的Google-数据库中只是一片混乱。

计划太宽松


这与NoSQL更为相关,但是关系DBMS的用户经常忘记或懒得创建所有必要的限制。由于应用程序代码中的错误,NULL可以将其保存在需要有意义的值的位置,也可以创建指向丢失条目的链接。随后,您会注意到并纠正代码,但是您不知道如何修复数据。

自然主键


假设我们要存储用户,每个用户必须有一个唯一的电子邮件。最明显的解决方案是创建user带有column 的表email,该也将成为主键。

不幸的是,当需求变化(并且需求不断变化)时,自然键可能无法用作主键。今天可以PRIMARY KEY(email)使用,明天我们决定通过Facebook添加注册,并让电子邮件成为可选内容。哪个更好:生成唯一的地址并添加表示虚拟电子邮件的标记,或者更改主键,引用了的所有外键user等,等等?如果我们仅使用代理主键,就不必选择较小的邪恶方法。

存储逻辑


我不喜欢这样做有两个原因:

  1. 应用程序代码通常比数据库模式容易更新。
  2. 所有这些SQL PL都使我想起了Pascal,它们同样难看。

特定于环境的迁移脚本


我知道有时候别无选择,但是总的来说,最好确保所有环境(开发,测试,生产等)都尽可能相似。环境之间的差异越大,犯错并仅在产品上发现错误的可能性就越大。

通常,即使DML脚本也可以是通用的。通常,不同的计划纯属邪恶。

因此,当我在liquibase脚本中看到特定于环境的标签时,我想杀死它。

容忍的迁移脚本


IF NOT EXISTS如果在所有环境中都使用相同的方案,则DDL中类似的内容不是必需的,但是可以掩盖错误。如果在数据库更新期间发生意外情况,我宁愿查找并尽快修复它,而不是一个星期后花时间去解决问题。

非原子更新


假设您基于生产运行变更集,并且迁移未成功。您正在修复某些东西,并想再试一次。能行吗如果某些变更集操作已提交而其他变更集未提交怎么办?

您可能会注意到,这实际上是一个变更集应该是幂等的故事,您将是对的。

不幸的是,许多开发人员考虑了幂等,使用IF NOT EXISTS或类似的东西。在上一节中,我解释了为什么这是邪恶的。

相反,将更改集设为atomic。然后,如果发生错误,所做的更改将被回滚,并且此更改集的后续应用程序将不会出现问题。

但是在指望交易时要小心。例如,MySQL事务中对DDL表达式的支持是黑暗的,充满了恐惧,因此当我为MySQL编写Liquibase脚本时,我总是为每个DDL表达式创建一个单独的变更集。

您看到了什么反模式?

Source: https://habr.com/ru/post/undefined/


All Articles