{"record":{"id":"622b18df469a2a35","repo":"hashicorp/terraform","slug":"provider-mirror-returned-invalid-provider-hash-q","errorCode":null,"errorMessage":"provider mirror returned invalid provider hash %q: %s","messagePattern":"provider mirror returned invalid provider hash %q: (.+?)","errorType":"http","errorClass":null,"httpStatus":null,"severity":"error","filePath":"internal/getproviders/http_mirror_source.go","lineNumber":246,"sourceCode":"\n\tret := PackageMeta{\n\t\tProvider:       provider,\n\t\tVersion:        version,\n\t\tTargetPlatform: target,\n\n\t\tLocation: PackageHTTPURL(absURL.String()),\n\t\tFilename: path.Base(absURL.Path),\n\t}\n\t// A network mirror might not provide any hashes at all, in which case\n\t// the package has no source-defined authentication whatsoever.\n\tif len(archiveMeta.Hashes) > 0 {\n\t\thashes := make([]Hash, 0, len(archiveMeta.Hashes))\n\t\tfor _, hashStr := range archiveMeta.Hashes {\n\t\t\thash, err := ParseHash(hashStr)\n\t\t\tif err != nil {\n\t\t\t\treturn PackageMeta{}, s.errQueryFailed(\n\t\t\t\t\tprovider,\n\t\t\t\t\tfmt.Errorf(\"provider mirror returned invalid provider hash %q: %s\", hashStr, err),\n\t\t\t\t)\n\t\t\t}\n\t\t\thashes = append(hashes, hash)\n\t\t}\n\t\tret.Authentication = NewPackageHashAuthentication(target, hashes)\n\t}\n\n\treturn ret, nil\n}\n\n// ForDisplay returns a string description of the source for user-facing output.\nfunc (s *HTTPMirrorSource) ForDisplay(provider addrs.Provider) string {\n\treturn \"provider mirror at \" + s.baseURL.String()\n}\n\n// ListVersionsResponseBody is the JSON structure of a response when a user queries the available versions\n// for a provider in the network mirror, i.e. a GET to path :hostname/:namespace/:type/index.json\n// See: https://developer.hashicorp.com/terraform/internals/provider-network-mirror-protocol#list-available-versions","sourceCodeStart":228,"sourceCodeEnd":264,"githubUrl":"https://github.com/hashicorp/terraform/blob/c9def3e214014c1188faabfc4a5bde5095139765/internal/getproviders/http_mirror_source.go#L228-L264","documentation":"If a version JSON archive entry includes a \"hashes\" array, each string is parsed with ParseHash. Any entry that is not a valid hash (e.g. not in the h1:... or zh:... form) fails the whole query via errQueryFailed with this message, quoting the bad hash and the parse error. The mirror published an invalid hash.","triggerScenarios":"An archive entry's hashes array contains a malformed string: missing scheme prefix, wrong algorithm prefix, base64 of wrong length, or plain garbage. Only valid h1:/zh: hashes are accepted.","commonSituations":"Mirror generator recorded SHA256 hex digests instead of h1: base64 hashes; copy-paste truncated a hash; mixed-in checksum from a different scheme.","solutions":["Inspect the version JSON and remove/fix the offending hash string.","Regenerate hashes using the documented h1: algorithm (dirhash.Hash1 over the archive).","If you do not want to publish hashes, omit the \"hashes\" field entirely (the protocol allows it)."],"exampleFix":"# before\n{\"hashes\":[\"9f2e...c1\"]}  # raw sha256 hex\n\n# after\n{\"hashes\":[\"h1:2f3b...=\"]}  # h1: base64 from dirhash.Hash1\n# or omit hashes entirely","handlingStrategy":"try-catch","validationCode":"// Validate each published hash parses before writing the version file.\nfor _, h := range entry.Hashes {\n    if _, err := getproviders.ParseHash(h); err != nil {\n        return fmt.Errorf(\"hash %q invalid: %w\", h, err)\n    }\n}","typeGuard":null,"tryCatchPattern":"var qf getproviders.ErrQueryFailed\nif errors.As(err, &qf) && strings.Contains(qf.Error(), \"invalid provider hash\") {\n    // mirror published a bad hash; surface to operator\n}","preventionTips":["Publish h1: hashes from dirhash.Hash1, not raw sha256 hex.","Omit the hashes array entirely if you don't have valid hashes.","Schema-validate hashes during mirror generation."],"tags":["protocol","mirror","hash"],"analyzedSha":"c9def3e214014c1188faabfc4a5bde5095139765","analyzedAt":"2026-08-07T15:39:49.278Z","schemaVersion":2},"datasetVersion":"2026-08-07T21:17:07.882Z"}