puppetlabs/puppet · error · ArgumentError
field 'data_provider' must be a string
Error message
field 'data_provider' must be a string
What it means
The non-String branch of Puppet::ModuleTool::Metadata#validate_data_provider: the legacy 'data_provider' field in metadata.json must be a string, and anything else — number, boolean, array, object, null-as-value — raises ArgumentError at line 216. It is a type check rather than a format check.
Source
Thrown at lib/puppet/module_tool/metadata.rb:216
raise ArgumentError, _("Invalid 'version' field in metadata.json: %{err}") % { err: err }
end
# Validates that the given _value_ is a symbolic name that starts with a letter
# and then contains only letters, digits, or underscore. Will raise an ArgumentError
# if that's not the case.
#
# @param value [Object] The value to be tested
def validate_data_provider(value)
if value.is_a?(String)
unless value =~ /^[a-zA-Z][a-zA-Z0-9_]*$/
if value =~ /^[a-zA-Z]/
raise ArgumentError, _("field 'data_provider' contains non-alphanumeric characters")
else
raise ArgumentError, _("field 'data_provider' must begin with a letter")
end
end
else
raise ArgumentError, _("field 'data_provider' must be a string")
end
end
# Validates that the version range can be parsed by Semantic.
def validate_version_range(version_range)
SemanticPuppet::VersionRange.parse(version_range)
rescue ArgumentError => e
raise ArgumentError, _("Invalid 'version_range' field in metadata.json: %{err}") % { err: e }
end
end
end
View on GitHub (pinned to e227c27540)
Solutions
- Quote the value so it is a JSON string: "data_provider": "hiera"
- If the field is meaningless for your module, delete it
- Lint the file: `python -m json.tool metadata.json` or a JSON schema validator to catch type mistakes
Example fix
// before - metadata.json "data_provider": 42, // after "data_provider": "hiera",
Defensive patterns
Strategy: type-guard
Validate before calling
value = JSON.parse(File.read('metadata.json'))['data_provider']
abort "data_provider must be a string, got #{value.class}" unless value.nil? || value.is_a?(String) Type guard
# Ruby predicate acting as a type guard before parsing module_provider_string?(v) = v.is_a?(String) && v.match?(/\A[a-zA-Z][a-zA-Z0-9_]*\Z/) # usage raise ArgumentError, 'data_provider must be a string' unless module_data_provider.nil? || module_provider_string?(module_data_provider)
Try / catch
begin
Puppet::ModuleTool::Metadata.from_hash('data_provider' => raw)
rescue ArgumentError => e
raise unless e.message =~ /data_provider.*must be a string/
raw = raw.to_s # coerce numbers/booleans from loose templates, then retry
retry
end Prevention
- Quote data_provider values in JSON templates; never interpolate unquoted Ruby values
- Parse with strict JSON tooling (python -m json.tool, jq) to catch type mistakes early
- Omit the field if the module does not use a custom data provider
When it happens
Trigger: A metadata.json containing "data_provider": 42, "data_provider": true, or "data_provider": ["hiera"] — the is_a?(String) test fails and line 216 raises.
Common situations: Generator templates interpolating a Ruby symbol or integer unquoted into JSON; YAML config reused as JSON with unquoted values; copy-paste from documentation showing enum-like values.
Related errors
- field 'data_provider' contains non-alphanumeric characters
- field 'data_provider' must begin with a letter
- Dependency conflict for %{module_name}: Dependency %{name} w
- Invalid 'name' field in metadata.json: %{err}
- Invalid 'version' field in metadata.json: %{err}
AI-assisted analysis of puppetlabs/puppet@e227c27540 (2026-08-21).
Data as JSON: /api/errors/54b5e329819aaa1d.
Report an issue: GitHub.