hibernate/hibernate-orm · error · IllegalArgumentException
The version attribute is not declared by this type [{}]
Error message
The version attribute is not declared by this type [{}] What it means
getDeclaredVersion(Class) must return a version attribute declared on the type itself. checkDeclaredVersion() throws when versionAttribute == null OR when a supertype already declares the version (inherited versions are not 'declared'). This mirrors the declared-vs-inherited distinction of the JPA metamodel API.
Source
Thrown at hibernate-core/src/main/java/org/hibernate/metamodel/model/domain/internal/AbstractIdentifiableType.java:317
}
else {
return null;
}
}
@Override
@Nonnull
public <Y> SingularPersistentAttribute<J, Y> getDeclaredVersion(@Nonnull Class<Y> javaType) {
checkDeclaredVersion();
checkType( versionAttribute, javaType );
@SuppressWarnings("unchecked") // safe, we just checked
final var castVersion = (SingularPersistentAttribute<J, Y>) versionAttribute;
return castVersion;
}
private void checkDeclaredVersion() {
if ( versionAttribute == null || supertypeDeclaresVersion() ) {
throw new IllegalArgumentException(
"The version attribute is not declared by this type [" + getJavaType() + "]"
);
}
}
private boolean supertypeDeclaresVersion() {
final var superType = getSuperType();
return superType != null && superType.hasVersionAttribute();
}
// @Override
// public void visitJdbcTypes(Consumer action, TypeConfiguration typeConfiguration) {
// id.visitJdbcTypes( action, typeConfiguration );
//
// if ( versionAttribute != null ) {
// versionAttribute.visitJdbcTypes( action, typeConfiguration );
// }
//View on GitHub (pinned to fad1729dce)
Solutions
- Use getVersion(Class) — it accepts inherited version attributes
- Guard with hasVersionAttribute() plus knowledge that the version may be inherited; or move @Version onto the concrete class if declared semantics matter
- Prefer findVersionAttribute() for nullable, hierarchy-aware lookup
Example fix
// before var v = subtypeType.getDeclaredVersion(Long.class); // @Version on AbstractEntity -> throws // after var v = subtypeType.getVersion(Long.class);
Defensive patterns
Strategy: validation
Validate before calling
// Use hierarchy-aware getVersion(); declared-only if you must ensure 'own' declaration var v = identifiableType.getVersion(javaType); // inherited ok // or: var v = identifiableType.findVersionAttribute(); // nullable
Try / catch
try {
return type.getDeclaredVersion(cls);
} catch (IllegalArgumentException e) {
if (e.getMessage() != null && e.getMessage().contains("version attribute is not declared by this type")) {
return type.getVersion(cls); // inherited version
}
throw e;
} Prevention
- Remember @Version in a @MappedSuperclass makes getDeclaredVersion fail on every subtype
- Default to getVersion(); use declared variant only for own-fields analysis
- Keep a single optimistic-locking helper so policy is in one place
When it happens
Trigger: Calling getDeclaredVersion(...) on an entity whose @Version lives in a @MappedSuperclass (typical AbstractEntity base with @Version); calling it on a subtype of a versioned root entity in an inheritance hierarchy.
Common situations: Base-entity templates that centralize @Version in a shared superclass. Generic frameworks calling the declared variant to find 'own' fields.
Related errors
- The id attribute is not declared on this type [{}]
- Mapped superclass '{}' may not specify an '@Inheritance' map
- Attribute '${attribute}' is declared as an '@Id' or '@Embedd
- Attribute '" + memberDetails.getName() + "' is declared by '
- {mappedSuperclassTypeName} is not a supertype of {componentT
AI-assisted analysis of hibernate/hibernate-orm@fad1729dce (2026-08-22).
Data as JSON: /api/errors/500e30fd82330f99.
Report an issue: GitHub.