ansible

ansible能夠批量管理多臺主機。經過調用各個功能模塊、ssh鏈接、發送python腳本、遠程主機上的一些命令來完成管理各被控端,因此不用給各被管理節點專門安裝客戶端工具。php


不過通常須要事先配置ansible端能基於密鑰認證的方式聯繫各被管理節點。html

若是要用密碼的方式,要啓用主配置文件中的ask_pass  = True,並安裝上sshpass軟件便可
python


目錄:linux

1、介紹nginx

2、經常使用模塊介紹web

3、playbookshell

4、rolesapache


wKioL1a8AeKzFMFhAABZ2m7AMb4382.png


想深刻了解的朋友請看這裏:http://www.ansible.com.cn/ubuntu

或這裏:http://docs.ansible.com/vim


1、介紹:

模塊化,調用特定的模塊來完成特定任務;
基於Python語言實現,由Paramiko, PyYAML和Jinja2三個關鍵模塊>實現;
支持自定義模塊
支持playbook: 能夠把多個任務編排好,一次性的執行完。
冪等性:屢次執行的結果是同樣的。


ansible命令的使用方式仍是很簡單的:

ansible <host-pattern> [-f forks] [-m module_name] [-a args]

host_pattern 是來指定主機的,能夠是單臺主機,也能夠是主機組。前提是要在ansible的hosts配置文件中指定。

-f 指定一次批量管理的主機數量。 能夠說就是併發管理數量。 與總的數量沒有關係。

-m 指定模塊。

-a  模塊參數


它全部的管理功能都是由各個模塊所提供,查看模塊使用方法:

ansible-doc [-M module_path] [-l] [-s] [module...]

-M 查看模塊的詳細信息,要指定模塊的路徑

-l   列出全部模塊。

-s  查看模塊使用方式。


安裝:

ansible依賴於Python 2.6或更高的版本、paramiko、PyYAML及Jinja2。

編譯安裝

# yum -y install python-jinja2 PyYAML python-paramiko python-babel python-crypto
# python setup.py build
# python setup.py install
# mkdir /etc/ansible
# cp -r examples/* /etc/ansible


注意:不一樣版本的ansible的功能差別可能較大。

我這裏就直接yum安裝了。

環境:

系統: CentOS Linux release 7.1.1503 (Core)

軟件: ansible-1.9.2-1.el7


看一下所生成的文件:

/etc/ansible
/etc/ansible/ansible.cfg          #ansible主配置文件。  通常不用修改,若是想自定義一下,請看上面的網址。
/etc/ansible/hosts                   #主配置文件中所指定的主機清單文件 
/etc/ansible/roles                   #用來定義roles的目錄
/usr/bin/ansible                      
/usr/bin/ansible-doc
/usr/bin/ansible-galaxy
/usr/bin/ansible-playbook
.....


首先咱們須要在hosts裏面定義各被管主機。這個文件被稱爲inventory文件。

[root@localhost ~]# vim /etc/ansible/hosts      
[wserver]
172.16.40.11
172.16.40.12

[dbserver]
172.16.40.20

這個文件裏面都是一些定義主機的例子,我這裏把它們註釋了,添加了上面幾個。

inventory文件遵循INI文件風格,中括號中的是組名,能夠用各個組名錶示多個主機。 也能夠用all來表示全部主機。 固然也可使用單個主機。同一個主機能夠出如今多個組中。

此外,當如若目標主機使用了非默認的SSH端口,還能夠在主機名稱以後使用冒號加端口號來標明。

如: 172.16.40.11:22022

組還能夠包含其它的組,組嵌套。


在這裏若是所管理主機的系統版本不同也沒問題,由於ansible會檢測主機的系統參數並作出不一樣的設置。但並非絕對不會有問題。

每次執行操做會發送python腳本到客戶端的   對應用戶家目錄下的.ansible/tmp目錄下面。 具體做用暫時不清楚,多是用來收集信息、執行任務和調用本地的命令的吧。


2、經常使用模塊介紹:

