{"record":{"id":"9388628b2b776435","repo":"quarkusio/quarkus","slug":"x-509-svid-response-from-spire-agent-contains-a-no","errorCode":null,"errorMessage":"X.509-SVID response from SPIRE agent contains a non-X.509 certificate in ${description}: ${certClassName}","messagePattern":"X\\.509-SVID response from SPIRE agent contains a non-X\\.509 certificate in (.+?): (.+?)","errorType":"exception","errorClass":"SpiffeConnectionException","httpStatus":null,"severity":"error","filePath":"extensions/spiffe-client/runtime/src/main/java/io/quarkus/spiffe/client/runtime/internal/SpiffeClientImpl.java","lineNumber":347,"sourceCode":"        var keyMaterial = new WorkloadCertificateChainImpl(unmodifiableList(certChain), privateKey);\n        var trustMaterial = new WorkloadTrustBundleImpl(unmodifiableList(trustBundle));\n        return new WorkloadCertificateDocumentImpl(protoSpiffeId, keyMaterial, trustMaterial);\n    }\n\n    private static List<X509Certificate> parseCertificates(byte[] derBytes, String description)\n            throws SpiffeConnectionException {\n        if (derBytes.length == 0) {\n            throw new SpiffeConnectionException(\"X.509-SVID response contains empty \" + description);\n        }\n        try {\n            CertificateFactory cf = CertificateFactory.getInstance(\"X.509\");\n            Collection<?> certs = cf.generateCertificates(new ByteArrayInputStream(derBytes));\n            List<X509Certificate> result = new ArrayList<>(certs.size());\n            for (var cert : certs) {\n                if (cert instanceof X509Certificate x509) {\n                    result.add(x509);\n                } else {\n                    throw new SpiffeConnectionException(\n                            \"X.509-SVID response from SPIRE agent contains a non-X.509 certificate in \"\n                                    + description + \": \" + cert.getClass().getName());\n                }\n            }\n            return result;\n        } catch (Exception e) {\n            throw new SpiffeConnectionException(\n                    \"X.509-SVID response from SPIRE agent contains an invalid \" + description, e);\n        }\n    }\n\n    private static List<String> certsToPem(List<X509Certificate> certs) {\n        try {\n            List<String> result = new ArrayList<>(certs.size());\n            for (X509Certificate cert : certs) {\n                result.add(toPem(\"CERTIFICATE\", cert.getEncoded()));\n            }\n            return unmodifiableList(result);","sourceCodeStart":329,"sourceCodeEnd":365,"githubUrl":"https://github.com/quarkusio/quarkus/blob/e1c734241f34c7919086ceb4c9262b4a58f6de44/extensions/spiffe-client/runtime/src/main/java/io/quarkus/spiffe/client/runtime/internal/SpiffeClientImpl.java#L329-L365","documentation":"While iterating certificates parsed from the DER bytes, an element was not an instance of X509Certificate. The Java CertificateFactory can yield other certificate types (e.g. X509CRL or legacy cert classes), and the SPIFFE client only supports X.509, so it rejects the payload naming the offending class.","triggerScenarios":"parseCertificates called with chain or bundle bytes whose generated certificate collection contains a non-X.509 element (cert instanceof X509Certificate fails).","commonSituations":"A custom security provider returning a different certificate implementation; corrupted or foreign DER data in the bundle field; test mocks feeding arbitrary bytes; extremely old agents embedding legacy formats.","solutions":["Restart/upgrade the SPIRE agent and re-fetch; valid SPIRE data is always X.509.","Inspect the bytes (openssl x509 -inform DER -in bundle.pem) to see what was actually delivered.","Remove/replace custom security providers that alter CertificateFactory behavior.","If a mock is used in tests, populate fields with genuine DER-encoded X.509 certificates."],"exampleFix":null,"handlingStrategy":"try-catch","validationCode":"// sanity-check the delivered DER parses as X.509:\nCertificateFactory cf = CertificateFactory.getInstance(\"X.509\");\nCollection<?> c = cf.generateCertificates(new ByteArrayInputStream(derBytes));\nc.forEach(x -> { if (!(x instanceof X509Certificate)) throw new IllegalStateException(); });\n","typeGuard":null,"tryCatchPattern":"try {\n    doc = client.getWorkloadCertificate();\n} catch (SpiffeConnectionException e) {\n    if (e.getMessage().contains(\"non-X.509 certificate\")) {\n        // inspect custom providers / mock data producing non-X.509 certs\n        throw new IllegalStateException(\"Non-X.509 data from Workload API: \" + e.getMessage(), e);\n    } else throw e;\n}","preventionTips":["Use only genuine SPIRE agent data (always X.509 DER)","Avoid security providers that change CertificateFactory output","In tests, use real DER-encoded X.509 certificates in mocks","Verify bundle bytes with openssl when in doubt"],"tags":["spiffe","x509","certificate","parsing"],"backgroundTag":"certificate-parse-failed","analyzedSha":"e1c734241f34c7919086ceb4c9262b4a58f6de44","analyzedAt":"2026-09-05T17:01:29.979Z","contentChangedAt":"2026-09-05T17:01:29.979Z","schemaVersion":2},"datasetVersion":"2026-09-12T22:17:10.623Z"}