隨着 DevOps 的流行,愈來愈多的工做被自動化處理。在搭建大規模的 IT 架構時,須要系統管理員夜以繼日地安裝配置服務器、調整各類參數等工做,直到Chef 的出現,將系統管理員從這種水深火熱的工做中解脫了出來,他們只須要編寫 Chef 腳本,描述出服務器所須要保持的狀態,而後運行腳本,服務器就配置好了。本文以配置一個 Web 服務器爲例,對 Chef 的概念和工做流程作一簡單介紹。html
0評論: node
2015 年 6 月 23 日web
在 IBM Bluemix 雲平臺上開發並部署您的下一個應用。bootstrap
「這是一個最好的時代,也是一個最壞的時代。他們都在直奔天堂,而咱們都在直奔相反的方向。」緩存
「90 後霸道總裁」 的超級課程表融資千萬美圓、WhatsApp 被 Facebook 以 190 億美圓收購……這個時代彷彿處處都充滿了機會。如今假設咱們也決定放棄朝九晚五的工做,要開發出一款 Web 應用改變這個世界,順便當上總經理、出任 CEO、贏取白富美、走向人生巔峯。七拼八湊,咱們的應用作出來了。它的架構很是簡單,若是非要描述的話,它的架構如圖 1 所示:服務器
這麼簡單的應用,咱們上網瀏覽一下資料,隨便租個服務器,安裝一個 Web 服務器,配置一下,應用順利上線。架構
幸福老是來得太快,很快咱們的應用就火了。隨着訪問量的增大,咱們須要單獨的數據庫服務器,一個都不夠,得來倆;應用服務器也不夠用了,再多添幾臺,上一個負載均衡;對數據庫的訪問又成了性能瓶頸,增長些數據庫緩存吧,最終,應用的架構變成了以下的樣子:
如今問題來了,面對如此複雜的架構,怎麼安裝和配置這些服務呢?Chef 就是用來解決這個問題的。
讓咱們暫且就此打住,先來看看怎麼使用 Chef。首先須要在一臺 Linux 機器上安裝Chef Development Kit。若是您實在找不到一臺 Linux 機器也沒有關係,可以使用一個用於教學用途的在線虛擬機,該虛擬機上已經預裝了 Chef Development Kit,能夠直接使用。
Recipe 是 Chef 中主要執行任務的地方,翻譯成中文是「菜譜」的意思。咱們的第一份「菜譜」的主要功能是使用 Chef 生成一個文本文件,其內容爲:Hello Chef。讓咱們先新建一個 chef-repo 目錄,用來存放「菜譜」,而後在該目錄下建立第一個「菜譜」:hello.rb,其內容以下:
file 'motd' do content 'Hello Chef’ end
在命令行中執行:chef-appy hello.rb,輸出以下:
可 以看到,命令執行後生成 motd 文件,該文件的內容爲字符串:Hello Chef。這就是咱們的第一份「菜譜」,雖然簡單,可是卻歸納了 Chef 的基本工做原理:使用一個 Ruby 文件,即「菜譜」描述服務器應有的狀態,而後執行 Chef 命令配置服務器。
您可嘗試再次執行 chef-appy hello.rb,Chef 會檢測到 motd 文件已經存在,且文件內容和「菜譜」中所描述的一致,所以不進行任何操做;您還可嘗試手動刪除 motd 文件,再次執行 chef-appy hello.rb 後,又從新生成了 motd 文件。這正是配置服務器所須要的,每次配置都能保證狀態一致。
固然,咱們的第一份「菜譜」只是一道開胃小菜,下面咱們看看如何使用 Chef 部署一個 Web 服務器。
部署一個 Web 服務器比生成一個文件複雜,但道理倒是相同的,讓咱們先來看看代碼:
package 'httpd' service 'httpd' do action [:start, :enable] end file '/var/www/html/index.html' do content '<html> <body> <h1>hello world</h1> </body> </html>' end service 'iptables' do action :stop end
這段代碼總共分紅四部分:第一部分安裝 Apache HTTP Server;第二部分啓動 HTTP 服務;第三部分生成主頁面;第四部分停用 iptables 服務,這一步主要是由於有些 Linux 安裝後,默認只打開 22 端口,其餘端口是被禁止的,停用 iptables 服務後,就能夠順利訪問 80 端口了,即 HTTP 協議所使用的端口。聰明的您朋友們,您能將這四部分和代碼對應起來嗎?
這裏要注意的是,這四部分的順序很是重要,必須先安裝 Apache HTTP Server,而後啓動它,這一點也不難想象,咱們手動配置服務器時不也如此嗎?
將 文件保存後,讓咱們再來運行 sudo chef-appy webserver.rb,由於腳本里包含安裝軟件包的操做,因此須要 root 權限,若是您不是以 root 帳號登陸(相信您不會真的這樣作吧?),務必在命令行前加 sudo,不然,Chef 會報錯。若是獲得相似下面的輸出,就證實服務器配置成功,打開瀏覽器,輸入http://localhost,能夠看到剛纔定製的主頁了吧?
然 而,做爲有「潔癖」的程序員,不難發現「菜譜」的第二部分好像混入了什麼奇怪的東西:一段 HTML 代碼。這段 HTML 代碼明顯和其餘部分不協調,若是網頁再變得複雜點,這份「菜譜」會變得很難管理。所以,咱們得想點什麼辦法,管理「菜譜」。方法就是「烹飪手冊」 (cookbook)。
和真實的烹飪同樣,「烹飪手冊」是用來組織「菜譜」的,在「烹飪手冊」裏,不光能夠定義各類「菜譜」,也能夠定義一些屬性文件或模板,這些屬性文件或模板能夠在「菜譜」裏直接引用。在實際工做中,咱們每每使用的也是「烹飪手冊」,而不是一個個單獨的「菜譜」。
讓咱們在當前目錄下新建一個文件夾 cookbooks,而後切換到該目錄,調用 chef generate cookbook learn_chef_httpd 會自動爲咱們生成一個「烹飪手冊」。「烹飪手冊」的目錄結構以下:
其中 recipes 目錄下的 default.rb 是默認的「菜譜」,讓咱們將其中內容替換爲以前編寫的「菜譜」。
現 在咱們要將原來「菜譜」中的 HTML 代碼移到一個外部文件中,使用 chef generate template learn_chef_httpd index.html 命令生成模板文件 index.html.erb,該文件被放置在 learn_chef_httpd/templates/default 目錄下。而後將該文件內容替換爲以前的 HTML,修改 default.rb,引用該模板,最終的「菜譜」變成了下面這個樣子:
package 'httpd' service 'httpd' do action [:start, :enable] end template '/var/www/html/index.html' do source 'index.html.erb' end service 'iptables' do action :stop end
在命令中執行 sudo chef-client --local-mode –runlist ‘recipe[learn_chef_httpd]’ ,打開瀏覽器,訪問http://localhost ,若是能正常訪問,那麼恭喜您完成了本身的第一個「烹飪手冊」!
上 面的例子只是爲了展現如何編寫「菜譜」和「烹飪手冊」,真實環境下的 Chef 卻不是這樣工做的。在真實環境下,系統管理員在一臺電腦上編寫 Chef 腳本,而後使用上述方式調試,調試成功後,將腳本上傳至 Chef 服務器,咱們從控制檯向 Chef 服務器發命令,Chef 服務器會將配置下發到各個待配置服務器,在每一個服務器上運行 Chef,完成對服務器的配置。
爲此,咱們需作三點準備:一臺用於編寫 Chef 腳本的電腦、一臺 Chef 服務器、不少待配置的服務器。咱們已經有了一臺能夠編寫 Chef 腳本的電腦,爲了方便學習,Chef 服務器能夠選用Chef 官網提供的託管服務,另外須要幾臺待配置的服務器,記得不要在服務器上安裝 Chef,當咱們配置這些服務器時,Chef 會自動在上面安裝所需的工具。
註冊成功 Chef 的託管服務後,先建立一個組織,而後下載與之對應的 Starter Kit,解壓到當前目錄,該工具是用來作認證的,有了它,才能夠從本地鏈接 Chef 服務器。如今讓咱們刪除之前建立的「烹飪手冊」,轉而從 Chef 超市上 下載一個現成的手冊。Chef 超市是一個開發者交流「烹飪手冊」的地方,由於配置服務器的不少操做都是通用的,因此人們把這些配置作成手冊,放在一個地方,你們都能使用。咱們編寫 Chef 腳本,每每也是先上 Chef 超市去看看有沒有可用的手冊,若是有,直接拿過來,或者在此基礎上修改一下就能用,若是沒有,再考慮編寫本身的手冊。使用以下命令下載前面配置 Web 服務器的手冊:
knife cookbook site download learn_chef_httpd
將下載後的手冊解壓到 cookbooks 目錄,刪除壓縮包:
tar -zxvf learn_chef_httpd-0.1.0.tar.gz -C cookbooks rm learn_chef_httpd*.tar.gz
接下來將該手冊上傳至 Chef 服務器,即咱們剛纔註冊的 Chef 託管服務:
knife cookbook upload learn_chef_httpd
打 開託管服務控制檯,在 Policy 選項卡下就能看見剛剛上傳成功的「烹飪手冊」。接下來咱們要作的工做是告訴 Chef 服務器來幫咱們讓服務器自舉,這一步會經過 SSH 登陸到待配置的服務器,下載並安裝 Chef,而後下載執行剛剛上傳到 Chef 服務器上的「烹飪手冊」。該操做只在第一次配置服務器時須要,自舉成功後,之後就再不須要自舉了:
knife bootstrap `address` --ssh-user `user` --ssh-password '`password`' \ --sudo --use-sudo-password --node-name node1 \ --run-list 'recipe[learn_chef_httpd]'
將其中的`address`、`user`、`password`替換爲待配置服務器的真實地址、用戶名和密碼。打開瀏覽器,輸入服務器地址,看看是否能訪問定製的主頁?
Chef 不光能夠管理服務器,同時服務器將本身的信息上傳至 Chef 服務器。使用以下命令查看當前組織裏被管理的服務器:
knife node list
使用以下命令查看服務器信息,包括服務器的 IP 地址、機器名、操做系統等信息:
knife node show node1
有了這些信息後,咱們能夠從新修改模板,讓其顯示給定服務器的信息:
<html> <body> <h1>hello from <%= node['fqdn'] %></h1> </body> </html>
再將「烹飪手冊」上傳至 Chef 服務器,而後使用以下命令配置服務器:
knife ssh `address` 'sudo chef-client' --manual-list \ --ssh-user `user` --ssh-password '`password`'
同理,將`address`、`user`、`password`替換爲待配置服務器的真實地址、用戶名和密碼。打開瀏覽器,輸入服務器地址,看看改動是否生效?
只要一臺服務器配置成功,咱們即可以用一樣的方法配置幾十臺、上百臺。並且一旦配置發生變化,咱們只需修改腳本,全部服務器即可以得到相同的更新,這個時候,Chef 的威力就顯示出來了。
細 心的您可能會注意到,上面的命令,一些是 chef *****,一些倒是 knife *****。初次接觸 Chef,很容易被這些命令搞混。這裏有一個簡單的規則:本地執行的命令以 chef 打頭,須要遠程鏈接到 Chef 服務器或待配置服務器的命令以 knife 打頭。
最後,讓咱們再複習一遍本文中所使用到的命令:
運行「菜譜」
chef-appy hello.rb
使用 Chef 生成「烹飪手冊」
chef generate cookbook learn_chef_httpd
使用 Chef 生成模板
chef generate template learn_chef_httpd index.html
使用 Chef 運行「烹飪手冊」
chef-client --local-mode –runlist ‘recipe[learn_chef_httpd]’
從 Chef 超市下載「烹飪手冊」
knife cookbook site download learn_chef_httpd
向 Chef 服務器上傳「烹飪手冊」
knife cookbook upload learn_chef_httpd
服務器自舉
knife bootstrap `address` --ssh-user `user` --ssh-password '`password`' \ --sudo --use-sudo-password --node-name node1 \ --run-list 'recipe[learn_chef_httpd]'
獲取當前組織下的服務器列表
knife node list
顯示服務器信息
knife node show node1
使用 Chef 遠程運行「烹飪手冊」,配置服務器
knife ssh `address` 'sudo chef-client' --manual-list \ --ssh-user `user` --ssh-password '`password`'
隨 着雲計算和 DevOps 技術的發展,有人斷言系統管理員和 DBA 會面臨失業,將來的雲計算公司和數據庫公司只會僱傭少數系統管理員和 DBA 管理他們的 IT 基礎設施和數據庫。雖然做者不大同意「機器替代人工」這一觀點,但提前下手,學點東西總不是壞事,所謂技多不壓身嘛。
Chef 可以實現服務器配置的自動化,在 DevOps 運動中佔有重要的位置。本文經過一個配置 Web 服務器的例子,一步步引導你們如何使用 Chef。但願您讀完本文,能編寫出本身的第一個「烹飪手冊」。