Ansible 系列之 Playbooks 劇本 (1)


 

一、Playbooks 介紹

1.Playbooks是Ansible的配置,部署和編排語言。它們可以描述您希望遠程系統執行的策略,或一般IT流程中的一組步驟。

如果說ansible 模塊 是你車間里的工具,那么playbooks 是你的說明書/使用手冊,並且資源清單上的主機是你的原材料。

在基本層面上,劇本可以用於管理遠程主機的配置與部署,在更高的一層來說,它們可以對涉及滾動更新的多層發布任務進行排序,並且可以將操作委派給其他主機,同時與監視服務器和負載平衡器進行交互。

官網介紹的說playbooks 篇章有很多的內容,他們不建議我們一下子學完,重在積累,以及在使用的過程中來學習,建議不錯。嘿嘿

在ansible 上使用Playbooks是一種完全不同於adhoc的任務執行模式,並且特別強大。簡單地說,playbooks是一個非常簡單的配置管理和多機器部署系統的基礎,以及非常適合部署復雜應用程序的系統。
Playbooks可以對任務進行編排,就像我們要安裝一個程序,寫個安裝shell腳本一樣,在哪一步復制配置文件,最后一步啟動服務。雖然/usr/bin/ansible 可以運行一些臨時任務,但是針對復雜的配置,並且可以將配置標准化,這個時候就需要Playbooks了。
 
2.Playbooks Language example
Playbooks 語言是以YAML 格式表示,並且有最小的語法,有意的說明它不是一個編程或者腳本語言,它是一種寫配置文件的語言。簡潔可讀性高。
 
YAML 語法:
這里我們先大致的看下YAML的語法吧,看看有什么需要遵守和記住的編寫規則。
a.對於Ansible來說,幾乎每個YAML文件都以列表開頭。列表中的每個項目是 鍵/值對的列表,通常稱為“列表”或“字典”。因此,我們需要知道如何在YAML中編寫列表和字典。
b.還有一個地方,每個文件都是以  --- 開始,以 ... 結尾。這也是yaml 語言格式的一部分,指出文檔的開始和結束。
c.列表中所有的詞都是 - (減號和空格)開頭的相同縮進的行。如下:
---
# A list of tasty fruits
fruits:
    - Apple
    - Orange
    - Strawberry
    - Mango
...

d.字典以簡單的形式表示 key: value (冒號后面必須跟一個空格),不能使用tab 鍵如下:

# An employee record
martin:
    name: Martin D'vloper
    job: Developer
    skill: Elite

e.也有復雜的數據結構,例如帶有字典的列表。

下面是一個隨意的YAML文件,和ansible無關。

---
# 員工記錄
name: xiaoming
job: Developer
skill: Elite
employed: True
foods:
    - Apple
    - Orange
    - Strawberry
    - Mango
languages:
    perl: Elite
    python: Elite
    pascal: Lame
education: |
    4 GCSEs
    3 A-Levels
    BSc in the Internet of Things

f.區分大小寫,如果在 key:value 里,value里面有冒號,需要用 “” 號將 整個value 包圍住。

 

OK,繼續學習palybooks。。。

每個palybook(劇本)都有一個或多個palys (每一場)組成。palys的目的是將一組主機映射到一些明確定義的角色,由ansible來調用任務。基本來說,一個任務就是調用ansible 的某個模塊。

 

 二、真槍實戰

1.看一個基本的palybook

---
- hosts: all
  tasks:
    - name: Installs nginx web server
      yum: name=nginx state=installed update_cache=true
      notify:
        - start nginx

  handlers:
    - name: start nginx
      service: name=nginx state=started

結合着上面YAML遵守的規則來分析下。

第一行中,文件開頭為 ---;這是YAML 將文件解釋為正確的文檔的要求。YAML 允許多個“文檔”存在於一個文件中,每個“文檔”由 --- 符號分割,但Ansible只需要一個文件存在一個文檔即可,因此這里需要存在於文件的開始行第一行。

YAML對空格非常敏感,並使用空格來將不同的信息分組在一起,在整個文件中應該只使用空格而不使用制表符,並且必須使用一致的間距,才能正確讀取文件。相同縮進級別的項目被視為同級元素。

