Published on 2 March 2012 by
Purpose Standard library for creating Puppet modules
Module puppetlabs/stdlib
Puppet Version 2.6+
Platforms Redhat, Debian, Solaris, Mac OS X, Windows

This week we’re going to cover the puppetlabs/stdlib module. This module is packed with lots of Puppet goodness, including custom Puppet functions for validating manifest data, a resource type for managing individual lines in files, extensions to facter, and more. Clearly, this is one bad-ass Puppet module!

Since the puppetlabs/stdlib module has so much utility, it’s required by many of the modules built by the crew here at Puppet Labs. My goal this week is to show you how to harness these features in your own modules. To ensure we cover this module properly we’re going to break the coverage into four posts.

We’ll kick things off with the file_line resource which allows you to manage individual lines in a file. This is really great when you’re not in position to manage the entire file. You can use file_line as many times as you like, but be sure to give each resource a unique name. Don’t get carried away—this is not a replacement for managing an entire file with the proper file resource and the optional template.

In Part 2 we’ll cover the validation functions provided by the puppetlabs/stdlib module and how to validate input in your manifests.

In Part 3 we’ll cover the use of facts-dot-d and discover how we can get Facts from external sources and cache them in a central location so Facter can find them.

We’ll round out the mini-series in Part 4 with a look at the remaining functionality by exploring some data functions that allow you to do things like load external data from YAML files and merge parameter values.

Resource Overview - file_line

Resources file_line

Installing the module

Complexity Easy
Installation Time 2 minutes

Installing the puppetlabs/stdlib module is as simple as using the puppet module tool (available as a rubygem on github; and coming soon in Puppet and Puppet Enterprise):

$ puppet config print modulepath
/etc/puppet/modules:/usr/share/puppet/modules

$ cd /etc/puppet/modules
$ puppet-module install puppetlabs/stdlib

You should now have a stdlib directory in your module path.

/etc/puppet/modules/stdlib

Testing the module

The puppetlabs/stdlib module comes with tests—let’s run them.

$ puppet apply tests/init.pp --noop
notice: Finished catalog run in 0.05 seconds

$ puppet apply tests/file_line.pp  --noop
notice: /Stage[main]//File[/tmp/dansfile]/ensure: current_value absent, should be present (noop)
err: /Stage[main]//File_line[dans_line]: Could not evaluate: No such file or directory - /tmp/dansfile
notice: Class[Main]: Would have triggered 'refresh' from 1 events
notice: Stage[main]: Would have triggered 'refresh' from 1 events
notice: Finished catalog run in 0.02 seconds

Hmm, that’s not telling me much. I need to run this test in normal mode to get the full effect. While running tests without --noop is normally a dangerous thing to do, this test only needs to create a file named dansfile under the /tmp directory—a change that won’t affect the state of my system. I’ll confirm this by looking at the code:

cat tests/file_line.pp
# This is a simple smoke test
# of the file_line resource type.
file { '/tmp/dansfile':
  ensure => present
}->
file_line { 'dans_line':
  line => 'dan is awesome',
  path => '/tmp/dansfile',
}

Looks good to me. Lets rerun the test, this time without the --noop flag:

$ puppet apply tests/file_line.pp
notice: /Stage[main]//File[/tmp/dansfile]/ensure: created
notice: /Stage[main]//File_line[dans_line]/ensure: created
notice: Finished catalog run in 0.02 seconds

$ cat /tmp/dansfile
dan is awesome

The test works as expected, and I can confirm that Dan is in fact awesome.

Complexity Easy
Installation Time 0 Minutes

Since file_line is a resource type, there is really nothing to configure here. Once the stdlib module is available in your modulepath, file_line will be automatically distributed and usable as a resource on all of your nodes.

Example usage

When prepping for blog posts, I normally start with a fresh VM and, without fail, forget to add a host entry for my test Puppetmaster to /etc/hosts. This leads to my Puppet agent complaining that it cannot locate its master, reminding me of the obvious mistake. It’s an easy fix. I just add the following line to /etc/hosts:

172.16.240.200  master.dev.puppetlabs.com master

