去年 5 月,勒索病毒爆發(fā),席卷全球,影響了政府部門、醫(yī)療機(jī)構(gòu)、公共交通、學(xué)校、企業(yè)等等,給全世界帶來了巨大損失。 如果有投資眼光的人,遇到這個(gè)事情,考慮的可能是購買比特幣。而作為運(yùn)維工程師,考慮的只是如何防止病毒影響自己公司的業(yè)務(wù)。相信很多運(yùn)維同行,都參與到了應(yīng)對(duì)勒索病毒的戰(zhàn)役中。 關(guān)于這個(gè)病毒,雖然傳播廣,看起來威力巨大,但是也有很多應(yīng)對(duì)措施。比如關(guān)閉 445 端口防止病毒傳播,或者內(nèi)網(wǎng)建立開關(guān)域名防止病毒運(yùn)行。 當(dāng)然,這些只是 workaround 的方案,最根本的還是要及時(shí)更新服務(wù)器的安全補(bǔ)丁。 如果只有幾臺(tái)、幾十臺(tái)服務(wù)器,補(bǔ)丁更新很簡(jiǎn)單,登陸上去點(diǎn)下安裝或者敲一條命令就可以搞定。 當(dāng)你有成千上萬臺(tái)服務(wù)器的時(shí)候靠人工是不可能的,如果一下子發(fā)一條命令下去到所有服務(wù)器也不合適,可能對(duì)業(yè)務(wù)造成巨大影響。 那么該如何自動(dòng)給上萬臺(tái)服務(wù)器打補(bǔ)丁呢?我們先看一下,一臺(tái)服務(wù)器上怎么操作打補(bǔ)丁。 上圖是個(gè)比較簡(jiǎn)單的操作流程。首先,檢查服務(wù)器是否已經(jīng)安裝了補(bǔ)丁,如果已經(jīng)安裝流程就結(jié)束。 如果還沒有安裝,先將服務(wù)器拉出集群脫離生產(chǎn),然后安裝補(bǔ)丁,重啟服務(wù)器讓補(bǔ)丁生效。 在拉入集群之前,可能還需要給應(yīng)用點(diǎn)火,比如讓應(yīng)用建緩存,讓應(yīng)用恢復(fù)到正常狀態(tài)再接入生產(chǎn)流量。 這其中還有一些復(fù)雜問題,比如一個(gè)集群拉出部分服務(wù)器后,剩余服務(wù)器可能扛不住,要考慮集群可用性。 這樣一個(gè)給一臺(tái)服務(wù)器打補(bǔ)丁的過程,如果要實(shí)現(xiàn)自動(dòng)化,就要完成兩方面的任務(wù):
實(shí)現(xiàn)了一臺(tái)服務(wù)器自動(dòng)打補(bǔ)丁后,再從 1 擴(kuò)展到 1000、10000,給成千上萬臺(tái)服務(wù)器打補(bǔ)丁,要做的一件事就是灰度、灰度、灰度,重要的事情說三遍。 不管你操作多么熟練,技術(shù)多么高超,對(duì)自己開發(fā)的工具多么自信,在做生產(chǎn)大批量運(yùn)維操作的時(shí)候,都要謹(jǐn)慎再謹(jǐn)慎。 而分批灰度是做到謹(jǐn)慎的很好的方法,可以大大減小對(duì)生產(chǎn)的影響,提高網(wǎng)站可用性。 綜合上述對(duì)實(shí)現(xiàn)上萬臺(tái)服務(wù)器自動(dòng)打補(bǔ)丁的需求,我們搭建了一套自動(dòng)化運(yùn)維平臺(tái),包括三個(gè)模塊:
而這樣一套系統(tǒng),不只是可以完成打補(bǔ)丁這樣一個(gè)功能,基本可以覆蓋各種日常運(yùn)維操作自動(dòng)化需求,所以拿出來和大家分享,下面將從三方面進(jìn)行具體介紹。 遠(yuǎn)程控制 SaltStack 是一個(gè)開源的遠(yuǎn)程管理平臺(tái),可以管理各種操作系統(tǒng)的服務(wù)器,主要有 minion 和 master 兩部分。 minion 安裝在要管理的服務(wù)器上,啟動(dòng)后與 master 建立長(zhǎng)連接,master 下發(fā)任務(wù)給 minion,minion 運(yùn)行完成后,將任務(wù)結(jié)果返回給 master。 類似的遠(yuǎn)程管理工具還有 ansible、chef、puppet,大家可以根據(jù)實(shí)際應(yīng)用場(chǎng)景選擇。 操作流程 我們從運(yùn)維發(fā)展的過程來看,首先是傳統(tǒng)運(yùn)維,主要靠手工操作。比如上線一臺(tái)服務(wù)器,登陸服務(wù)器按照操作文檔一步一步操作,更高級(jí)一點(diǎn),把配置命令寫到腳本里,運(yùn)行一個(gè)或多個(gè)腳本完成配置。 有什么缺點(diǎn)呢?首先,人每天重復(fù)這樣的工作,很累,又沒有體現(xiàn)價(jià)值,交付效率低,疲勞時(shí)還容易出錯(cuò),忘記某些配置。 使用腳本呢,容易出現(xiàn)相同功能重復(fù)開發(fā),很多腳本不專門記錄日志,查找歷史操作比較困難。 使用腳本進(jìn)行運(yùn)維操作,發(fā)生了故障,由于沒有統(tǒng)一的運(yùn)維操作日志,無法及時(shí)了解誰做了什么。 隨著時(shí)間的發(fā)展,運(yùn)維發(fā)展到更高級(jí)的 DevOps 時(shí)代,我們也正處于這個(gè)時(shí)代。 這個(gè)時(shí)代有一個(gè)明顯的特征,就是各種各樣開源工具的使用,同時(shí)自己會(huì)開發(fā)很多工具。工具帶來了效率的提升,大大加速了運(yùn)維自動(dòng)化的進(jìn)程。 有這么多的工具可以使用,也會(huì)存在一些問題。比如下面這些問題:
針對(duì)上面這些問題,我們考慮使用基于事件驅(qū)動(dòng)的開源自動(dòng)化運(yùn)維平臺(tái) StackStorm。 你有各種各樣的工具,會(huì)提供很多操作的 API,你把這些 API 調(diào)用實(shí)現(xiàn)成 action 放在 StackStorm 上,然后可以把這些 action 組合成復(fù)雜的 Workflow 實(shí)現(xiàn)不同的任務(wù)。 StackStorm 可以實(shí)現(xiàn)操作插件化、操作邏輯可視化、運(yùn)維日志統(tǒng)一化。 StackStorm 提供了 Web 界面,也提供了 API。你把各種工具的操作放在里面,選中一個(gè)操作,填入?yún)?shù),就可以點(diǎn)擊運(yùn)行。 使用 StackStorm 具體能做一些什么事情呢? 我們?nèi)粘S泻芏嗖煌淖兏僮鳎墙?jīng)常會(huì)重復(fù)做一些相同的事情,比如安裝軟件、重啟服務(wù)、拉入拉出集群等。 如果把不同變更操作過程進(jìn)行拆分,就會(huì)拆出這樣一個(gè)個(gè)小的運(yùn)維原子操作。 反過來,我們可以把這些運(yùn)維原子操作進(jìn)行組合,像樂高積木可以拼出各種各樣的模型,我可以將原子操作組合成各種各樣的變更流程。 這樣相同的操作只需要實(shí)現(xiàn)一次,就可以重復(fù)使用,避免了重復(fù)造輪子,大大提高了開發(fā)效率。 在故障處理方面,我們來看一個(gè)常規(guī)的 oncall case。 比如凌晨 2 點(diǎn),出現(xiàn)了一個(gè)訂單下跌的告警,NOC 開啟電話會(huì)議,將相關(guān)工程師 call 進(jìn)來,工程師接到電話后迷迷糊糊地爬起來,問出現(xiàn)了什么問題,NOC 需要陳述一遍。 然后工程師匆匆忙忙打開電腦,通過 VPN 登陸到內(nèi)網(wǎng)查看相關(guān)監(jiān)控指標(biāo),利用自己的經(jīng)驗(yàn)進(jìn)行故障排查,花了很多時(shí)間終于定位到故障,然后進(jìn)行修復(fù)操作,最后故障恢復(fù)。 這樣的故障處理過程,存在什么問題呢?
如果使用 StackStorm,故障處理的過程是怎么樣的呢? StackStorm 有 webhook 可以監(jiān)聽報(bào)警,當(dāng)一個(gè)報(bào)警發(fā)送給 StackStorm 后,StackStorm 可以先進(jìn)行一些分析,基于專家經(jīng)驗(yàn)或者基于機(jī)器學(xué)習(xí),分析完成之后,判斷這個(gè)報(bào)警是否可以自動(dòng)處理,如果可以就執(zhí)行故障修復(fù)操作,故障恢復(fù)。 如果自己無法處理,會(huì)收集故障異常內(nèi)容,以及初步分析結(jié)果,發(fā)送給相應(yīng)的工程師,為工程師節(jié)省了一些收集信息和排查的時(shí)間,工程師可以快速進(jìn)行故障修復(fù)。 對(duì)于一些常規(guī)的頻繁發(fā)生的故障,如果已經(jīng)有一些固定的處理方法,完全可以交給 StackStorm 自動(dòng)處理。 StackStorm 可以與 ChatOps 結(jié)合,進(jìn)行日常運(yùn)維操作,比如你正在參加 GOPS,StackStorm 將報(bào)警和初步分析發(fā)給你,你通過手機(jī)在 Chat Room 下發(fā)指令給 StackStorm,快速進(jìn)行故障修復(fù)。 了解了 StackStorm 的一些功能,再來看看 StackStorm 的部署架構(gòu)。 圖中黃色的部分是 StackStorm 的主要模塊,包括認(rèn)證、api、規(guī)則引擎、worker、chatops、webui 等等。 mistral 作為 Workflow 引擎,以 PostgreSQL 作為數(shù)據(jù)庫,MongoDB 存儲(chǔ) action 定義、日志,RabbitMQ 是所有任務(wù)的消息隊(duì)列。這是一個(gè)高可用的架構(gòu),每一臺(tái)服務(wù)器上都運(yùn)行著 worker 和 mistral。 這是 StackStorm 的數(shù)據(jù)流圖,StackStorm 將 chat message 對(duì)應(yīng)到動(dòng)作是通過這里的規(guī)則引擎,上面提到的運(yùn)維原子操作組合成工作流,工作流的解析由 mistral 來完成,每一個(gè)具體 action 的執(zhí)行由 worker 完成。 StackStorm 有下面三大好處:
分批灰度 雖然 StackStorm 有很多優(yōu)點(diǎn),但是當(dāng)你想對(duì)上萬臺(tái)服務(wù)器做一個(gè)操作時(shí),你一定不會(huì)希望自己手動(dòng)分批次,手動(dòng)輸入到 StackStorm 里面點(diǎn)擊運(yùn)行,運(yùn)行如果出錯(cuò),還要去看 StackStorm 不便于閱讀的輸出及報(bào)錯(cuò)堆棧。 你想要的,是建一個(gè)任務(wù),指定一批服務(wù)器,在某個(gè)時(shí)間,執(zhí)行某個(gè)任務(wù),最后給出一個(gè)運(yùn)行結(jié)果統(tǒng)計(jì)。所以基于大批量服務(wù)器自動(dòng)操作需求,我們開發(fā)了稱作 Jobs 的工具。 主要為了實(shí)現(xiàn)三個(gè)目標(biāo):
上圖就是 Jobs 系統(tǒng)的新建任務(wù)界面,有分批策略、篩選服務(wù)器等等。 上圖是 Jobs 任務(wù)詳情頁,左邊是任務(wù)信息,右邊是具體的分批的情況。分批運(yùn)行任務(wù),即使任務(wù)運(yùn)行造成了故障,可以及時(shí)發(fā)現(xiàn)及時(shí)停止,控制影響范圍。 總結(jié) 如果想搭建一套運(yùn)維自動(dòng)化的平臺(tái),首先部署一套遠(yuǎn)程管理框架,可以是 saltstack 或者 ansible 等。 然后在 StackStorm 上實(shí)現(xiàn)日常的運(yùn)維原子操作,再根據(jù)具體的操作需求,將原子操作組合成工作流。 最后,對(duì)于大批量服務(wù)器運(yùn)維任務(wù),可以考慮開發(fā)一套具有分批灰度功能的系統(tǒng),完成自動(dòng)化操作。 作者:胡俊雅 |
|