hibernate/hibernate-orm · error · ParameterLabelException
Ordinal parameter label was not an integer
Error message
Ordinal parameter label was not an integer
What it means
When ParameterParser sees '?' followed by a digit it assumes a JPA-style ordinal parameter and must parse everything up to the next separator as an integer. If that token contains non-digits (e.g. '?1a', '?2b'), Integer.parseInt throws NumberFormatException and Hibernate rethrows it as ParameterLabelException with this message.
Source
Thrown at hibernate-core/src/main/java/org/hibernate/query/sql/internal/ParameterParser.java:189
recognizer.other( ':' );
}
}
}
}
else if ( c == '?' ) {
// could be either a positional or JPA-style ordinal parameter
if ( indx < stringLength - 1 && Character.isDigit( sqlString.charAt( indx + 1 ) ) ) {
// a peek ahead showed this as a JPA-positional parameter
final int right = StringHelper.firstIndexOfChar( sqlString, HQL_SEPARATORS, indx + 1 );
final int chopLocation = right < 0 ? sqlString.length() : right;
final String param = sqlString.substring( indx + 1, chopLocation );
// make sure this "name" is an integral
try {
recognizer.jpaPositionalParameter( Integer.parseInt( param ), indx );
indx = chopLocation - 1;
}
catch( NumberFormatException e ) {
throw new ParameterLabelException( "Ordinal parameter label was not an integer" );
}
}
else {
if ( !nativeJdbcParametersIgnored ) {
recognizer.ordinalParameter( indx );
}
}
}
else {
recognizer.other( c );
}
}
}
recognizer.complete();
}
public static void parse(String sqlString, ParameterRecognizer recognizer) throws QueryException {View on GitHub (pinned to fad1729dce)
Solutions
- Make the label a pure integer: use ?1, ?2, ... with no trailing characters.
- If the trailing text was accidental (e.g. '?1a' meant '?1 AND a'), add the missing separator (space, comma, parenthesis) after the label.
- If the '?...' sequence is literal SQL for your dialect, wrap it in quotes or restructure the SQL so it is not parsed as a parameter.
- Prefer named parameters (:name) in native queries to avoid ordinal parsing entirely.
Example fix
-- before select * from person where id = ?1a and name = :name -- after select * from person where id = ?1 and name = :name
Defensive patterns
Strategy: validation
Validate before calling
static void validateOrdinalLabelsAreIntegers(String sql) {
var m = java.util.regex.Pattern.compile("\\?(\\d+[A-Za-z_\\w]*)").matcher(sql);
if (m.find()) throw new IllegalArgumentException("Bad ordinal parameter label '" + m.group(1) + "' — labels must be pure integers like ?1");
} Try / catch
try { em.createNativeQuery(sql); } catch (org.hibernate.query.ParameterLabelException e) { /* locate '?<digits><letters>' in sql and fix */ throw e; } Prevention
- Use only ?1, ?2, ... labels — never append letters.
- Run the regex check in a unit test over your SQL resources.
- Prefer named parameters in native queries.
When it happens
Trigger: A native or HQL query string containing a token like '?1x', '?01a', or '?2foo' — i.e. '?' + digits + trailing letters/underscore, since letters are not separators and become part of the chopped token. Triggered at query creation when the string is parsed, before any parameter binding.
Common situations: Typos when relabeling JDBC '?' parameters to JPA '?n' style; SQL dialect text or JSON path expressions colliding with '?digit+letter' sequences; copy-pasted snippets mixing named and ordinal styles.
Related errors
- Ordinal parameter labels start from '?{position}' (ordinal p
- Gap between '?{previous}' and '?{position}' in ordinal param
- Incoming parameter position [{position}] is less than base [
- Named native query definition object is null
- Named native query definition name is null: {}
AI-assisted analysis of hibernate/hibernate-orm@fad1729dce (2026-08-22).
Data as JSON: /api/errors/0b600a1553365478.
Report an issue: GitHub.