1

在带有 EclipseLink 的 JPA 应用程序中,有一个 Circular 实体与 Keyword 实体具有 oneToMany 关系。圆形实体有两个@Lob 类型的属性。当我运行此 JQL 以获取不同的实体时,我收到以下错误。如何在具有 @Lob 属性的此类实体中使用 distinct in?

JQL 是

SQL is select DISTINCT c from CircularKeyword k join k.circular c where c.retired = false and c.administrativeDivision.id = 1  and k.retired = false and  ( upper(c.circularNumber) like '%3%' or  upper(c.topic) like '%3%' or  upper(k.name) like '%3%'   )  order by c.name

错误是

Exception [EclipseLink-4002] (Eclipse Persistence Services - 2.3.2.v20111125-r10461): org.eclipse.persistence.exceptions.DatabaseException
Internal Exception: java.sql.SQLException: Columns of type 'BLOB' may not be used in CREATE INDEX, ORDER BY, GROUP BY, UNION, INTERSECT, EXCEPT or DISTINCT statements because comparisons are not supported for that type.
Error Code: -1
Call: SELECT DISTINCT t0.ID, t0.BAIMAGE, t0.CIRCULARDATE, t0.CIRCULARLANGUAGE, t0.CIRCULARNUMBER, t0.CODE, t0.CONTENTS, t0.CREATEDAT, t0.DESCRIPTION, t0.FILENAME, t0.FILETYPE, t0.INTERNAL, t0.KEYWORDS, t0.NAME, t0.ORIGINATINGFILENO, t0.RETIRECOMMENTS, t0.RETIRED, t0.RETIREDAT, t0.TOPIC, t0.ADMINISTRATIVEDIVISION_ID, t0.CATEGORY_ID, t0.CREATER_ID, t0.PERSON_ID, t0.RETIRER_ID, t0.SIGNINGAUTHORITY_ID FROM CIRCULAR t0, CIRCULARKEYWORD t1 WHERE (((((t0.RETIRED = ?) AND (t0.ADMINISTRATIVEDIVISION_ID = ?)) AND (t1.RETIRED = ?)) AND ((UCASE(t0.CIRCULARNUMBER) LIKE ? OR UCASE(t0.TOPIC) LIKE ?) OR UCASE(t1.NAME) LIKE ?)) AND (t0.ID = t1.CIRCULAR_ID)) ORDER BY t0.NAME ASC
    bind => [6 parameters bound]
Query: ReportQuery(referenceClass=CircularKeyword sql="SELECT DISTINCT t0.ID, t0.BAIMAGE, t0.CIRCULARDATE, t0.CIRCULARLANGUAGE, t0.CIRCULARNUMBER, t0.CODE, t0.CONTENTS, t0.CREATEDAT, t0.DESCRIPTION, t0.FILENAME, t0.FILETYPE, t0.INTERNAL, t0.KEYWORDS, t0.NAME, t0.ORIGINATINGFILENO, t0.RETIRECOMMENTS, t0.RETIRED, t0.RETIREDAT, t0.TOPIC, t0.ADMINISTRATIVEDIVISION_ID, t0.CATEGORY_ID, t0.CREATER_ID, t0.PERSON_ID, t0.RETIRER_ID, t0.SIGNINGAUTHORITY_ID FROM CIRCULAR t0, CIRCULARKEYWORD t1 WHERE (((((t0.RETIRED = ?) AND (t0.ADMINISTRATIVEDIVISION_ID = ?)) AND (t1.RETIRED = ?)) AND ((UCASE(t0.CIRCULARNUMBER) LIKE ? OR UCASE(t0.TOPIC) LIKE ?) OR UCASE(t1.NAME) LIKE ?)) AND (t0.ID = t1.CIRCULAR_ID)) ORDER BY t0.NAME ASC")
4

2 回答 2

3

假设circular有一个简单的 id,您可以通过更新查询以仅选择不同的标识符作为子查询来解决此问题:

SELECT k.circular FROM CircularKeyword k 
WHERE k.circular.id IN (SELECT DISTINCT c.id FROM CircularKeyword k2 
                        JOIN k2.circular c ...rest of your query...)

重要的是您要求DISTINCT c.id而不是DISTINCT c这样生成的本机 SQL 不会在语句中包含您的BLOB列。DISTINCT

于 2013-05-27T05:36:04.113 回答
1

解决此问题的另一个选项是将 @Lob 包装到单独的实体中。这是有效的,因为它不会尝试解析实际的 lob,而只会尝试解析数据库可以使用 distinct 处理的 lob 键引用。我已经将一个工作代码片段改编为一个提供信息的示例。

圆形实体

//Other attributes, and ids omitted

@ManyToOne()
@JoinColumn(name = "LOB_ATTRIBUTE_1_KEY")
LobAttribute lobAttribute1;

@ManyToOne()
@JoinColumn(name = "LOB_ATTRIBUTE_2_KEY")
LobAttribute lobAttribute2;

LobAttribute 实体

@Id
@Column(name = "LOB_ATTRIBUTE_KEY")
Long lobAttributeKey;

@Lob
@Basic(fetch = FetchType.LAZY)
@Column(name = "LOB")
String lob;

我不是特别喜欢这个,但我相信这是对查询和模型限制最少的最佳解决方案。我希望这对遇到此问题的其他人有所帮助。

于 2016-04-05T19:24:14.553 回答