On Thu, 23 Sep 2010 18:36:21 +0200, Daniel Maher <d...@witbe.net> wrote:
> Hello,
> 
> I have two sites with a small number of machines at each.  Each site is 
> functionally identical.  I would like to set up a bunch of templates for 
> the various services at each site, with a handful of variables that 
> indicate which site the service is configured for.  What would be "best 
> practice" way to accomplish this in Puppet ?

Here's the way we do it, and it works very well for us, while avoiding
"globals" and the associated issues.

First, we have a "basezone" class, which is empty and really is just a
place holder (you'll see what this is for in a minute):

class bazezone {
}

Next, we define datacenters, so we have something like

class dc1 {
  $var1 = "foo"
  $var2 = "bar"
  include basezone
}

Note how the last thing (and it must be the last thing) it includes is the
basezone.  This is basically the landing area for all variables we define,
so they're nice and easy to find later.

Next, we have a basenode:

class basenode {
  include role_general
}

The role_general class is stuff we apply to every system, regardless of
where it is.  All of our modules are site-independent, and use templates
extensively.

Finally, we define zones:

class dc1_zone1 {
  include dc1

  $zone_var1 = "hi"
  $zone_var2 = "bye"

  include basenode
}

Zones are common areas inside a datacenter that use similar services - for
instance database servers, web servers, etc. 

Each node then gets assigned to a zone, and that's it for the most part.

node 'mysystem' {
  include dc1_zone1
}

Now, the importance of basezone - when using templates, you have to do a
lookup for the variable.  Having the basezone makes this easy, since all
the variables we define along the way are visible at that level - we don't
have to know specific class names.  One example I can share - we use puppet
to manage our root password hash.  For some systems, we override this on a
per-node basis, but for the rest we use the root password that's defined
for the zone (Every month we generate a new random 12-character root
password, that's why we set it per-zone instead of having unique passwords
everywhere):

# included in role_general
class user_root {
  if ( inline_template("<%= scope.lookupvar('root_password') %>") != "" ) {
    # The root password was over-ridden in the node
    $root_password = inline_template("<%= scope.lookupvar('root_password')
%>")
  }
  else {
    # Use the root password defined in the zone
    $root_password = inline_template("<%=
scope.lookupvar('basezone::root_password') %>")
  }
  user { "root":
    uid => 0,
    gid => 0,
    password => "$root_password",
  }
}

If we do 'node "test" {$root_password="hash"}' it will use that variable,
otherwise it will pull it out of the higher level classes (either the DC or
the zone).  

So, that's what we do, and I've found it to be reasonably scalable, and
allows us the ability to deploy generic modules across multiple datacenters
without making any changes.  We can also make modules "zone aware", which
allows us to do things like give users more permissions in our development
environment while keeping production restricted.

Hope this helps :)

-- 
This message has been scanned for viruses and
dangerous content by MailScanner, and is
believed to be clean.

-- 
You received this message because you are subscribed to the Google Groups 
"Puppet Users" group.
To post to this group, send email to puppet-us...@googlegroups.com.
To unsubscribe from this group, send email to 
puppet-users+unsubscr...@googlegroups.com.
For more options, visit this group at 
http://groups.google.com/group/puppet-users?hl=en.

Reply via email to