以 - 開頭的項目被視為列表項目。作為散列或字典操作,它具有key:value格式的項。YAML文檔基本上定義了一個分層的樹結構,其中位於左側是包含的元素。

在第二行

---
- hosts: all
這是我們在上面學到的YAML中的列表項,但由於它在最左側的級別,它也是一個Ansible“palys”(某個任務)。plays基本上是在某一組主機上執行的任務組,以允許它們實現要分配給它們的功能。每個play必須指定一個主機或一組主機,正如上面一樣,指定了all 所有主機。
 
往下看,看下第一個任務
---
- hosts: all
  tasks:
    - name: Installs nginx web server
      yum: name=nginx state=installed update_cache=true
      notify:
        - start nginx

在上面,有 “tasks:"與 "hasts:" 同級。它包含一個包含鍵值對的列表(因為它以一個 "-" 開頭).

第一個,“name”,這是一個任務的描述。可以隨意定義。

下一個key 是 "yum",這里引用的是Ansible 的一個模塊,就像我們直接在命令行使用ansible 命令一樣,如下面:

# ansible all -m yum -a "name=nginx state=present update-cache=true"

"yum" 這個模塊允許我們指定一個軟件包和它應該在的狀態,上面例子中是應“已安裝”的狀態。update-cache = true 部分告訴我們的遠程機器在安裝軟件之前更新其軟件包緩存(相當於yum makecache)。

“notify”項 包含具有一個項目的列表,它會呼叫 “start nginx”。這不是一個Ansible內部命令,它是對handlers的引用,當從任務中調用該處理程序時,它可以執行某些功能。我們將在下面定義“start nginx” 的處理程序

---
- hosts: all
  tasks:
    - name: Installs nginx web server
      yum: name=nginx state=installed update_cache=true
      notify:
        - start nginx

  handlers:
    - name: start nginx
      service: name=nginx state=started

“handlers” 部分與“hosts”、“tasks” 處於同一級別。handlers就像任務,但它們只有在客戶端系統發生了更改的任務被告知時才運行。

例如,我們在這里有一個handlers,在安裝軟件包后啟動Nginx服務。除非 “Installs nginx web server” 任務導致系統更改,否則不會調用處理程序,這意味着包必須安裝,並且之前沒有被安裝。

 我們將上述內容保存一個nginx_install.yml 文件中。

   本文中文屬於作者原創,轉載請注明出處。飛走不可http://www.cnblogs.com/hanyifeng/p/6435875.html

2. 運行Ansible-playbook

一旦你制作了一個playbook.yml,可以使用這種格式輕松地調用:

ansible-playbook playbook.yml

例如,如果我們想在所有的主機上安裝和啟動Nginx,我們可以使用上面的nginx_install.yml,運行以下命令:

[root@ansibler task]# ansible-playbook nginx_install.yml

執行完成后會輸出以下信息:

[root@ansibler task]# ansible-playbook nginx_install.yml

PLAY [all] *********************************************************************

TASK [setup] *******************************************************************
ok: [192.168.30.177]
ok: [192.168.30.176]

TASK [Installs nginx web server] ***********************************************
changed: [192.168.30.176]
changed: [192.168.30.177]

RUNNING HANDLER [start nginx] **************************************************
changed: [192.168.30.177]
changed: [192.168.30.176]

PLAY RECAP *********************************************************************
192.168.30.176             : ok=3    changed=2    unreachable=0    failed=0
192.168.30.177             : ok=3    changed=2    unreachable=0    failed=0

從上面可以看出,ansible 的 任務是按順序來執行的,並且每個任務執行都會顯示該任務的名稱及狀態,便於我們了解當前任務的執行狀態。在結尾處,是每個任務的狀態統計。

上面我們指定了運行playbook的主機為所有hosts 列表中的主機,如果需要指定某些主機可以使用 -l 選項,如下:

ansible-playbook -l 192.168.30.176 nginx.yml

 

3.增加一些功能到playbook 中

 接着上面的nginx_install 文件,繼續。上面的劇本是服務器安裝了軟件,並正常運行。我們可以向 palybook中添加任務 來擴展功能。

