This is one of the best descriptions of how to do things in Puppet (or
maybe how not to) that I've seen, and touches on a *lot* of common
misunderstandings.
I think I might have to keep a short url to the archive of this handy...
Thanks, John.
On 01/03/2014 10:35 AM, jcbollinger wrote:
>
>
> On Thursday, January 2, 2014 8:28:33 AM UTC-6, Jelle B. wrote:
>
> Hi all,
>
> I have been kinda stuck with the following few issues (all
> related to one and other)
>
> What I want ot ddo is define a couple of standard actions in
> puppet that I can use across all my classes.
> So for example I define a exec for apt-get update , or a reload.
> When built in to a class it works fine I would just have to
> redeclare it with an other name in the next class and I want to
> get away from it.
>
>
>
> Part of your problem may be that you have a wrong conception of Puppet
> DSL. The DSL is not a scripting language; in fact, it is not an
> imperative language at all. There are no "actions" in it. You need
> to discard the mindset that you are telling Puppet what to do.
> Instead, embrace the concept that you are describing to Puppet what
> state it needs to achieve.
>
>
>
> Now I have started working on importing it via my site.pp but I
> can not define say the exec for "service $service_name reload", it
> will generate an error when I include it : Must pass service_name
> to Class[Defaults] (class defaults being the collective class I
> brought all these snippets together)
>
>
>
> With respect to services in particular, you are likely to be better
> off relying on the Service resource than to roll your own service
> management via Exec resources.
>
>
>
> So question one am I on the right path in creating this , using
> the top scope prinocipal in my design for this.
>
>
>
> I think not, but it's hard to tell because I don't know what you mean
> by "using the top-scope principal". On the other hand, you are right
> to be trying to consolidate redundant declarations and to avoid
> repeating yourself.
>
>
>
> Second question how do I pass a variable in this setup , as I can
> not include the class in site.pp as it will generate the "must
> pass error" but just doing an import in my site.pp and then an
> include in my module init.pp does not actually work either but
> then silentlly.
>
>
>
> The "import" function and the "include" function do very different
> things. You use "import" to persuade Puppet to parse a /manifest
> file/ that it otherwise would not parse (because it's in the wrong
> place for the autoloader to find it or because there is nothing to
> trigger the autoloader to load it in the first place). That has
> little to do with declaring classes on the target node, and there are
> very few good use cases for it in modern Puppet. Instead, put your
> classes and defined types in modules, laid out appropriately for
> autoloading.
>
> The "include" function, on the other hand, instructs Puppet that the
> named /class/ must be included in the target node's catalog. That is
> sometimes referred to as "declaring" the class. This form of class
> declaration does not explicitly specify any class parameters, which
> can be useful.
>
> In your case, however, it appears that your class has a defined
> parameter with no default value. If you must use class parameters --
> a discussion that I will omit for now -- then you must ensure that
> each parameter of each declared class is assigned a value exactly
> once. Parameter values can come from these places (from highest
> precedence to lowest):
>
> * from a parameterized-style class declaration or ENC-based class
> declaration
> * from hiera via automated data binding (Puppet 3+ only)
> * from a default value specified in the class itself
>
> I predict that you will be inclined to use parameterized-style class
> declarations, but I urge you to avoid them. They will cause you
> grief. Instead, avoid parameterization where it is unneeded, define
> sensible default parameter values, and use Hiera to provide parameter
> overrides where necessary.
>
>
>
> I am missing somethign I think just not sure what and where .
>
>
>
> You are missing several things, I suspect. Among them may be that
>
> * classes are idempotent -- declaring the same class more than once
> has no different meaning than declaring it exactly once
> * defined types and custom functions are therefore better vehicles
> for parameterized declarations that you want to reuse within the
> scope of the same node's catalog
> * Puppet terminology incorporates some words from the
> object-oriented programming world that may mislead people with OO
> programming background. In particular,
> o a Puppet "class" is not a model or type for objects, rather it
> represents a classification of the target node. There are no
> class instances, or if that's too alien for you then you can
> consider all Puppet classes to be Singletons.
> o Puppet class and node inheritance does not work the way OO
> programmers tend to expect.
> * A few other Puppet keywords and terminology sometimes trip up
> people coming from a programming background, not necessarily OO:
> o Defined types, created via the "define" keyword, are not
> analogous to C preprocessor macros. They are more like OO
> classes (a lot more so than Puppet classes are, in fact), such
> that we sometimes talk about "defined type instances" or similar.
> o Unlike the C preprocessor macro and similar statements in
> several other programming languages, Puppet's "include"
> statement does not perform textual interpolation. I already
> covered what it actually does do.
> o The "import" statement does not perform textual interpolation
> either, though what it actually does do is fairly similar to
> what Python's "import" does.
>
>
>
> Here below the code snippets of what I am doing.
>
> site.pp in /etc/puppet/environments/dev/manifests/
> Exec { path => [ "/bin/", "/sbin/" , "/usr/bin/", "/usr/sbin/" ] }
>
>
>
> Ok. A default path for all Execs is a reasonably sensible thing. If
> you are using third-party modules, however, then I would be very
> cautious about setting global defaults. Even something as innocuous
> as that could conceivably cause trouble for a module that did not
> expect it.
>
>
>
> import 'classes/*.pp'
>
>
>
> No. Do not use 'import' to load class definitions. Instead, put your
> classes into one or more modules, and lay them out where the
> autoloader will find them.
>
>
>
> the defaults.pp with the class from
> /etc/puppet/environments/dev/manifests/classes/ :
> class defaults ( $service_name ){
>
>
>
> To put this properly in a module named "site", change the class name
> to "site::defaults"
>
> class site::defaults ($service_name) {
>
> and move the file to
> /etc/puppet/environments/dev/modules/site/manifests/default.pp. In
> your puppet.conf, make sure the master's configuration for the "dev"
> environment has "/etc/puppet/environments/dev/modules" as or in its
> module path. (Though in truth, I would leave environments for later
> if I were you.)
>
>
>
> case $::operatingsystem {
> debian, ubuntu: {
> exec { "apt update":
> command => "/usr/bin/apt-get update",
> # onlyif => < snipped >
> }
> }
> }
>
> exec { "reload":
> command => "/usr/sbin/service $service_name reload",
> refreshonly => true,
> require => Service[[$service_name]],
> }
>
> exec { "restart":
> command => "/usr/sbin/service $service_name restart",
> refreshonly => true,
> require => Service[[$service_name]],
> }
>
>
>
> Those particular Execs pretty much duplicate functionality that the
> Service resource provides already. If you trigger a refresh on a
> running Service resource then the service will be restarted.
>
>
>
> }
>
>
>
> Overall, however, the class doesn't make sense. More specifically, it
> doesn't make sense to parameterize the class with a service name,
> because classes are idempotent. You would only be able to use it
> once, anyway. You might, however, be able to make use of something
> like this as a defined type.
>
>
>
> And the class calling it from
> /etc/puppet/environments/dev/modules/pdns/init.pp
>
> include defaults
>
>
>
> See above: include does not perform textual interpolation. (Also,
> classes are not analogous to macros.)
>
>
>
> class pdns_33 ( $mysql_password, $srv_type, $web_password ) {
> <-- snipped -->
> file { "/etc/powerdns/pdns.conf":
> ensure => present,
> owner => root,
> group => root,
> mode => 644,
> content => template("pdns_33/pdns.conf.erb"),
> notify => Exec[[reload]],
> }
> <-- snipped -->
>
>
>
> What you are trying to do will not work. Puppet DSL does not have
> macros. If your intended uses are similar enough to each other, then
> you might be able to achieve at least some of what you're after via a
> defined type, but in general, you're approaching the whole thing in a
> very non-idiomatic way.
>
> Successful and effective Puppet manifest design is an exercise in
> /modeling/, not programming. Your objective is to model the target
> configuration of your nodes. It follows that when writing manifests
> you should be thinking primarily in terms of describing the
> configuration artifacts you want Puppet to manage, rather than in
> terms of specifying actions for Puppet to perform.
>
> Recommended reading:
>
> * http://docs.puppetlabs.com/puppet/3/reference/lang_summary.html
> * http://docs.puppetlabs.com/puppet/3/reference/modules_fundamentals.html
> *
> http://www.devco.net/archives/2012/12/13/simple-puppet-module-structure-redux.php
>
> Additionally, you should at least skim these:
>
> * http://docs.puppetlabs.com/references/3.stable/type.html
> * http://docs.puppetlabs.com/references/3.stable/function.html
>
>
> John
>
> --
> You received this message because you are subscribed to the Google
> Groups "Puppet Users" group.
> To unsubscribe from this group and stop receiving emails from it, send
> an email to [email protected].
> To view this discussion on the web visit
> https://groups.google.com/d/msgid/puppet-users/ddad9657-6496-41f7-bf0f-e8fee43df7fe%40googlegroups.com.
> For more options, visit https://groups.google.com/groups/opt_out.
--
You received this message because you are subscribed to the Google Groups
"Puppet Users" group.
To unsubscribe from this group and stop receiving emails from it, send an email
to [email protected].
To view this discussion on the web visit
https://groups.google.com/d/msgid/puppet-users/52C80B7C.7070404%40jasonantman.com.
For more options, visit https://groups.google.com/groups/opt_out.