{"record":{"id":"01d536550f940f41","repo":"hashicorp/terraform","slug":"provider-s-locked-version-selection-s-doesn-t-m","errorCode":null,"errorMessage":"provider %s: locked version selection %s doesn't match the updated version constraints %q","messagePattern":"provider (.+?): locked version selection (.+?) doesn't match the updated version constraints %q","errorType":"validation","errorClass":null,"httpStatus":null,"severity":"error","filePath":"internal/configs/config.go","lineNumber":312,"sourceCode":"\t\t\tcontinue\n\t\t}\n\n\t\tselectedVersion := lock.Version()\n\t\tallowedVersions := providerreqs.MeetingConstraints(constraints)\n\t\tlog.Printf(\"[TRACE] Config.VerifyDependencySelections: provider %s has %s to satisfy %q\", providerAddr, selectedVersion.String(), providerreqs.VersionConstraintsString(constraints))\n\t\tif !allowedVersions.Has(selectedVersion) {\n\t\t\t// The most likely cause of this is that the author of a module\n\t\t\t// has changed its constraints, but this could also happen in\n\t\t\t// some other unusual situations, such as the user directly\n\t\t\t// editing the lock file to record something invalid. We'll\n\t\t\t// distinguish those cases here in order to avoid the more\n\t\t\t// specific error message potentially being a red herring in\n\t\t\t// the edge-cases.\n\t\t\tcurrentConstraints := providerreqs.VersionConstraintsString(constraints)\n\t\t\tlockedConstraints := providerreqs.VersionConstraintsString(lock.VersionConstraints())\n\t\t\tswitch {\n\t\t\tcase currentConstraints != lockedConstraints:\n\t\t\t\terrs = append(errs, fmt.Errorf(\"provider %s: locked version selection %s doesn't match the updated version constraints %q\", providerAddr, selectedVersion.String(), currentConstraints))\n\t\t\tdefault:\n\t\t\t\terrs = append(errs, fmt.Errorf(\"provider %s: version constraints %q don't match the locked version selection %s\", providerAddr, currentConstraints, selectedVersion.String()))\n\t\t\t}\n\t\t}\n\t}\n\n\t// Return multiple errors in an arbitrary-but-deterministic order.\n\tsort.Slice(errs, func(i, j int) bool {\n\t\treturn errs[i].Error() < errs[j].Error()\n\t})\n\n\treturn errs\n}\n\n// ProviderRequirements searches the full tree of modules under the receiver\n// for both explicit and implicit dependencies on providers.\n//\n// The result is a full manifest of all of the providers that must be available","sourceCodeStart":294,"sourceCodeEnd":330,"githubUrl":"https://github.com/hashicorp/terraform/blob/d32a084675427f5ac3f7d2868578ef8b2c1dc525/internal/configs/config.go#L294-L330","documentation":"The locked version of a provider does not satisfy the configuration's version constraints, AND the current constraints differ from the constraints recorded in the lock file. This means the module author (or user) updated the version constraint in required_providers but did not run terraform init --upgrade to re-resolve. The lock file is stale relative to the changed requirement.","triggerScenarios":"A required_providers version constraint was changed (e.g., from ~> 3.0 to ~> 4.0) but terraform init was not run with --upgrade. The locked version satisfies the old constraint but not the new one, and the lock file still records the old constraint string.","commonSituations":"Team upgrades a provider major version in the config and pushes without re-running init. A module is updated upstream with tighter constraints. User edits required_providers locally to test a newer version but forgets to update the lock. Lock file and config are out of sync after a git merge or rebase.","solutions":["Run terraform init --upgrade to re-resolve providers against the updated constraints and refresh the lock file.","If you intentionally want to keep the old version, revert the version constraint change in required_providers.","After upgrading, commit the updated .terraform.lock.hcl to version control.","Verify the new constraint is satisfiable: check the registry for available versions matching the constraint."],"exampleFix":"# before — constraint changed but lock file not updated\nrequired_providers {\n  aws = { version = \"~> 4.0\" }  # was ~> 3.0, lock still says 3.x\n}\nterraform plan  # → error\n\n# after — re-resolve\nterraform init --upgrade\nterraform plan","handlingStrategy":"validation","validationCode":"// Verify lock file constraints match config constraints before plan\n// Shell pre-check:\n//   terraform init -lockfile=readonly  # fails if lock is stale\n// If stale:\n//   terraform init -upgrade\n\n// Go-side check (embedding):\nfunc verifyLockFreshness(workingDir string) error {\n    cmd := exec.Command(\"terraform\", \"init\", \"-lockfile=readonly\", \"-input=false\")\n    cmd.Dir = workingDir\n    return cmd.Run()\n}","typeGuard":null,"tryCatchPattern":null,"preventionTips":["Run terraform init -upgrade whenever you change version constraints in required_providers.","Use terraform init -lockfile=readonly in CI to detect stale locks immediately.","Commit the updated .terraform.lock.hcl after every constraint change.","Review constraint changes in code review — they require a corresponding lock file update."],"tags":["config","providers","version-constraints","dependency-lock","upgrade"],"backgroundTag":null,"analyzedSha":"d32a084675427f5ac3f7d2868578ef8b2c1dc525","analyzedAt":"2026-08-11T18:43:52.779Z","contentChangedAt":null,"schemaVersion":2},"datasetVersion":"2026-09-23T08:17:48.524Z"}