On Sunday, May 25, 2014 6:16:28 PM UTC-5, Jesse Cotton wrote:
>
> I am new to puppet and decided to really get my feet wet by writing a 
> duplicity module (https://github.com/JCotton1123/puppet-duplicity.git). I 
> am struggling to deal with the fact that variables are immutable and cannot 
> be reassigned (within the same scope). This has become a real issue while 
> trying to dynamically build hashes and arrays that reflect the options and 
> flags that are passed to duplicity. I opted for this approach b/c it makes 
> composition easier and it results in a very clean template definition. For 
> example,
>
> ```
>
>   <%- @_flags.each do |flag| -%>
>   <%= flag -%> \
>   <%- end -%>
>   <%- @_options.each do |key,val| -%>
>   <%= key -%> <%= val -%> \
>   <%- end -%>
> ```
>
>
> As opposed to checking for the existence of a dozen different variables 
> and outputting their values if they have a "good" value.
>
> How do others work around this issue? I am looking at this the wrong way?
>


Well, yes, in a sense you are looking at it the wrong way.   Regardless of 
your reasons for wanting to use an approach that relies on dynamically 
building hashes and arrays, no such approach can work altogether smoothly 
in Puppet.  It's like the guy who went to the doctor, complaining that his 
head hurt whenever he hit it with a hammer.

Puppet has good reasons for immutable variables.  If you want mutable ones, 
then your only alternative is to move your computation out of DSL.  The 
easiest avenues for that are templates and custom functions.  Of the two, I 
would think the latter is preferable for your case, at least if the 
constructed composite data objects must persist beyond the evaluation of 
one template.  On the other hand, if you only need them once, for creating 
one config file, say, then you can do that in a code block at the top of 
your template, and then use the result later.

There are other alternatives, too, most of them probably worse.  For 
example, you could use a chain of defined types or classes to build up your 
data objects in functional programming style.  Or you could use a template 
to build a string representation of your composite object, and then split() 
it into an array, and, if appropriate, convert it into a hash from there.  
No doubt there are others.  PuppetLabs's add-in "stdlib" module has some 
functions that could be applied to such tasks.

Another option is to go in an altogether different direction.  Require the 
data to be fed to your class in a form that is easy for it to digest, and 
have your templates use it as the class receives it.

In between, you have the option to make your DSL code a lot cleaner and 
easier at the expense of making your template a little messier.  For 
example:

myclass.pp
----
class mymodule::myclass($param1 = 'NOT SET', $param2 = 'NOT SET', $param3 = 
'NOT SET') {
  $params = {
    'param1' => $param1,
    'param2' => $param2,
    'param3' => $param3,
  }
  template('mytemplate.erb')
}


mytemplate.erb:
----
<%
  @params.each do |key, value|
    next if value == 'NOT SET'
%><%= key %> = <%= value %>  <%
  end
%>


That is, build the data object unconditionally, in such a way that it can 
be easily filtered when it is processed.


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 puppet-users+unsubscr...@googlegroups.com.
To view this discussion on the web visit 
https://groups.google.com/d/msgid/puppet-users/b9ee3363-0637-4e62-aafe-9e3ece798dcb%40googlegroups.com.
For more options, visit https://groups.google.com/d/optout.

Reply via email to