"Prerelease version constraints are not supported: %s. Remove the prerelease information from the constraint. Prerelease versions of terraform will match constraints using their version core only.",
required.String()),
Subject:constraint.DeclRange.Ptr(),
})
}
}
iflen(prereleaseDiags)>0{
// There were some prerelease fields in the constraints. Don't check the constraints as they will
// fail, and populate the diagnostics for these constraints with the prerelease diagnostics.
diags=diags.Extend(prereleaseDiags)
continue
}
if!constraint.Required.Check(tfversion.SemVer){
switch{
caselen(path)==0:
diags=diags.Append(&hcl.Diagnostic{
Severity:hcl.DiagError,
Summary:"Unsupported Terraform Core version",
Detail:fmt.Sprintf(
"This configuration does not support Terraform version %s. To proceed, either choose another supported Terraform version or update this version constraint. Version constraints are normally set for good reason, so updating the constraint may lead to other errors or unexpected behavior.",
tfversion.String(),
),
Subject:constraint.DeclRange.Ptr(),
})
default:
diags=diags.Append(&hcl.Diagnostic{
Severity:hcl.DiagError,
Summary:"Unsupported Terraform Core version",
Detail:fmt.Sprintf(
"Module %s (from %s) does not support Terraform version %s. To proceed, either choose another supported Terraform version or update this version constraint. Version constraints are normally set for good reason, so updating the constraint may lead to other errors or unexpected behavior.",
Detail:fmt.Sprintf("Module %q (declared at %s line %d) has invalid version constraint %q: %s.",callName,call.Pos.Filename,call.Pos.Line,call.Version,err),
Detail:fmt.Sprintf("Module %q (declared at %s line %d) has invalid source address %q: %s.\n\nTerraform assumed that you intended a module registry source address because you also set the argument \"version\", which applies only to registry modules.",callName,call.Pos.Filename,call.Pos.Line,call.Source,err),
fmt.Sprintf("The requested module %q refers to a module via its parent directory. To use this as a new root module this source string must be rewritten as a remote source address, such as %q.",sourceAddr,newAddr),
fmt.Sprintf("The requested module %q refers to a module via its parent directory. To use this as a new root module this source string must be rewritten as a remote source address, such as %q.",sourceAddrStr,newAddr),
@ -255,12 +297,13 @@ func (i *ModuleInstaller) installLocalModule(req *earlyconfig.ModuleRequest, key
panic(fmt.Errorf("missing manifest record for parent module %s",parentKey))
}
iflen(req.VersionConstraints)!=0{
diags=diags.Append(tfdiags.Sourceless(
tfdiags.Error,
"Invalid version constraint",
fmt.Sprintf("Cannot apply a version constraint to module %q (at %s:%d) because it has a relative local path.",req.Name,req.CallPos.Filename,req.CallPos.Line),
))
iflen(req.VersionConstraint.Required)!=0{
diags=diags.Append(&hcl.Diagnostic{
Severity:hcl.DiagError,
Summary:"Invalid version constraint",
Detail:fmt.Sprintf("Cannot apply a version constraint to module %q (at %s:%d) because it has a relative local path.",req.Name,req.CallRange.Filename,req.CallRange.Start.Line),
Subject:req.CallRange.Ptr(),
})
}
// For local sources we don't actually need to modify the
@ -272,25 +315,31 @@ func (i *ModuleInstaller) installLocalModule(req *earlyconfig.ModuleRequest, key
// it is possible that the local directory is a symlink
newDir,err:=filepath.EvalSymlinks(newDir)
iferr!=nil{
diags=diags.Append(tfdiags.Sourceless(
tfdiags.Error,
"Unreadable module directory",
fmt.Sprintf("Unable to evaluate directory symlink: %s",err.Error()),
))
diags=diags.Append(&hcl.Diagnostic{
Severity:hcl.DiagError,
Summary:"Unreadable module directory",
Detail:fmt.Sprintf("Unable to evaluate directory symlink: %s",err.Error()),
})
}
mod,mDiags:=earlyconfig.LoadModule(newDir)
// Finally we are ready to try actually loading the module.
fmt.Sprintf("Module %q (from %s:%d) cannot be found in the module registry at %s.",req.Name,req.CallPos.Filename,req.CallPos.Line,hostname),
))
diags=diags.Append(&hcl.Diagnostic{
Severity:hcl.DiagError,
Summary:"Module not found",
Detail:fmt.Sprintf("Module %q (from %s:%d) cannot be found in the module registry at %s.",req.Name,req.CallRange.Filename,req.CallRange.Start.Line,hostname),
Subject:req.CallRange.Ptr(),
})
}elseiferrors.Is(err,context.Canceled){
diags=diags.Append(tfdiags.Sourceless(
tfdiags.Error,
"Module installation was interrupted",
fmt.Sprintf("Received interrupt signal while retrieving available versions for module %q.",req.Name),
))
diags=diags.Append(&hcl.Diagnostic{
Severity:hcl.DiagError,
Summary:"Module installation was interrupted",
Detail:fmt.Sprintf("Received interrupt signal while retrieving available versions for module %q.",req.Name),
})
}else{
diags=diags.Append(tfdiags.Sourceless(
tfdiags.Error,
"Error accessing remote module registry",
fmt.Sprintf("Failed to retrieve available versions for module %q (%s:%d) from %s: %s.",req.Name,req.CallPos.Filename,req.CallPos.Line,hostname,err),
))
diags=diags.Append(&hcl.Diagnostic{
Severity:hcl.DiagError,
Summary:"Error accessing remote module registry",
Detail:fmt.Sprintf("Failed to retrieve available versions for module %q (%s:%d) from %s: %s.",req.Name,req.CallRange.Filename,req.CallRange.Start.Line,hostname,err),
// Should never happen, but since this is a remote service that may
// be implemented by third-parties we will handle it gracefully.
diags=diags.Append(tfdiags.Sourceless(
tfdiags.Error,
"Invalid response from remote module registry",
fmt.Sprintf("The registry at %s returned an invalid response when Terraform requested available versions for module %q (%s:%d).",hostname,req.Name,req.CallPos.Filename,req.CallPos.Line),
))
diags=diags.Append(&hcl.Diagnostic{
Severity:hcl.DiagError,
Summary:"Invalid response from remote module registry",
Detail:fmt.Sprintf("The registry at %s returned an invalid response when Terraform requested available versions for module %q (%s:%d).",hostname,req.Name,req.CallRange.Filename,req.CallRange.Start.Line),
// Should never happen if the registry server is compliant with
// the protocol, but we'll warn if not to assist someone who
// might be developing a module registry server.
diags=diags.Append(tfdiags.Sourceless(
tfdiags.Warning,
"Invalid response from remote module registry",
fmt.Sprintf("The registry at %s returned an invalid version string %q for module %q (%s:%d), which Terraform ignored.",hostname,mv.Version,req.Name,req.CallPos.Filename,req.CallPos.Line),
))
diags=diags.Append(&hcl.Diagnostic{
Severity:hcl.DiagWarning,
Summary:"Invalid response from remote module registry",
Detail:fmt.Sprintf("The registry at %s returned an invalid version string %q for module %q (%s:%d), which Terraform ignored.",hostname,mv.Version,req.Name,req.CallRange.Filename,req.CallRange.Start.Line),
log.Printf("[WARN] ModuleInstaller: %s ignoring %s because the version constraints (%s) could not be parsed: %s",key,v,req.VersionConstraints.String(),err.Error())
log.Printf("[WARN] ModuleInstaller: %s ignoring %s because the version constraints (%s) could not be parsed: %s",key,v,req.VersionConstraint.Required.String(),err.Error())
fmt.Sprintf("Module %q (%s:%d) has no versions available on %s.",addr,req.CallPos.Filename,req.CallPos.Line,hostname),
))
diags=diags.Append(&hcl.Diagnostic{
Severity:hcl.DiagError,
Summary:"Module has no versions",
Detail:fmt.Sprintf("Module %q (%s:%d) has no versions available on %s.",addr,req.CallRange.Filename,req.CallRange.Start.Line,hostname),
Subject:req.CallRange.Ptr(),
})
returnnil,nil,diags
}
iflatestMatch==nil{
diags=diags.Append(tfdiags.Sourceless(
tfdiags.Error,
"Unresolvable module version constraint",
fmt.Sprintf("There is no available version of module %q (%s:%d) which matches the given version constraint. The newest available version is %s.",addr,req.CallPos.Filename,req.CallPos.Line,latestVersion),
))
diags=diags.Append(&hcl.Diagnostic{
Severity:hcl.DiagError,
Summary:"Unresolvable module version constraint",
Detail:fmt.Sprintf("There is no available version of module %q (%s:%d) which matches the given version constraint. The newest available version is %s.",addr,req.CallRange.Filename,req.CallRange.Start.Line,latestVersion),
fmt.Sprintf("Module registry %s returned invalid source location %q for %s %s: must be a direct remote package address.",hostname,realAddrRaw,addr,latestMatch),
))
diags=diags.Append(&hcl.Diagnostic{
Severity:hcl.DiagError,
Summary:"Invalid package location from module registry",
Detail:fmt.Sprintf("Module registry %s returned invalid source location %q for %s %s: must be a direct remote package address.",hostname,realAddrRaw,addr,latestMatch),
// Report up to the caller that we're about to start downloading.
addr:=req.SourceAddr.(addrs.ModuleSourceRemote)
packageAddr:=addr.Package
hooks.Download(key,packageAddr.String(),nil)
iflen(req.VersionConstraints)!=0{
diags=diags.Append(tfdiags.Sourceless(
tfdiags.Error,
"Invalid version constraint",
fmt.Sprintf("Cannot apply a version constraint to module %q (at %s:%d) because it doesn't come from a module registry.",req.Name,req.CallPos.Filename,req.CallPos.Line),
))
iflen(req.VersionConstraint.Required)!=0{
diags=diags.Append(&hcl.Diagnostic{
Severity:hcl.DiagError,
Summary:"Invalid version constraint",
Detail:fmt.Sprintf("Cannot apply a version constraint to module %q (at %s:%d) because it doesn't come from a module registry.",req.Name,req.CallRange.Filename,req.CallRange.Start.Line),
suggestion="\n\nTerraform treats absolute filesystem paths as external modules which establish a new module package. To treat this directory as part of the same package as its caller, use a local path starting with either \"./\" or \"../\"."
"The given source directory for %s would be outside of its containing package %q. Local source addresses starting with \"../\" must stay within the same package that the calling module belongs to.%s",
"This configuration does not support Terraform version %s. To proceed, either choose another supported Terraform version or update this version constraint. Version constraints are normally set for good reason, so updating the constraint may lead to other errors or unexpected behavior.",
tfversion.String(),
),
Subject:constraint.DeclRange.Ptr(),
})
default:
diags=diags.Append(&hcl.Diagnostic{
Severity:hcl.DiagError,
Summary:"Unsupported Terraform Core version",
Detail:fmt.Sprintf(
"Module %s (from %s) does not support Terraform version %s. To proceed, either choose another supported Terraform version or update this version constraint. Version constraints are normally set for good reason, so updating the constraint may lead to other errors or unexpected behavior.",
"Prerelease version constraints are not supported: %s. Remove the prerelease information from the constraint. Prerelease versions of terraform will match constraints using their version core only.",
required.String()),
Subject:constraint.DeclRange.Ptr(),
})
}
}
iflen(prereleaseDiags)>0{
// There were some prerelease fields in the constraints. Don't check the constraints as they will
// fail, and populate the diagnostics for these constraints with the prerelease diagnostics.
diags=diags.Append(prereleaseDiags)
continue
}
if!constraint.Required.Check(tfversion.SemVer){
switch{
caselen(config.Path)==0:
diags=diags.Append(&hcl.Diagnostic{
Severity:hcl.DiagError,
Summary:"Unsupported Terraform Core version",
Detail:fmt.Sprintf(
"This configuration does not support Terraform version %s. To proceed, either choose another supported Terraform version or update this version constraint. Version constraints are normally set for good reason, so updating the constraint may lead to other errors or unexpected behavior.",
tfversion.String(),
),
Subject:constraint.DeclRange.Ptr(),
})
default:
diags=diags.Append(&hcl.Diagnostic{
Severity:hcl.DiagError,
Summary:"Unsupported Terraform Core version",
Detail:fmt.Sprintf(
"Module %s (from %s) does not support Terraform version %s. To proceed, either choose another supported Terraform version or update this version constraint. Version constraints are normally set for good reason, so updating the constraint may lead to other errors or unexpected behavior.",