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: 574
        
puppet
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