puppetlabs/puppet · error · Puppet::Pops::Types::StringConverter::FormatError
Illegal format '#{actual}' specified for value of Array type
Error message
Illegal format '#{actual}' specified for value of Array type - expected one of the characters 'asp' What it means
StringConverter raises this FormatError when formatting an Array with a container format letter outside 'asp': 'a' (angle/normal array rendering with per-element formats), 's' (plain to_s style) and 'p' (Puppet-notation, quoted elements). Container formats also carry separator/delimiter options parsed from the format string, but the leading letter itself must be a/s/p; otherwise the else at string_converter.rb:1015 raises FormatError('Array', format.format, 'asp').
Source
Thrown at lib/puppet/pops/types/string_converter.rb:1015
else
buf << sep
# if break on each (and breaking will not occur because next is an array or hash)
# or, if indenting, and previous was an array or hash, then break and continue on next line
# indented.
if (sz_break && !is_a_or_h?(v)) || (format.alt? && i > 0 && is_a_or_h?(val[i - 1]) && !is_a_or_h?(v))
buf.rstrip! unless buf[-1] == "\n"
buf << "\n"
buf << children_indentation.padding
end
end
# remove trailing space added by separator if followed by break
buf.rstrip! if buf[-1] == ' ' && str_val[0] == "\n"
buf << str_val
end
buf << delims[1]
buf
else
raise FormatError.new('Array', format.format, 'asp')
end
end
def is_a_or_h?(x)
x.is_a?(Array) || x.is_a?(Hash)
end
def is_container?(t)
case t
when PArrayType, PHashType, PStructType, PTupleType, PObjectType
true
else
false
end
end
# @api private
def string_PTupleType(val_type, val, format_map, indentation)View on GitHub (pinned to e227c27540)
Solutions
- Use '%a' for array formatting and put element formats in the container options, e.g. String($arr, '%a') or with per-element format via the container syntax
- Use '%s' for simple rendering or '%p' for Puppet-notation output
- Whitelist the container letter against %w[a s p]
Example fix
# before $str = String([1, 2, 3], '%d') # after $str = String([1, 2, 3], '%a')
Defensive patterns
Strategy: validation
Validate before calling
fmt = '%d'
letter = fmt[/\A%[#\-+ 0\d.]*([a-zA-Z])\z/, 1]
raise ArgumentError, "#{fmt} invalid for Array (container letter must be a/s/p)" unless %w[a s p].include?(letter) Prevention
- Use %a as the array container letter and express element formats in the container options
- Prefer join() when you only need a flat string
- Distinguish container formats from element formats in shared format configuration
When it happens
Trigger: `String([1,2,3], '%d')` — applying a scalar format as the container letter; in general any `String($array, '<letter>...')` where the letter is not a/s/p. Note per-element formats are specified inside the container format (e.g. '%(d, )' style); putting the element format first is the classic mistake.
Common situations: Rendering lists into templates/logs and reusing an element format as the top-level letter; upgrading code from join() to String() with formats and misplacing the letters.
Related errors
- Illegal format '#{actual}' specified for value of Object typ
- Illegal format '#{actual}' specified for value of Runtime ty
- Illegal format '#{actual}' specified for value of Default ty
- Illegal format '#{actual}' specified for value of Undef type
- Illegal format '#{actual}' specified for value of Boolean ty
AI-assisted analysis of puppetlabs/puppet@e227c27540 (2026-08-21).
Data as JSON: /api/errors/cc5d2f1d3dfc147e.
Report an issue: GitHub.