Ansible工具(2)
4 Playbook
4.1 playbook介紹

playbook 劇本是由一個(gè)或多個(gè)“play”組成的列表
play的主要功能在于將預(yù)定義的一組主機(jī),裝扮成事先通過ansible中的task定義好的角色。Task實(shí)際是調(diào)用ansible的一個(gè)module,將多個(gè)play組織在一個(gè)playbook中,即可以讓它們聯(lián)合起來,按事先編排的機(jī)制執(zhí)行預(yù)定義的動(dòng)作。
Playbook 文件是采用YAML語言編寫的
4.2 YAML 語言
4.2.1 YAMl 語言介紹YAML是一個(gè)可讀性高的用來表達(dá)資料序列的格式。
YAML參考了其他多種語言,包括:XML、C語言、Python、Perl以及電子郵件格式RFC2822等。Clark Evans在2001年在首次發(fā)表了這種語言,另外Ingyd?t Net與Oren Ben-Kiki也是這語言的共同設(shè)計(jì)者,目前很多軟件中采有此格式的文件,如:ubuntu,anisble,docker,k8s等
YAML:YAML Ain't Markup Language,即YAML不是XML。不過,在開發(fā)的這種語言時(shí),YAML的意思其實(shí)是:"Yet Another Markup Language"(仍是一種標(biāo)記語言)
YAML 官方網(wǎng)站:http://www.yaml.org
4.2.2 YAML 語言特性
YAML的可讀性好
YAML和腳本語言的交互性好
YAML使用實(shí)現(xiàn)語言的數(shù)據(jù)類型
YAML有一個(gè)一致的信息模型
YAML易于實(shí)現(xiàn)
YAML可以基于流來處理
YAML表達(dá)能力強(qiáng),擴(kuò)展性好
4.2.3 YAML語法簡(jiǎn)介
1、在單一文件第一行,用連續(xù)三個(gè)連字號(hào)“-”開始,還有選擇性的連續(xù)三個(gè)點(diǎn)號(hào)(...)用來表示文件的結(jié)尾 2、次行開始正常寫playbook的內(nèi)容,一般建議寫明該playbook的功能 3、使用#號(hào)注釋代碼 4、所進(jìn)的級(jí)別也必須一致的,同樣的縮進(jìn)代表同樣的級(jí)別,程序判別配置的級(jí)別是通過縮進(jìn)結(jié)合換行來實(shí)現(xiàn) 5、YAML文件內(nèi)容是區(qū)分大小寫的,key/value的值軍需大小寫敏感 6、多個(gè)k/v可同行寫也可換行寫,同行使用“,”分隔 7、v可以個(gè)字符串,也可以是另一個(gè)列表 8、一個(gè)完整的代碼塊功能最少元素需包括name和task 9、一個(gè)name只能包含一個(gè)task 10、YAML文件擴(kuò)展名通常為yml或yaml
YAML的語法和其他高階語言類似,并且可以簡(jiǎn)單表達(dá)清單、散列表、標(biāo)量等數(shù)據(jù)結(jié)構(gòu)。其結(jié)構(gòu)(Structure)通過空格來展示,序列(Sequence)里的項(xiàng)用"-"來代表,Map里的鍵值對(duì)用":"分隔,下面介紹常見的數(shù)據(jù)結(jié)構(gòu)。
4.3 Playbook核心元素
hosts 執(zhí)行的遠(yuǎn)程主機(jī)列表
Tasks 任務(wù)集
Variables 內(nèi)置變量或自定義變量在playbook中的調(diào)用
Templates 模板,可替換模板文件中的變量并實(shí)現(xiàn)一些簡(jiǎn)單邏輯的文件
Handlers 和 notify 結(jié)合使用,由特定條件觸發(fā)的操作,滿足條件方才執(zhí)行,否則不執(zhí)行
tags 標(biāo)簽 指定某條任務(wù)執(zhí)行,用于選擇運(yùn)行playbook中的部分代碼。ansible具有冪等性,因此會(huì)自動(dòng)跳過沒有變化的部分,即便如此,有些代碼為測(cè)試其確實(shí)沒有發(fā)生變化的時(shí)間依然會(huì)非常地長(zhǎng)。此時(shí),如果確信其沒有變化,就可以通過tags跳過此些代碼片斷。
4.3.1 hosts 組件
Hosts:playbook中的每一個(gè)play的目的都是為了讓特定主機(jī)以某個(gè)指定的用戶身份執(zhí)行任務(wù)。hosts用于指定要執(zhí)行指定任務(wù)的主機(jī),須事先定義在主機(jī)清單中。
案例:
- hosts: websrvs:appsrvs
4.3.2 remote_user 組件
remote_user: 可用于Host和task中。也可以通過指定其通過sudo的方式在遠(yuǎn)程主機(jī)上執(zhí)行任務(wù),其可用于play全局或某任務(wù);此外,甚至可以在sudo時(shí)使用sudo_user指定sudo時(shí)切換的用戶
案例
- hosts: websrvs
remote_user: root
tasks:
- name: test connection
ping:
remote_user: magedu
sudo: yes #默認(rèn)sudo為root
sudo_user:wang #sudo為wang
4.3.3 task列表和action組件
play的主體部分是task list , task list中有一個(gè)或多個(gè)task,各個(gè)task按序逐個(gè)在hosts中指定的所有主機(jī)上執(zhí)行,即在所有主機(jī)上完成第一個(gè)task之后,再開始第二個(gè)task。
task的目的是使用指定的參數(shù)執(zhí)行模塊,而在模塊參數(shù)中可以使用變量。模塊執(zhí)行是冪等的,這意味著多次執(zhí)行是安全的,因?yàn)槠浣Y(jié)果均一致。
每個(gè)task都應(yīng)該有其name,用于playbook的執(zhí)行結(jié)果輸出,建議其內(nèi)容能清晰地描述任務(wù)執(zhí)行步驟。如果未能提供name,則action的結(jié)果將用于輸出。
task兩種格式:
(1) action: module arguments
(2) module: arguments 建議使用
注意:shell和command模塊后面跟命令,而非key=value
--- - hosts: lou remote_user: root tasks: - name: install httpd yum: name=httpd - name: start httpd service: name=httpd state=started enabled=yes
4.3.4 ShellScripts VS Playbook 案例
#SHELL腳本實(shí)現(xiàn) #!/bin/bash # 安裝Apache yum install --quiet -y httpd # 復(fù)制配置文件 cp /tmp/httpd.conf /etc/httpd/conf/httpd.conf cp/tmp/vhosts.conf /etc/httpd/conf.d/ # 啟動(dòng)Apache,并設(shè)置開機(jī)啟動(dòng) systemctl enable --now httpd #Playbook實(shí)現(xiàn) --- - hosts: websrvs remote_user: root tasks: - name: "安裝Apache" yum: name=httpd - name: "復(fù)制配置文件" copy: src=/tmp/httpd.conf dest=/etc/httpd/conf/ - name: "復(fù)制配置文件" copy: src=/tmp/vhosts.conf dest=/etc/httpd/conf.d/ - name: "啟動(dòng)Apache,并設(shè)置開機(jī)啟動(dòng)" service: name=httpd state=started enabled=yes
4.4 playbook 命令
格式:
ansible-playbook <filename.yml> ... [options]
常見選項(xiàng)
--check -C #只檢測(cè)可能會(huì)發(fā)生的改變,但不真正執(zhí)行操作 --list-hosts #列出運(yùn)行任務(wù)的主機(jī) --list-tags #列出tag --list-tasks #列出task --limit 主機(jī)列表 #只針對(duì)主機(jī)列表中的主機(jī)執(zhí)行 -v -vv -vvv #顯示過程
范例
ansible-playbook file.yml --check #只檢測(cè) ansible-playbook file.yml ansible-playbook file.yml --limit websrvs
范例:remove_httpd.yml
#remove_httpd.yml --- - hosts: websrvs remote_user: root tasks: - name: remove httpd package yum: name=httpd state=absent - name: remove apache user user: name=apache state=absent - name: remove data file file: name=/etc/httpd state=absent
4.5 Playbook中使用handlers和notify
Handlers本質(zhì)是task list ,其中的task與前述的task并沒有本質(zhì)上的不同,用于當(dāng)關(guān)注的資源發(fā)生變化
時(shí),才會(huì)采取一定的操作.Notify對(duì)應(yīng)的action可用于在每個(gè)play的最后被觸發(fā),這樣可避免多次有改變
發(fā)生時(shí)每次都執(zhí)行指定的操作,僅在所有的變化發(fā)生完成后一次性地執(zhí)行指定操作。在notify中列出的
操作稱為handler,也即notify中調(diào)用handler中定義的操作
--- - hosts: websrvs remote_user: root tasks: - name: add group nginx user: name=nginx state=present - name: add user nginx user: name=nginx state=present group=nginx - name: Install Nginx yum: name=nginx state=present - name: config copy: src=/root/config.txt dest=/etc/nginx/nginx.conf notify: Restart Nginx handlers: - name: Restart Nginx service: name=nginx state=restarted enabled=yes
4.6 playbook使用when
when語句,可以實(shí)現(xiàn)條件測(cè)試。如果需要根據(jù)變量、facts或此前任務(wù)的執(zhí)行結(jié)果來做為某task執(zhí)行與否的前提時(shí)要用到條件測(cè)試,通過在task后添加when子句即可使用條件測(cè)試,jinja2的語法格式
--- - hosts: websrvs remote_user: root tasks: - name: "shutdown Centos systems" command: /sbin/shutdown -h now when: ansible_os_family == "Centos"
4.7 Playbook中使用變量
變量名:僅能由字母、數(shù)字和下劃線組成,且只能以字母開頭
變量定義:
key=value
變量調(diào)用方式:
通過{{ variable_name }} 調(diào)用變量,且變量名前后建議加空格,有時(shí)用“{{ variable_name }}”才生效
變量來源:
1. ansible 的 setup facts 遠(yuǎn)程主機(jī)的所有變量都可直接調(diào)用 2. 通過命令行指定變量,優(yōu)先級(jí)最高
在playbook文件中定義變量
vim var2.yml --- - hosts: websrvs remote_user: root vars: - username: user1 - groupname: group1 tasks: - name: create group group: name={{ groupname }} state=present - name: create user user: name={{ username }} state=present ansible-playbook -e "username=user2 groupname=group2” var2.yml #命令行變量?jī)?yōu)先級(jí)更高
浙公網(wǎng)安備 33010602011771號(hào)