Issue #1427 has been updated by daniel.

Adam Jacob proposes:

I've done a bit of digging in the template class, and I think you might be able 
to
refactor it thusly:

Look up all the variables in @scope, and turn them in to instance_variables of 
the
template wrapper class.  This would let you do:

<%= @operatingsystem == "foo" %>

Instead of the current

<%= @operatingsystem == "foo" %>

If you really want to have local variables, we could do the same thing within a 
lambda,
and use that as the binding:

<%= operatingsystem == "foo" %>

That would eliminate the need for the method_missing entirely.

You'll be looking in templatewrapper.rb, and @scope is in scope.rb. 

Something like, and this is from the top of my head, in templatewrapper.rb:

@scope.each_variable do |k|
  self.instance_variable_set("@#{k}".to_sym, @scope.lookupvar(k))
end

Would do the trick for @variable.

Adam

----------------------------------------
Refactor #1427: using missing_method for variable looking in TemplateWrapper 
allows trivial conflicts with built-in methods such as 'Kernel#fork'
http://reductivelabs.com/redmine/issues/show/1427

Author: daniel
Status: Unreviewed
Priority: Normal
Assigned to: 
Category: 
Target version: 


G'day.

I have encountered what I think is a problem with template expansion as
part of puppet, and wanted to confirm that my understanding is correct
that this is a bug -- or identify how to work around it.

So, I have created a class (with define) to represent a new
configuration file that I am managing.  One of the options in the
configuration file is 'fork', for better or worse.

So, using define I have, roughly, the following:

test.pp:

define foo ($fork = "yes") {
  file { "/tmp/output.txt": content => template("test.erb") }
}
node myhost { foo { "bar": } }

test.erb:
<%= fork.class %>
<%= fork %>


The output is 'Fixnum' and a PID on my machine, because ERB resolves the
variable into the kernel method 'fork', forks the puppet process, and
returns that PID to the parent.  Ouch.

The same can be demonstrated with 'object_id' in the ERB file, which is
never resolved to an object_id variable no matter what.


Sadly, according to the puppet documentation this should all work, but
it doesn't.  Worse, the root cause is the implementation of the template
wrapper, which is all ... exciting:

lib/puppet/parser/templatewrapper.rb:32 says:
    # Ruby treats variables like methods, so we can cheat here and
    # trap missing vars like they were missing methods.
    def method_missing(name, *args)

Darn!  This is never going to work if the ERB code is evaluated in an
environment where Kernel is visible, and I don't believe Ruby allows us
to create a new execution environment where that isn't the case. :?

(We could, in theory, clone the default Binding, excise everything from
 it, then insert the ERB code and anything it depends on, including the
 Kernel object, at which point we face the same problem.  Yay!)



----------------------------------------
You have received this notification because you have either subscribed to it, 
or are involved in it.
To change your notification preferences, please click here: 
http://reductivelabs.com/redmine/my/account

--~--~---------~--~----~------------~-------~--~----~
You received this message because you are subscribed to the Google Groups 
"Puppet Bugs" group.
To post to this group, send email to [email protected]
To unsubscribe from this group, send email to [EMAIL PROTECTED]
For more options, visit this group at 
http://groups.google.com/group/puppet-bugs?hl=en
-~----------~----~----~----~------~----~------~--~---

Reply via email to