Upload
puppet-labs
View
808
Download
0
Embed Size (px)
Citation preview
Module Contents
foo/ manifests/ defaults.pp init.pp install.pp config.pp service.pp templates/ foo.conf.erb
manifests/defaults.ppclass foo::defaults { case $osfamily { 'Debian': { $package_name = 'foo-ruby' $service_name = 'foo' $config_path = '/etc/foo/foo.conf' $log_file = '/var/log/foo/foo.log' $storage_path = '/var/lib/foo' } 'RedHat': { $package_name = 'ruby-foo' $service_name = 'foo' $config_path = '/etc/foo.conf' $log_file = '/var/log/foo.log' $storage_path = '/var/lib/foo' } default: { fail("${osfamily} not currently supported by this module") } }}
manifests/init.ppclass foo ( $package_ensure = installed, $listen = '127.0.0.1', $port = '1234', $verbose = false,) inherits foo::defaults { if (!is_ip_address($listen)) { fail('listen parameter needs to be an ip address') } $verbose_bool = str2bool($verbose)
include foo::install include foo::config include foo::service
Class['foo::install'] -> Class['foo::config'] ~> Class['foo::service']
anchor { 'foo::begin': before => Class['foo::install','foo::config'], notify => Class['foo::service']; 'foo::end': require => Class['foo::service']; }}
manifests/init.pp
class foo ( $package_ensure = installed, $listen = '127.0.0.1', $port = '1234', $verbose = false,) inherits foo::defaults {
manifests/init.pp
if (!is_ip_address($listen)) { fail('listen parameter needs to be an ip address') } $verbose_bool = str2bool($verbose)
manifests/init.pp
include foo::install include foo::config include foo::service
Class['foo::install'] -> Class['foo::config'] ~> Class['foo::service']
manifests/init.pp
anchor { 'foo::begin': before => Class['foo::install','foo::config'], notify => Class['foo::service']; 'foo::end': require => Class['foo::service']; }
containment example
include site::mountsinclude site::webappinclude mysqlinclude apache
Class['site::mounts'] -> Class['mysql']Class['site::mounts'] -> Class['apache']Class['mysql'] -> Class['apache']Class['mysql'] -> Class['site::webapp']
manifests/init.pp
anchor { 'foo::begin': before => Class['foo::install','foo::config'], notify => Class['foo::service']; 'foo::end': require => Class['foo::service']; }
manifests/init.ppclass foo ( $package_ensure = installed, $listen = '127.0.0.1', $port = '1234', $verbose = false,) inherits foo::defaults { if (!is_ip_address($listen)) { fail('listen parameter needs to be an ip address') } $verbose_bool = str2bool($verbose)
include foo::install include foo::config include foo::service
Class['foo::install'] -> Class['foo::config'] ~> Class['foo::service']
anchor { 'foo::begin': before => Class['foo::install','foo::config'], notify => Class['foo::service']; 'foo::end': require => Class['foo::service']; }}
manifests/install.pp
class foo::install inherits foo { package { $package_name: ensure => $package_ensure, }}
manifests/config.pp
class foo::config inherits foo { file { $config_path: content => template('foo/foo.conf.erb'), owner => 'root', group => 'root', mode => '0644'; }}
Module Contents
class foo::service inherits foo { service { $service_name: ensure => running, enable => true, }}
templates/foo.conf.erb
[main]listen = <%= @listen %>port = <%= @port %>verbose = <%= @verbose_bool ? 'yes' : 'no' %>log_file = <%= @log_file %>storage_dir = <%= @storage_dir %>
Module Contents
foo/ manifests/ defaults.pp init.pp install.pp config.pp service.pp templates/ foo.conf.erb
example
# profile/manifests/server.ppclass profile::server { class { 'foo': port => 3389, verbose => true, }}
example
# hiera/global.yamlfoo::port: 3389foo::verbose: true
# profile/manifests/server.ppclass profile::server { include ::foo}
Module Contents
foo/ manifests/ defaults.pp init.pp install.pp config.pp service.pp plugin.pp templates/ foo.conf.erb plugin.conf.erb
manifests/defaults.pp
class foo::defaults { case $osfamily { 'Debian': { $package_name = 'foo-ruby' $service_name = 'foo' $config_path = '/etc/foo/foo.conf' $log_file = '/var/log/foo/foo.log' $storage_path = '/var/lib/foo' $conf_d_path = '/etc/foo/conf.d' $plugin_path = '/usr/share/foo/plugins' } 'Redhat': { $package_name = 'ruby-foo' $service_name = 'foo' $config_path = '/etc/foo.conf' $log_file = '/var/log/foo.log' $storage_path = '/var/lib/foo' $conf_d_path = '/etc/foo.d/' $plugin_path = '/usr/lib/foo/plugins' } }}
manifests/config.ppclass foo::config inherits foo { file { $config_path: content => template('foo/foo.conf.erb'), owner => 'root', group => 'root', mode => '0644'; $conf_d_path: ensure => directory, purge => true, recurse => true, owner => 'root', group => 'root', mode => '0755'; }}
templates/foo.conf.erb
[main]listen = <%= @listen %>port = <%= @port %>verbose = <%= @verbose_bool ? 'yes' : 'no' %>log_file = <%= @log_file %>storage_dir = <%= @storage_dir %>@include <%= @conf_d_path %>/*.conf
manifests/plugin.ppdefine foo::plugin ( $type, $path = "${foo::defaults::plugin_path}/${name}.rb", $verbose = undef,) { include foo::defaults
validate_absolute_path($path) $verbose_bool = str2bool($verbose)
file { "${foo::defaults::conf_d_path}/${name}.conf": content => template('foo/plugin.conf.erb'), owner => 'root', group => 'root', mode => '0755', notify => Class['foo::service'], }}
templates/plugin.conf.erb
[plugin <%= @name %>]type = <%= @type %>path = <%= @path %>
<%- if [email protected]? -%>verbose = <%= @verbose_bool ? 'yes' : 'no' %><%- end -%>
example
include foo
foo::plugin { 'webapp': type => 'passenger'; 'db': type => 'mysql', verbose => true, path => '/usr/local/share/custom_mysql.rb';}
role/profile exampleclass profile::app { include foo foo::plugin { 'webapp': type => 'passenger'; }}
class profile::db { include foo foo::plugin { 'db': type => 'mysql'; }}
class role::server { include profile::app include profile::db}
manifests/config.pp
class foo::config inherits foo { concat { $config_path: owner => 'root', group => 'root', mode => '0644'; }
concat::fragment { 'foo_conf_header': content => template('foo/foo.conf.erb'), target => $config_path, order => '00_header', }}
manifests/plugin.ppdefine foo::plugin ( $type, $path = "${foo::defaults::plugin_path}/${name}.rb", $verbose = undef,) { include foo::defaults
validate_absolute_path($path) $verbose_bool = str2bool($verbose)
concat { "foo_conf_plugin_${name}": content => template('foo/plugin.conf.erb'), target => $conf_file, order => "10_plugin_${name}", }}
README.md
• What it manages
• Top level class parameters
• Defined types and their parameters
• Optional dependencies
• Common usage examples
spec/classes/foo_spec.rb
describe 'foo' do context 'default parameters' do let (:params) {{ }} it { should compile.with_all_deps } it { should contain_class('foo::defaults') } it { should contain_class('foo::install') } it { should contain_class('foo::config') } it { should contain_class('foo::service') } endend
spec/classes/foo_spec.rbdescribe 'foo' do let (:facts) {{ :osfamily => 'Redhat' }} context 'default parameters' do it { should contain_package('ruby-foo') } it { should contain_file('/etc/foo.conf').with( :owner => 'root', :group => 'root', :mode => '0644', )} it { should contain_file('/etc/foo.d').with( :owner => 'root', :group => 'root', :mode => '0755', :purge => true, :recurse => true, )} it { should contain_service('foo').with( :ensure => 'running', :enable => true, )} endend
spec/classes/foo_spec.rbdescribe 'foo' do let (:facts) {{ :osfamily => 'Redhat' }} let (:config_file) { '/etc/foo.conf' } context 'default parameters' do it { should contain_file(config_file) .with_content(/listen = 127\.0\.0\.1/) } it { should contain_file(config_file) .with_content(/port = 1234/) } it { should contain_file(config_file) .with_content(/verbose = no/) } it { should contain_file(config_file) .with_content(%r{log_file = /var/log/foo.log}) } it { should contain_file(config_file) .with_content(%r{storage_dir = /var/lib/foo}) } endend
spec/classes/foo_spec.rbdescribe 'foo' do let (:facts) {{ :osfamily => 'Redhat' }} let (:config_file) { '/etc/foo.conf' }
context 'parameters set' do let (:params) {{ :listen => '10.0.0.42', :port => '4567', }} it { should contain_file(config_file).with_content(/listen = 10\.0\.0\.42/) } it { should contain_file(config_file).with_content(/port = 4567/) } end
context 'boolean values true' do let (:params) {{ :verbose => true, }} it { should contain_file(config_file).with_content(/verbose = yes/) } end
context 'boolean values fales' do let (:params) {{ :verbose => true, }} it { should contain_file(config_file).with_content(/verbose = no/) } endend
Forge Tips
• Limit dependencies
• External resource dependencies (user, repo)
• anchor pattern
• use include foo vs class {‘foo’: }
ResourcesExample modules
• puppetlabs/ntp: https://forge.puppetlabs.com/puppetlabs/ntp
• pdxcat/collectd: https://forge.puppetlabs.com/pdxcat/collectd
Library modules
• puppetlabs/stdlib: https://forge.puppetlabs.com/puppetlabs/stdlib
• puppetlabs/concat: https://forge.puppetlabs.com/puppetlabs/concat
Testing
• rspec-puppet: http://rspec-puppet.com
• beaker: https://github.com/puppetlabs/beaker