Skip to content

[Bug]: using Deferred values in group resources fails when preprocess_deferred = false #213

@qralston

Description

@qralston

Is this a critical security issue?

  • This is not a security issue.

Describe the Bug

We have a locally-written mock module, which contains the following Puppet code:

group { 'mock':
  ensure          => present,
  require         => Package['mock'],
  members         => Deferred('mock::expand_groups', [$users]),
  forcelocal      => true,
  system          => true,
  auth_membership => $users_authoritative,
}

The mock::expand_groups() function expands any users in $users that are actually groups. We use this to work around the limitation that Unix groups don’t permit nested groups.

If the preprocess_deferred option is overridden to true in the agent configuration, this works exactly as one would expect.

However, if the preprocess_deferred option is not overridden to true in the agent configuration (the default is false), applying the resource fails:

Info: Refreshing CA certificate
Info: CA certificate is unmodified, using existing CA certificate
Info: Refreshing CRL
Info: CRL is unmodified, using existing CRL
Info: Using environment 'beta'
Info: Retrieving pluginfacts
Info: Retrieving plugin
Info: Loading facts
Notice: Requesting catalog from puppet-beta.example.org:8140 (100.64.1.1)
Notice: Catalog compiled by server.example.org
Info: Caching catalog for client.example.org
Info: Applying configuration version '1757728064'
Error: undefined method `split' for #<Puppet::Pops::Evaluator::DeferredValue:0x00007fdfa075ffd0 @proc=#<Proc:0x00007fdfa0730050 /opt/puppetlabs/puppet/lib/ruby/vendor_ruby/puppet/pops/evaluator/deferred_resolver.rb:210>>
Error: /Stage[main]/Mock/Group[mock]/members: change from user1@example.org to #<Puppet::Pops::Evaluator::DeferredValue:0x00007fdfa075ffd0> failed: undefined method `split' for #<Puppet::Pops::Evaluator::DeferredValue:0x00007fdfa075ffd0 @proc=#<Proc:0x00007fdfa0730050 /opt/puppetlabs/puppet/lib/ruby/vendor_ruby/puppet/pops/evaluator/deferred_resolver.rb:210>> (corrective)
Notice: Applied catalog in 7.70 seconds

After searching, I discovered issue #189, which didn’t seem to be related. But when I tested with preprocess_deferred = true, this error did not occur, and the agent updated the group membership successfully.

In Puppet Functions: An Overview + Key Updates, this paragraph appears:

As of Puppet 7.17, functions can now be lazily evaluated with the new preprocess_deferred setting. This instructs the agent to resolve deferred functions during enforcement instead of before. In other words, if you use standard Puppet relationships to ensure that tooling is managed prior to classes or resources that use the deferred functions using that tooling, then it will operate as expected and the function will execute properly.

And later, towards the end of the blog post:

Set preprocess_deferred when your functions depend on tooling installed by the Puppet run.

If I’m doing something wrong here, it’s not obvious to me what my error is. I know how to order Puppet resources, but none of the documentation on deferred functions that I have read explains how to declare to the agent that this specific group resource requires the mock::expand_groups function.

Is my Puppet code wrong? Or is this a bug with preprocess_deferred = false (the default value)?

Expected Behavior

I expected the agent to correctly apply the catalog, regardless of whether the preprocess_deferred option is true or false.

Steps to Reproduce

Attempting to define a group resource that uses a deferred function to expand the members parameter, when the preprocess_deferred option is set to false, should reproduce the issue.

Environment

Version: 8.23.1
Platform: Red Hat Enterprise Linux 9

Additional Context

No response

Relevant log output

Metadata

Metadata

Assignees

No one assigned

    Labels

    bugSomething isn't working

    Type

    No type

    Projects

    No projects

    Milestone

    No milestone

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions