Azure DevOps Server(以前名TFS)是微软公司实现软件研发、测试和部署一体化的全流程解决方案。在近几年的研发过程当中,Azure DevOps Server 大幅加强了软件部署过程的自动化功能。对于系统运维人员而言,确保软件的稳定运行,是本身的第一工做目标。可是,在信息技术飞速发展的今天,信息系统的升级变动已经成了屡见不鲜。每周升级、天天升级、甚至一天升级数次,都已经见怪不怪。程序员
为了提升软件的变动效率和质量,许多运维部门都使用部署脚本,实现系统升级的自动化。在软件升级过程当中,为了确保信息系统正常运转,最大程度的下降由于升级致使系统宕机的风险,运维人员首先考虑的是回退(Rollback)方案。即,在系统升级过程当中,万一出现因为升级致使的异常情况,为了最快恢复系统的正常运行,回退到部署前的版本,是一个运维人员恢复系统正常的首选方案。shell
在下面的内容中,咱们介绍在使用Azure DevOps Server实现部署过程当中,如何应用回退方案。数据库
在软件部署过程当中,咱们能够选择多种回退方案:json
1. 基于虚拟机的快照技术windows
在升级变动以前,为即将发生变动的服务器建立快照,当系统部署失败时,直接将虚拟机退回到建立快照时的状态。服务器
目前Azure DevOps Server支持包括VMware, SCVMM(Hyper-V)等多种虚拟化平台。若是微软原生的技术支持,通常虚拟化平台都提供快照的API,能够将API经过PowerShell、Shell等方式集成到发布流水线中。下图是在Azure DevOps中使用VMware和SCVMM的截图:数据结构
图1:Azure DevOps Server流水线中的SCVMM任务运维
图2:Azure DevOps Server流水线中的vCenter任务测试
基于虚拟机快照的回退方案,简单粗暴,可是却很是适用。在手动部署过程当中,这种方案就是运维人员经常使用的方式。插件
可是虚拟机的快照并非万能的,它存在许多不足,例如快照会消耗大量的磁盘存储;若是是域环境中运行的虚拟机,快照还原可能出现脱域的问题;快照合并的时间较长等问题。在选择使用快照技术做为回退方案时,须要重复考虑快照还原对系统形成的影响。
2. 从新部署上一个版本
在Azure DevOps Server中,从新部署上一个版本,是最为简单和快速的方式。
Azure DevOps Server 最大的特色,是完整地保留了软件研发运维过程当中的全部日志、交付物数据,而且保护交付物数据的各类版本,其中就包括部署部署过程当中的每个版本。单本次部署失败时,咱们能够从上一次的部署中,选择从新部署按钮,实现一键回退功能。
例如,在下图中,因为四次部署是上一次成功的部署,而且系统运行正常,我选中从新部署,就能够重复运行上一次部署的全部任务,而且在部署过程当中,使用上一次部署的升级包、环境变量等数据。
图3:在Azure DevOps Server 中从新部署
若是你熟悉IBM UrbanCode Deploy,会发现Azure DevOps Server的从新部署功能与它的“Replace with Last Deployed”有殊途同归之妙。经过从新部署上一次的版本实现回退,简单快速。可是,问题也显而易见,不必定可以实现系统回退的效果。这种方案只适合独立运行的信息系统。
例如,当系统依赖与第三方系统运行,须要和第三方系统同步升级时,从新部署只能将本身的系统回退到了上一个版本,可是并不能将系统恢复到健康状态,由于此时第三方系统已经完成了升级,可能第三方系统不能兼容你的上一个版本。一样,若是当前版本对应的数据库结构已经完成了升级,从新部署也不能恢复系统的健康状态。
3. 中止自动部署,手动修复问题
程序员和运维工程师不是万能的,相反,这是一群最容易犯错误的人,由于他们实现的大部分需求,都没有能够照搬的方案。都是在开发过程当中,不断试错,实现信息系统的增量发展。一样,在部署过程当中,每次都存在许多不肯定因素。当发现部署问题时,分析缘由找到解决方案,并修复问题,将当前环境恢复到健康状态。同事,将解决方案集成到系统源代码或者部署脚本中,做为下一个版本的部署内容。
固然,做为程序员,咱们能够提高系统部署智能化,提升部署过程当中错误探测和解决的自动化水平,这也是后面要重点介绍的方案。
4. 在流水线中部署回退脚本
在Azure DevOps Server 中,发布流水线由一个一个的任务组合而成。在发布过程当中,系统按照流水线中配置的顺序,执行每个阶段中的任务。当发布流水线中的中的任何任务失败时,对应环境的部署可能会失败。为了让环境恢复正常,咱们能够执行一个回滚脚本Shell (on Linux)或PowerShell(on windows)。脚本自己须要具如下要求:
下面咱们来演示如何实现这个功能:
首先,编写回退脚本,并将其推送到代码库中,例如个人回退脚本以下:
echo $env:Release_Tasks
try
{
$jsonobject = ConvertFrom-Json $env:Release_Tasks
}
catch
{
Write-Verbose -Verbose "Error parsing Release_Tasks environment variable"
Write-Verbose -Verbose $Error
}
foreach ($task in $jsonobject | Get-Member -MemberType NoteProperty)
{
$taskproperty = $jsonobject.$($task.Name) | ConvertFrom-Json
echo "task name: $($taskproperty.Name)"
echo "task rank: $($task.Name)"
echo "task status: $($taskproperty.Status)"
echo "Task $($taskproperty.Name) with rank $($task.Name) has status $($taskproperty.Status)"
$task_status=$taskproperty.Status
if($task_status -eq "failed")
{
Write-Warning "This is a error generated in a PowerShell script"
}
}
而后,在发布流水线中添加回退任务。注意须要将其标记为老是运行“即便上一任务已失败,即便已经取消部署”:
最后,咱们看一下回退脚本运行的结果:
在上图中,能够看到回退脚本顺利运行,下图是回退脚本的输出:
在上面第4个方案中,咱们只是介绍了基于Azure DevOps Server 的回退机制,而具体的回退脚本,须要根据系统部署的内容来定。须要开发人员或者运维人员根据本次变动的具体内容编写脚本。例如文件的变更,则须要编辑将备份文件覆盖回来;若是数据结构的变更,则须要更改数据库。
微软DevOps MVP 张洪君 http://www.cnblogs.com/danzhang
--End--