Orm 为什么使用数据库迁移而不是版本控制的架构

Orm 为什么使用数据库迁移而不是版本控制的架构,orm,migration,Orm,Migration,迁移无疑比仅仅启动phpMyAdmin并随意更改模式要好(就像我在php时代所做的那样),但在使用它们一段时间后,我认为它们存在致命的缺陷 版本控制是一个已解决的问题。迁移的主要功能是保存数据库更改的历史记录。但是,为每次更改存储不同的文件是一种笨拙的跟踪方法。当您想要添加新的虚拟属性时,您不会创建新版本的post.rb(或表示增量的文件)——当您想要添加新的非虚拟属性时,为什么要创建新的迁移 换句话说,正如您将post.rb检查到版本控制中一样,为什么不将schema.rb检查到版本控制中并直

迁移无疑比仅仅启动phpMyAdmin并随意更改模式要好(就像我在php时代所做的那样),但在使用它们一段时间后,我认为它们存在致命的缺陷

版本控制是一个已解决的问题。迁移的主要功能是保存数据库更改的历史记录。但是,为每次更改存储不同的文件是一种笨拙的跟踪方法。当您想要添加新的虚拟属性时,您不会创建新版本的
post.rb
(或表示增量的文件)——当您想要添加新的非虚拟属性时,为什么要创建新的迁移

换句话说,正如您将
post.rb
检查到版本控制中一样,为什么不将schema.rb检查到版本控制中并直接对文件进行更改呢

这在功能上与为每个增量保留一个文件相同,但使用起来更容易。我的心智模型是“我希望表X有这样或那样的列(或者说,我真的希望模型X有这样或那样的属性)”--为什么你必须从这个模型中推断出如何从现有的模式到达那里;只需打开schema.rb并为表X提供正确的列

但即使是类包装表的想法也是一个实现细节!为什么我不能打开post.rb并说:

 Class Post
    t.string :title
    t.text :body
 end
如果使用这样的模型,则必须决定如何处理现有数据。但即便如此,迁移也过于繁琐——当您迁移数据时,使用迁移的
down
方法将失去保真度

无论如何,我的问题是,即使你想不出更好的方法,迁移不是有点恶心吗?

为什么不将schema.rb签入版本控制并直接对文件进行更改

因为数据库本身与版本控制不同步

例如,您可以使用源树的头。但您正在连接的数据库定义为某个旧版本,而不是您签出的版本。迁移允许您增量地将数据库架构从任何版本升级或降级到任何版本


但要回答你的最后一个问题,是的,迁移有点恶心。它们在另一个版本控制系统之上实施冗余版本控制系统。但是,这些修改控制系统并没有真正与数据库同步。

也有一些重要的数据问题需要考虑,迁移解决了。 假设我的模式的旧版本有一个

英尺
英寸
列。为了提高效率,我想将其合并到一个
inches
列中,以简化排序和搜索

我的迁移可以在更新数据库时(即在删除
feet
列之前)将所有英尺和英寸数据合并到英寸列(英尺*12+英寸)

很明显,在迁移过程中,当您稍后将更改应用到生产数据库时,它会自动工作。

我假设给定“即使您想不出更好的方法”,那么,是的,在总体方案中,迁移有点粗俗。Ruby、Rails、ORMs、SQL、web应用程序也是如此


迁移有其存在的优势(并非微不足道)。粗俗但存在的人往往会战胜愉快但不存在的人。我相信可能有一些令人愉快且不存在的方法来迁移您的数据,但我不确定这意味着什么。:-)

就目前而言,它们令人恼火且不充分,但很可能是我们目前拥有的最佳选择。相当多的聪明人在这个问题上花了相当多的时间,到目前为止,这是他们能想到的最好的方法。在经历了大约20年的数据库版本更新之后,当我发现ActiveRecord时,我很快意识到迁移是一项重大改进

正如您所说,版本控制是一个已解决的问题。在某种程度上,我同意:特别是对于文本文件,这是一个非常好的解决方案,对于其他文件类型,这一点就不那么好了,对于数据库之类的资源,这一点也不太好

如果将迁移视为数据库的版本控制增量,迁移会是什么样子?它们是从一个版本到另一个版本获取模式所必须应用的增量的总和。我不知道,即使是git,尽管它有着强大的功能,但它也可以获取两个模式文件并生成必要的DDL来实现这一点

至于在模型中声明表内容,我相信DataMapper就是这么做的(没有个人经验)。我认为那里可能也有一些DDL推理功能

“即使你想不出更好的方法,迁移不是有点恶心吗?”


对。但它们比我们所有的东西都不恶心。请务必在您完成非总体备选方案后通知我们。

好的,我在这里大胆猜测一下,您可能正在独自工作。在团队开发项目中,每个人对开发人员正在编写的代码所需的数据库更改负责的能力要重要得多


另一种选择是,更大的程序员群体(例如,我工作的10-15名Java开发人员)最终依赖于两名专职数据库管理员,以及他们的其他维护、优化、,等等。职责。

仅解释一下其他人所说的:迁移允许您随着模式的发展保护数据。维护单个
schema.rb
文件的概念只有在应用程序投入生产之前才有吸引力。此后,随着模式的改变,您将需要一种方法来迁移现有用户的数据。

就像温斯顿·丘吉尔(Winston Churchill)关于民主的一句话:这是最糟糕的解决方案,除了所有其他解决方案外,其他解决方案都是如此