How to write re-usable puppet definitions?

Posted by Oliver Probst on Server Fault See other posts from Server Fault or by Oliver Probst
Published on 2012-12-03T14:21:09Z Indexed on 2012/12/04 5:07 UTC
Read the original article Hit count: 452

Filed under:

I'd like to write a puppet manifest to install and configure an application on target servers.

Parts of this manifest shall be re-usable. Thus I used define for defining my re-usable functionality. Doing so, I've always the problem that there are parts of the definition which are not re-usable.

A simple example is a bunch of configuration files to be created. These file must be placed in the same directory. This directory must be created only once.

Example:

nodes.pp

node 'myNode.in.a.domain' {
  mymodule::addconfig {'configfile1.xml':
    param => 'somevalue',
  }
  mymodule::addconfig {'configfile2.xml':
    param => 'someothervalue',
  }
}

mymodule.pp

define mymodule::addconfig ($param) {

  $config_dir = "/the/directory/"

  #ensure that directory exits:
  file { $config_dir:
    ensure  => directory,
  }

  #create the configuration file:     
  file { $name:
    path    => "${config_dir}/${name}"
    content => template('a_template.erb'),
    require => File[$config_dir],
  }
}

This example will fail, because now the resource file {$config_dir: is defined twice.

As far as I understood, it is required to extract these parts into a class. Then it looks like this:

nodes.pp

node 'myNode.in.a.domain' {

  class { 'mymodule::createConfigurationDirectory':
  }

  mymodule::addconfig {'configfile1.xml':
    param => 'somevalue',
    require => Class ['mymodule::createConfigurationDirectory'],
  }
  mymodule::addconfig {'configfile2.xml':
    param => 'someothervalue',
    require => Class ['mymodule::createConfigurationDirectory'],
  }
}

But this makes my interface hard use. Every user of my module has to know, that there is a class which is additionally required. For this simple use case the additional class might be acceptable. But with growing module complexity (lots of definitions) I'm a bit afraid of confusing the modules user.

So I'd like to know is there a better way to handle this dependencies. Ideally, classes like createConfigurationDirectory are hidden from the user of the modules api.

Or are there some other "Best Practices"/Patterns handling such dependencies?

© Server Fault or respective owner

Related posts about puppet