Puppet is a quite powerful configuration manager tool which allows you to configure automatically hosts and keep configurations consistence.
I did some tests using 3 VMs:
- puppetmaster (server)
- puppetagent01 (client)
- puppetagent02 (client)
Of course, most of the work is done on puppetmaster server. On the last two machines you will simply see the outcome of the configurations that you’re going do set on puppetmaster.
Important: all the machines have to be able to communicate between each others. Please make sure DNS is working or set local names/IPs in
/etc/hosts
file, and do some ping tests before proceeding.
Client setup
On each puppetagent machine, just install the package puppet
apt-get install puppet
By default, the client will look for a host called “puppet” on the network.
If your DNS/hosts file doesn’t have this entry, and it can’t be resolved, you can manually set the name of the puppetmaster in /etc/puppet/puppet.conf
file, adding this line under [main]
section:
server=puppetmaster.yournet.loc
Now, no more configuration is required from the client side. Just edit /etc/default/puppet to start at boot time and start the service.
# Defaults for puppet - sourced by /etc/init.d/puppet # Start puppet on boot? START=yes # Startup options DAEMON_OPTS=""
service puppet start
Starting the service, will make automatically a request to the server to be added under his control.
If you want to do some tests, you can eventually use the following command to run puppet only once. This will also force the polling updates, which by default runs every 30 minutes.
puppet agent --no-daemonize --onetime --verbose
You can repeat all these steps on the second client machine.
Server setup
apt-get install puppetmaster
Check if the service is running, otherwise, start it up.
Sign clients’ certificates on the server side
Puppet uses this client/server certificate sign system to add/remove hosts from being managed by the server.
To see who has requested to be “controlled” use this command:
puppet cert --list
This will show all the hosts waiting to be added under puppetmaster server.
puppet cert --sign
This command will add the host.
Puppetmaster configuration files
The main configuration file is /etc/puppet/manifests/site.pp
Inside manifests
folder, I’ve created a subfolder called classes
with extra definitions (content of these files is showed later in this post).
/etc/puppet/manifests# tree . |___ classes | |___ apache.pp | |___ mysite.pp | |___ ntpd.pp | |___ packages.pp |___ site.pp
/etc/puppet/manifests/site.pp
import 'classes/*.pp' # This add all the custom .pp files into classes folder class puppettools { # Creates a file, setting permissions and content file { '/usr/local/sbin/puppet_once.sh': owner => root, group => root, mode => 755, content => "#!/bin/sh\npuppet agent --no-daemonize --onetime --verbose $1\n", } # Install (if not present) some puppet modules required for 'vimconf' class exec { "install_puppet_module": command => "puppet module install puppetlabs-stdlib", path => [ "/bin", "/sbin", "/usr/bin", "/usr/sbin", "/usr/local/bin", "/usr/local/sbin" ], onlyif => "test `puppet module list | grep puppetlabs-stdlib | wc -l` -eq 0" } } class vimconf { # Modify vimrc conf file, enabling syntax on file_line { 'vim_syntax_on': path => '/etc/vim/vimrc', match => '^.*syntax on.*$', line => 'syntax on', } } node default { # this will be applied to all nodes without specific node definitions include packages include vimconf include ntp include puppettools } node 'puppetagent01' inherits default { # this specific node, gets all the default classes PLUS some extras include mysite }
Here the content of the single files .pp
in classes
folder:
class apache { package { 'apache2-mpm-prefork': ensure => installed } service { 'apache2': ensure => running, hasstatus => true, hasrestart => true, } }
class mysite { include apache file { '/etc/apache2/sites-available/mysite': owner => root, group => root, mode => 0644, source => "puppet:///files/mysite/mysite_apache.conf", } file {'/var/www/mysite.localdomain': ensure => directory, } file {'/var/www/mysite.localdomain/index.html': owner => root, group => www-data, mode => 0755, source => "puppet:///files/mysite/index.html", } exec {'/usr/sbin/a2dissite * ; /usr/sbin/a2ensite mysite': onlyif => '/usr/bin/test -e /etc/apache2/sites-available/mysite', notify => Service['apache2'], } }
class ntp { package { ntp: ensure => present } file { "/etc/ntp.conf": owner => root, group => root, mode => 444, backup => false, source => "puppet:///files/etc/ntp.conf", require => Package["ntp"], notify => Service["ntp"], } service { "ntp": enable => true , ensure => running, subscribe => [Package[ntp], File["/etc/ntp.conf"],], } }
class packages { Package { ensure => "installed" } package { "screen": } package { "dselect": } package { "vim": } package { "curl": } }
It’s important to remember to NOT duplicate entries.
For example, in this case, we have a specific file where we have setupntp
service, including the required package. This means that we do NOT have to add this package in the list intopackages.pp
, otherwise you will get an error and configs won’t get pushed.
As I’m sure you’ve noted, there are references to some “files”.
Yes, we need some extra configuration, to tell puppet to run as file server as well and where files are located.
In our example we are storing our files in here:
mkdir -p /etc/puppet/files
Now we need to add the following in /etc/puppet/fileserver.conf
[files] path /etc/puppet/files allow *
Last bit, is creating the subfolders and place the files required for our configuration:
mkdir -p /etc/puppet/files cd /etc/puppet/files mkdir mysite mkdir etc
Inside mysite
create mysite_apache.conf
and index.html
files.
Example mysite_apache.conf
<VirtualHost *:80> ServerName mysite.localdomain DocumentRoot /var/www/mysite.localdomain </VirtualHost>
For index.html
, you can simply have some text, just for testing purposes.
In this example, we have also setup ntp
to be installed and to have a custom ntp.conf
file pushed.
For this reason, we need to make sure to have this file present into /etc/puppet/files/etc
as declared into our .pp
file.
After doing all these changes, you should restart your puppetmaster service on the server.
If all went well, you should have the following:
- puppetagent02 host with screen, dselect, vim (installed and with syntax on), ntp (installed, running with custom ntp.conf file)
- puppetagent01: with the same as puppetagent02 PLUS apache with a running website
Of course this is just a raw example and you can use template and other super features.
But I think it’s a good start 😉
Sources:
https://forge.puppetlabs.com/puppetlabs/stdlib
http://finninday.net/wiki/index.php/Zero_to_puppet_in_one_day
http://www.puppetcookbook.com/
http://foaa.de/old-blog/2010/07/playing-with-puppets-on-debian/trackback/index.html
http://www.harker.com/puppet/BayLISA100715.html
http://docs.puppetlabs.com/puppet/latest/reference/lang_relationships.html