发布流程改进

时间:2010-04-23 02:05:19

标签: build-process release release-management sdlc

创建新构建并将其发布到生产中的过程是SDLC中的关键步骤,但它通常是事后的想法,并且随着公司的不同而变化很大。

我希望人们能够在他们的组织中分享他们对这个过程所做的改进,这样我们都可以采取措施'减轻痛苦'。

所以问题是,指定一个痛苦/耗时的发布过程部分,你做了些什么来改善它?

我的例子:在之前的雇主中,所有开发人员都在一个公共开发数据库上进行了数据库更改然后,当发布时,我们使用Redgate的SQL Compare从Dev和QA数据库之间的差异生成一个巨大的脚本。

这种方法效果相当不错,但这种方法的问题是: -

  1. 包含Dev数据库中的所有更改,其中一些可能仍在“正在进行中”。
  2. 有时开发人员会做出相互矛盾的更改(在发布生产之前就没有注意到)
  3. 创建和验证脚本是一个耗时且手动的过程(通过验证我的意思是,尝试清除问题1和问题2)。
  4. 当脚本出现问题时(例如,运行事物的顺序,例如创建依赖于脚本中但尚未运行的外键记录的记录),需要时间来“调整”它它运行顺利。
  5. 这不是持续集成的理想方案。
  6. 所以解决方案是: -

    1. 强制执行必须编写数据库所有更改的策略。
    2. 命名约定对于确保脚本的正确运行顺序非常重要。
    3. 创建/使用工具在发布时运行脚本。
    4. 开发人员对自己的数据库副本做了反对(因此没有更多'踩到彼此的脚趾')
    5. 我们开始此过程后的下一个版本速度更快,问题更少,实际上发现的唯一问题是由于人们违反了规则,例如没有创建脚本。

      一旦发布到质量保证的问题得到解决,当发布到生产时,它就非常顺利。

      我们应用了一些其他更改(例如引入CI)但这是最重要的,总体而言我们将发布时间从大约3小时减少到最多10-15分钟。

7 个答案:

答案 0 :(得分:3)

我们在过去一年左右做了一些事情来改善我们的构建过程。

  1. 完全自动化且完整的构建。我们总是有一个夜间“构建”,但我们发现构成构成的内容有不同的定义。有些人会认为它是编译的,通常人们包括单元测试,有时还有其他东西。我们在内部澄清说,我们的自动化构建确实完成了从源控制到我们交付给客户所需的一切。我们自动化各个部件的次数越多,流程就越好,而且在发布时我们不必手动完成(并且不必担心忘记某些事情)。例如,我们的构建版本用svn版本号标记所有内容,编译以几种不同语言完成的各种应用程序部分,运行单元测试,将编译输出复制到适当的目录以创建我们的安装程序,创建实际的安装程序,将安装程序复制到我们的测试网络,在测试机器上运行安装程序,并验证新版本是否已正确安装。

  2. 代码完成和发布之间的延迟。随着时间的推移,我们逐渐增加了在完成特定版本的编码和该版本发布给客户之间的延迟时间。这为测试人员提供了更多的专用时间来测试产品变化不大并产生更稳定的生产版本。源控制分支/合并在这里非常重要,因此开发团队可以在下一个版本上工作,而测试人员仍在处理上一个版本。

  3. 分公司所有者。一旦我们将代码分支以创建发布分支,然后继续在后续版本的trunk上工作,我们就会分配一个轮换发布分支所有者,负责验证应用于分支的所有修复。无论规模大小,每次办理登机手续必须由两位开发人员审核。

答案 1 :(得分:3)

我们已经使用TeamCity(一种出色的持续集成工具)来完成我们的构建,其中包括单元测试。提到了三个重大改进:

1)安装套件和一键式UAT部署

我们使用NSIS将我们的应用程序打包为安装工具包(不是MSI,这对我们的需求来说更加复杂和不必要)。此安装工具包完成了所有必要的操作,例如停止IIS,复制文件,将配置文件放在正确的位置,重新启动IIS等。然后,我们创建了一个TeamCity构建配置,使用{{3}在测试服务器上远程运行该安装工具包}。

这允许我们的测试人员自己进行UAT部署,只要他们不包含数据库更改 - 但这些更改比代码更改少得多。

生产部署当然涉及更多,我们无法自动化这些,但我们仍然使用相同的安装工具包,这有助于确保UAT与生产之间的一致性。如果有任何遗失或没有复制到正确的地方,通常会在UAT中找到它。

2)自动化数据库部署

部署数据库更改也是一个大问题。我们已经编写了所有数据库更改的脚本,但是在知道哪些脚本已经运行以及哪些脚本仍然需要运行以及按什么顺序运行时仍然存在问题。我们为此研究了几种工具,但最终还是推出了自己的工具。

数据库脚本按版本号组织在目录结构中。除了脚本之外,开发人员还需要将脚本的文件名添加到文本文件中,每行一个文件名,指定正确的顺序。我们编写了一个命令行工具,它处理这个文件并针对给定的DB执行脚本。它还记录了它在DB中的特殊表中运行(以及何时)的脚本,并且下次它不再运行它们。这意味着开发人员可以简单地添加一个数据库脚本,将其名称添加到文本文件中,并针对UAT数据库运行该工具,而无需向其他人询问他们上次运行的脚本。我们在生产中使用了相同的工具,但当然每次发布只运行一次。

