2017-06-13 21 views
2

我是一個傀儡初學者 - 如此忍受我:) 我試圖寫一個模塊,執行以下操作:木偶:複製文件只有在包需要安裝最新的

  • 檢查軟件包是否安裝了最新版本的軟件倉庫
  • 如果需要安裝軟件包,那麼配置文件將從puppet源位置複製到客戶端。然後將安裝該軟件包
  • 一旦文件被複制並安裝軟件包,運行腳本將使用客戶端上的配置文件來應用必要的設置。
  • 一旦這一切完成後,刪除客戶端

我已經想出以下複製的文件:

class somepackage(
    $package_files_base = "/var/tmp", 
    $package_setup  = "/var/tmp/package-setup.sh", 
    $ndc_file   = "/var/tmp/somefile.ndc", 
    $osd_file   = "/var/tmp/somefile.osd", 
    $nds_file   = "/var/tmp/somefile.nds", 
    $configini_file  = "/var/tmp/somefile.ini", 
    $required_files  = ["$package_setup", "$ndc_file", "$osd_file", $nds_file", "$configini_file"]) 
{ 
    package { 'some package': 
    ensure => 'latest', 
    notify => Exec['Package Setup'], 
    } 

    file { 'Package Setup Files': 
    path => $package_files_base, 
    ensure => directory, 
    replace => false, 
    recurse => true, 
    source => "puppet:///modules/somepackage/${::domain}", 
    mode => '0755', 
    } 

    exec { 'Package Setup': 
    command  => "$package_setup", 
    logoutput => true, 
    timeout  => 1800, 
    require  => [ File['Package Setup Files']], 
    refreshonly => true, 
    notify  => Exec['Remove config files'], 
    } 

    exec { 'Remove config files': 
    path  => ['/usr/bin','/usr/sbin','/bin','/sbin'], 
    command  => "rm \"${package_setup}\" \"${ndc_file}\" \"${osd_file}\" \"${nds_file}\" \"${configini_file}\"", 
    refreshonly => true, 
    } 
} 

雖然這實現了大多數的什麼,我想做的事情,我注意到在重新運行傀儡時,應用這些文件雖然被刪除,但正在被複制。

我可以理解爲什麼會發生這種情況,但我不知道如何對它進行編碼,以便只有在程序包得到更新/安裝(例如,程序包未安裝或舊版本)時纔會複製文件。否則,每當木偶每隔30分鐘(默認設置)在客戶端上運行時,文件就會被一遍又一遍地複製,我假設...我試圖使用replace => false來防止這種情況,但這只是意味着文件在從/var/tmp之後這是該類的第一次運行,因爲它僅阻止後續運行的類重新複製文件(從我的測試中)。這確實可以防止多餘的重複性複製 - 但是我只想讓這些文件在第一時間消失!

這可能嗎? !頭好痛:(提前

感謝我們正在EL7.3運行木偶版本3.8.6

編輯:要清楚,這是我掙扎了一下:資源file { 'Package Setup Files':這種狀態越來越文件複製即使包不更新/安裝。如何防止這種情況的發生?

+0

從我所瞭解的情況來看,只有在軟件包不是最新的版本時才需要執行「軟件包設置文件」?那是你唯一面臨的問題? –

+0

不,執行得很好 - 「文件{'程序包設置文件''位是無論如何都會一直執行的文件。如果軟件包已更新/安裝,我只想限制這一點。 –

+0

我注意到$ package_files_base沒有在任何地方定義。錯字? –

回答

2

下面是一些建議。

1)建議了短期的解決辦法

如果您不需要,請停止嘗試清理這些文件。把它們放在/opt,忘記它們。更好的是,讓Puppet在那裏放置一個README文件,它會向你的未來自我和同行管理員解釋他們是什麼以及他們爲什麼在那裏。

雖然我完全理解清理的願望,但您需要權衡在某個目錄中有幾個舊文件的成本,而不是在Puppet代碼中具有複雜邏輯的代價,這對於任何人來說都沒有任何意義幾個月。

這就是我會做的,根據我的經驗,這也是大多數Puppet模塊作者用這些類型的設置文件所做的。

2)考慮業務流程框架

這就是說,在我看來,你要使用木偶做作戰任務,雖然它可以種做作戰任務(通過功能,如ensure => latest等)它真的打算成爲一個配置管理工具。

我建議人們使用Puppet到ensure => installed的包(確保Puppet可以正確安裝應用程序,如果你需要完全重建節點);然後委託在Puppet之外應用版本升級和修補程序等問題。

這有幾個原因。

木偶是聲明性配置管理系統;你的Puppet代碼應該定義一個結束狀態。 Puppet不像一個shell腳本,它不是一個結束狀態,而是定義了一些步驟,這些步驟可以強制性地改變服務器的狀態,「一步一個腳印」。

的第一個問題是ensure => latest哲學。 latest沒有定義單個最終狀態。你的代碼在X時刻的行爲與Y時刻的行爲不同,所以你的代碼不是冪等的。

第二個問題是實用的。因爲Puppet永遠無法知道系統中的所有RPM及其依賴關係,所以永遠無法通過使用Puppet解決RPM更新的問題。所以,無論如何,你仍然需要專門的工具來管理版本更新。因此,由於無論如何您都需要專門的工具來管理版本更新,因此在兩個工具的角色之間繪製清晰的邊界更清晰:始終使用Puppet來管理配置和初始安裝;然後始終使用其他工具來管理更新。

好,太好了。我看到您的意見,您已經有了一個紅帽衛星服務器,你已經寫了:

...衛星內的一些主機已經得到百勝內 軟件的舊版本。但是我們不會經常更新這個軟件 .....也許每年一次。

所以,它聽起來就像你正在使用木偶這裏解決您正在使用衛星的方式有問題。是否可以通過修復您使用Satellite的方式來解決這個問題?如果是這樣,我認爲這會更清潔。

當然,有時做正確的事情是使用一個變通,這就是爲什麼我提供了一些其他的選擇。

3)如果你真的好想木偶來清理這些文件

也許移動shell腳本內部的邏輯。例如:

class somepackage { 

    $shell = 

'#!/bin/bash 

# maybe use wget instead of puppet to get the files 
wget http://a.b/c.tgz 
tar zxf c.tgz 

# install stuff 

# clean up stuff 
' 

    file { '/usr/local/bin/installer.sh': 
    ensure => file, 
    mode => '0755', 
    content => $shell, 
    } 

    package { 'some package': 
    ensure => latest, 
    notify => Exec['installer'], 
    } 

    exec { 'installer': 
    command  => '/usr/local/bin/installer.sh', 
    refreshonly => true, 
    require  => File['/usr/local/bin/installer.sh'], 
    } 
} 
+0

她並不是在嘗試編排,但第1和第3點仍然有效。 –

+0

這取決於你如何定義「編排」,但我可以告訴你,與Nigel Kersten(Puppet首席技術官)相同,我認爲你不應該使用Puppet的'ensure => latest'(IIRC,墨爾本木偶營,2014 );這是一個操作/服務器維護任務,最好由Puppet之外的編排框架處理。 –

+0

他可能會說「儘量避免」而不是「永遠」。 –