這裏只是經常使用的部分,詳細的能夠用ansible-doc來查看。如查看一下user模塊。

[root@localhost ~]# ansible-doc -s user

帶=號的表示必選項。

http://docs.ansible.com/ansible/modules_by_category.html


user: 用戶管理

state={present|absent}   #present表示建立,absent表示刪除。
force=yes          #強制刪除用戶。 通常狀況下用戶在已登陸狀態下是不能刪除的。至關於userdel -f
remove=yes     #在刪除用戶的時候,同時刪除家目錄與mail spool。至關於userdel -r    
system=yes   #建立的系統用戶   
uid                #指定uid
shell             #指定shell
password       #用來指定密碼,要用已加密的密碼。

上面的password後面的密碼能夠用openssl passwd 來生成。可是好像只能是md5加密的。

[root@localhost ~]# openssl passwd --help
Usage: passwd [options] [passwords]
where options are
-crypt             standard Unix password algorithm (default)
-1                 MD5-based password algorithm
.....

例:

[root@localhost ~]# openssl passwd -1 
Password: 
Verifying - Password: 
$1$.0isU960$NDoCtqtkDBa2q9TQJYQml1

[root@localhost ~]# ansible all -m user -a 'name=test1 password="$1$.0isU960$NDoCtqtkDBa2q9TQJYQml1"'
172.16.40.11 | success >> {
    "changed": true,                                                                                                                        
    "comment": "",                                                                                                                          
    "createhome": true,                                                                                                                     
    "group": 1007,                                                                                                                          
    "home": "/home/test1",                                                                                                                  
    "name": "test1",                                                                                                                        
    "password": "NOT_LOGGING_PASSWORD",                                                                                                     
    "shell": "/bin/bash",                                                                                                                   
    "state": "present",                                                                                                                     
    "system": false,                                                                                                                        
    "uid": 1007                                                                                                                             
} 
.....

刪除:

[root@localhost ~]# ansible all -m user -a 'name=test1 state=absent'


group: 組管理

  action: group
      gid                    # Optional `GID' to set for the group.
      name=             # Name of the group to manage.
      state                 # Whether the group should be present or not on the remote host.
      system             # If `yes', indicates that the group created is a system group.

與user差很少,並且參數也就只有這幾個。


cron:  管理cron計劃任務

      day                    # Day of the month the job should run ( 1-31, *, */2, etc )
      hour                   # Hour when the job should run ( 0-23, *, */2, etc )
      job                    # The command to execute. Required if state=present.
      minute                 # Minute when the job should run ( 0-59, *, */2, etc )
      month                  # Month of the year the job should run ( 1-12, *, */2, etc )
      name=                  # Description of a crontab entry.
      state                  # Whether to ensure the job is present or absent.
      user                   # The specific user whose crontab should be modified.
      weekday                # Day of the week that the job should run ( 0-6 for Sunday-Saturday, *, etc )
      .....

只要使用過cron,我想也不用過多解釋吧。state與上面的模塊一個意思,時間參數不寫表示*。

name用來描述任務,andible也用它來識別各個添加的任務,才能用來刪除不一樣的任務。

若是有name相同的任務,會覆蓋。


例:

[root@localhost ~]# ansible wserver -m cron -a 'name=sync_time minute=*/5 job="/sbin/ntpdate 172.16.0.1 > /dev/null;/sbin/hwclock -w"'

連到一臺主機看一下crontab。

[root@localhost ~]# crontab -l
*/15 * * * * /sbin/ntpdate 172.16.0.1 > /dev/null;/sbin/hwclock > /dev/null    #這個是原來就有的。
#Ansible: sync_time                #這個就是咱們剛添加的。
*/5 * * * * /sbin/ntpdate 172.16.0.1 > /dev/null;/sbin/hwclock -w

刪除:

[root@localhost ~]# ansible wserver -m cron -a 'name=sync_time state=absent'


例: 添加每2天的2:30備份/etc目錄到/var/backup下。