Problem solved! Until next week, that is.

Some of you may be thinking, “Hard code the line above and take a snapshot of the VM.” I will then pretend that I did not just hear you say that. I’ll then remind you that this is a blog about Puppet and there’s obviously a better way to solve this problem. Besides, that approach is less than optimal. I would have to repeat that process for each of my VMs and remember to keep them all updated if things were to change.

Lets put the file_line resource to use.

The current state of my /etc/hosts file looks like this:

cat /etc/hosts
127.0.0.1	localhost
127.0.1.1	pmotw.puppetlabs.com	pmotw

# The following lines are desirable for IPv6 capable hosts
::1     ip6-localhost ip6-loopback
fe00::0 ip6-localnet
ff00::0 ip6-mcastprefix
ff02::1 ip6-allnodes
ff02::2 ip6-allrouters

Notice the missing entry for master.dev.puppetlabs.com?

We’ll skip creating a whole manifests and declare our file_line resource on the node:

$ cat /etc/puppet/manifests/site.pp
node 'pmotw.puppetlabs.com' {
  file_line { 'puppet master host entry':
    ensure => present,
    line   => '172.16.240.200  master.dev.puppetlabs.com	 master',
    path   => '/etc/hosts',
  }
}

Apply the changes.

$ puppet agent -t
...
notice: /Stage[main]//Node[pmotw.puppetlabs.com]/File_line[puppet master host entry]/ensure: created
notice: Finished catalog run in 0.02 seconds

$ cat /etc/hosts
127.0.0.1	localhost
127.0.1.1	pmotw.puppetlabs.com	pmotw

# The following lines are desirable for IPv6 capable hosts
::1     ip6-localhost ip6-loopback
fe00::0 ip6-localnet
ff00::0 ip6-mcastprefix
ff02::1 ip6-allnodes
ff02::2 ip6-allrouters
172.16.240.200 master.dev.puppetlabs.com master

It works, but what happens if I remove that line and rerun Puppet?

$ vim /etc/hosts
remove 172.16.240.200  master.dev.puppetlabs.com    master

$ puppet agent -t
...
notice: /Stage[main]//Node[pmotw.puppetlabs.com]/File_line[puppet master host entry]/ensure: created
notice: Finished catalog run in 0.02 seconds

Puppet does the right thing, and puts it back. The other nice thing about file_line, it continues to work even if I manually add new lines above or below the one being managed:

$ cat /etc/hosts
..
172.16.240.200  master.dev.puppetlabs.com	     master
172.16.240.100  someotherhost.puppetlabs.com  someotherhost

$ puppet agent -t
notice: Finished catalog run in 0.02 seconds

Notice: no changes are being reported.

Conclusion

We’ve only scratched the surface of the puppetlabs/stdlib module. Be sure to join us next week as we cover the validation functions provided by puppetlabs/stdlib which can help make your manifests more resilient to run-time failures by utilizing the ability to validate input; nothing like catching errors before hosing your systems!

Additional Resources:

Share via:
Posted in:

Tried the same for editing /etc/profile
I can see the module - file_line in /etc/puppet/modules
Still i cannot access the resource from the manifests, error being
-------------
Error: Could not retrieve catalog from remote server: Error 400 on SERVER: Puppet::Parser::AST::Resource failed with error ArgumentError: Invalid resource type file_line at /etc/puppet/modules/postgresql/manifests/profilechange1.pp:7 on node sys-server
Please give some pointers to solve this issue

Using Puppet 3.7.4, the command to install it didn't work:
$ puppet-module install puppetlabs/stdlib
Instead I used:
$ puppet module install puppetlabs-stdlib

The content of this field is kept private and will not be shown publicly.

Restricted HTML

  • Allowed HTML tags: <a href hreflang> <em> <strong> <cite> <blockquote cite> <code> <ul type> <ol start type> <li> <dl> <dt> <dd> <h2 id> <h3 id> <h4 id> <h5 id> <h6 id>
  • Lines and paragraphs break automatically.
  • Web page addresses and email addresses turn into links automatically.