SQL与NoSQL:其他问题比ACID和可扩展性怎么样?
最近我读了不少篇文章,描述了SQL和NoSQL这两个方面的分歧,比如
http://use-the-index-luke.com/blog/2013-04/whats-left-of-nosql.这些文章经常触及诸如ACID和可伸缩性之类的主题.然而,我通常使用SQL的一些问题似乎在这些文章中很少被提及,我想知道为什么,这是否与我有关,我不完全理解SQL.如果有任何人可以启发我,至少部分是在以下一个或多个项目中,我将非常感激.
我的SQL问题: > SQL本质上是不安全的:SQL是一种用于插入的语言,没有任何方法可以防止插入代码而不是数据.防止插入的唯一方法是将SQL与使用它的应用程序完全隔离.为什么还没有在SQL中解决呢? >数据的一致性完全依赖关系表 > SQL不保留历史记录,因为默认情况下它具有破坏性的更新:当然,创建历史记录的方式有各种各样的方法,但是需要使用额外的表格和使用时间戳的自定义书写的东西,或者写一个新的记录对于每一个变化,导致表格规模增长. 我知道(但不是很熟悉)PostgreSQL Hstore这样的东西,但是我完全不知道如何解决上面提到的事情. 解决方法> SQL本身是不安全的吗?我想你是指SQL Injections这是最危险的安全漏洞之一. 然而,SQL注入主要是教育的问题,因为大多数教科书和课程根本不解释bind parameters.当人类直接使用数据库时,将文字值写入SQL语句本身就适用于即席查询,但在程序中只是简单的错误方式.程序应始终使用绑定参数(非常少的性能异常),有效地保护程序100%免受SQL注入.问题是SQL教科书没有这样说. 否则,SQL具有可靠的安全系统,允许您基于某些规则(“行级安全性”)限制对表,视图以及有时甚至选择的行的访问. 对不起,我没有得到这个问题. 你是对的.规范化解决了一些问题(重复数据删除和防止无意的不一致),但打开了其他一些问题.即: >如何从多个表轻松访问数据. 原则上,SQL应该提供工具来补偿正常化引起的这些挑战. 应该使用连接和SQL的类似操作来访问来自许多表的数据. SQL不仅仅是以1:1的方式存储和检索数据,它提供工具(联接,子查询,集合操作…),以将归一化数据转换为最适合特定任务的形式.这是在运行时有意做的,因为任务不需要事先知道.另一方面,数据的性质被认为是静态的,因此将其存储为归一化方式是有效的.这是关系模型和SQL的一个非常重要的关键概念:数据的性质不会改变,所以它应该是持久的.如何使用这些数据变化很大,并且经常会随着时间的推移而变化 – 因此,这必须是动态的.这当然是一个非常规则的任务,所以有一个坚实的工具使其变得容易.我们称这个工具SQL;)DRY规则可以通过使用视图或CTEs来实现,但是两者都可能会损害性能,因为实现没有被很好地优化(我公开批评!). 在多个表中保持数据一致性大多是在约束的帮助下完成的. SQL:2011终止了处理意图的“不一致”(历史):这将允许“AS OF”查询,并提供保持时间一致性的工具(例如,一行的有效性可能与另一行的有效性不重叠).可以说,相当糟糕的是,花了40年左右的时间才提出了一个解决办法.而且我甚至不知道这是什么时候常用的! 我认为这一点对于每个系统来说都是非常真实的:“数据在人类失败的情况下很难理解”(我的重点).但是,我认为您可能意味着很难调查问题,因为所需的数据可能会分散在多个表中. SQL的答案是:基本上只是存储查询的VIEW.但是,根据数据库带VIEW可能会引入性能问题.然而,这是一些数据库频段的限制,而不是SQL或关系模型的限制. 以上我已经提到过(SQL:2011). 每个想要保留历史的系统也是如此:“导致指数级增长的表格大小”.虽然我会说它“不断增长”不是“指数级”. 应对这些工具是触发器或ORM.如果你想确定没有人做“破坏性的更新”,你可以撤销该表上的UPDATE权限(也可以在保存方面删除DELETE). 我发现一个有趣的观点.但是,SQL的答案是,您首先尝试非常难以将错误的数据导入系统.主要通过使用适当的模式,约束ACID.以这种方式,您的声明是正确的:而不是接受不一致的数据被拒绝(这是不同于丢失的东西!).因此,您必须在有人输入拒绝的数据时处理错误,而不是稍后您尝试解决不一致的原因,因为您首先接受了错误的数据.所以是的,这是关系模型和SQL的哲学! 缺乏人的可读性显然取决于你的背景.但是,使用SQL的正确性是相当不错的,我想说.在这里,我也想引用原来的IBM文章,关于SEQUEL(当时是真正的名字):
在我的观察中,这是绝对真实的:我最近有一个任务来教SQL来支持员工,以便他们直接在数据库中调查案例.他们不是程序员,而是很快了解SQL.我认为这里踢你的“人”论点:他们有什么问题是导航一个包含几百个表的真实世界的关系模型.但是,通过要求开发为涉及多个表的一些常见任务提供意见,很快解决了这个问题.然后加入这些观点就没有问题了. 对于关系思维,你需要一个不同的思维方式,你需要一个不同的中间集功能编程.这不是好还是坏 – 但对你而言可能不常见.一旦你经常使用它,你会习惯它. 我认为这个话题不需要任何长时间的讨论:是的,它存在,是的,有工具以某种方式来处理它.我在我的文章中提到过度使用我的观点. 我认为这主要是由于对关系模式的了解不佳.比较如下:“数据的性质” 这也是一个非常好的讨论参数:模式与“架构少”.选择你的味道“模式少”通常意味着“不提供模式管理工具”,但是您必须应对事实,即我们有时希望向现有实体添加更多属性. RDBMS为此提供了工具:新列可以为空或具有默认值.可以使用CREATE AS SELECT来进行更大的更改,例如将一个属性移动到一个额外的表(例如1:n).您甚至可以提供一个兼容性视图,它仍然可以传递数据,就像移动的属性仍然存储在表中一样.一旦您更改了架构,您的应用程序就可以依赖于它的约束(例如列的存在或约束的有效性).数据库可以非常可靠的方式为您做的很多事情.你不需要在你的应用程序中关心的东西. 您没有提到的一个争论是,这些架构更改通常涉及停机时间.对于过去,在某种程度上也是如此,这是肯定的.例如. MySQL最近在5.6中引入了ALTER TABLE.然而,这通常是实现限制,而不是固有地关系到关系模型或SQL的问题.甚至一些更复杂的更改(如将属性移动到另一个表)可以在完成权限并仔细计划时在线完成(我已经用昂贵的数据库之一完成了所需的所有工具).一般来说,将迁移代码保留在应用程序之外,并使用它来处理数据库.在迁移之后,您不应该在数据库中或应用程序代码中都有迁移工件.当然,有些情况下,停机时间是不可避免的(我认为). SQL实际上完全相反:SQL完全消除了存储层. 没有人强迫你使用存储过程.我个人也认为存储过程被过度使用,主要是因为存储过程存储在数据库中,因此可以由可能无法访问其他源代码的数据库管理员进行更改(优化).换句话说:我认为这绝对是绝望的. 第二个参数当然是过度使用ORMs和不允许在应用程序中使用真实SQL的策略. (编辑:李大同) 【声明】本站内容均来自网络,其相关言论仅代表作者个人观点,不代表本站立场。若无意侵犯到您的权利,请及时与联系站长删除相关内容! |