[root@localhost ~]# ansible wserver -m cron -a 'name=etc_tar minute=30 hour=2 day=*/2 job="/bin/tar -Jcf /var/backup/`/bin/date "+\\%Y\\%m\\%d-\\%H\\%M"`.tar.xz /etc"'

查看一下:

#Ansible: etc_tar
30 2 */2 * * /bin/tar -Jcf /var/backup/`/bin/date +\%Y\%m\%d-\%H\%M`.tar.xz /etc


ping: 探測主機是否在線

[root@localhost ~]# ansible all -m ping

這個模塊沒有參數,只是用來探測主機是否在線的。


file: 文件管理

path=            #表示文件路徑,必選項。
mode            #表示設置權限
owner            #屬主  
group             #屬組
state=directory      #建立目錄或修改目錄權限。
state=touch            #建立文件或修改文件權限。
state=file                 #修改文件權限。
state=link                #建立文件的符號連接。src=源文件   path=連接文件
state=absent           #刪除文件或目錄。

建立目錄是遞歸建立的,也就是會自動建立所需的目錄。 而文件或連接文件都不行。


例:建立目錄。

[root@localhost ~]# ansible wserver -m file -a 'path=/var/backup/ state=directory'
[root@localhost ~]# ansible wserver -m file -a 'path=/tmp/6/7/8/9  state=directory'

例:建立連接文件。把etc目錄連接至/tmp/etc。

[root@localhost ~]# ansible wserver -m file -a 'path=/tmp/etc src=/etc  state=link'


copy: 複製文件

content          #代替src,設置文件中的內容爲指定的內容。若是目標文件不存在,則自動建立隨機名稱文件。
                                   #若是原來文件有數據,則覆蓋。  暫時不知道有什麼用。
src                    #源文件路徑。
owner              #屬主。
group                #屬組。
mode                #權限。   
dest=                 #目標路徑。
backup              #覆蓋文件以前,先備份。 yes/no


例: 把/etc/nginx目錄複製到遠程主機的/etc/下面。

[root@localhost ~]# ansible wserver -m copy -a 'src=/etc/nginx dest=/etc/'


例:複製本地的/home/star/httpd.conf文件到遠程主機的/etc/httpd/conf/目錄下,並修改權限。

ansible wserver -m copy -a 'src=/home/star/httpd.conf owner=root group=root mode=644 dest=/etc/httpd/conf/'


例: 修改遠程主機的/var/listen文件內容爲, 第一行listen=80 第二行listen=8080

[root@localhost ~]# ansible wserver -m copy -a 'content="listen=80\nlisten=8080\n" dest=/var/listen'

查看一下遠程主機的這個文件:

[root@localhost ~]# ssh 172.16.40.11 'cat /var/listen'
listen=80
listen=8080


template:模板複製文件

也是用來複制數據的,只不過文件中的數據能夠用變量替換,爲不一樣的主機附加不一樣的變量,會把文件中定義的變量在發送以前轉換爲給對應主機所定義的變量的值,也就能夠實現不一樣的主機所複製的文件中的數據是不一樣的。

而同組中主機定義不一樣的變量能夠經過定義主機變量來實現

主機變量:定義在inventory中的主機以後的變量

如:

/etc/ansible/hosts文件中的主機後面加上變量。

[wserver]
172.16.40.11 port=8800
172.16.40.12 port=8888

要複製的源文件中引用變量能夠這樣: Listen ` port `

但我這裏好像說當前版本中template不支持命令行使用

[root@localhost ~]# ansible wserver -m template -a 'src=/home/star/http.conf dest=/etc/httpd/conf'
172.16.40.11 | FAILED => in current versions of ansible, templates are only usable in playbooks
172.16.40.12 | FAILED => in current versions of ansible, templates are only usable in playbooks

一下子在playbooks的時候再來講明template模塊。 其它變量也在那裏說明。


yum: yum安裝軟件,也有apt,zypper。

