Depending on a class from a class?

22 views
Skip to first unread message

Daniel Piddock

unread,
Nov 30, 2010, 10:03:39 AM11/30/10
to Puppet Users
Hello,

I fear that I have done something stupid in my manifests that requires
a redesign. To take an example:

I have the global statement:
Package {
ensure => latest,
require => Class['repositories'],
}

I then have a repositories module with init.pp containing:
class repositories {
case $operatingsystem {
debian: {
include repositories::debian
}
fedora: {
include repositories::fedora
}
default: {
fail "Unsupported OS $operatingsystem'"
}
}
}

Unfortunately I was hoping that an include here would act like a
requirement, however it does not. The contents of debian.pp/fedora.pp
get evaluated at an arbitrary later point causing interesting issues
when first installing a system. Puppet attempts to install some
packages before the repositories have been configured.

Is there any way for a class to depend on another class or for the
include statement to act more like a require?

In this example it would be trivial to change the global statement to
directly require the operating system's repositories subclass.
Unfortunately I have used this paradigm in multiple locations, some
where the alternative may not be as obvious or would increase the
verbosity of the including classes.

Thank you for any pointers,

Dan

Patrick

unread,
Nov 30, 2010, 12:59:15 PM11/30/10
to puppet...@googlegroups.com

I think this will work, but I don't have a machine to test the syntax on right now:

include repositories


Package {
ensure => latest,
require => Class['repositories'],
}

class repositories {

case $operatingsystem {
debian: {
$repositoryclass
}
fedora: {
$repositoryclass


}
default: {
fail "Unsupported OS $operatingsystem'"
}
}

require( Class[ $repositoryclass ] )

}

Eric Sorenson

unread,
Nov 30, 2010, 1:07:05 PM11/30/10
to puppet...@googlegroups.com
On Nov 30, 2010, at 7:03 AM, Daniel Piddock wrote:

> Is there any way for a class to depend on another class or for the
> include statement to act more like a require?


Two things here:

If you're on 2.6.3 put your repositories class in a 'pre' stage, that way you eliminate putting an individual dependency on every package resource as you're currently doing.

Minimally in your current code change 'include repositories::debian' to 'require("repositories::debian")' - this is a built-in function that does an include-plus-require and will produce the ordering you want (Thanks to Jeff Mccune for pointing me at this) http://docs.puppetlabs.com/references/latest/function.html#require

- Eric Sorenson - N37 17.255 W121 55.738 - http://twitter.com/ahpook -

Daniel Piddock

unread,
Dec 1, 2010, 4:57:37 AM12/1/10
to puppet...@googlegroups.com
On 30/11/10 18:07, Eric Sorenson wrote:
> On Nov 30, 2010, at 7:03 AM, Daniel Piddock wrote:
>
>> Is there any way for a class to depend on another class or for the
>> include statement to act more like a require?
>
> Two things here:
>
> If you're on 2.6.3 put your repositories class in a 'pre' stage, that way you eliminate putting an individual dependency on every package resource as you're currently doing.

Unfortunately I'm still stuck in 0.25 land. Staging looks like a nicer
solution to some of my problems.

> Minimally in your current code change 'include repositories::debian' to 'require("repositories::debian")' - this is a built-in function that does an include-plus-require and will produce the ordering you want (Thanks to Jeff Mccune for pointing me at this) http://docs.puppetlabs.com/references/latest/function.html#require

require was the function I was looking for. So obvious and documented.

Thank you,

Dan

Daniel Piddock

unread,
Dec 1, 2010, 7:18:01 AM12/1/10
to puppet...@googlegroups.com

It appears that I was a little too early in my celebration.

"require $class" causes you to import the class, however no dependency
is then placed on the *contents* of said class. I'm in exactly the same
position. If I have "require => Class[repository::fedora]" instead of
just "require => Class[repository]" in the Package definition I get the
results desired. This strikes me as a design flaw.

I tried the puppet 2.6.3 gem but it still performs in the same fashion.

I'll try generating some simplified configs in a test environment and
file a bug report. Then I'll redesign everything else.

Dan

Nigel Kersten

unread,
Dec 1, 2010, 10:03:24 AM12/1/10
to puppet...@googlegroups.com
On Wed, Dec 1, 2010 at 4:18 AM, Daniel Piddock
<dgp-...@corefiling.co.uk> wrote:
>  On 01/12/10 09:57, Daniel Piddock wrote:
>>  On 30/11/10 18:07, Eric Sorenson wrote:
>>> Minimally in your current code change 'include repositories::debian' to 'require("repositories::debian")' - this is a built-in function that does an include-plus-require and will produce the ordering you want  (Thanks to Jeff Mccune for pointing me at this)  http://docs.puppetlabs.com/references/latest/function.html#require
>> require was the function I was looking for. So obvious and documented.
>
> It appears that I was a little too early in my celebration.
>
> "require $class" causes you to import the class, however no dependency
> is then placed on the *contents* of said class. I'm in exactly the same
> position. If I have "require => Class[repository::fedora]" instead of
> just "require => Class[repository]" in the Package definition I get the
> results desired. This strikes me as a design flaw.

