puppetlabs/puppet · error · Puppet::Network::FormatHandler::FormatError

Serialized YAML did not contain a collection of instances wh

Error message

Serialized YAML did not contain a collection of instances when calling intern_multiple

What it means

The yaml format's intern_multiple requires the safe_load result to be a collection (respond_to?(:collect)). A syntactically valid YAML document that is a scalar or a single mapping — '--- 42', '--- foo', even a lone instance hash — fails this check and raises FormatError stating a collection is required. The document parsed; its shape is wrong for multi-instance interning.

Source

Thrown at lib/puppet/network/formats.rb:48

      Puppet::Node::Facts,
      Puppet::Node,
      Puppet::Transaction::Report,
      Puppet::Resource,
      Puppet::Resource::Catalog
    ]
  end

  def intern(klass, text)
    data = Puppet::Util::Yaml.safe_load(text, allowed_yaml_classes)
    data_to_instance(klass, data)
  rescue Puppet::Util::Yaml::YamlLoadError => e
    raise Puppet::Network::FormatHandler::FormatError, _("Serialized YAML did not contain a valid instance of %{klass}: %{message}") % { klass: klass, message: e.message }
  end

  def intern_multiple(klass, text)
    data = Puppet::Util::Yaml.safe_load(text, allowed_yaml_classes)
    unless data.respond_to?(:collect)
      raise Puppet::Network::FormatHandler::FormatError, _("Serialized YAML did not contain a collection of instances when calling intern_multiple")
    end

    data.collect do |datum|
      data_to_instance(klass, datum)
    end
  rescue Puppet::Util::Yaml::YamlLoadError => e
    raise Puppet::Network::FormatHandler::FormatError, _("Serialized YAML did not contain a valid instance of %{klass}: %{message}") % { klass: klass, message: e.message }
  end

  def data_to_instance(klass, data)
    return data if data.is_a?(klass)

    unless data.is_a? Hash
      raise Puppet::Network::FormatHandler::FormatError, _("Serialized YAML did not contain a valid instance of %{klass}") % { klass: klass }
    end

    klass.from_data_hash(data)
  end

View on GitHub (pinned to e227c27540)

Solutions

  1. Change the document to a YAML sequence — each item an instance or Hash ('- name: a' entries).
  2. On the producer, dump collections: Puppet::Util::Yaml.dump(items) where items is an Array.
  3. Use intern (convert_from) for genuine single documents.
  4. Add a shape pre-check (respond_to?(:collect)) before calling intern_multiple.

Example fix

# before — widgets.yaml
# ---
# id: 1
# (single mapping → error)

# after
# ---
# - id: 1
# - id: 2
list = Widget.convert_from_multiple(:yaml, File.read('widgets.yaml'))
Defensive patterns

Strategy: validation

Validate before calling

data = Puppet::Util::Yaml.safe_load(text, [])
raise ArgumentError, 'yaml payload must be a sequence of instances' unless data.respond_to?(:collect)
items = Klass.convert_from_multiple(:yaml, text)

Try / catch

begin
  items = Klass.convert_from_multiple(:yaml, text)
rescue Puppet::Network::FormatHandler::FormatError
  # if the cause is 'not a collection', fall back to single interning
  items = [Klass.convert_from(:yaml, text)]
end

Prevention

When it happens

Trigger: Klass.convert_from_multiple(:yaml, '--- foo'); a producer calling YAML.dump(single_object) where the consumer expects YAML.dump([obj1, obj2]); sending a one-element mapping document instead of a sequence.

Common situations: Batch endpoints receiving single-object documents; fixtures written as single documents; producers whose dump path changed from arrays to single objects.

Related errors


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