hashicorp/terraform · error
Must provide one of 'source' or 'content'
Error message
Must provide one of 'source' or 'content'
What it means
Validation diagnostic from the 'file' provisioner when both 'source' and 'content' are null. Because 'destination' is Required but the payload to copy is missing, the provisioner has nothing to transfer.
Source
Thrown at internal/builtin/provisioners/file/resource_provisioner.go:72
resp.Provisioner = schema
return resp
}
func (p *provisioner) ValidateProvisionerConfig(req provisioners.ValidateProvisionerConfigRequest) (resp provisioners.ValidateProvisionerConfigResponse) {
cfg, err := p.GetSchema().Provisioner.CoerceValue(req.Config)
if err != nil {
resp.Diagnostics = resp.Diagnostics.Append(err)
}
source := cfg.GetAttr("source")
content := cfg.GetAttr("content")
switch {
case !source.IsNull() && !content.IsNull():
resp.Diagnostics = resp.Diagnostics.Append(errors.New("Cannot set both 'source' and 'content'"))
return resp
case source.IsNull() && content.IsNull():
resp.Diagnostics = resp.Diagnostics.Append(errors.New("Must provide one of 'source' or 'content'"))
return resp
}
return resp
}
func (p *provisioner) ProvisionResource(req provisioners.ProvisionResourceRequest) (resp provisioners.ProvisionResourceResponse) {
if req.Connection.IsNull() {
resp.Diagnostics = resp.Diagnostics.Append(tfdiags.WholeContainingBody(
tfdiags.Error,
"file provisioner error",
"Missing connection configuration for provisioner.",
))
return resp
}
comm, err := communicator.New(req.Connection)
if err != nil {View on GitHub (pinned to c9def3e214)
Solutions
- Provide exactly one of 'source' (path to a local file) or 'content' (inline string).
- If the file provisioner is optional, use a dynamic/count = 0 block instead of leaving both fields null.
Example fix
// before
provisioner "file" {
destination = "/etc/app.conf"
}
// after
provisioner "file" {
content = "raw config"
destination = "/etc/app.conf"
} Defensive patterns
Strategy: validation
Validate before calling
# Ensure at least one of source/content is provided:
terraform validate
# For dynamic provisioners, gate on the variable being set:
# dynamic "provisioner" { for_each = var.content == null ? [] : [1] ... } Prevention
- Default variables used for source/content to a concrete value, not null.
- Use count = 0 on the resource when the provisioner has nothing to copy.
- Validate configuration in CI before provisioning.
When it happens
Trigger: A provisioner "file" block omits both 'source' and 'content', or sets them both to null via a variable whose value is empty.
Common situations: Conditionally setting source/content through a variable that resolves to null; leftover placeholder block during refactoring.
Related errors
- Cannot set both 'source' and 'content'
- source and content cannot both be null
- invalid null string in 'scripts'
- invalid empty string in 'scripts'
- invalid empty string in 'script'
AI-assisted analysis of hashicorp/terraform@c9def3e214 (2026-08-07).
Data as JSON: /api/errors/08591432c6a06487.
Report an issue: GitHub.