It sounds like you don't have a relationship defined between
Class[repository] and Class[repository::fedora] ?

Setting up a relationship with the former does not imply a
relationship with the latter.

>
> I tried the puppet 2.6.3 gem but it still performs in the same fashion.
>
> I'll try generating some simplified configs in a test environment and
> file a bug report. Then I'll redesign everything else.
>
> Dan
>

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

--
Nigel Kersten - Puppet Labs -  http://www.puppetlabs.com

Daniel Piddock

unread,
Dec 1, 2010, 10:22:02 AM12/1/10
to puppet...@googlegroups.com
On 01/12/10 15:03, Nigel Kersten wrote:
> On Wed, Dec 1, 2010 at 4:18 AM, Daniel Piddock
> <dgp-...@corefiling.co.uk> wrote:
>> On 01/12/10 09:57, Daniel Piddock wrote:
>>> On 30/11/10 18:07, Eric Sorenson wrote:
>>>> Minimally in your current code change 'include repositories::debian' to 'require("repositories::debian")' - this is a built-in function that does an include-plus-require and will produce the ordering you want (Thanks to Jeff Mccune for pointing me at this) http://docs.puppetlabs.com/references/latest/function.html#require
>>> require was the function I was looking for. So obvious and documented.
>> It appears that I was a little too early in my celebration.
>>
>> "require $class" causes you to import the class, however no dependency
>> is then placed on the *contents* of said class. I'm in exactly the same
>> position. If I have "require => Class[repository::fedora]" instead of
>> just "require => Class[repository]" in the Package definition I get the
>> results desired. This strikes me as a design flaw.
> It sounds like you don't have a relationship defined between
> Class[repository] and Class[repository::fedora] ?

class repository contains a "require repository::fedora" line (context
has been lost from the first mail)

> Setting up a relationship with the former does not imply a
> relationship with the latter.

I've tracked it down to being a problem with 0.25.5. Using 2.6.3 the
require gets expanded correctly. Either solution I need to upgrade to 2.6.3.

I was previously calling puppetd which is not maintained by the 2.6.3
gem, so I was not actually testing 2.6.3. "puppet agent --test --noop"
works.

I now have large expanded_relationships graph with yum repos at the top
and a long line of Packages below.

Dan

Nigel Kersten

unread,
Dec 1, 2010, 11:14:47 AM12/1/10
to puppet...@googlegroups.com
On Wed, Dec 1, 2010 at 7:22 AM, Daniel Piddock

<dgp-...@corefiling.co.uk> wrote:
>  On 01/12/10 15:03, Nigel Kersten wrote:
>> On Wed, Dec 1, 2010 at 4:18 AM, Daniel Piddock
>> <dgp-...@corefiling.co.uk> wrote:
>>>  On 01/12/10 09:57, Daniel Piddock wrote:
>>>>  On 30/11/10 18:07, Eric Sorenson wrote:
>>>>> Minimally in your current code change 'include repositories::debian' to 'require("repositories::debian")' - this is a built-in function that does an include-plus-require and will produce the ordering you want  (Thanks to Jeff Mccune for pointing me at this)  http://docs.puppetlabs.com/references/latest/function.html#require
>>>> require was the function I was looking for. So obvious and documented.
>>> It appears that I was a little too early in my celebration.
>>>
>>> "require $class" causes you to import the class, however no dependency
>>> is then placed on the *contents* of said class. I'm in exactly the same
>>> position. If I have "require => Class[repository::fedora]" instead of
>>> just "require => Class[repository]" in the Package definition I get the
>>> results desired. This strikes me as a design flaw.
>> It sounds like you don't have a relationship defined between
>> Class[repository] and Class[repository::fedora] ?
>
> class repository contains a "require repository::fedora" line (context
> has been lost from the first mail)
>
>> Setting up a relationship with the former does not imply a
>> relationship with the latter.
>
> I've tracked it down to being a problem with 0.25.5. Using 2.6.3 the
> require gets expanded correctly. Either solution I need to upgrade to 2.6.3.

That's really good to know Daniel. Thanks for that.

>
> I was previously calling puppetd which is not maintained by the 2.6.3
> gem, so I was not actually testing 2.6.3. "puppet agent --test --noop"
> works.
>
> I now have large expanded_relationships graph with yum repos at the top
> and a long line of Packages below.
>
> Dan
>

Reply all
Reply to author
Forward
0 new messages