{"record":{"id":"ebee7a8b70e48768","repo":"hashicorp/terraform","slug":"invalid-provider-type-q-in-provider-matching-patt","errorCode":null,"errorMessage":"invalid provider type %q in provider matching pattern %q: must either be the wildcard * or a provider type name","messagePattern":"invalid provider type %q in provider matching pattern %q: must either be the wildcard \\* or a provider type name","errorType":"validation","errorClass":null,"httpStatus":null,"severity":"error","filePath":"internal/getproviders/multi_source.go","lineNumber":174,"sourceCode":"\t\t\tgivenHost := parts[0]\n\t\t\tif givenHost == \"*\" {\n\t\t\t\thost = svchost.Hostname(Wildcard)\n\t\t\t} else {\n\t\t\t\tnormalHost, err := svchost.ForComparison(givenHost)\n\t\t\t\tif err != nil {\n\t\t\t\t\treturn nil, fmt.Errorf(\"invalid hostname in provider matching pattern %q: %s\", str, err)\n\t\t\t\t}\n\n\t\t\t\t// The remaining code below deals only with the namespace/type portions.\n\t\t\t\thost = normalHost\n\t\t\t}\n\n\t\t\tparts = parts[1:]\n\t\t}\n\n\t\tpType, err := normalizeProviderNameOrWildcard(parts[1])\n\t\tif err != nil {\n\t\t\treturn nil, fmt.Errorf(\"invalid provider type %q in provider matching pattern %q: must either be the wildcard * or a provider type name\", parts[1], str)\n\t\t}\n\t\tnamespace, err := normalizeProviderNamespaceOrWildcard(parts[0])\n\t\tif err != nil {\n\t\t\treturn nil, fmt.Errorf(\"invalid registry namespace %q in provider matching pattern %q: must either be the wildcard * or a literal namespace\", parts[1], str)\n\t\t}\n\n\t\tret[i] = addrs.Provider{\n\t\t\tHostname:  host,\n\t\t\tNamespace: namespace,\n\t\t\tType:      pType,\n\t\t}\n\n\t\tif ret[i].Hostname == svchost.Hostname(Wildcard) && !(ret[i].Namespace == Wildcard && ret[i].Type == Wildcard) {\n\t\t\treturn nil, fmt.Errorf(\"invalid provider matching pattern %q: hostname can be a wildcard only if both namespace and provider type are also wildcards\", str)\n\t\t}\n\t\tif ret[i].Namespace == Wildcard && ret[i].Type != Wildcard {\n\t\t\treturn nil, fmt.Errorf(\"invalid provider matching pattern %q: namespace can be a wildcard only if the provider type is also a wildcard\", str)\n\t\t}","sourceCodeStart":156,"sourceCodeEnd":192,"githubUrl":"https://github.com/hashicorp/terraform/blob/c9def3e214014c1188faabfc4a5bde5095139765/internal/getproviders/multi_source.go#L156-L192","documentation":"The provider type (the last segment) is normalized via normalizeProviderNameOrWildcard: it must be exactly \"*\" or pass addrs.ParseProviderPart (lowercase alphanumerics and hyphens, non-empty). Anything else yields this error, quoting the bad type and the full pattern.","triggerScenarios":"Pattern's final segment is invalid: uppercase letters (\"hashicorp/AWS\"), contains dots/underscores, is empty (trailing slash), or has characters ParseProviderPart rejects.","commonSituations":"Uppercase provider names pasted from marketing docs; provider name with disallowed punctuation; trailing slash producing an empty type segment.","solutions":["Lowercase the provider type and use only letters, digits, and hyphens.","Use \"*\" to wildcard the type (then namespace must also be \"*\").","Remove any trailing slash that creates an empty final segment."],"exampleFix":"# before\ninclude = [\"hashicorp/AWS\"]\n\n# after\ninclude = [\"hashicorp/aws\"]","handlingStrategy":"validation","validationCode":"// Validate the provider type segment before parsing.\nif t := parts[len(parts)-1]; t != \"*\" {\n    if err := validateProviderPart(t); err != nil {\n        return fmt.Errorf(\"provider type %q invalid: %w\", t, err)\n    }\n}","typeGuard":null,"tryCatchPattern":null,"preventionTips":["Lowercase provider types; use only letters, digits, hyphens.","Use \"*\" to wildcard the type (and namespace).","Strip trailing slashes to avoid empty type segments."],"tags":["config","validation","pattern"],"analyzedSha":"c9def3e214014c1188faabfc4a5bde5095139765","analyzedAt":"2026-08-07T15:39:49.278Z","schemaVersion":2},"datasetVersion":"2026-08-07T20:17:04.800Z"}