conf_file         #設定遠程yum安裝時所依賴的配置文件。如配置文件沒有在默認的位置。
disable_gpg_check    #是否禁止GPG checking,只用於`present' or `latest'。
disablerepo   #臨時禁止使用yum庫。 只用於安裝或更新時。
enablerepo    #臨時使用的yum庫。只用於安裝或更新時。
name=            #所安裝的包的名稱
state               #present安裝, latest安裝最新的, absent 卸載軟件。
update_cache  #強制更新yum的緩存。


例:安裝httpd。

這裏只是說明一下conf_file的用法,yum的倉庫文件沒有在/etc/yum.repos.d/目錄下的話。

[root@localhost ~]# ansible wserver -m yum -a 'name=httpd state=present conf_file="/root/local.repo"'


若是庫原本是禁止使用的,就要用enablerepo來臨時使用這個庫。

這裏的yum庫文件已經在/etc/yum.repos.d/目錄下了,不須要conf_file指定配置文件了。

[root@localhost html]# ansible wserver -m yum -a 'name=httpd state=present enablerepo=local'

這裏的庫ID 就是local.


卸載:

[root@localhost html]# ansible wserver -m yum -a 'name=httpd state=absent'

注意:返回的數據的    "changed": true, 


安裝包組,只要在名稱前面加上@就能夠了。

如:安裝開發工具的包組:

[root@localhost html]# ansible dbserver -m yum -a 'name="@Development Tools" state=present'


service: 服務程序管理


arguments            #命令行提供額外的參數
enabled                 #設置開機啓動。
name=                  #服務名稱
runlevel                #開機啓動的級別,通常不用指定。
sleep                     #在重啓服務的過程當中,是否等待。如在服務關閉之後等待2秒再啓動。
state                      #started啓動服務, stopped中止服務, restarted重啓服務, reloaded重載配置。

啓動httpd服務:

[root@localhost html]# ansible all -m service -a 'name=httpd state=started'

設置開機啓動:

[root@localhost ~]# ansible all -m service -a 'name=httpd enabled=yes'

重啓服務:

[root@localhost ~]# ansible all -m service -a 'name=httpd sleep=2 state=restarted'


command: 直接執行命令,默認模塊,能夠不用指定。

顯示全部主機時間:

[root@localhost ~]# ansible all -a 'date'
172.16.40.20 | success | rc=0 >>
Thu Feb 11 16:04:37 CST 2016

172.16.40.12 | success | rc=0 >>
Thu Feb 11 16:04:37 CST 2016

172.16.40.11 | success | rc=0 >>
Thu Feb 11 16:04:37 CST 2016


這個模塊與shell差很少,可是不能執行管道類的操做,如:

wKioL1a8SOWQtOUxAABDd8hs1KY380.png

還有點不一樣是,command是在當前shell所執行的命令,而shell是在子shell中執行的命令。可是在被控端和管理端用pstree查看進程的時候,卻也沒發現不同的。這個說法如今是有點不明白。


shell: 直接執行命令,參數通常也用不到。

這個能夠執行管道類的命令,如:

wKiom1a8THvTuM8_AABlMTYCPyE033.png


script:發送腳本到各被管理節點,並執行。一樣不須要參數。

[root@localhost ~]# ansible all -m script -a 'test.sh'

直接在-a 後面指定腳本便可。


selinux: 管理selinux。

conf     #指定應用selinux的配置文件。
state=enforcing|permissive|disabled           #對應於selinux配置文件的SELINUX。
policy=targeted|minimum|mls        #對應於selinux配置文件的SELINUXTYPE

關閉selinux:

[root@localhost ~]# ansible all -m selinux -a 'state=disabled'

在selinux處於enforceing狀態下的時候好像只能用permissive。

在state非disabled的狀況下必需要指定policy。


setup:獲取指定主機的facts。

facts是由正在通訊的遠程目標主機發回的信息,這些信息被保存在ansible變量中。

[root@localhost ~]# ansible 172.16.40.11 -m setup

 返回不少對應主機的信息,在後面的操做中能夠根據不一樣的信息來作不一樣的操做。如redhat系列用yum安裝,而debian系列用apt來安裝軟件。



