具有继承的实体的JPA本机查询

时间:2010-01-26 16:54:36

标签: java hibernate inheritance orm jpa

我有一个实体类和一个基于该实体的子类:

@Entity
@Inheritance(strategy = InheritanceType.TABLE_PER_CLASS)
public class A

@Entity
public class B extends A

我需要发出一个仅在基类(A)上使用存储过程的本机查询。如果我按如下方式尝试:

entityManager.createNativeQuery("select * from A a where procedure(f)",A.class).getResultList()

我收到有关“在ResultSet中找不到列clazz_”的错误。我假设JPA提供程序添加此列以区分基类和扩展类。我可以通过显式添加clazz列和子类中的所有字段来解决这个问题:

entityManager.createNativeQuery("select *,1 as clazz_,null as prop1,null as prop2 from A a where procedure(f)",A.class).getResultList()

其中“prop1”和“prop2”是子类B的属性。但是,这似乎是一种不必要的破解,如果子类B发生变化,则容易出现维护问题。

我的问题是:如何在已定义继承的实体上使用存储过程进行查询?

2 个答案:

答案 0 :(得分:9)

正如您可能已经看到的那样,Hibernate团队并未在定义您如何执行此操作方面投入大量精力。文档只是声明:

  

16.1.6。处理继承

     

查询的本机SQL查询   作为一部分映射的实体   继承必须包括所有   基类和所有的属性   它的子类。

因此,如果你想使用Native查询,看起来你就像是在做这样的事情。关于子类B改变的关注,也许稍微不那么繁重的实现方法是尝试在共享ID属性上使用LEFT OUTER JOIN语法:

entityManager.createNativeQuery("select a.*, b*, 1 as clazz_, from A a LEFT OUTER JOIN B b on id = a.id where procedure(f)",A.class).getResultList()

这样,如果添加或删除某些属性,您将始终从B获取所有属性。

答案 1 :(得分:0)