目錄
1、引語
2、puppet模塊目錄結構
3、各資源清單的編寫
4、配置文件及模板文件準備
5、測試
6、總結
1、引語
在上一次博文(http://zhaochj.blog.51cto.com/368705/1661642)中已完成puppet的master/agent環境的部署,agent端也能夠接收master端推送或每30分鐘後向master請求catalog,我們還編寫了一個簡單的tengine模塊進行測試,但在生產環境中編寫的模塊並不是你的生產環境中的一個服務或應用,而是puppet agent本身,仔細想一下就能想明白,假如你想調整一下agent端自動到master請求catalog的時間,你想配置agent支持kick功能,想調整一下puppet的配置文件等,那master端就要對puppet本身做管理,所以你就得編寫一個模塊來做這些工作。
2、puppet模塊目錄結構
現在開始規劃puppet模塊的組織結構,目錄樹如下:
[root@nod1 modules]# pwd /etc/puppet/modules [root@nod1 modules]# tree puppet/ puppet/ #模塊名 ├── files #存放一些模塊中所需要的配置文件等 │ └── namespaceauth.conf #agent支持kick的相關文件 ├── manifests #資源清單目錄 │ ├── config.pp #涉及到配置文件的資源清單 │ ├── init.pp #資源清單的開始位置 │ ├── install.pp #關於puppet,facter軟件的管理文件 │ ├── params.pp #一些變量所在的文件 │ └── service.pp #關於puppet服務的文件 └── templates #模板目錄 ├── auth.conf.erb #認證用的模板 └── puppet.conf.erb #puppet的配置文件模板
上邊的這些目錄結構請自行創建。
puppet這個模塊大概是這樣的,install.pp清單定義puppet、facter軟件包的目標狀態,得先有這兩個軟件包,那才能談接下來的配置文件這些,這個清單的定義的主要是實現對軟件的升級管理用;config.pp主要是對puppet的各個配置文件的管理,而service是管理puppet服務狀態的,params.pp定義了一些變量和判斷語句,便於在其他清單中進行引用。接下來對這些清單文件一一剖析。
3、各資源清單的編寫
[root@nod1 puppet]# pwd /etc/puppet [root@nod1 puppet]# vim manifests/site.pp node "nod1.test.com" { #定義一個節點清單 include puppet #包含puppet模塊 }
如果所有節點都是使用相同的模板,那可以寫成下邊的樣子:
node default { include puppet }
這個site.pp是所有模塊調用的入口,你想運用哪些模塊,只要在此文件中包含進來即可。
[root@nod1 modules]# vim puppet/manifests/init.pp class puppet { include puppet::install,puppet::config,puppet::service }
解釋:init.pp是資源清單的入口,所有的資源引用都是從這裏進入,這個文件中只定義了一個class,名爲puppet,這個名稱必須與模塊名稱相同,即“/etc/puppet/modules/puppet”的基名相同。其他pp文件中定義的類都是以puppet類爲父類定義的相應子類,include語句中引用了三個類,puppet::install這個類表示install.pp文件中定義的類,puppet::config這個類表示config.pp文件中定義的類,puppet::service表示在service.pp文件中定義的類。
[root@nod1 modules]# vim puppet/manifests/install.pp class puppet::install { include puppet::puppet_install,puppet::facter_install #包含了兩個類,分別定義puppet與facter,在下邊有定義, } class puppet::puppet_install { package {'puppet': ensure => $operatingsystemmajrelease ? { #這裏做條件判斷 6 => '3.3.1-1.el6', } } } class puppet::facter_install { package {'facter': ensure => $operatingsystemmajrelease ? { #這裏也是做條件判斷 6 => '1.7.3-1.el6', } } }
解釋:這個資源清單定義了puppet與facter兩個軟件包的狀態,可以根據agent系統的版本來定義安裝的軟件版本。
[root@nod1 modules]# vim puppet/manifests/config.pp class puppet::config { include puppet::params #因config.pp會調用變量,所以先要引用params.pp文件 file {'/etc/puppet/puppet.conf': #定義puppet.conf文件的屬性 ensure => file, content => template('puppet/puppet.conf.erb'), owner => 'root', group => 'root', mode => '0644', require => Class['puppet::install'], #定義依賴關係,表示puppet.conf這個資源是在puppet安裝之後 notify => Class['puppet::service'], #表示puppet.conf文件被修改後要通知service重新加載服務 } file {'/etc/puppet/auth.conf': #定義認證文件的屬性 ensure => file, content => template('puppet/auth.conf.erb'), #引用模板生成配置文件 owner => 'root', group => 'root', mode => '0644', require => Class['puppet::install'], #表示puppet軟件安裝之後才配置auth.conf文件 notify => Class['puppet::service'], #auth.conf文件被修改後通知service重新加載服務 } file {'/etc/puppet/namespaceauth.conf': #定義命名空間認證文件 ensure => file, source => 'puppet:///modules/puppet/namespaceauth.conf', #定義namespaceauth.conf文件的下載路徑,注意puppet 下的files文件不需要寫明 owner => 'root', group => 'root', mode => '0644', require => Class['puppet::install'], notify => Class['puppet::service'], } }
解釋:config.pp資源清單主要配置一些配置文件的屬性,配置文件一般會有依賴關係。
[root@nod1 modules]# vim puppet/manifests/service.pp class puppet::service { service {'puppet': ensure => running, #表示puppet是運行狀態 enable => true, #表示puppet開機啓用 hasrestart => true, #表示以標準的方式重啓服務,即調用“/etc/rc.d/init.d/”下的腳本 hasstatus => true, #表示經標準方式探測服務的運行狀態 path => '/etc/rc.d/init.d/', #指定服務腳本的路徑 restart => '/etc/rc.d/init.d/puppet reload', #修改restart操作爲reload require => Class['puppet::install'], #puppet軟件先安裝好後,服務才能運行 } }
解釋:這個資源清單文件定義了puppet服務的一些屬性,並修改了restart操作爲reload操作,因爲有這樣的需要,當配置文件修改後,只是重新載入一下配置文件即可,在這裏對於puppet服務來說重啓與重新載入都不會產生什麼不良的影響,但有些服務可不是這樣。
[root@nod1 modules]# vim puppet/manifests/params.pp class puppet::params { $puppetserver = 'nod1.test.com' #聲明一個變量 case $operatingsystemmajrelease { #引用了一個facter變量做系統發行版本判斷應該裝哪個版本的puppet和facter,這裏我只列舉了一個,可以擴充,在測試中發現我在install.pp中無法引用下邊定義的“ $puppet_release”和“$facter_release”兩個變量,所以在install.pp文件中直接做判斷 6: { $puppet_release = '3.3.1-1.el6' $facter_release = '1.7.3-1.el6' } default: { #在case語句中一定要有default語句,不然會報錯 fail("Module puppet is not supported on ${::operatingsystem}") } } }
解釋:這個資源清單就是聲明一些變量,定義判斷語句的,case條件判斷語句的格式如下:
case CONTROL_EXPRESS { case1,.....: {.....statement...} case2,.....: {......statement..} ..... default: {....statement..} }
4、配置文件及模板文件準備
接下來準備所需要的配置文件及模板文件:
[root@nod1 modules]# vim puppet/files/namespaceauth.conf [puppetrunner] allow *.test.com #這是定義kick功能時的權限訪問控制 [root@nod1 modules]# vim puppet/templates/auth.conf.erb #這個文件就是在agent端的/etc/puppet/auth.conf配置文件的基礎上增加了下邊的代碼 ##puppet master path /run method save allow <%= scope.lookupvar('puppet::params::puppetserver') %>
#這段代碼必須在"path /"之前,“<%= scope.lookupvar('puppet::params::puppetserver') %>”這是模板文件中引用變量的方式,這個變量引用過來就是“nod1.test.com”。
[root@nod1 modules]# vim puppet/templates/puppet.conf.erb [main] logdir = /var/log/puppet rundir = /var/run/puppet ssldir = $vardir/ssl [agent] classfile = $vardir/classes.txt localconfig = $vardir/localconfig server = <%= scope.lookupvar('puppet::params::puppetserver') %> listen = true #定義支持kick功能,讓puppet監聽在tcp的8139端口 runinterval = 900 #定義去master端獲取catalog的間隔時間,單位爲秒 #這個文件是/etc/puppet/puppet.conf去掉註釋與空白行的數據。
5、測試
啓動master端上的服務:
[root@nod1 modules]# service puppetmaster start Starting puppetmaster: [ OK ]
再把agent上的facter軟件版本降低:
[root@nod2 ~]# rpm -e facter --nodeps [root@nod2 ~]# rpm -ivh facter-1.7.2-1.el6.x86_64.rpm warning: facter-1.7.2-1.el6.x86_64.rpm: Header V4 RSA/SHA1 Signature, key ID 4bd6ec30: NOKEY Preparing... ########################################### [100%] 1:facter ########################################### [100%] [root@nod2 ~]# facter -v 1.7.2 [root@nod2 ~]# yum list facter --showduplicates #查看yum中有哪些版本的facter Loaded plugins: fastestmirror, priorities Loading mirror speeds from cached hostfile * base: mirror.bit.edu.cn * epel: mirrors.neusoft.edu.cn * extras: mirrors.cqu.edu.cn * updates: ftp.yz.yamagata-u.ac.jp Installed Packages facter.x86_64 1:1.7.2-1.el6 installed Available Packages facter.x86_64 1.6.18-8.el6 epel facter.x86_64 1:1.7.3-1.el6 puppetrepo facter.x86_64 1:1.7.6-1.el6
puppetrepo
#這裏的puppetrepo是自己製作的puppet軟件包源
[root@nod2 x86_64]# puppet agent -t --no-daemonize --noop #先做測試 Notice: Ignoring --listen on onetime run Info: Retrieving plugin Info: Caching catalog for nod2.test.com Info: Applying configuration version '1434507925' Notice: /Stage[main]/Puppet::Facter_install/Package[facter]/ensure: current_value 1.7.2-1.el6, should be 1.7.3-1.el6 (noop) #這裏發現了版本與定義的不一致 Notice: Class[Puppet::Facter_install]: Would have triggered 'refresh' from 1 events Notice: /Stage[main]/Puppet::Service/Service[puppet]/ensure: current_value stopped, should be running (noop) #這裏發現服務沒有啓動 Info: /Stage[main]/Puppet::Service/Service[puppet]: Unscheduling refresh on Service[puppet] Notice: Class[Puppet::Service]: Would have triggered 'refresh' from 1 events Notice: Stage[main]: Would have triggered 'refresh' from 2 events Notice: Finished catalog run in 0.73 seconds [root@nod2 x86_64]# puppet agent -t --no-daemonize #強制執行 Notice: Ignoring --listen on onetime run Info: Retrieving plugin Info: Caching catalog for nod2.test.com Info: Applying configuration version '1434507925' Notice: /Stage[main]/Puppet::Facter_install/Package[facter]/ensure: ensure changed '1.7.2-1.el6' to '1.7.3-1.el6' #版本已發生改變 Notice: /Stage[main]/Puppet::Service/Service[puppet]/ensure: ensure changed 'stopped' to 'running' Info: /Stage[main]/Puppet::Service/Service[puppet]: Unscheduling refresh on Service[puppet] Notice: Finished catalog run in 11.40 seconds You have new mail in /var/spool/mail/root [root@nod2 x86_64]# facter -v #查看facter版本 1.7.3
再在agent上修改一下配置文件的內容後再執行一次看一下文件會不會被還原:
[root@nod2 x86_64]# echo "###" >> /etc/puppet/namespaceauth.conf You have new mail in /var/spool/mail/root [root@nod2 x86_64]# cat /etc/puppet/namespaceauth.conf [puppetrunner] allow *.test.com ### [root@nod2 x86_64]# puppet agent -t --no-daemonize [root@nod2 x86_64]# cat /etc/puppet/namespaceauth.conf #文件內容被成功還原了 [puppetrunner] allow *.test.com
再去查看一下auth.conf與puppet.conf都是我們在master端定義好的文件內容。
至此測試已結束。
6、總結
一個模塊的編寫並不是像我當初想像的那麼困難,但這次測試中關於變量的引用問題還是依然沒有解決,在網上查了一些資料,我引用的方法似乎沒有錯誤,但對install.pp文件反覆排查,發現在params.pp中定義的變量始終無法引用,不知爲何?
puppet模塊文件保存在:https://github.com/zhaochj/myrepository/tree/master/puppet_modules