jwtk/jjwt · error · IllegalArgumentException

X509Certificate encoded bytes cannot be null or empty. Cert

Error message

X509Certificate encoded bytes cannot be null or empty.  Certificate: {${cert}}.

What it means

After successfully calling cert.getEncoded(), JwtX509StringConverter.applyTo checks the DER bytes are non-null and non-empty; if not, it throws IllegalArgumentException with this message. A certificate that yields zero-length encoded bytes cannot be represented in the x5c header.

Source

Thrown at impl/src/main/java/io/jsonwebtoken/impl/security/JwtX509StringConverter.java:50

    // Returns a Base64 encoded (NOT Base64Url encoded) string of the cert's encoded byte array per
    // https://www.rfc-editor.org/rfc/rfc7515.html#section-4.1.6
    // https://www.rfc-editor.org/rfc/rfc7516.html#section-4.1.8
    // https://www.rfc-editor.org/rfc/rfc7517.html#section-4.7
    @Override
    public String applyTo(X509Certificate cert) {
        Assert.notNull(cert, "X509Certificate cannot be null.");
        byte[] der = Bytes.EMPTY;
        try {
            try {
                der = cert.getEncoded();
            } catch (CertificateEncodingException e) {
                String msg = "Unable to access X509Certificate encoded bytes necessary to perform DER " +
                        "Base64-encoding. Certificate: {" + cert + "}. Cause: " + e.getMessage();
                throw new IllegalArgumentException(msg, e);
            }
            if (Bytes.isEmpty(der)) {
                String msg = "X509Certificate encoded bytes cannot be null or empty.  Certificate: {" + cert + "}.";
                throw new IllegalArgumentException(msg);
            }
            return Encoders.BASE64.encode(der);
        } finally {
            Bytes.clear(der);
        }
    }

    // visible for testing
    protected X509Certificate toCert(final byte[] der) throws SecurityException {
        return new JcaTemplate("X.509").generateX509Certificate(der);
    }

    @Override
    public X509Certificate applyFrom(CharSequence s) {
        Assert.hasText(s, "X.509 Certificate encoded string cannot be null or empty.");
        try {
            byte[] der = Decoders.BASE64.decode(s); //RFC requires Base64, not Base64Url
            return toCert(der);

View on GitHub (pinned to fb71496164)

Solutions

  1. Replace the certificate with one parsed from real encoded bytes via CertificateFactory.
  2. Verify getEncoded() outside the library and fix the certificate source.
  3. If seen in tests, use a real certificate fixture (PEM file) instead of a stub.
  4. Regenerate the certificate if its encoding is genuinely empty.

Example fix

// before
X509Certificate cert = mock(X509Certificate.class);
when(cert.getEncoded()).thenReturn(new byte[0]);

// after
X509Certificate cert = (X509Certificate) CertificateFactory.getInstance("X.509")
    .generateCertificate(getClass().getResourceAsStream("/test-cert.pem"));
Defensive patterns

Strategy: validation

Validate before calling

boolean hasNonEmptyEncoding(X509Certificate cert) throws CertificateEncodingException {
    return cert.getEncoded() != null && cert.getEncoded().length > 0;
}

Try / catch

try {
    String x5c = converter.applyTo(cert);
} catch (IllegalArgumentException e) {
    if (e.getMessage().contains("encoded bytes cannot be null or empty")) {
        // replace the certificate object with a real parsed one
    } else throw e;
}

Prevention

When it happens

Trigger: Applying an X509Certificate whose getEncoded() returns an empty byte array when converting it to an x5c header string.

Common situations: Defective or mock/stub certificate implementations in tests returning empty encodings; certificates constructed by custom Provider code with uninitialized contents.

Understand the failure class

Background: "must not be empty", "cannot be empty" — required-field validation errors across open-source libraries — this error's family across 41 libraries.

Related errors


AI-assisted analysis of jwtk/jjwt@fb71496164 (2026-09-09). Data as JSON: /api/errors/559ba3db371cc111. Report an issue: GitHub.