当与其他几个人一起开展项目时,通常有几个人有不同的区域,例如数据库。
我的挑战是如何让多人在持续集成环境中编辑数据库模型。
开发人员建议编写一个“版本控制脚本”,其中每个编辑都输入到.sql脚本中,其中包含数据库能够检测到的版本号。模型的新增内容将在此文件中标记一个版本,并且一旦提交了脚本并运行了构建,数据库就会更新。
我也听说过发布者/订阅者......并仔细阅读了一下。
您如何在日常工作中管理这种情况,以及您可以给我什么建议让数据库更改尽可能无缝地运行?
**编辑**
已经提到了迁移框架和迁移脚本。如果您有一些实践经验并建议一个框架,那也将受到赞赏。
答案 0 :(得分:21)
在杰出的Get Your Database Under Version Control帖子中引用杰夫阿特伍德:
...
我再次考虑这个问题 因为我的朋友和co-author K. 斯科特艾伦刚刚写了一篇辉煌 关于哲学和哲学的五部分系列 数据库版本控制的实践:
真的,即使很多人似乎对第3部分特别感兴趣,整个系列也值得一读。顺便说一下,看看第3部分提到的Bulletproof Sql Change Scripts Using INFORMATION_SCHEMA Views文章。您可能已经意识到这一点,但它解释了为什么编写idempotent更改脚本很重要。
关于工具,您可能需要查看UpToDater(以代码为中心),LiquiBase(基于xml)或... dbdeploy,稍微宝石基于ThoughtWorks中软件开发的实际经验。这不是第一个不好,但这个是我的首选(并且可用于Java,PHP或.NET)。
答案 1 :(得分:6)
我倾向于使用'migration'脚本运行得最好,这是从简单的版本化脚本开始的下一个阶段。通过迁移,您可以指定对数据库的更改(添加,删除等)以及如何撤消迁移所执行的更改。然后使用某种形式的版本对其进行标记,该版本不会与其他开发人员发生冲突。一个特别好的版本号是当前时间(以YYYYMMDDHHMMSS格式或从纪元开始的秒数)。这是一个不错的选择,因为你不太可能得到版本冲突,而且由于这些时间戳的严格增加性质,仍然很容易看到是否存在新版本。
注意:这很大程度上受Rails中迁移系统的影响。有关更多详情和想法,我强烈建议您查看该系统。
Rails迁移:
class CreateGroups < ActiveRecord::Migration
def self.up
create_table :groups do |t|
t.string :name
t.references :owner
t.timestamps
end
end
def self.down
drop_table :groups
end
end
学说迁移:
class CreateGroups extends Doctrine_Migration
{
public function up()
{
// Create new author table
$columns = array('id' => array('type' => 'integer',
'length' => 4,
'autoincrement' => true),
'name' => array('type' => 'string',
'length' => 255),
'owner_id' => array('type' => 'integer',
'length' => 4));
$this->createTable('groups', $columns, array('primary' => array('id')));
}
public function down()
{
$this->dropTable('groups');
}
}
(抱歉教条中缺少时间戳...在rails中,timestamps调用会将created_at和updated_at字段添加到为您自动管理的表中。我不确定教条中的类似行为所以我将它们排除在外)。
答案 2 :(得分:1)
查看迁移框架。 AFAIK,这个想法来自rails,但是人们已经为这几乎所有其他东西构建了框架。
答案 3 :(得分:1)
取决于。
如果这是您正在讨论的已发布产品,则需要仔细跟踪架构编辑,以便您可以规划升级过程。现在开始考虑这个问题会很好,所以“版本控制脚本”会有一定的意义。但是向后/向前兼容性通常只是用户可见的要求,而不是“编译之间”要求。在发行版之间,维护升级脚本是有意义的,该脚本修改数据库表以将其引入新模式。
如果这是一个新的/未发布的产品,如果有人更改架构,您关心什么?为什么你甚至想要在持续集成构建之间保持数据库?无论如何,您应该能够使用自动化测试重新生成任何测试数据。但是,任何更改架构的人都应该更新测试。
对于已发布的产品,您可能希望拥有一组可以处理“1.0版”数据库的测试,以确保它可以成功升级到“1.1版”(例如)。
答案 4 :(得分:1)
问题中没有描述技术堆栈(包括使用的数据库),这与哪种解决方案最适合。
一种非常受欢迎的以Java为中心的迁移解决方案是Flyway。 DBUp非常相似,但侧重于.NET堆栈。
在Redgate,我们提供ReadyRoll,它与Visual Studio紧密集成,专门针对SQL Server。
答案 5 :(得分:0)
我们编写Subversion中的所有内容,并像其他任何代码一样将其检入项目中。所有数据库部署都是从源控制系统中提取的脚本完成的。如果两个人碰巧在同一个脚本上工作(这是相当罕见的),Subversion将允许你合并这两个脚本。