saltstack系統中管理對象叫作Target,在master上能夠採用不一樣的Tatget去管理不一樣的minion。這些Target都是經過去管理和匹配Minion的ID來作一些集合。php
# salt -E '[a-z].*' test.ping #直接就是匹配字母開頭的minionnode
# salt -E 'a.*' test.ping #匹配a開頭的minionmysql
# salt -E '(a|z).*' test.ping #匹配a或者z開頭的minion,切記是開頭而不是包含。web
#salt -L 'dasha_ceshi_172.16.5.239,dasha_ceshi_172.16.5.240' test.ping ##同時讓多個minion去執行,多minion之間用逗號隔開(這裏只是ID,組的不行)。正則表達式
minions的Grains信息時在Minions服務啓動的時候彙總給Master的,Grains是saltstack組建中很是重要的,由於在配置部署的過程當中會常用它,Grains是saltstack記錄minion的一些靜態信息的組件,grains裏面記錄着每臺minion的一些經常使用屬性如CPU、內存、操做系統類型和版本等,能夠經過grains.item查看某臺minion的全部grains信息。sql
# salt -G 'os:CentOS' test.ping #讓minion端操做系統是CentOS去執行,固然也支持正則表達式的方式shell
# salt -G 'os:C*' test.ping #如匹配操做系統是C開頭的apache
# salt -G 'osmajorrelease:[1-9]' test.ping #匹配系統版本是數字的。centos
cat /etc/salt/master | grep nodegroups
這裏還可使用正則及其餘匹配方式,我這裏寫的是最簡單,也是最繁瑣的一種。安全
nodegroups: ceshi1: dasha_ceshi_172.16.5.239 ceshi2: dasha_ceshi_172.16.5.240
#salt -N ceshi1 test.ping #測試test這組。
解釋:複合匹配的意思是,使用不一樣的判斷條件精準的在指定的minion中執行。
#salt -C 'G@os:CentOS and G@osmajorrelease:7' test.ping #讓os是CentOS而且系統版本是7的去執行 #salt -C 'G@os:CentOS and G@osmajorrelease:7 and E@dasha_ceshi*' test.ping # 在操做系統是CentOS版本是7,而且id開頭是dasha_ceshi的機器是執行test.ping操做。
[root@bogon ~]# salt -S '172.16.5.0/24' test.ping #匹配IP是172.16.5.0網段的的全部IP地址,執行test.ping操做 dasha_ceshi_172.16.5.240: True dasha_ceshi_172.16.5.239: True [root@bogon ~]# salt -S '172.16.5.239' test.ping #在IP是172.16.5.239服務器上執行test.ping操做。 dasha_ceshi_172.16.5.239: True
Grains上面已經介紹過了,相似於facter。簡單的說就是把minion端在啓動的時候把自身的的各類屬性信息採集彙報給master端,可使用 salt ‘id’ grains.items查看。
# salt '*' grains.ls #能夠查看有哪些屬性能夠查看,顯示的是屬性的名字,相似於os之類的。
#salt 'dasha_ceshi_172.16.5.239' grains.item os osrelease oscodename ##知道了屬性的名稱,咱們就能夠查看屬性的值,這裏就是查看os,osrelease,oscodename這三個屬性的值,多屬性用空格隔開。
# salt '*' grains.items #這種就是將全部minion端屬性以及屬性的值全打印出來,建議打印是指定某個minion id,不然打印的東西太多。
上面咱們說了,在master上執行grains.items能查看到不少minion的參數,可是好比設備的具體位置,業務名稱等信息就顯的力不從心了,可是有了minion自定義grains後,就沒有那麼難了。
minion端的操做:
grains: #以grains開頭 roles: #設置一個屬性叫roles,下面若是多條就像下面同樣- value值,這裏的意思是標註服務器屬於什麼業務 - webserver - memcache deployment: bj-zb-5F #這裏是標註所在機房的位置 cabinet: B11 #標註所在機櫃的位置 cab_u: 19-21 #標註所在機櫃的U位
# systemctl restart salt-minion #上面已經說了,grains信息是在minion端啓動的時候纔會發送,因此要重啓minion端。
master端的查看:
# salt 'dasha_ceshi_172.16.5.240' grains.ls #用這個查看會發現咱們自定義的哪幾個grains的屬性已經出現了。
#salt '*' grains.item roles deployment cabinet cab_u #查看咱們在minion自定義的grains信息。
#salt 'dasha_ceshi_172.16.5.239' grains.append purpose 'ceshi' #經過grains.append方法爲dasha_ceshi_172.16.5.239機器添加了一個屬性,purpose 用途,後面跟的值是ceshi,注意空格和引號。
這種自定義的方法配置文件位置再minion的/etc/salt/grains配置文件中,永久生效,刪除的話,能夠直接去minion操做。還可使用其餘的方法,如grains.setvals來定義多個屬性,或者還能夠刪除自定義的grains。這都是立馬生效並永久生效的。
Pillar是saltstack組件中很是重要的一個,是數據管理中心,常常配合states在大規模的配置管理工做中使用它,它的主要做用是存儲和定義配置管理中須要的一些數據。它的定義存儲格式跟grains相似,都是YAML格式。
下面的操做都是在master端的操做:
# mkdir /srv/pillar #這是master配置文件裏面#pillar_roots:默認指定的路徑。默認不存在須要手工建立。 # cat /srv/pillar/top.sls #top.sls是配置管理的入口文件,一切都是從這裏開始,這裏是默認位置,在這裏定義誰來執行那個方法或者說模塊。 base: #top.sls 默認從 base 標籤開始解析執行,下一級是操做的目標,能夠經過正則,grain模塊,或分組名,來進行匹配,再下一級是要執行的state文件,不包換擴展名。 '*': - pkgs # cat /srv/pillar/pkgs.sls #一個簡單的根據minion端的grains信息,動態的設置apache軟件包對應的name名稱。前面咱們學習saltstack的minion,咱們知道給客戶端定義新的屬性時候,是須要在客戶端文件加內容的,可是pillar則是在服務器給客戶端定義新屬性,並且不用重啓服務, pkgs: {% if grains['os_family'] == 'RedHat' %} apache: httpd {% elif grains['os_family'] == 'Debian' %} apache: apache2 {% elif grains['os'] == 'Arch' %} apache: apache {% endif %} # salt '*' pillar.item pkgs
有結果來看,pillar數據是在Salt master上生成的並被安全地分佈到minions上。Salt當定義pillar的時候,沒必要限制在sls文件,也能夠從外部資源得到數據,咱們能夠把Pillar數據。pillar中最強大的抽象之一就是將states參數化的能力。
States是SaltStack中的配置語言,在平常進行配置管理時須要編寫大量的States文件。如安裝軟件啊,更改配置啊等,就須要編寫states sls文件(描述狀態配置的文件)去描述和實現這些功能。編寫states sls文件通常是是YAML語法格式,也支持使用Python語言來編寫。
#salt 'dasha_ceshi_172.16.5.239' sys.list_state_modules ##查看minion支持的全部states列表。
1 - acl 2 - alias 3 - alternatives 4 - archive 5 - artifactory 6 - beacon 7 - bigip 8 - blockdev 9 - buildout 10 - ceph 11 - chronos_job 12 - cloud 13 - cmd 14 - composer 15 - cron 16 - cryptdev 17 - csf 18 - disk 19 - elasticsearch 20 - elasticsearch_index 21 - elasticsearch_index_template 22 - environ 23 - esxdatacenter 24 - etcd 25 - ethtool 26 - event 27 - file 28 - firewall 29 - firewalld 30 - gem 31 - glassfish 32 - gnomedesktop 33 - gpg 34 - grafana4_dashboard 35 - grafana4_datasource 36 - grafana4_org 37 - grafana4_user 38 - grains 39 - group 40 - highstate_doc 41 - hipchat 42 - host 43 - http 44 - incron 45 - infoblox_a 46 - infoblox_cname 47 - infoblox_host_record 48 - infoblox_range 49 - ini 50 - ipset 51 - iptables 52 - jboss7 53 - jenkins 54 - junos 55 - k8s 56 - kernelpkg 57 - keyboard 58 - kmod 59 - ldap 60 - libcloud_dns 61 - libcloud_loadbalancer 62 - libcloud_storage 63 - locale 64 - logrotate 65 - loop 66 - lxc 67 - marathon_app 68 - modjk 69 - modjk_worker 70 - module 71 - mount 72 - msteams 73 - network 74 - nexus 75 - openstack_config 76 - opsgenie 77 - pagerduty 78 - pagerduty_escalation_policy 79 - pagerduty_schedule 80 - pagerduty_service 81 - pagerduty_user 82 - pkg 83 - pkgbuild 84 - pkgng 85 - pkgrepo 86 - powerpath 87 - process 88 - pushover 89 - pyenv 90 - rbenv 91 - rvm 92 - salt 93 - salt_proxy 94 - schedule 95 - serverdensity_device 96 - service 97 - slack 98 - smtp 99 - solrcloud 100 - sqlite3 101 - ssh_auth 102 - ssh_known_hosts 103 - stateconf 104 - status 105 - statuspage 106 - supervisord 107 - sysctl 108 - syslog_ng 109 - telemetry_alert 110 - test 111 - timezone 112 - tuned 113 - uptime 114 - user 115 - vault 116 - vbox_guest 117 - virtualenv 118 - winrepo 119 - zenoss
#salt 'dasha_ceshi_172.16.5.239' sys.list_state_functions file host ##查看file和host的全部function,多模塊用空格隔開
1 dasha_ceshi_172.16.5.239: 2 - file.absent 3 - file.accumulated 4 - file.append 5 - file.blockreplace 6 - file.cached 7 - file.comment 8 - file.copy 9 - file.decode 10 - file.directory 11 - file.exists 12 - file.line 13 - file.managed 14 - file.missing 15 - file.mknod 16 - file.mod_run_check_cmd 17 - file.not_cached 18 - file.patch 19 - file.prepend 20 - file.recurse 21 - file.rename 22 - file.replace 23 - file.retention_schedule 24 - file.sdecode 25 - file.serialize 26 - file.shortcut 27 - file.symlink 28 - file.touch 29 - file.uncomment 30 - host.absent 31 - host.only 32 - host.present
# salt 'agent1.salt' sys.list_state_modules #查看minion支持的全部states列表。
# salt 'agent1.salt' sys.list_state_functions file host #查看file和host的全部function,多模塊用空格隔開
# salt 'agent1.salt' sys.state_doc file #查看指定模塊的function的用法與例子,平常編寫states按照例子編寫即可。
# salt 'agent1.salt' sys.state_doc file.managed #查看file.managed的詳細用法與例子,這也是咱們常常用到的function。
如今咱們有個需求,往minion的特定目錄下傳一個配置文件,前面咱們說過使用cp.get_file方法就能夠傳文件,可是咱們常常要給某些minion傳特定的配置文件的話,使用state的文件傳送就很方便。
首先咱們先來看一下master裏面state路徑定義的方法,咱們一共定義了三個路徑,base是必需要有的,剩下的隨意,注意空格。注意:salt://這幾個字符分別表明了裏面的三個路徑,好比salt://file/test,絕對路徑就是/srv/salt/base/file/test,/srv/salt/prod/file/test,/srv/salt/test/file/test。
分別建立配置文件裏面的三個路徑,最後完成後必定要重啓master服務。
如今咱們來看看寫法,首先你要定義個須要傳送到客戶端的文件,能夠新建,隨便寫點內容便可,首先咱們分析一下基本環境,只須要看你標紅位置便可。
我在base裏面又新建了一個目錄files,我把my.cnf配置文件放在了這裏面,而後我在base下面新建了衣蛾cp_file.sls文件,在這個文件中寫了點傳送文件的內容。
基本寫法介紹:
cp-file-my.cnf: #惟一表示ID file.managed: #方法,我用哪一個方法,這裏用file.managed方法傳送文件 - name: /root/my.cnf #目標機器上的哪一個文件,必定要加文件名。 - source: salt://files/my.cnf #master端的路徑,上線咱們說過,這裏的絕對路徑是/srv/salt/base/files/my.cnf - user: root #文件屬主 - group: root #文件屬組 - mode: 644 #文件權限 注意:salt全部配置文件裏面禁止用tab鍵,層級關係用兩個空格隔開,-符號後面還有個空格,例如- name: 冒號後面也得有空格。
寫好具體要作什麼之後,這裏要發送了
#state.sls是用state.sls這個方法,cp_file是隻cp_file.sls這個文件,這裏去掉文件.後面的內容便可,test=True指先測試一下,若是肯定要發送的話,去掉test=True便可。 salt '*' state.sls cp_file test=True
這裏可能有同窗要說了,好麻煩啊,我直接scp過去就ok了,你這裏還得寫這麼東東西,彆着急,若是有1000臺機器,你也一個一個scp麼,而這裏我只須要匹配哪些服務器須要便可。
#若是你源文件沒有發生改變,再次執行的話,Comment會提示你這個文件是正確的。Changes:下面沒內容。Succeeded: 1,這就是區別,也就是不更新
SLS(表明SaLt State文件)是Salt State系統的核心。SLS描述了系統的目標狀態,由格式簡單的數據構成。這常常被稱做配置管理,簡單的講就說你寫了那麼多的路徑和sls文件,到底要讓誰來執行top裏面能夠寫誰來執行哪些sls文件。
由於咱們用YAML格式來編寫sls文件,因此掌握編寫技巧利於後面少出錯。
5.1.1 什麼是YAML?
YAML 語言(發音 /ˈjæməl/ )的設計目標,就是方便人類讀寫。它實質上是一種通用的數據串行化格式。語法很簡單,結構經過空格來展現,項目使用「-」來表明,鍵值對使用「:」分隔。
它的基本語法規則以下:
大小寫敏感,以「:」來分隔key和value。對象:鍵值對的集合,又稱爲映射(mapping)/ 哈希(hashes) / 字典(dictionary)。
使用固定的縮進風格表示層級關係。縮進時不容許使用Tab鍵,只容許使用空格,通常每一個縮進級別由兩個空格組成。
# 表示註釋,從這個字符一直到行尾,都會被解析器忽略。
想要表示列表項,使用一個短橫槓加一個空格。多個項目使用一樣的縮進級別做爲同一列表的一部分。列表能夠做爲一個鍵值對的value。
top.sls是配置管理的入口文件,這個很重要在生產中很重要,默認存放在/srv/salt/目錄.默認從base標籤開始解析執行,下一級是操做的目標也就是要對哪些主機進行操做,能夠經過正則、grain模塊或分組名等來進行匹配,而後再下一級是要執行的state文件(不包含.sls擴展名)。
基本寫法1:
首先top文件必須寫在base環境下,必需要叫top.sls,而後咱們看一下基本寫法:
base: #下面的sls在哪一個路徑這裏就寫什麼 'dasha_ceshi_172.16.5.239' #哪一個minion去執行 - cp_file #執行哪一個方法
基本寫法2:
base: 'dasha_ceshi_172.16.5.239' - cp_file 'dasha_ceshi_172.16.5.240' - cp_file
正則寫法1:
base: #下面的sls在哪一個路徑這裏就寫什麼 'dasha_ceshi*' #哪一個minion去執行,不會正則的同窗能夠去看看 - cp_file #執行哪一個方法
# cat /srv/salt/base/top.sls
base:
centosgroups: #這裏就是咱們上面在master配置文件裏面定義的那個組名
- match: nodegroup #這句話是必需要有的,指定以組匹配
- cp_file
# cat /srv/salt/base/top.sls #同上-match: grain也是必需要帶的,指定讓其按照grain進行匹配,指定讓os是Centos的操做系統來執行。
base:
'os:CentOS':
- match: grain
- cp_file
# cat /srv/salt/base/top.sls #上面的grain模塊匹配可能知足不了咱們的匹配條件,我想要更加精確的讓全部Centos6.4的操做系統去執行,就是我下面的設置。
base:
'G@os:CentOS and G@osrelease:6.4':
- match: compound
- cp_file
# cat /srv/salt/base/top.sls
base:
'192.168.1.0/24':
- match: ipcidr
- cp_file
# salt '*' state.highstate #master將會指導全部的目標minions運行 state.highstate。當minion執行highstate,它將會下載top文件中匹配的內容,minion將表達式中匹配的內容下載、編譯、執行。一旦完成,minion將返回全部的動做執行結果和全部更改。基本意思就是誰來執行什麼操做,去看top文件裏面是怎麼寫的,就怎麼執行。
# salt '*' state.highstate test=True #只是測試執行,相似於模擬,不會在minion真正執行,便於咱們編寫測試時使用,建議每次執行都測試一下。
5.5 state的層級關係
include:將別的SLS添加到當前文件中,因此能夠require或watch被引用的SLS中定義的內容,還能夠extend覆蓋其內容。include語句使得state能夠跨文件引用。使用include至關於把被引用的內容文件添加到自身。
extend:擴展被引用的SLS數據。不須要重頭寫新的SLS,能夠先直接include sls文件,而後在其基礎上增長或者覆蓋內容。
首先說應用場景,如今我在prod下面新建了三個目錄web,php,mysql,裏面分別寫了init.sls(初始化環境配置),按照上面的寫法,我須要一鍵執行的話,首先須要在top裏面把它們加進去,以下圖
top.sls
這樣的話,若是我要安裝的環境特別的多,這裏都直接下載top裏面就比較亂了,因此爲了醒目,我在prod下直接新建一個lamp.sls文件,而後把這些操做文件都寫進去,而後就方便了,而後只須要在top文件裏面寫上lamp就oK了,是否是很方便。
這裏只會一種用法,生產中還有不少種用法。
環境需求,若是已經寫好了lamp的安裝配置環境了,而後忽然發現還有安裝一個軟件,這個時候直接去改文件就顯的有點粗暴了,這裏能夠直接在include的裏面寫,例如,這裏我須要給lamp環境下安裝一個tree的包。
其它的什麼都不須要動,只須要在lamp下添加extend便可。
這裏注意,既然是擴展,那就得知道給誰擴展,include的中咱們已經標註了要執行的操做是web,php,mysql下的init操做。可是擴展的還怎麼寫呢?extend:是標準寫法,層級關係是兩個空格,那這個id怎麼寫呢?有人說隨便寫,你寫個試試,確定不行。既然是擴展你得指定給誰擴展。我在php裏面的init文件中寫過php-install這個id,這裏我指定是給它擴展,因此必須得把它的id寫在這裏,而後再寫是什麼方法,要幹什麼。這裏須要注意的就是這個id寫法,其實也不難理解,既然是擴展,確定是要寫給誰擴展的,不然不是亂套了。
match : 配模某個模塊,好比 match: grain match: nodegroup
require: 依賴某個state,在運行此state前,先運行依賴的state,依賴能夠有多個,被誰依賴是require_in
watch : 在某個state變化時運行此模塊,watch除具有require功能外,還增了關注狀態的功能,被誰依賴是watch_in。
order : 優先級比require和watch低,有order指定的state比沒有order指定的優先級高,假如一個state模塊內安裝多個服務,或者其餘依賴關係,可使用
require和require_in示例:
應用場景,首先咱們是肯定哪些操做都作了之後才能執行此操做,好比全部的安裝操做都完成,最後要重啓一些服務,就可使用此參數
以下,若是file這個模塊下的id是apache-config這個操做成功的話,就執行id是apache-service操做,若是有enable就是重啓,若是有reload的參數就是重載配置。
require:
require_in:
寫法以下,能夠理解爲被誰依賴,以下,若是我這個文件操做成功的話就執行service這個模塊的id是apache-service的操做。
watch和watch_in示例:
這個就NB了,它具有require的特性。應用場景,若是咱們服務都安裝完了,這個時候我須要給全部的minion修改一下配置文件,修改完成後從新加載配置文件,用watch就能夠解決,用法和require如出一轍。
若是file這個模塊下的id是apache-config這個操做成功(首先是從source這個路徑傳送到minino端的name路徑下後,從新加載httpd這個服務)。watch_in用法恰好相反,相似於require_in0。
6.一、介紹
Jinja2 是一個現代的,設計者友好的,仿照 Django 模板的 Python 模板語言。 它速度快,被普遍使用,而且提供了可選的沙箱模板執行環境保證安全:
參考地址:http://docs.jinkan.org/docs/jinja2/
Jinja的使用分爲三個步驟:
File狀態使用template參數 - template: jinja。
模板文件裏面變量使用{{名稱}},好比{{PORT}}.
File狀態模塊裏面指定變量列表。
6.二、jinji的基本使用
環境介紹,爲了區分,我在master配置文件中新加一個/srv/salt/jiaja2的模塊。
基本寫法
{% set iplist= grains['ipv4'] %} #申明變量名稱 /files/minion.conf: #定義傳輸文件id file.managed: #執行方法 - name: /root/minion.conf #目的路徑 - source: salt://files/minion.conf.jinja #文件存放位置 - template: jinja #申請只用jinja模板 - defaults: #定義默認將值傳遞給模板 IP_ADDR: {{iplist[1]}} #獲取iplist這個變量的值,由於返回的是一個列表,因此咱們須要取第2個值。
cat files/minion.conf.jinja 這裏爲了明顯,我只寫了一個值,
ipaddr:{{IP_ADDR}}
minion效果
總結,這就很厲害了,好比我定義安裝minion客戶端的某個服務要根據寫入本身的ip地址或者固定端口,就能夠在這裏定義多個變量defaults下面新加就行。它不但能夠寫變量還支持條件判斷和循環。
6.三、邏輯判斷
Jinja還主要用來給狀態增長邏輯關係,如for循環,或者if判斷,也是常用到的。
salt,grains,pillar是salt中jinja裏面的三個特殊字典,salt是包含全部salt函數對象的字典,grains是包含minion上grains的字典,pillar是包含minion上pillar的字典。上面已經介紹瞭如何使用了。
if...elif...endif的示例:
# cat /srv/pillar/pkgs.sls
apache: pkg.installed: #這是根據系統的不一樣,判斷安裝的軟件名稱。若是有變量就放到{{}}中 {% if grains['os_family'] == 'RedHat' %} #jinja中判斷,循環等標籤是放在{% %}中 - name: httpd {% elif grains['os_family'] == 'Debian' %} - name: apache2 {% elif grains['os'] == 'Arch' %} - name: apache {% endif %} #也會有結束標籤{% end** %}
#固然還支持:{% if %}...{% elif %}...{% else %}...{% endif %}之類的寫法。
for循環的示例:
{% set userlist = ['yunwei','cacti','www'] %} {% for user in userlist %} {{ user }}: user.present: - shell: /bin/bash - home: /home/{{ user }} {% endfor %}
參考地址:http://www.51niux.com/?id=117