3、playbook。

playbook就是一個用yaml語法把多個模塊堆起來的一個文件而已。

yaml: http://www.yaml.org


3.1: 結構介紹

playbooks核心元素:
Tasks            定義任務
Variables      定義變量
Templates      定義模板
Handlers        Notify 處理
Roles


除了核心元素之外還有額外的元素,而每一個元素也包含了獨有的元素。

YAML參考了多種語言,其中就有python。因此在寫playbook的時候,段落縮進很重要。

看一下下面這個例子,最外圍就是主要的元素,而各個主元素裏面還有各個子元素。


每個-開始表示一個列表的開始,到下一個-以前結束,也能夠說這之間就是一個項目,一齣戲。

各個列表之間是沒有關係的,咱們只要區分開也就不混亂了。tasks裏面就是模塊的使用了,因此總體來講結構仍是很直觀的。

        - hosts: 172.16.100.68        #定義主機
          vars:                      #定義變量
               var1: value
               var2: value
          tasks:                    #定義任務
               - name:           #任務名稱。
                                        #這裏就能夠開始用模塊來執行具體的任務了。
               - name:

               - name:

          handlers:             #定義觸發通知所做的操做。裏面也是跟tasks同樣,用模塊定義任務。
               - name:

          remote_user:             #遠程主機執行任務時的用戶。通常都是root,通常也不用指定。
        - hosts: 172.16.100.69
          vars:
          tasks:
          handlers:
          remote_user:


-表示一個列表的開始,一個列表表示一個獨立的總體結構,而列表裏面的元素(表項)是由字典組成的,字典中存儲的就是各個要定義的鍵值。如:tasks是字典的鍵,裏面的各部分是值。只不過這部分同時又是列表。

vars是用來定義變量的,因此裏面的各變量都是字典而不是列表。只不過vars是字典的鍵,裏面的兩項是字典的值,而這個值一樣也是字典。

網上有的說每個-表示一個表項。不過意思差很少,只不過最外圍加了一個列表而已。不過這樣好亂啊。

這裏跟使用沒有關係,若是感受混亂就不用管了。瞭解一下python的話也就容易理解了。


結構差很少也就是這樣了,來補充點:
各字典項的鍵冒號與值之間要有空格。  如:hosts: abc

字典項要與-之間有空格。表示在結構內。並非說Hosts特殊要在-的後面。 它也能夠在下面的一行開始。如:

-
  hosts:
  tasks:


-表示列表的開始,後面的hosts跟下面的vars之類的都是同一級。不過要注意前面都要有兩個空格的縮進,表示在此結構內。就好像是第一級結構爲- ,  每二級結構與第一級結構之間要用空格隔開。


3.2:變量

變量名僅能由字母、數字和下劃線組成,且只能以字母開頭。

變量種類:
一、facts:由遠程主機發回的主機屬性信息,這些信息被保存在ansible變量中;無須定義,可直接調用;
二、自定義變量:
        2.一、經過命令行傳遞: ansible-playbook  指令後面指定變量:--extra-vars "var1= var2=" ,簡寫 -e 「vars="

        2.二、經過roles傳遞
        2.三、主機變量:定義在inventory中的主機以後的變量
        2.四、組變量:定義在inventory中的組上的變量。如:

[wserver]
172.16.40.11 port=8800
172.16.40.12 port=8888

[wserver:vars]
port=80

[dbserver]
172.16.40.20

[dbserver:vars]
port=3306


       2.五、在playbook的vars元素下面定義變量.

3.3 使用:

實現目標:

一、wserver組主機安裝httpd。

二、複製本機已配置好的httpd配置文件到各主機。

三、啓動httpd,並設置開機啓動。

[root@localhost ~]# vim httpd.yml

- hosts: wserver
  remote_user: root
  tasks:
        - name: install httpd
          yum: name=httpd state=present
        - name: copy httpd configuration
          copy: src=/root/httpd dest=/etc/
        - name: start httpd
          service: name=httpd state=started
        - name: boot httpd start
          service: name=httpd enabled=yes

