elastic/elasticsearch · error · IOException
Invalid DER: object is not a string
Error message
Invalid DER: object is not a string
What it means
Thrown by Asn1Object.getString() in its default branch when the element type does not match any supported string type (OCTET_STRING, NUMERIC/PRINTABLE/VIDEOTEX/IA5/GRAPHIC/ISO646/GENERAL, BMP, UTF8) and is not UNIVERSAL_STRING. The parser refuses to interpret an arbitrary tag as text.
Source
Thrown at libs/ssl-config/src/main/java/org/elasticsearch/common/ssl/DerParser.java:264
case Type.GRAPHIC_STRING:
case Type.ISO646_STRING:
case Type.GENERAL_STRING:
encoding = "ISO-8859-1"; //$NON-NLS-1$
break;
case Type.BMP_STRING:
encoding = "UTF-16BE"; //$NON-NLS-1$
break;
case Type.UTF8_STRING:
encoding = "UTF-8"; //$NON-NLS-1$
break;
case Type.UNIVERSAL_STRING:
throw new IOException("Invalid DER: can't handle UCS-4 string"); //$NON-NLS-1$
default:
throw new IOException("Invalid DER: object is not a string"); //$NON-NLS-1$
}
return new String(value, encoding);
}
public String getOid() throws IOException {
if (type != Type.OBJECT_OID) {
throw new IOException("Ivalid DER: object is not object OID");
}
StringBuilder sb = new StringBuilder(64);
switch (value[0] / 40) {
case 0 -> sb.append('0');
case 1 -> {
sb.append('1');
value[0] -= 40;
}
default -> {View on GitHub (pinned to db6a809a66)
Solutions
- Re-export the key from a trusted source to rule out corruption.
- Validate with `openssl asn1parse -inform DER -in key.der` to confirm element types and order.
- Convert to PKCS#8 so PemUtils uses a single uniform code path.
- If parsing custom DER, re-check the schema and read elements in the correct order/types.
Example fix
// before: parser misaligned, readAsn1Object returns SEQUENCE not OCTET_STRING
DerParser.Asn1Object elem = parser.readAsn1Object(); // unexpectedly a SEQUENCE
String s = elem.getString(); // throws
// after: validate type before reading
if (elem.getType() != DerParser.Type.OCTET_STRING && elem.getType() != DerParser.Type.UTF8_STRING) {
throw new IOException("unexpected tag 0x" + Integer.toHexString(elem.getType()));
}
String s = elem.getString(); Defensive patterns
Strategy: type-guard
Type guard
private static final Set<Integer> STRING_TYPES = Set.of(
DerParser.Type.OCTET_STRING, DerParser.Type.NUMERIC_STRING,
DerParser.Type.PRINTABLE_STRING, DerParser.Type.VIDEOTEX_STRING,
DerParser.Type.IA5_STRING, DerParser.Type.GRAPHIC_STRING,
DerParser.Type.ISO646_STRING, DerParser.Type.GENERAL_STRING,
DerParser.Type.BMP_STRING, DerParser.Type.UTF8_STRING);
public static boolean isStringElement(DerParser.Asn1Object o) {
return o != null && STRING_TYPES.contains(o.getType());
} Prevention
- Verify the element type is a supported string type before calling getString().
- Ensure parser alignment by reading elements in the correct order.
- Validate the overall structure with `openssl asn1parse`.
When it happens
Trigger: getString() switch hits default. Typical when getString() is called on a SEQUENCE, SET, INTEGER, OID, BOOLEAN, or any other non-string element — most commonly because the parser is misaligned (a previous element was skipped or read with the wrong type).
Common situations: Corrupted or misaligned DER, wrong key format, or a key whose internal layout does not match the expected structure (e.g. an RSA key with extra fields that shifts subsequent reads).
Related errors
- Invalid DER: size of ASN.1 object to be parsed appears to be
- Invalid DER: stream too short, missing value. Could only rea
- Invalid DER: length missing
- Invalid DER: length field too big ({})
- Invalid DER: length too short
AI-assisted analysis of elastic/elasticsearch@db6a809a66 (2026-08-12).
Data as JSON: /api/errors/bf6ac3f357be9d2f.
Report an issue: GitHub.