真正使这项工作正常运行的额外步骤是作为构建的一部分运行数据库部署。我们的单元测试针对的是真正的数据库(非常小的数据库)。构建脚本将从先前版本恢复数据库的备份,然后运行当前版本的所有脚本并进行新备份。 (实际上它有点复杂,因为我们也有补丁版本,备份只针对完整版本完成,但该工具足够智能来处理它。)这确保了数据库脚本一起被测试< / em>在每个构建版本中,如果开发人员进行了相互冲突的架构更改,它将很快被选中。

唯一的手动步骤是在发布时:我们增加了构建服务器上的版本号,并复制了“当前数据库”备份,使其成为“最后发布”备份。除此之外,我们不再需要担心构建使用的DB。 UAT数据库有时仍然需要从备份中恢复(例如,因为系统无法撤消已删除的DB脚本的更改),但这种情况非常罕见。

3)分支发布

这听起来很基本,几乎不值得一提,但我们开始时并没有这样做。合并回来的变化肯定是一种痛苦,但并不像今天发布和下个月的单一代码库那么痛苦!我们还让在发布分支上做出最多更改的人进行合并,这有助于提醒每个人将发布分支的提交保持在最低限度。

答案 2 :(得分:2)

尽可能自动化您的发布流程。

正如其他人暗示的那样,使用不同级别的构建“深度”。例如,开发人员构建可以使所有二进制文件直接从存储库中运行您的产品,而安装程序构建可以组装所有内容以便在新机器上安装。

这可能包括

  • 二进制文件,
  • JAR / WAR档案,
  • 默认配置文件,
  • 数据库方案安装脚本,
  • 数据库迁移脚本,
  • 操作系统配置脚本,
  • man / hlp pages,
  • HTML文档,
  • PDF文档

等等。安装程序构建可以将所有这些填充到可安装的软件包(InstallShield,ZIP,RPM或其他)中,甚至可以构建用于物理分发的CD ISO。

安装程序版本的输出通常是移交给测试部门的。无论安装包中没有包含什么(安装顶部的补丁......)都是一个错误。挑战您的开发人员以提供无故障安装程序。

答案 3 :(得分:1)

自动单步构建。 ant构建脚本编辑所有安装程序配置文件,需要更改的程序文件(版本控制),然后构建。无需干预。

在完成后仍然会运行一个脚本来生成安装程序,但我们将消除它。

CD图稿是手动版本的;这也需要修复。

答案 4 :(得分:1)

同意之前的评论。

以下是我工作的地方。这个当前的过程消除了你在问题中描述的'陷阱'。

我们使用ant从svn中提取代码(通过标记版本)并引入依赖项并构建项目(有时也可以部署)。

相同的ant脚本(传递params)用于每个env(dev,integration,test,prod)。

项目流程

  • 将需求捕获为用户“故事”(有助于避免对需求的解释进行狡辩,当表达为与产品的有意义的用户交互时)
  • 遵循敏捷原则,以便项目的每次迭代(2周)都会产生当前功能的演示以及可释放的(如果有限的)产品
  • 在整个项目中管理发布故事,以了解范围内外的内容(防止最后一分钟修复的混淆)
  • (重复上一个回复)代码冻结,然后只测试(没有添加功能)

开发流程

  • 单元测试
  • code checkins
  • 预定的自动构建(例如巡航控制)
  • 完成构建/部署到集成环境,并运行冒烟测试
  • 标记代码并与团队沟通(用于测试和发布计划)

测试流程

  • 功能测试(例如硒)
  • 执行测试计划和功能方案

一个人管理发布过程,并确保每个人都遵守。此外,所有版本都会在发布前一周进行审核。发布仅在以下情况下获得批准:

发布流程

  • 批准特定日期/时间的发布
  • 审核发布/回滚计划
  • 使用'生产部署'参数
  • 运行ant
  • 执行数据库任务(如果有的话)(此外,这些脚本可以是版本并标记为生产)
  • 执行其他系统更改/配置
  • 沟通变更

答案 5 :(得分:0)

我不了解或练习SDLC,但对我来说,这些工具对于实现顺利发布是不可或缺的:

  • Maven for build,Nexus本地存储库管理器
  • Hudson持续集成,发布版本,SCM标记和构建促销
  • 声纳质量指标。
  • 跟踪数据库更改到开发数据库架构并管理qa更新并通过DbMaintainLiquiBase
  • 发布

答案 6 :(得分:0)

在我工作的项目中,我们使用Doctrine(PHP ORM)迁移来升级和降级数据库。我们遇到了各种各样的问题,因为生成的模型不再与数据库模式匹配,导致迁移在中途完全失败。

最后,我们决定编写我们自己的同一件事的超级基本版本 - 没什么好看的,只是执​​行SQL的向上和向下。无论如何它效果很好(到目前为止 - 触摸木材)。虽然我们通过编写自己的方式稍微重新发明了轮子,但重点在于保持简单,这意味着我们遇到的问题要少得多。现在发布很简单。

我想这里的故事的寓意是,只要你这样做,有时候重新发明轮子是合理的。