wKioL1a8faqRwgUQAAA1abdNwDM345.png

執行過程。用ansible-playbook來執行playbook文件。文件擴展名隨意,我這裏習慣用yml了。

wKioL1a8famA_w5nAADCBtKPAGc725.png

***表示發生變化,綠色表示未變化,紅色表示錯誤。 ok=5  changed=4 表示完成了5個,其中4個發生變化。


查看httpd是否啓動:

[root@localhost ~]# ansible wserver -m shell -a 'ss -tnlp'            #直接查看信息,但多了之後。。。
[root@localhost ~]# ansible wserver -m shell -a 'ss -tnlp' | grep httpd | wc -l     #能夠直接用wc來計數。

是否開機啓動:

[root@localhost ~]# ansible wserver -m shell -a 'systemctl status httpd'
或者:
[root@localhost ~]# ansible wserver -m shell -a 'systemctl status httpd' | grep enabled | wc -l

條件判斷

若是要管理有主機中有不一樣系列的系統,這裏只是作個比喻。正常狀況下應該連繫統版本都是相同的。

好比有一臺ubuntu的主機,由於它的軟件管理用的是apt-get。在ansible裏面是用apt模塊來操做的。並且配置文件也不同,軟件的名稱也不同,服務腳本也不同。額,複雜了好像。

只要在一個任務的最後加上when就能夠了,意思是說只有當後面的條件知足的時候才執行此任務。

條件變量就是facts類的變量。能夠用ansible 主機 -m setup來查看,上面模塊部分也說了。能夠用ansible_os_family這個變量。

wKioL1a8j0yQcyfaAAASa_qPiYc681.png

wKiom1a8jvCyT6tPAAATtIJtQMI735.png


httpd.yml

- hosts: wserver
  remote_user: root
  tasks:
        - name: install httpd redhat
          yum: name=httpd state=present
          when: ansible_os_family == "RedHat"
        - name: copy httpd configuration
          copy: src=/root/httpd dest=/etc/
          when: ansible_os_family == "RedHat"

        - name: install apache2 debian
          apt: name=apache2 state=present
          when: ansible_os_family == "Debian"
        - name: copy apache2 configuration
          copy: src=/root/apache2 dest=/etc/
          when: ansible_os_family == "Debian"

        - name: start httpd
          service: name=httpd state=started
          when: ansible_os_family == "RedHat"
        - name: boot httpd start
          service: name=httpd enabled=yes
          when: ansible_os_family == "RedHat"


        - name: start apache2
          service: name=apache2 state=started
          when: ansible_os_family == "Debian"
        - name: boot apache2 start
          service: name=apache2 enabled=yes
          when: ansible_os_family == "Debian"

wKioL1a8j4Hgv1r7AACzJcxOmAY815.png

執行效果:

wKioL1a8kEnjQWKqAAEGXPj-U0A311.png

wKiom1a8j-6Ak4zMAAB9cvHEfMk653.png

這裏由於apache2的配置文件沒有修改,與安裝完成所生成的配置如出一轍,經過檢驗發現同樣就不會再複製了。因此是綠色的字。

有沒有發現這樣麻煩的不是一星半點啊。


再貼一個刪除這些軟件的:

- hosts: wserver
  remote_user: root
  tasks:
        - name: stop httpd
          service: name=httpd state=stopped
          when: ansible_os_family == "RedHat"
        - name: erase httpd
          yum: name=httpd state=absent
          when: ansible_os_family == "RedHat"
        - name: erase /etc/httpd
          file: path=/etc/httpd state=absent
          when: ansible_os_family == "RedHat"

        - name: stop apache2
          service: name=apache2 state=stopped
          when: ansible_os_family == "Debian"
        - name: erase apache2
          apt: name=apache2 state=absent purge=yes
          when: ansible_os_family == "Debian"
        - name: erase /etc/apache2
          file: path=/etc/apache2 state=absent
          when: ansible_os_family == "Debian"


標籤:

