在Azure DevOps Server(TFS系統)中部署回退/回滾方案(Rollback)


概述

Azure DevOps Server(之前名TFS)是微軟公司實現軟件研發、測試和部署一體化的全流程解決方案。在近幾年的研發過程中,Azure DevOps Server 大幅增強了軟件部署過程的自動化功能。對於系統運維人員而言,確保軟件的穩定運行,是自己的第一工作目標。但是,在信息技術飛速發展的今天,信息系統的升級變更已經成了家常便飯。每周升級、每天升級、甚至一天升級數次,都已經見怪不怪。

為了提高軟件的變更效率和質量,許多運維部門都使用部署腳本,實現系統升級的自動化。在軟件升級過程中,為了確保信息系統正常運轉,最大程度的降低因為升級導致系統宕機的風險,運維人員首先考慮的是回退(Rollback)方案。即,在系統升級過程中,萬一出現由於升級導致的異常狀況,為了最快恢復系統的正常運行,回退到部署前的版本,是一個運維人員恢復系統正常的首選方案。

在下面的內容中,我們介紹在使用Azure DevOps Server實現部署過程中,如何應用回退方案。

回退方案

在軟件部署過程中,我們可以選擇多種回退方案:

1. 基於虛擬機的快照技術

在升級變更之前,為即將發生變更的服務器創建快照,當系統部署失敗時,直接將虛擬機退回到創建快照時的狀態。

目前Azure DevOps Server支持包括VMware, SCVMM(Hyper-V)等多種虛擬化平台。如果微軟原生的技術支持,一般虛擬化平台都提供快照的API,可以將API通過PowerShell、Shell等方式集成到發布流水線中。下圖是在Azure DevOps中使用VMware和SCVMM的截圖:

圖1:Azure DevOps Server流水線中的SCVMM任務

image

圖2:Azure DevOps Server流水線中的vCenter任務

image

基於虛擬機快照的回退方案,簡單粗暴,但是卻非常適用。在手動部署過程中,這種方案就是運維人員常用的方式。

但是虛擬機的快照並不是萬能的,它存在許多不足,例如快照會消耗大量的磁盤存儲;如果是域環境中運行的虛擬機,快照還原可能出現脫域的問題;快照合並的時間較長等問題。在選擇使用快照技術作為回退方案時,需要重復考慮快照還原對系統造成的影響。

2. 重新部署上一個版本

在Azure DevOps Server中,重新部署上一個版本,是最為簡單和快速的方式。

Azure DevOps Server 最大的特點,是完整地保留了軟件研發運維過程中的所有日志、交付物數據,並且保護交付物數據的各種版本,其中就包括部署部署過程中的每一個版本。單本次部署失敗時,我們可以從上一次的部署中,選擇重新部署按鈕,實現一鍵回退功能。

例如,在下圖中,由於四次部署是上一次成功的部署,並且系統運行正常,我選中重新部署,就可以重復運行上一次部署的所有任務,並且在部署過程中,使用上一次部署的升級包、環境變量等數據。

圖3:在Azure DevOps Server 中重新部署

image

如果你熟悉IBM UrbanCode Deploy,會發現Azure DevOps Server的重新部署功能與它的“Replace with Last Deployed”有異曲同工之妙。通過重新部署上一次的版本實現回退,簡單快速。但是,問題也顯而易見,不一定能夠實現系統回退的效果。這種方案只適合獨立運行的信息系統。

例如,當系統依賴與第三方系統運行,需要和第三方系統同步升級時,重新部署只能將自己的系統回退到了上一個版本,但是並不能將系統恢復到健康狀態,因為此時第三方系統已經完成了升級,可能第三方系統不能兼容你的上一個版本。同樣,如果當前版本對應的數據庫結構已經完成了升級,重新部署也不能恢復系統的健康狀態。

3. 停止自動部署,手動修復問題

程序員和運維工程師不是萬能的,相反,這是一群最容易犯錯誤的人,因為他們實現的大部分需求,都沒有可以照搬的方案。都是在開發過程中,不斷試錯,實現信息系統的增量發展。同樣,在部署過程中,每次都存在許多不確定因素。當發現部署問題時,分析原因找到解決方案,並修復問題,將當前環境恢復到健康狀態。同事,將解決方案集成到系統源代碼或者部署腳本中,作為下一個版本的部署內容。

當然,作為程序員,我們可以提升系統部署智能化,提高部署過程中錯誤探測和解決的自動化水平,這也是后面要重點介紹的方案。

4. 在流水線中部署回退腳本

在Azure DevOps Server 中,發布流水線由一個一個的任務組合而成。在發布過程中,系統按照流水線中配置的順序,執行每一個階段中的任務。當發布流水線中的中的任何任務失敗時,對應環境的部署可能會失敗。為了讓環境恢復正常,我們可以執行一個回滾腳本Shell (on Linux)或PowerShell(on windows)。腳本本身需要具以下要求:

  • 當部署工作流中的任何任務失敗時,對環境的部署可能會失敗。為了讓環境恢復正常,我們將執行一個回滾腳本。即使在另一個任務失敗時,腳本本身也會為環境執行腳本。通過Azure DevOps的發布管理,您可以使用PowerShell或shell任務來實現此目的,並將其標記為“始終運行”。這樣,無論部署成功或失敗,腳本都將始終得到執行。
  • 如果前一個任務失敗,則應跳過未標記為“始終運行”的任何任務,但將執行始終運行的任務。根據部署失敗的任務對環境進行選擇性更改。執行腳本只是任務的一半。為了避免破壞任何不需要的東西,我們需要了解更多內容。首先,我們需要檢測是否有故障。如果失敗了,那么什么任務失敗了。目前,腳本中沒有一種方法可以了解這些內容。我們需要在腳本中查詢這些版本。幸運的是,Azure DevOps 的市場(https://marketplace.visualstudio.com)中擴展插件“Release Management Utility tasks”(https://marketplace.visualstudio.com/items?itemName=ms-devlabs.utilitytasks),其中包含了一個任務“Powershell to rollback”,這個任務可以協助我們,使回退腳本變得更加簡便。如果你想驗證下面的腳本,需要將這個擴展安裝在你的Azure DevOps Server中。

下面我們來演示如何實現這個功能:

首先,編寫回退腳本,並將其推送到代碼庫中,例如我的回退腳本如下:

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"

}

}

image

然后,在發布流水線中添加回退任務。注意需要將其標記為總是運行“即使上一任務已失敗,即使已經取消部署”:

image

最后,我們看一下回退腳本運行的結果:

image

在上圖中,可以看到回退腳本順利運行,下圖是回退腳本的輸出:

image

在上面第4個方案中,我們只是介紹了基於Azure DevOps Server 的回退機制,而具體的回退腳本,需要根據系統部署的內容來定。需要開發人員或者運維人員根據本次變更的具體內容編寫腳本。例如文件的變動,則需要編輯將備份文件覆蓋回來;如果數據結構的變動,則需要更改數據庫。


微軟DevOps MVP 張洪君 http://www.cnblogs.com/danzhang

--End--


免責聲明!

本站轉載的文章為個人學習借鑒使用,本站對版權不負任何法律責任。如果侵犯了您的隱私權益,請聯系本站郵箱yoyou2525@163.com刪除。



 
粵ICP備18138465號   © 2018-2025 CODEPRJ.COM