添加nginx默認首頁

我們可以通過添加幾行內容來,告訴它將文件從我們的Ansible服務器傳輸到選定的主機上,完整內容如下:

---
- hosts: all
  tasks:
    - name: Installs nginx web server
      yum: name=nginx state=installed update_cache=true
      notify:
        - start nginx
    - name: Upload default index.html for host
      copy: src=static_files/index.html dest=/usr/share/nginx/html/ mode=0644

  handlers:
    - name: start nginx
      service: name=nginx state=started

然后我們可以在我們ansible 主機的當前目錄中創建一個名為static_files的目錄,並將一個index.html文件放在其中。

mkdir static_files

index.html文件內容如下:

<html>
  <head>
    <title>This is a sample page</title>
  </head>
  <body>
    <h1>Here is a heading!</h1>
    <p>Here is a regular paragraph.  Wow!</p>
  </body>
</html>

現在,當我們重新運行playbook時,Ansible會檢查每個任務。它會看到Nginx已經安裝在選定主機上,所以它會進行下一步。並看到新的任務部分,然后將我們的服務器中的index.html文件替換選定主機上默認的index.html文件。

 

4.注冊結果

當我們手動安裝和配置服務時,幾乎總是需要知道當前的操作是否成功。我們可以通過使用“register”,把這個功能放到我們的palybooks中。對於每個任務,我們可以選擇將其結果(失敗或成功)注冊在我們稍后可以檢查的變量中。

當使用這個功能時,我們還必須告訴Ansible忽略該任務的錯誤,因為如果發生任何錯誤或異常,它會中止該劇本的執行。因此,如果我們想檢查任務是否失敗或者不決定后續的步驟,我們可以使用 register 功能。

例如,index.php如果文件存在,我們可以讓我們的playbooks上傳index.php文件。如果該任務失敗,我們可以嘗試上傳index.html文件。我們將檢查任務中的失敗情況,因為我們只想在PHP文件失敗時上傳HTML文件:

---
- hosts: all
  tasks:
    - name: Installs nginx web server
      yum: name=nginx state=installed update_cache=true
      notify:
        - start nginx

    - name: Upload default index.html for host
      copy: src=static_files/index.php dest=/usr/share/nginx/html/ mode=0644
      register: php
      ignore_errors: True

    - name: Remove index.html for host
      command: rm /usr/share/nginx/html/index.html
      when: php|success

    - name: Upload default index.html for host
      copy: src=static_files/index.html dest=/usr/share/nginx/html/ mode=0644
      when: php|failed

  handlers:
    - name: start nginx
      service: name=nginx state=started

備注:

目前nginx web環境中還不能處理PHP文件
上述的playbooks版本,嘗試將index.php文件上傳到選定的主機上。並將該任務的成功或者失敗注冊到名為“php”的變量中。

a.如果此操作成功,則接下來運行刪除index.html文件的任務。(該刪除操作的前提是index.html 存在於playbooks中選定的主機上)

b.如果此操作失敗,則會上傳index.html文件。

 

三、故障記錄

1. 由於之前的系列文章中,測試環境是docker 平台上的容器,鑒於docker 容器內無法由宿主機安裝軟件並啟動,這篇文章便使用了3台虛擬機,系統是centos 6.6,ansible 版本2.2.1,在運行ansible 時,出現以下錯誤:

上一個命令還成功了,下一個就失敗了。參考以下鏈接,更新了內核到2.6.32-642.15.1.el6.x86_64.之后就沒問題了。

也有人說是openssh 的問題,升級openssh即可。如果在有人碰到,請先升級openssh組件。如果不行的話,在升級內核。

 

本文中文屬於作者原創,轉載請注明出處。飛走不可http://www.cnblogs.com/hanyifeng/p/6435875.html

參考資料:

如何寫playbooks  https://www.digitalocean.com/community/tutorials/how-to-create-ansible-playbooks-to-automate-system-configuration-on-ubuntu

ansible故障:https://github.com/ansible/ansible/issues/13876


免責聲明!

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



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