使用git在测试和生产环境之间同步数据库

时间:2014-01-11 15:41:25

标签: mysql database git

我正在尝试在php / mysql应用程序的开发过程中实现git。

到目前为止,我已经设置了git repos,我们正在使用我们的本地机器进行测试,我们已成功将其用于文件,但我真的不知道如何处理数据库?

服务器上有一个cron脚本导出并将新版本的实时数据库提交到repo,我在我的开发机器上设置了一个后合并钩子来更新我的本地数据库,这很有效用于同步生产 - >测试。

我不知道如何以相反的方式进行同步。目前我正在对实时服务器上的数据库进行更改,但我认为这不是一个好习惯。

所以我愿意接受建议。

编辑:在我了解架构迁移的工作原理之前,我问了这个问题。我现在正在使用django进行大部分的Web开发工作,它有一个很棒的迁移模块叫做South(django core的一部分来自1.7版本)。因此,大多数MVC框架都应该有一个处理此问题的迁移模块。

2 个答案:

答案 0 :(得分:3)

如果您想版本控制在平面文件中实现的完整数据库,我建议使用sqlite后端。

如果您的应用程序需要MySQL(例如某些过程或视图),则版本控制数据库操作脚本(例如CREATEALTER)和填充脚本(例如INSERT)并将其作为构建过程的一部分运行。 dbdeploy is a good pattern to follow

更新评论现有程序
您实际上将生产视为架构的主副本。如果你有多个大师会怎么样?当您的数据库太大而无法有效地执行此操作时会发生什么?如果您需要隔离旧版本代码中的错误怎么办 - 回滚到特定代码/架构状态有多容易?

十年前,我做了这件事。我有一个小型数据库 - 十几个表左右。该应用程序已经增长。它现在有2000个表。想想我是圣诞节未来的鬼魂,警告你远离我经历过的痛苦。

<强>建议
理论上这个过程很简单:在开发过程中进行数据库更改,将其应用于生产,完成。现实要困难得多。我会用例子来解释我的意思......

您是开发团队的一员。您想添加对禁用帐户的支持。除了代码更改之外,您决定将其作为数据库中的位字段实现,如下所示:

ALTER TABLE Account ADD COLUMN disabled BIT(1) DEFAULT 0;

就像我上面提到的那样,你把它放在版本控制下的文件中,我们称它为addDisabledColumnToAccount.sql。您提交SQL并更改代码并推送它们。

其他团队成员获取您的更改,应用架构更改并对其进行测试。您们共同决定增加更改的原始范围以支持帐户的状态,而不仅仅是禁用。所以你这样做:

ALTER TABLE Account DROP COLUMN disabled;
ALTER TABLE Account ADD COLUMN status ENUM('active','disabled','closed') NOT NULL DEFAULT 'active';

并提交您的更改,然后推送。每个人都重新申请这个并且很高兴。你将它推入你的行李箱(或者你标记稳定),它已准备好投入生产。

确定。你能发现问题吗?有几个。第一个主要问题是,如果您尝试在生产中运行此脚本,它将失败。为什么?因为生产从未添加过“禁用”列。

一般问题是开发数据库经历了临时变更,生产不需要/可能不会通过。有很多方法可以解决这个问题。我喜欢这样做的方法是保留两个更改脚本:开发和生产。开发脚本是累积的,随着开发的进行而不断变化 - 生产脚本代表了开发的最终结果。它们都使数据库以相同的状态结束,这意味着你对最后一个的最终测试都应该通过。

还有哪些其他问题?好吧,开发人员可能会将两个脚本文件命名为同一个。因此,您必须建立一些标准,以防止脚本名称发生冲突。通常,如果脚本名称与某个唯一的问题ID相关联,则可以执行此操作。

另一个问题是每个架构更改脚本可能都有MySQL版本,SQLite版本,Oracle版本等。您支持的数据库越多,您需要处理的架构更改就越多。在命名脚本时请记住这一点。类似addColumnToTable.mysql.sqladdColumnToTable.sqlite.sql

的内容

最后,您必须确保在应用相应的代码更改的同时应用架构更改。我所说的是,通常代码和数据库的变化是相辅相成的。只要您的部署技术允许您同时应用两者,并且 - 重要的是 - 如果出现问题就回滚,那么您就是好的。但是这种自动化水平很难,而且手工操作很容易出错。

总之,git将帮助您跟踪更改,并帮助您协作地创建对架构的更改。但它并不是特别的部署工具,因为随着时间的推移处理模式的变化很复杂。

答案 1 :(得分:0)

大多数数据库都具有数据库复制功能。在我看来,这比使用git更适合数据库同步。