有時候只想用這個文件中的複製配置文件的功能,而不想再每一項都檢查,雖然也沒什麼問題。

- hosts: wserver
  remote_user: root
  tasks:
        - name: install httpd redhat
          yum: name=httpd state=present

        - name: copy httpd configuration
          copy: src=/root/httpd dest=/etc/
          tags: config                                                #加了一個tags.

        - name: start httpd
          service: name=httpd state=started

        - name: boot httpd start
          service: name=httpd enabled=yes

wKiom1a8k9fxY0_4AACPy9YK-8s601.png

我這裏的httpd給從新安裝了,因此配置文件是不一樣的,纔會顯示changed。否則會是綠色的ok。

如今只執行了config標符所指定的任務了。 我這裏忘了把hosts文件中的172.16.40.1去掉了。

那麼複製完配置文件之後應該重載配置文件纔對。但是就算再添加一個任務,由於咱們指定了標籤也不會執行。那麼就能夠用handlers啦。


handlers:

也是task任務,但只有其關注的條件知足時,纔會被觸發執行。這裏的條件其實就是發生修改。

若是咱們複製配置文件和遠程主機上的同樣,那就不會觸發了。

- hosts: wserver
  remote_user: root
  tasks:
        - name: install httpd redhat
          yum: name=httpd state=present

        - name: copy httpd configuration
          copy: src=/root/httpd dest=/etc/
          notify: reload httpd                            #添加了一行這個。用以觸發名稱爲reload httpd的handlers。
          tags: config

        - name: start httpd
          service: name=httpd state=started

        - name: boot httpd start
          service: name=httpd enabled=yes
  handlers:
        - name: reload httpd
          service: name=httpd state=reloaded

如今配置文件沒有修改以前:

wKioL1a8l2rxtZffAABmdXa4rmo705.png

修改以後:

wKioL1a8l42T9gdXAACNBDeWXYE133.png


templates:
用於生成文本文件(配置文件);模板文件中可以使用jinja2表達式,表達式要定義在` `,也能夠簡單地僅執行變量替換;咱們這裏也只來演示一下變量替換的。

如我想給不一樣的主機的配置文件所監聽的端口不同。

能夠經過主機變量,定義/etc/ansible/hosts文件:

[wserver]
172.16.40.11 port=8800
172.16.40.12 port=8888

修改要複製過去的配置文件,

httpd.conf

Listen {{ port }}        #httpd的配置文件,listen用來監聽端口。在複製以前ansible會把{{ port }}替換爲對應主機所設置的變量值。

如今的playbook文件:爲了節省篇幅,我這裏把如今用不到都刪了。而由於是修改端口,因此把reload改爲了restart。

- hosts: wserver
  remote_user: root
  tasks:
        - name: template httpd configuration
          template: src=/root/httpd/conf/httpd.conf dest=/etc/httpd/conf/         #src好像不能再指目錄了。
          notify: restart httpd

  handlers:
        - name: restart httpd
          service: name=httpd state=restarted

wKiom1a8nGvCvm4pAACPRS3QHYM246.png

一臺主機監聽在8800,一臺主機監聽在8888。


迭代:

若是想要批量建立多個用戶怎麼辦,固然用script模塊最簡單了,不過這裏也只是來講明一下問題而已:

在task中調用內置的item變量;在某個task後面使用with_items語句來定義元素列表;

- hosts: wserver
  remote_user: root
  tasks:
        - name: create test user
          user: name={{ item }} state=present
          with_items:
                - test1
                - test2
                - test3
                - test4

wKiom1a8n7yRWI8iAAAgqFLHFSk335.png

wKioL1a8oBfhthJ1AAC9CUt8YzA592.png


而上面所指定item還能夠有子集, 能夠用字典來表示item中的各個鍵值,而不僅是用表示單個值。

如:

- hosts: wserver
  remote_user: root
  tasks:
        - name: create test user
          user: name={{ item.user }} group={{ item.group }} state=present
          with_items:
                - { user: "test10", group: "root" }
                - { user: "test11", group: "root" }
                - { user: "test12", group: "root" }

