{"record":{"id":"0a185a16e4718688","repo":"grpc/grpc-go","slug":"invalid-spiffeid-v","errorCode":null,"errorMessage":"invalid spiffeid: %v","messagePattern":"invalid spiffeid: (.+?)","errorType":"validation","errorClass":null,"httpStatus":null,"severity":"error","filePath":"internal/credentials/spiffe/spiffe.go","lineNumber":104,"sourceCode":"\tfor _, root := range roots {\n\t\trootPool.AddCert(root)\n\t}\n\treturn rootPool, nil\n}\n\n// idFromCert parses the SPIFFE ID from the x509.Certificate. If the certificate\n// does not have a valid SPIFFE ID, returns an error.\nfunc idFromCert(cert *x509.Certificate) (*spiffeid.ID, error) {\n\tif cert == nil {\n\t\treturn nil, fmt.Errorf(\"input cert is nil\")\n\t}\n\t// A valid SPIFFE Certificate should have exactly one URI.\n\tif len(cert.URIs) != 1 {\n\t\treturn nil, fmt.Errorf(\"input cert has %v URIs but should have 1\", len(cert.URIs))\n\t}\n\tid, err := spiffeid.FromURI(cert.URIs[0])\n\tif err != nil {\n\t\treturn nil, fmt.Errorf(\"invalid spiffeid: %v\", err)\n\t}\n\treturn &id, nil\n}\n","sourceCodeStart":86,"sourceCodeEnd":108,"githubUrl":"https://github.com/grpc/grpc-go/blob/0c51461d27177d997e14c642fe18c11668fc09a3/internal/credentials/spiffe/spiffe.go#L86-L108","documentation":"Raised by idFromCert when spiffeid.FromURI fails on the certificate's single URI. The URI must use the `spiffe://` scheme, have a valid trust domain in the host, and a path satisfying SPIFFE ID rules. Any deviation (wrong scheme, empty host, disallowed characters, missing path) is rejected.","triggerScenarios":"A URI SAN like `https://example.org/svc`, `spiffe:///svc` (empty trust domain), `spiffe://example.org` (no path), or `spiffe://Exa mple/svc` (illegal characters).","commonSituations":"Cert generator wrote a non-SPIFFE URI into the SAN; SPIFFE ID constructed with an empty trust domain; copy-paste introduced a scheme typo; trust domain with uppercase or spaces.","solutions":["Confirm the URI SAN is a well-formed SPIFFE ID: scheme `spiffe://`, lowercase host = trust domain, non-empty path with no query/fragment.","Re-mint the certificate with the corrected SPIFFE ID.","Validate SPIFFE IDs at issuance time using spiffeid.FromURI in a test.","Inspect the URI SAN with openssl and correct the CA template."],"exampleFix":"// before: URI = https://example.org/workload\n// after: URI = spiffe://example.org/workload","handlingStrategy":"validation","validationCode":"func validSpiffeURI(u *url.URL) bool {\n    if u == nil { return false }\n    if u.Scheme != \"spiffe\" { return false }\n    if u.Host == \"\" { return false }\n    if u.Path == \"\" || u.Path == \"/\" { return false }\n    if u.RawQuery != \"\" || u.Fragment != \"\" { return false }\n    return true\n}","typeGuard":"func parseSpiffeID(u *url.URL) (spiffeid.ID, error) {\n    if !validSpiffeURI(u) { return spiffeid.ID{}, errors.New(\"not a valid spiffe URI\") }\n    return spiffeid.FromURI(u)\n}","tryCatchPattern":"Wrap spiffeid.FromURI; on error, capture the offending URI (redacted) and re-mint the cert. Do not treat a non-spiffe URI as a fallback identity.","preventionTips":["Validate SPIFFE IDs at issuance with spiffeid.FromURI in a unit test of the CA template.","Use lowercase trust domains; never embed spaces or slashes in the host.","Reject certs whose URI SAN scheme is not exactly spiffe://."],"tags":["grpc","spiffe","tls","certificates","san","parsing","security"],"backgroundTag":null,"analyzedSha":"0c51461d27177d997e14c642fe18c11668fc09a3","analyzedAt":"2026-08-11T14:49:15.055Z","contentChangedAt":null,"schemaVersion":2},"datasetVersion":"2026-09-23T08:17:48.524Z"}