運維自動化之ansible--(playbook模式) php
1、Ansible Playbook簡介python
playbook是ansible用於配置,部署,和管理被控節點的劇本。mysql
經過playbook的詳細描述,執行其中的一系列tasks,可讓遠端主機達到預期的狀態。playbook就像Ansible控制器給被控節點列出的的一系列to-do-list,而被控節點必需要完成。也能夠這麼理解,playbook 字面意思,即劇本,現實中由演員按照劇本表演,在Ansible中,此次由計算機進行表演,由計算機安裝,部署應用,提供對外服務,以及組織計算機處理各類各樣的事情。nginx
2、Ansible playbook使用場景web
使用ad-hoc命令能夠方便的執行一些簡單的任務來解決問題,可是有時一個設施過於複雜,須要大量的操做時候,執行的ad-hoc命令是不適合的,這時最好使用playbook。sql
就像執行shell命令與寫shell腳本同樣,也能夠理解爲批處理任務,不過playbook有本身的語法格式。shell
使用playbook你能夠方便的重用這些代碼,能夠移植到不一樣的機器上面,像函數同樣,最大化的利用代碼。在你使用Ansible的過程當中,你也會發現,你所處理的大部分操做都是編寫playbook。能夠把常見的應用都編寫成playbook,以後管理服務器會變得十分簡單。vim
3、Ansible playbook格式tomcat
playbook由YMAL語言編寫。YAML參考了其餘多種語言,包括:XML、C語言、Python、Perl以及電子郵件格式RFC2822。ruby
YMAL格式是相似於JSON的文件格式,便於人理解和閱讀,同時便於書寫。如下爲playbook經常使用到的YMAL格式。
①文件的第一行應該以 」—」 (三個連字符,無空格)開始,代表YMAL文件的開始。
②在同一行中,#以後的內容表示註釋,相似於shell,python和ruby。
③YMAL中的列表元素以」-」開頭而後緊跟着一個空格,後面爲元素內容。就像這樣- apple
④[ 「apple」, 「banana」, 「orange」 ] 同一個列表中的元素應該保持相同的縮進。不然會被當作錯誤處理。
⑤play中hosts,variables,roles,tasks等對象的表示方法都是鍵值中間以」:」分隔,」:」後面還要增長一個空格。
house:
family: { name: Doe, parents: [John, Jane], children: [Paul, Mark, Simone] }
address: { number: 34, street: Main Street, city: Nowheretown, zipcode: 12345 }
⑥劇本以.yml後綴
4、在mysql.yml劇本中,主要由三個部分組成
①hosts部分:使用hosts指示使用哪一個主機或主機組來運行下面的tasks,每一個playbook都必須指定hosts,hosts也可使用通配符格式。主機或主機組在inventory清單中指定,可使用系統默認的/etc/ansible/hosts,也能夠本身編輯,在運行的時候加上-i選項,指定清單的位置便可。在運行清單文件的時候,-list-hosts選項會顯示哪些主機將會參與執行task的過程當中。
②remote_user:指定遠端主機中的哪一個用戶來登陸遠端系統,在遠端系統執行task的用戶,能夠任意指定,也可使用sudo,可是用戶必需要有執行相應task的權限。
③tasks:指定遠端主機將要執行的一系列動做。tasks的核心爲ansible的模塊,前面已經提到模塊的用法。tasks包含name和要執行的模塊,name是可選的,只是爲了便於用戶閱讀,不過仍是建議加上去,模塊是必須的,同時也要給予模塊相應的參數。
5、執行有三個步驟:
一、收集facts
二、執行tasks
三、報告結果
示例:安裝samba服務並啓動
vim /etc/ansible/smb.yml
---
- hosts: web
remote_user: root
tasks:
- name: yum install samba
yum: name=samba state=latest
- name: start smb
service: name=smb state=started
tags: startsmb #標記此start smb任務
執行:ansible-playbook smb.yml
6、Playbook的核心元素:
Hosts:主機
Tasks:任務列表
Variables 變量
Templates:包含了模板語法的文本文件;
Handlers:由特定條件觸發的任務;
Playbooks配置文件的基礎組件:
Hosts:運行指定任務的目標主機;
remoute_user: 在遠程主機上執行任務的用戶;
sudo_user:sudo權限的用戶
tasks:任務列表
一、模塊,模塊參數格式:
(1) action: module arguments
(2) module: arguments
注意:shell和command模塊後面直接跟命令,而非key=value類的參數列表;
(1) 某任務的狀態在運行後爲changed時,可經過「notify」通知給相應的handlers;
(2) 任務能夠經過「tags「打標籤,然後可在ansible-playbook命令上使用-t指定進行調用;
示例:
vim /etc/ansible/nginx.yml
---
- hosts: web
remote_user: root
tasks:
- name: yum install nginx #安裝nginx
yum: name=nginx state=latest
- name:copy nginx.conf #拷貝配置文件
copy: src=/etc/nginx/nginx.conf dest=/etc/nginx/nginx.conf backup=yes
notify: reload #會觸發handlers中名字爲reload的任務
tags: reloadnginx
- name: start nginx #啓動nginx服務
service: name=nginx state=started
tags: startnginx
handlers:
- name: reload #重載配置
service: name=nginx state=reloaded
執行:ansible-playbook nginx.yml -vv
修改配置文件內容以後執行時調用標籤ansible-playbook nginx.yml -vv -t reloadnginx,就會跳過安裝步驟直接重載配置文件並啓動服務
二、variables:變量
(1) facts:可直接調用;
注意:可以使用setup模塊直接獲取目標主機的facters;
(2) 用戶自定義變量:
(a) ansible-playbook命令的命令行中的
-e VARS, --extra-vars=VARS
(b) 在playbook中定義變量的方法:
vars:
- var1: value1
- - var2: value2
(3) 經過roles傳遞變量;
(4) Host Inventory
(a) 用戶自定義變量
(i) 向不一樣的主機傳遞不一樣的變量;
IP/HOSTNAME varaiable=value var2=value2
(ii) 向組中的主機傳遞相同的變量;
[groupname:vars]
variable=value
好比:向web組傳遞變量rpmname=samba
[web]
172.17.251.188
172.17.250.209
[web:vars]
rpmname=samba
示例:使用變量rpmname來代替服務名
vim /etc/ansible/nginx.yml
---
- hosts: web
remote_user: root
vars:
- rpmname: nginx
tasks:
- name: yum install {{ rpmname }} #安裝{{ rpmname }}
yum: name={{ rpmname }} state=latest
- name: copy {{ rpmname }}.conf #拷貝配置文件
copy: src=/etc/{{ rpmname }}/{{ rpmname }}.conf dest=/etc/{{ rpmname }}/{{ rpmname }}.conf backup=yes
notify: reload #會觸發handlers中名字爲reload的任務
tags: reload{{ rpmname }}
- name: start {{ rpmname }} #啓動{{ rpmname }}服務
service: name={{ rpmname }} state=started
tags: start{{ rpmname }}
handlers:
- name: reload #重載配置
service: name={{ rpmname }} state=reloaded
運行:ansible-playbook nginx.yml
三、模板:模板文件以.j2後綴
示例:
編輯模板配置文件
cp /etc/nginx/nginx.conf /etc/nginx/nginx.conf.j2
vim /etc/nginx/nginx.conf.j2
worker_processes {{ ansible_processor_vcpus }}; #引用內置變量得到cpu顆數
listen {{ nginxport }}; #自定義變量
編輯劇本:vim /etc/ansible/nginx.yml
---
- hosts: web
remote_user: root
vars:
- rpmname: nginx
nginxport: 8888 #定義nginx監聽端口爲8888
tasks:
- name: yum install {{ rpmname }} #安裝{{ rpmname }}
yum: name={{ rpmname }} state=latest
- name: copy {{ rpmname }}.conf #拷貝配置文件
template: src=/etc/{{ rpmname }}/{{ rpmname }}.conf.j2 dest=/etc/{{ rpmname }}/{{ rpmname }}.conf backup=yes
notify: reload #會觸發handlers中名字爲reload的任務
tags: reload{{ rpmname }}
- name: start {{ rpmname }} #啓動{{ rpmname }}服務
service: name={{ rpmname }} state=started
tags: start{{ rpmname }}
handlers:
- name: reload #重載配置
service: name={{ rpmname }} state=reloaded
運行:ansible-playbook nginx.yml -t reloadnginx
查看是否開啓端口8888:ansible web -m shell -a 'ss -ntlp|grep "nginx"'
四、循環:迭代,即須要重複執行的任務。
對迭代項的引用,固定變量名爲」item「,然後,要在task中使用with_items給定要迭代的元素列表:
好比:vim /etc/ansible/items.yml
---
- hosts: web
remote_user: root
tasks:
- name: install packages #安裝with_items中列出的包
yum: name={{ item }} state=latest
with_items:
- vsftpd
- php
- php-mysql
執行:ansible-playbook items.yml 就會安裝列表中的包
五、Ansible playbook字典:實現一一對應
示例:vim adduser.yml
---
- hosts: web
remote_user: root
tasks:
- name: add some groups #添加一些組
group: name={{ item }} state=present
with_items:
- group11
- group12
- group13
- name: add some users #建立用戶到對應的組
user: name={{ item.name }} group={{ item.group }} state=present
with_items:
- { name: 'user11', group: 'group11' }
- { name: 'user12', group: 'group12' }
- { name: 'user13', group: 'group13' }
執行:ansible-playbook adduser.yml 就會建立對應的用戶及組
六、角色定製:roles
對於以上全部的方式有個弊端就是沒法實現複用假設在同時部署Web、db、ha 時或不一樣服務器組合不一樣的應用就須要寫多個yml文件。很難實現靈活的調用。
roles 用於層次性、結構化地組織playbook。roles 可以根據層次型結構自動裝載變量文件、tasks以及handlers等。要使用roles只須要在playbook中使用include指令便可。簡單來說,roles就是經過分別將變量(vars)、文件(file)、任務(tasks)、模塊(modules)及處理器(handlers)放置於單獨的目錄中,並能夠便捷地include它們的一種機制。角色通常用於基於主機構建服務的場景中,但也能夠是用於構建守護進程等場景中。
示例:定製三個角色(nginx、mysql、tomcat)
(1)、在roles目錄下生成對應的目錄結構
mkdir -pv /etc/ansible/roles/{nginx,mysql,tomcat}/{files,templates,vars,tasks,handlers,meta,default}
(2)、定義tasks/main.yml的配置文件.先將模板文件考到template目錄下
cp /etc/nginx/nginx.conf.j2 ./roles/nginx/templates/
vim task/main.yml
- name: cp
copy: src=/etc/ansible/roles/nginx/files/nginx-1.10.2-1.el7.ngx.x86_64.rpm dest=/tmp/nginx-1.10.2- 1.el7.ngx.x86_64.rpm
- name: install
yum: name=/tmp/nginx-1.10.2-1.el7.ngx.x86_64.rpm state=latest
- name: conf
template: src=/etc/ansible/roles/nginx/templates/nginx.conf.j2 dest=/etc/nginx/nginx.conf
tags: nginxconf
notify: new conf to reload #觸發名字爲new conf to reload的handles執行
- name: start service
service: name=nginx state=started
(3)、修改變量文件vars/main.yml
添加變量nginxport: 8080
(4)、定義handlers文件handlers/main.yml
- name: new conf to reload
service: name=nginx state=reload
(5)、定義/etc/ansible/roles.yml的playbook文件
- hosts: web
remote_user: root
roles:
- nginx
運行劇本:ansible-playbook roles.yml
查看端口:ansible web -m shell -a 'ss -ntlp|grep "nginx"'
總結:ansible-playbook模式比較易於實現功能以及排錯,除非是很簡單的業務實現可使用hoc模式,其餘較複雜的場景通常都是playbook模式。