{"record":{"id":"3beedbfd8d4aed91","repo":"hashicorp/nomad","slug":"unable-to-parse-public-key-for-jwt-auth-v","errorCode":null,"errorMessage":"unable to parse public key for JWT auth: %v","messagePattern":"unable to parse public key for JWT auth: (.+?)","errorType":"exception","errorClass":null,"httpStatus":null,"severity":"error","filePath":"lib/auth/jwt/validator.go","lineNumber":95,"sourceCode":"\t\t\t)\n\t\t}\n\t\tif iss, ok := claims[\"iss\"].(string); !ok {\n\t\t\treturn nil, fmt.Errorf(\"unable to read iss property of provided token\")\n\t\t} else if !slices.Contains(methodConf.BoundIssuer, iss) {\n\t\t\treturn nil, fmt.Errorf(\"invalid JWT issuer: %v\", claims[\"iss\"])\n\t\t}\n\t}\n\n\treturn claims, nil\n}\n\nfunc usingStaticKeys(keys []string) (jwt.KeySet, error) {\n\tvar parsedKeys []crypto.PublicKey\n\tfor _, v := range keys {\n\t\tkey, err := jwt.ParsePublicKeyPEM([]byte(v))\n\t\tparsedKeys = append(parsedKeys, key)\n\t\tif err != nil {\n\t\t\treturn nil, fmt.Errorf(\"unable to parse public key for JWT auth: %v\", err)\n\t\t}\n\t}\n\treturn jwt.NewStaticKeySet(parsedKeys)\n}\n\nfunc usingJWKS(ctx context.Context, jwksurl, jwkscapem string) (jwt.KeySet, error) {\n\t// Measure the JWKS endpoint performance.\n\tdefer metrics.MeasureSince([]string{\"nomad\", \"acl\", \"jwt\", \"jwks\"}, time.Now())\n\n\tkeySet, err := jwt.NewJSONWebKeySet(ctx, jwksurl, jwkscapem)\n\tif err != nil {\n\t\treturn nil, fmt.Errorf(\"unable to get validation keys from JWKS: %v\", err)\n\t}\n\treturn keySet, nil\n}\n\nfunc usingOIDC(ctx context.Context, oidcurl string, oidccapem []string) (jwt.KeySet, error) {\n\t// Measure the OIDC endpoint performance.","sourceCodeStart":77,"sourceCodeEnd":113,"githubUrl":"https://github.com/hashicorp/nomad/blob/482b49bf1aec006f089bcfc7e632d8f6ac303e5e/lib/auth/jwt/validator.go#L77-L113","documentation":"usingStaticKeys wraps jwt.ParsePublicKeyPEM failures: one of the public keys configured on the auth method (RSAPublicKey or JWKSCACert-style static key list) could not be parsed as a valid PEM-encoded public key. The wrapped underlying error (usually go-jose's asn1/pem parse error) identifies the exact key that failed.","triggerScenarios":"Validate → keyset construction when the auth method uses static keys (JWTAuthMethodConfig with RSAPublicKeys and no JWKS/OIDC URL) and any entry is not parseable PEM.","commonSituations":"Pasted key missing the BEGIN/END PEM headers or with broken line endings; a private key pasted where a public key is expected; cert (X.509) pasted instead of a public key; secrets UI stripped newlines.","solutions":["Check each configured key has valid PEM headers/footers (`-----BEGIN PUBLIC KEY-----` / `-----END PUBLIC KEY-----`) and intact newlines; re-paste the key.","Ensure you pasted a PUBLIC key, not the private key or the X.509 certificate; extract with `openssl rsa -in key.pem -pubout`.","Inspect the wrapped %v error — asn1 errors usually mean wrong key type or corrupted base64."],"exampleFix":"// before: private key in config\nRSAPublicKeys: []string{\"-----BEGIN RSA PRIVATE KEY-----\\n...\"}\n// after: public key with clean PEM\nRSAPublicKeys: []string{\"-----BEGIN PUBLIC KEY-----\\nMIIBIjANBg...\\n-----END PUBLIC KEY-----\"}","handlingStrategy":"validation","validationCode":"// validate every configured key parses before writing the auth method\nfor i, k := range keys {\n  if _, err := jwt.ParsePublicKeyPEM([]byte(k)); err != nil {\n    return fmt.Errorf(\"RSAPublicKeys[%d] invalid: %w\", i, err)\n  }\n}","typeGuard":"func isPEMPublicKey(s string) bool {\n  blk, _ := pem.Decode([]byte(s))\n  return blk != nil && strings.Contains(blk.Type, \"PUBLIC KEY\")\n}","tryCatchPattern":"keyset, err := usingStaticKeys(keys)\nif err != nil {\n  return fmt.Errorf(\"auth method key config invalid; check each RSAPublicKeys entry is a public PEM: %w\", err)\n}","preventionTips":["Round-trip keys through `openssl pkey -pubin -in key.pem -noout` before uploading.","Never paste private keys or certificates into RSAPublicKeys.","Preserve newlines when pasting into UIs or JSON configs (escape as \\n)."],"tags":["jwt","auth","pem","key-parsing"],"backgroundTag":"invalid-pem-key","analyzedSha":"482b49bf1aec006f089bcfc7e632d8f6ac303e5e","analyzedAt":"2026-09-04T07:54:14.808Z","contentChangedAt":"2026-09-04T07:54:14.808Z","schemaVersion":2},"datasetVersion":"2026-09-08T10:18:20.063Z"}