puppetlabs/puppet · error · Puppet::Error

"%{value}" is not a positive integer: the timeout parameter

Error message

"%{value}" is not a positive integer: the timeout parameter must be specified as a positive integer

What it means

The service `timeout` parameter (seconds Puppet waits when syncing service properties, for providers with configurable_timeout) munges the value with to_i and requires the result to be >= 1, else Puppet::Error (lib/puppet/type/service.rb:285). Because of the to_i cast, non-numeric strings like 'soon' become 0 and also surface as "not a positive integer".

Source

Thrown at lib/puppet/type/service.rb:285

        the init script's `stop` and `start` commands will be used."
      newvalues(:true, :false)
    end

    newparam(:manifest) do
      desc "Specify a command to config a service, or a path to a manifest to do so."
    end

    newparam(:timeout, :required_features => :configurable_timeout) do
      desc "Specify an optional minimum timeout (in seconds) for puppet to wait when syncing service properties"
      defaultto { provider.respond_to?(:default_timeout) ? provider.default_timeout : 10 }

      munge do |value|
        value = value.to_i
        raise if value < 1

        value
      rescue
        raise Puppet::Error, _("\"%{value}\" is not a positive integer: the timeout parameter must be specified as a positive integer") % { value: value }
      end
    end

    # Basically just a synonym for restarting.  Used to respond
    # to events.
    def refresh
      # Only restart if we're actually running
      if (@parameters[:ensure] || newattr(:ensure)).retrieve == :running
        provider.restart
      else
        debug "Skipping restart; service is not running"
      end
    end

    def self.needs_ensure_retrieved
      false
    end

View on GitHub (pinned to e227c27540)

Solutions

  1. Set a positive integer (e.g. timeout => 60)
  2. Fix the upstream data (Hiera/ENC) that supplies 0 or non-numeric values
  3. Validate/cast in the wrapper: fail fast on timeout < 1

Example fix

# before
service { 'mysvc':
  ensure  => running,
  timeout => 0,
}

# after
service { 'mysvc':
  ensure  => running,
  timeout => 60,
}
Defensive patterns

Strategy: validation

Validate before calling

if $timeout != undef and !($timeout =~ /\A\d+\z/ and Integer($timeout) >= 1) {
  fail('service timeout must be a positive integer')
}

Type guard

def valid_timeout?(v)
  n = v.to_i
  v.is_a?(Integer) ? v >= 1 : (v.is_a?(String) && v =~ /\A\d+\z/ && n >= 1)
end

Try / catch

begin
  Puppet::Type.type(:service).new(name: 'mysvc', timeout: 0)
rescue Puppet::Error => e
  raise unless e.message.include?('positive integer')
  # clamp to a sane minimum (e.g. 10) and rebuild
end

Prevention

When it happens

Trigger: `service { 'svc': timeout => 0 }`; `timeout => -1`; `timeout => 'soon'` ('soon'.to_i == 0); data-driven values computed as 0.

Common situations: Hiera defaults of 0 meaning 'no wait'; numeric strings from ENC/external data; arithmetic producing 0 or negatives.

Understand the failure class

Related errors


AI-assisted analysis of puppetlabs/puppet@e227c27540 (2026-08-21). Data as JSON: /api/errors/b80b8154000adaab. Report an issue: GitHub.