Reputation: 179
I am trying to migrate from hibernate 4.3.1.Final to 5.4.27.Final in an oldish Spring application (most Spring components are on version 4.3.13.Final). After updating the version fixing couple minor issues (class imports) and building the application with maven I get the following error while trying to deploy this web application on Tomcat 7.0.107 (part of the stack trace pointing to the root exception):
2121 Caused by: java.lang.IllegalArgumentException: Validation failed for query for method public abstract java.util.List hr.chus.plus.dao.repository.StatusUpdateRepository .findAlarmLogsByZoneAndDatesAndNeedsAck(java.lang.Integer,java.lang.String,java.util.Date,java.util.Date)!
-- cut --
2150 Caused by: org.hibernate.QueryException: Could not resolve identifier `acks` as plural-attribute [FROM hr.chus.plus.dao.model.jpa.StatusUpdate WHERE updateType='ALARM' AND relatedId=:alarmId AND subtype='ZONE' AND subtypeUuid=:zone AND timestamp BETWEEN :start AND :end AND needAck=true AND size(acks)=0]
2151 at org.hibernate.QueryException.generateQueryException(QueryException.java:120) ~[hibernate-core-5.4.27.Final.jar:5.4.27.Final]
2152 at org.hibernate.QueryException.wrapWithQueryString(QueryException.java:103) ~[hibernate-core-5.4.27.Final.jar:5.4.27.Final]
2153 at org.hibernate.hql.internal.ast.QueryTranslatorImpl.doCompile(QueryTranslatorImpl.java:220) ~[hibernate-core-5.4.27.Final.jar:5.4.27.Final]
2154 at org.hibernate.hql.internal.ast.QueryTranslatorImpl.compile(QueryTranslatorImpl.java:144) ~[hibernate-core-5.4.27.Final.jar:5.4.27.Final]
2155 at org.hibernate.engine.query.spi.HQLQueryPlan.<init>(HQLQueryPlan.java:113) ~[hibernate-core-5.4.27.Final.jar:5.4.27.Final]
2156 at org.hibernate.engine.query.spi.HQLQueryPlan.<init>(HQLQueryPlan.java:73) ~[hibernate-core-5.4.27.Final.jar:5.4.27.Final]
2157 at org.hibernate.engine.query.spi.QueryPlanCache.getHQLQueryPlan(QueryPlanCache.java:162) ~[hibernate-core-5.4.27.Final.jar:5.4.27.Final]
2158 at org.hibernate.internal.AbstractSharedSessionContract.getQueryPlan(AbstractSharedSessionContract.java:604) ~[hibernate-core-5.4.27.Final.jar:5.4.27.Final]
2159 at org.hibernate.internal.AbstractSharedSessionContract.createQuery(AbstractSharedSessionContract.java:716) ~[hibernate-core-5.4.27.Final.jar:5.4.27.Final]
2160 ... 79 common frames omitted
2161 Caused by: org.hibernate.QueryException: Could not resolve identifier `acks` as plural-attribute
2162 at org.hibernate.hql.internal.ast.tree.CollectionPathNode.from(CollectionPathNode.java:123) ~[hibernate-core-5.4.27.Final.jar:5.4.27.Final]
This JPQL was running and deploying fine with the previous version.
Pertinent parts of the mentioned entities are as follows:
AlarmLog:
@Entity
@Table(name = "z_alarm_log")
@SecondaryTable(name = "z_alarm_log_data", pkJoinColumns = { @PrimaryKeyJoinColumn(name = "id") })
@Cache(usage = CacheConcurrencyStrategy.READ_ONLY)
public class AlarmLog extends AbstractLogEntity {
private static final int SUBTYPE_MAX_LENGTH = 10;
@Column(name = "alarm_id")
private Integer alarmId;
@Column(name = "trouble", columnDefinition = "TINYINT")
private Boolean trouble;
@Lob
@Basic(fetch = FetchType.EAGER)
@Column(name = "data", columnDefinition = "BLOB", table = "z_alarm_log_data")
private String data;
@Column(name = "need_ack", columnDefinition = "TINYINT")
private Boolean needAck = false;
@OneToMany(mappedBy = "log", fetch = FetchType.LAZY, cascade = { CascadeType.ALL })
private Set<AlarmLogAck> acks = new HashSet<>();
@Column(name = "code", nullable = false)
private int code = 0;
@Column(name = "subtype", length = SUBTYPE_MAX_LENGTH)
private String subtype;
@Column(name = "subtype_id")
private Integer subtypeId;
@Column(name = "subtype_uuid", nullable = true, columnDefinition = "CHAR")
private String subtypeUuid;
AlarmLogAck:
@Entity
@Table(name = "z_alarm_log_ack")
@Cache(usage = CacheConcurrencyStrategy.READ_WRITE)
public class AlarmLogAck extends AbstractLongIdEntity {
private static final int MESSAGE_MAX_LENGTH = 200;
@ManyToOne(fetch = FetchType.LAZY)
@JoinColumn(name = "zipato_id")
private Zipato zipato;
@ManyToOne(fetch = FetchType.LAZY, optional = false)
@JoinColumn(name = "log_id")
private AlarmLog log;
@ManyToOne(fetch = FetchType.LAZY, optional = false)
@JoinColumn(name = "user_id")
private User user;
@Column(name = "show_date", nullable = false, columnDefinition = "DATETIME")
private Date showDate;
@Column(name = "ack_date", nullable = true, columnDefinition = "DATETIME")
private Date ackDate;
@Column(name = "message", length = MESSAGE_MAX_LENGTH, nullable = true)
private String message;
AlarmLogRepository:
@Transactional(readOnly = true)
public interface AlarmLogRepository extends JpaRepository<AlarmLog, Long>, JpaSpecificationExecutor<AlarmLog> {
@Query("FROM AlarmLog " + //
"WHERE zipato=:zipato " + //
" AND alarmId=:alarmId " + //
" AND subtype='ZONE' " + //
" AND subtypeUuid=:zone " + //
" AND timestamp BETWEEN :start AND :end" + //
" AND needAck=true " + //
" AND size(AlarmLog.acks)=0")
List<AlarmLog> findAlarmLogsByZoneAndDatesAndNeedsAck(@Param("zipato") Zipato p_zipato,
@Param("alarmId") Integer p_alarmId,
@Param("zone") String p_zone,
@Param("start") Date p_start,
@Param("end") Date p_end);
I have tried googling this error and I could not find this exact combination of plural-attribute
not being recognized. I also tried debugging to a certain level and found out that this Set
is not being recognized as a Collection type or to be more precise that the acks Set
is not in the list and therefore could not be recognized as a plural-attribute
.
I am at a loss how to fix this...
Any ideas?
Upvotes: 0
Views: 429
Reputation: 2694
For that query you should set identifier for entity AlarmLog
and use that identifier in where conditions in following way:
...
@Query("FROM AlarmLog al " +
"WHERE zipato=:zipato " +
" AND alarmId=:alarmId " +
" AND subtype='ZONE' " +
" AND subtypeUuid=:zone " +
" AND timestamp BETWEEN :start AND :end" +
" AND needAck=true " +
" AND size(al.acks)=0")
...
Upvotes: 1