hibernate/hibernate-orm · error · IllegalArgumentException
Can't parse JSON array for selectable [%s] which is not of t
Error message
Can't parse JSON array for selectable [%s] which is not of type BasicPluralType.
What it means
While parsing a JSON document into an embeddable, encountering ARRAY_START for a selectable whose JdbcMapping is not a BasicPluralType throws IllegalArgumentException - the stored JSON holds an array where the mapping expects a scalar or embeddable. Example: the attribute is Integer but the column value is [1,2].
Source
Thrown at hibernate-core/src/main/java/org/hibernate/type/descriptor/jdbc/JsonHelper.java:104
final int selectableIndex = currentEmbeddableMappingType.getSelectableIndex( selectableName );
if ( selectableIndex < 0 ) {
throw new IllegalArgumentException(
String.format(
"Could not find selectable [%s] in embeddable type [%s] for JSON processing.",
selectableName,
currentEmbeddableMappingType.getMappedJavaType().getJavaTypeClass().getName()
)
);
}
final SelectableMapping selectableMapping =
currentEmbeddableMappingType.getJdbcValueSelectable( selectableIndex );
currentSelectableData = new SelectableData( selectableName, selectableIndex, selectableMapping );
}
case ARRAY_START -> {
assert currentSelectableData != null;
if ( !(currentSelectableData.selectableMapping.getJdbcMapping() instanceof BasicPluralType<?, ?> pluralType) ) {
throw new IllegalArgumentException(
String.format(
"Can't parse JSON array for selectable [%s] which is not of type BasicPluralType.",
ParseLevel.determineSelectablePath( parseLevel, currentSelectableData )
)
);
}
parseLevel.push( new ParseLevel( currentSelectableData, pluralType ) );
currentSelectableData = null;
}
case ARRAY_END -> {
assert currentLevel.arrayType != null;
assert currentLevel.selectableData != null;
parseLevel.pop();
final ParseLevel parentLevel = parseLevel.getCurrent();
assert parentLevel.embeddableMappingType != null;
// flush array valuesView on GitHub (pinned to fad1729dce)
Solutions
- If the attribute really is a collection, map it as one: List<T>/T[] with @JdbcTypeCode(SqlTypes.JSON) (a BasicPluralType) so ARRAY_START is legal.
- If the attribute is scalar, fix the stored data to a scalar value instead of an array.
Example fix
// before: data is {"tags":["a","b"]} but attribute is scalar
@Embeddable public class Meta { String tags; }
// load -> Can't parse JSON array for selectable [tags]
// after: map it as the collection it is
@Embeddable public class Meta {
@JdbcTypeCode(SqlTypes.JSON)
List<String> tags;
}
// or fix the data: UPDATE t SET doc = '{"tags":"a,b"}'; Defensive patterns
Strategy: validation
Validate before calling
// Before relying on a load, check scalar keys do not hold arrays (Jackson example)
static void assertNoArraysOnScalarKeys(JsonNode doc, Set<String> scalarKeys) {
for (String key : scalarKeys) {
JsonNode n = doc.get(key);
if (n != null && n.isArray()) {
throw new IllegalStateException("Key '" + key + "' holds an array but is mapped as scalar");
}
}
} Try / catch
try {
return session.find(Product.class, id);
} catch (IllegalArgumentException e) {
if (e.getMessage() != null && e.getMessage().contains("not of type BasicPluralType")) {
// stored array vs scalar mapping: fix the attribute to a plural JSON type or migrate the data
} else {
throw e;
}
} Prevention
- When changing an attribute between scalar and collection, migrate stored JSON in the same release
- Map collection attributes with @JdbcTypeCode(SqlTypes.JSON) so arrays are legal
- Seed test data from the same mapping that reads it
When it happens
Trigger: Loading an aggregate/json-mapped embeddable whose stored document contains an array under a key mapped to a non-collection attribute; data written by an older mapping where the attribute was a List and later changed to a scalar without data migration (or vice versa).
Common situations: Changing an embeddable attribute between List<T> and T without migrating the JSON column; other applications writing arrays into the column; copy-pasted fixture data.
Related errors
- Can't parse JSON object for selectable [%s] which is not of
- Malformed JSON. Expected array but got: " + event
- Unwrap strategy not known for this Java type: " + getTypeNam
- Wrap strategy not known for this Java type: " + getTypeName(
- Could not find selectable [%s] in embeddable type [%s] for J
AI-assisted analysis of hibernate/hibernate-orm@fad1729dce (2026-08-22).
Data as JSON: /api/errors/4c515a93d4a21494.
Report an issue: GitHub.