[dispatcherServlet] in context with path [] threw exception [Request processing failed: org.springframework.dao.InvalidDataAccessApiUsageException: Can't compare test expression of type [Facility] with element of type [basicType@4(java.lang.Integer,4)]] with root cause
java.lang.IllegalArgumentException: Can't compare test expression of type [Facility] with element of type [basicType@4(java.lang.Integer,4)]
at org.hibernate.query.sqm.internal.SqmCriteriaNodeBuilder.assertComparable(SqmCriteriaNodeBuilder.java:2098)
at org.hibernate.query.sqm.internal.SqmCriteriaNodeBuilder.equal(SqmCriteriaNodeBuilder.java:2121)
at org.hibernate.query.sqm.internal.SqmCriteriaNodeBuilder.equal(SqmCriteriaNodeBuilder.java:182)
at com.freit.medicalservice.repository.specification.PatientSpecification.lambda$facilityIdEqual$2a154287$1(PatientSpecification.java:139)
at org.springframework.data.jpa.domain.SpecificationComposition.toPredicate(SpecificationComposition.java:62)
at org.springframework.data.jpa.domain.SpecificationComposition.lambda$composed$e1dcbe07$1(SpecificationComposition.java:49)
at org.springframework.data.jpa.domain.SpecificationComposition.toPredicate(SpecificationComposition.java:62)
I remain stuck on this silly error for 2 days that I was getting on JPA specification after I migrated from spring and its related packages(including JPA, Hibernate) from version 5 to 6.
The line I was getting error on;
public static Specification<Patient> facilityIdEqual(Integer facilityId) {
return (root, query, builder) -> {
if (facilityId != null) {
query.distinct(Boolean.TRUE);
return builder.equal(root.join("patientFacilities").get("facility"), facilityId); //throws error
}
return null;
};
}
Where patientFacilities is of type PatientFacility (JPA Entity) and facility is of type Facility (JPA Entity)
simple change
root.join("patientFacilities").get("facility")
to
root.join("patientFacilities").get("facility").get("id")
Basically the error was that Facility (JPA entity type) was not a match for Integer id. Earlier version of spring (version 5) supported query like root.join("patientFacilities").get("facility") on referenced tables via joined column name but in Spring 6 (JPA 6, Hibernate 6) we have to be specific in types of the db table columns.