Take the 2-minute tour ×
Server Fault is a question and answer site for professional system and network administrators. It's 100% free, no registration required.

I'm trying Puppet and it seems to be good.

My question is very easy but I can't answer.

I have a file "node.pp" :

node basenode {
         include "dns"
#        include "ntp"
}


node 'myserver.domain.com' inherits basenode {
        $type_server = "client"
        include "ntp"
}

I would like to declare my variable "$type_server" without to do declare "include ntp" on each server. I would like "basenode" includes "ntp" and use the value of "$type_server" in the node of my server.

The variable is used in the manifests of NTP.

Thanks in advance.

share|improve this question

3 Answers 3

Don't use variables -- as Shane said, variable scoping in Puppet is FUBAR, and trying to use it just causes pain, suffering, nausea, headaches, and probably heart disease.

Instead, use defined types. It's what they're designed for. So, instead of using classes and includes everywhere, use a defined type and pass it the data it needs:

define ntp_server($type_server) {
    # Do all the things you'd normally do, using $type_server as needed
}

node 'myserver.domain.com' {
    ntp_server { ntp:
        type_server => "client"
    }
}
share|improve this answer
    
Nicer than my scoping workaround! –  Shane Madden Jul 19 '11 at 20:13
1  
Puppet variables need to die in a fire. –  womble Jul 19 '11 at 20:14

The scoping in puppet is a bit.. unintuitive. It's a linear evaluation behavior - since the inherit happens before the variable is defined, and the classes included in the inherited class are evaluated immediately, the variable is set after you need it.

Instead of inheriting, try just including the "base" at the bottom of every node, so that it's evaluated after the necessary variables are set. It's not a very object oriented way to do things, but this scoping behavior doesn't leave a lot of options.

node 'myserver.domain.com' {
    $type_server = "client"
    include basenode
}
share|improve this answer
2  
"unintuitive"... that's a funny way to spell "completely f**ked" <grin> –  womble Jul 19 '11 at 17:27

I know this is pretty old, but as I was having some troubles with it and found this thread, it might be useful for others.

Instead of using defined types or including a node within a node - which doesn't sound very nice imo - I would suggest using parameterized classes. By using that, the author could keep using his classes normally, and those classes would only have a slight modification to receive the variables (that they are already using) as parameters.

So, as example, instead of:

class foo {
  file { 'abc':
    path => "some/path"
    content => $content
  }
}

It could have:

class foo($content) {
  file { 'abc':
    path => "some/path"
    content => $content
  }
}

And use it like this:

node 'myserver.domain.com' {
    class { 'foo':
        $content => "something pretty smart"
    }
}
share|improve this answer
    
It should be content not $content in Puppet 3.5 FYI –  Brian May 23 at 15:03

Your Answer

 
discard

By posting your answer, you agree to the privacy policy and terms of service.

Not the answer you're looking for? Browse other questions tagged or ask your own question.