在查询中使用子项计数时 Hibernate 生成的 MySQLSyntaxErrorException

标签 mysql hibernate jpa-2.0 jpql

我有一个查询,我只想在其中检索具有一个或多个 Link 子项的 Message 对象。

我的消息类是:

package zzz.community.domain;

/**
* Entity implementation class for Entity: Message.
*/
@Entity
@Table(name = "MESSAGE")
public class Message implements Serializable {

private static final long serialVersionUID = 2252587276028343749L;

public static final int MAX_LENGTH_TITLE = 255;

public static final int MAX_LENGTH_TEXT = 200000;

@Id @GeneratedValue
private Long id;

private String title;

@Column(columnDefinition = "TEXT")
private String text;

/**
 * The date at which the message was posted.
 */
private Date creationDate;

/**
 * The profile id of the user that posted this message.
 */
@OneToOne
private Profile creator;

/**
 * The id of the circle the message was posted to.
 */
@OneToOne
private Circle circle;

/**
 * When true, only members of the circle may see this message.
 */
private Boolean membersOnly;

@OneToMany(mappedBy="message")
@OrderBy("id DESC")
private Set<Link> links;

public Long getId() {
    return id;
}

public void setId(final Long id) {
    this.id = id;
}

public String getText() {
    return text;
}

public void setText(final String text) {
    this.text = text;
}

public String getTitle() {
    return title;
}

public void setTitle(final String title) {
    this.title = title;
}

public Date getCreationDate() {
    return creationDate;
}

public void setCreationDate(final Date creationDate) {
    this.creationDate = creationDate;
}

public Profile getCreator() {
    return creator;
}

public void setCreator(final Profile creator) {
    this.creator = creator;
}

public Circle getCircle() {
    return circle;
}

public void setCircle(final Circle circle) {
    this.circle = circle;
}

public Boolean getMembersOnly() {
    return membersOnly;
}

public void setMembersOnly(final Boolean membersOnly) {
    this.membersOnly = membersOnly;
}

public Set<Link> getLinks() {
    return this.links;
}

public void setLinks(final Set<Link> links) {
    this.links = links;
}

public void addLink(final Link link) {
    this.links.add(link);
}

}

我写的 JPA 查询是:

 select m from Message m 
 where m.circle = :circle 
 and count(m.links) > 0
 order by m.creationDate DESC

Hibernate 正确解析此代码(无 AST 异常)但生成的 mysql 语句不正确并抛出 MySQLSyntaxErrorException

09:01:22.153 [http-apr-8080-exec-3] DEBUG org.hibernate.hql.ast.ErrorCounter - throwQueryException() : no errors
09:01:22.154 [http-apr-8080-exec-3] DEBUG o.h.hql.ast.QueryTranslatorImpl - HQL: select m from zzz.domain.Message m where m.circle = :circle and count(m.links) > 0 order by m.creationDate DESC
09:01:22.154 [http-apr-8080-exec-3] DEBUG o.h.hql.ast.QueryTranslatorImpl - SQL: select message0_.id as id3_, message0_.circle_id as circle6_3_, message0_.creationDate as creation2_3_, message0_.creator_id as creator7_3_, message0_.membersOnly as membersO3_3_, message0_.text as text3_, message0_.title as title3_ from MESSAGE message0_ cross join LINK links1_ where message0_.id=links1_.message_id and message0_.circle_id=? and count(.)>0 order by message0_.creationDate DESC

Again, the resulting MySQL query:

select 
  message0_.id as id3_
, message0_.circle_id as circle6_3_
, message0_.creationDate as creation2_3_
, message0_.creator_id as creator7_3_
, message0_.membersOnly as membersO3_3_
, message0_.text as text3_
, message0_.title as title3_ 
from MESSAGE message0_ 
cross join LINK links1_ 
where message0_.id=links1_.message_id 
and   message0_.circle_id=? 
and   count(.)>0 
order by message0_.creationDate DESC

变通的办法当然是去掉选择标准

count(m.links) > 0

并用java中的一些代码替换它。但我希望能从你们中得到更好的建议。
在此先感谢,

亨克

最佳答案

在 JPQL 中,这可以通过以下结构之一来完成:

  • 空集合比较表达式 IS [NOT] EMPTY
  • SIZE函数

第一个如下:

count(m.links) > 0

替换为:

m.links IS NOT EMPTY

第二种方法是:

SIZE(m.links) > 0

关于在查询中使用子项计数时 Hibernate 生成的 MySQLSyntaxErrorException,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/17964331/

相关文章:

java - 使用 Servlet 将 MySQL 转为 JSP

java - 在 JPA2 中创建 EntityManager 时出错

java - Spring data jpa, native 查询,返回错误的字段类型

java - EhCache、JPA 2.0 L2缓存、缓存策略

mysql - 输出每个赛道的最佳时间,需要一些指导

MySQL计算特定值的列

mysql - RailsReady 中未包含的内容?

mysql - 使用 Spring、Hibernate 和 mySQL 进行事务管理

hibernate - 如何捕获 "integrity constraint violation: unique constraint or index violation"

java - 自定义 Spring Data Rest @ManyToMany 关系处理