wKioL1a8obmBXEyGAABCGSydaTk976.png

wKiom1a8oVyhsw6eAADBfCgaLKk626.png


一直沒有介紹vars自定義變量,這裏咱們來看一下。

wKioL1a8owSDvH0TAABVoQkYmLI981.png

wKioL1a8owbhT9JnAADBXjvIw_w359.png

這樣想建立什麼用戶,就能夠直接修改vars裏面的變量就能夠。


4、roles。

roles只是把任務給分離出去了。只要在playbook文件中調用此role就可執行這些任務。

如咱們定義了一個很複雜的任務,可是要用在另外的主機組或只想用於單臺主機的時候就要修改這個文件,總修改也不是辦法。 能夠複製多份,但有時候也不夠靈活。

因此就能夠用role把任務主體分離出來,只在playbook中寫一些額外的東西,如變量,主機等等。


roles用於實現「代碼複用」。

roles以特定的層次型格式組織起來playbook中的各主元素(vars, tasks, handlers)。每個主元素都以一個目錄來表示。


各目錄以下:

files:此角色中用到的全部文件均放置於此目錄中; 對應於copy模塊。
templates:Jinja2模板文件存放位置;  對應於template模塊。
tasks:任務列表文件;裏面能夠有多個文件,但至少有一個叫作main的文件;
handlers:處理器列表文件;裏面能夠有多個文件,但至少有一個叫作main的文件;
vars:變量字典文件;裏面能夠有多個文件,但至少有一個叫作main的文件;
meta:此角色的特殊設定及依賴關係;


在/etc/ansible/roles/目錄下面的目錄就是各個單獨的rule。調用的時候直接調用目錄名稱。

[root@localhost createweb]# pwd
/etc/ansible/roles/createweb
[root@localhost createweb]# ls
files  handlers  meta  tasks  templates  vars
[root@localhost createweb]# tree -L 2
.
├── files                    #存放copy用到的文件。
│   ├── config
│   ├── httpd
│   ├── index.php
│   ├── iptables.bak.conf
│   └── rc.local
├── handlers             #定義handlers。
│   └── main
├── meta
├── tasks                    #定義任務。
│   └── main
├── templates           #存放template模塊用到的文件。
│   └── httpd.conf
└── vars                     #定義變量。
    └── main


如我這裏的tasks/main文件:

效果就是:安裝httpd,建立所須要的網頁目錄,建立日誌目錄,複製全部配置文件,複製php測試頁面。並啓動httpd。

- name: install httpd
  yum: name=httpd state=present
- name: install php
  yum: name=php state=present
- name: install mod_ssl
  yum: name=mod_ssl state=present

#create http_page file
- name: create directory
  file: state=directory path={{ http_page_path_www }}
  file: state=directory path={{ http_page_path_myadm }}

#create log_file directory
- name: create log directory
  file: state=directory path={{ http_log_path_www }}
  file: state=directory path={{ http_log_path_myadm }}

- name: copy all web config
  copy: src=httpd dest=/etc/
  notify: restart httpd

- name: copy php_test file
  copy: src=index.php dest=/web/vhosts/www/
  copy: src=index.php dest=/web/vhosts/myadm/

- name: start httpd and enabled
  service: name=httpd state=started enabled=yes

handlers/main

- name: restart httpd
  service: name=httpd state=restarted

vars/main  

http_port: 8000

http_log_path_www: /var/log/httpd/www
http_log_path_myadm: /var/log/httpd/myadm

http_page_path_www: /web/vhosts/www
http_page_path_myadm: /web/vhosts/myadm


定義playbook:

- hosts: wserver
  roles:
       - createweb


我這個的執行結果在遠程主機上有點問題。不過大致上也就是這種結構,在playbook的roles裏面還能夠定義很參數,這裏就先不介紹了,之後有時間再來改改。


謝謝瀏覽,若有錯誤還請指出。j_0022.gif

相關文章
相關標籤/搜索