Centos – Puppet – Call custom function (which contains case/when) from manifest

centospuppetruby

I am working on puppetizing my httpd and nginx vhost confs. Right now I have 5 servers which each have their own port and are run on server1, while nginx is running on server2. Obviously I need to keep the manifest calls to httpd and nginx separate because they can be run on different servers.

What I am trying to do is share the ports between both manifests, so all I need to do is pass in the name of the vhost I want, to either httpd, and nginx and it will lookup the port in a central location. I am trying to implement a custom function and currently have it setup like this:

# /path/to/puppet/modules/global/lib/puppet/parser/functions/app_to_port.rb
module Puppet::Parser::Functions
    newfunction(:app_to_port, :type => :rvalue) do |args|
        case args[0]
            when app_1
                return 27960
            when app_2
                return 27961
        end
    end
end

# /path/to/puppet/modules/httpd/manifests/vhost/conf.pp

...

$vhost_port = app_to_port($name)

...

I keep running into various issues, with $name I keep getting undefined local variable or method 'app_1' errors, and if I pass in an int, the $vhost_port variable never gets a value. I'm new to ruby and puppet, which leads me to believe I am missing some language or app construct. I ran ruby -rpuppet /path/to/app_to_port.rb with no response, which leads me to believe that the code is syntactically correct.

For the record, I was reading up on http://docs.puppetlabs.com/guides/custom_functions.html and https://stackoverflow.com/questions/948135/how-to-write-a-switch-statement-in-ruby to get me to this point.

Current env: ruby 1.8.7 and puppet 2.7.19

Best Answer

Hiera is included in Puppet 3.0 - in 2.7, you'll need to install it separately on your masters.

Since it sounds like you'll want the mapping to be global, you'll want to put it in a Hiera file that applies to all systems. So in your hiera.yaml, you'll want something like..

:backends:
  - yaml

:hierarchy:
  - common

:yaml:
   :datadir: /etc/puppet/hieradata

Then in /etc/puppet/hieradata/common.yaml, set up your port mappings:

port_app_1: "27960"
port_app_2: "27961"

With that in place, you can look it up in your vhost config.

$vhost_port = hiera("port_${name}")