我正在尝试为视图创建一个JPA实体。从数据库层来看,表和视图应该是相同的。
然而,问题开始出现,它们是两方面的:
1.当试图设置正确的注解时。视图没有与之关联的主键,但是如果没有在字段上注解适当的@javax.persistence.Id
,您将得到一个org.hibernate.AnnotationException: No identifier specified for entity
。
- Sping Boot
JpaRepository
接口定义要求ID
类型扩展Serializable
,这排除了使用java.lang.Void
作为视图实体上缺少id的解决方案。
什么是正确的JPA/SpringBoot/Hibernate方式来与缺少主键的视图交互?
5条答案
按热度按时间a7qyws3x1#
1.在数据库中使用原生SQL创建View,
字符串
2.将ViewMap到“不可变的属性”
型
3.现在用你想要的方法创建仓库,
型
dgenwo3n2#
我也在探索这个主题。我最终使用Spring Data JPA基于接口的投影与原生查询。
我创建了一个接口,确保大写部分与DB列名匹配:
字符串
然后我为一个实体(用户)创建了一个存储库,这个实体与视图没有任何关系。在这个存储库中,我创建了一个简单的本地查询。vReport1_1是我的视图。
型
pzfprimi3#
我希望这对你有帮助,你可以在你的观点中将它分配给一个统一的值。
我们将视图Map到JPA对象,如下所示:
字符串
然后我们创建一个repository:
型
yshpjwxd4#
如果你的视图没有候选键,你可以通过创建查询使用类似数据库UUID函数的东西添加一个,然后使用UUID作为实体ID的类型。
如果你需要使你的实体只读,你可以用
字符串
或者用org.hibernate.annotations注解你的实体类。如果你的提供者是Hibernate >= 5.2,则不可变。
js5cn81o5#
关于实体IDMap
如果可以更改视图定义,则可以使用addrownum as column。
它通常是特定于DBMS的,其思想是使表中的行号成为实体的ID。
作为替代方案,您可以使用唯一ID的生成器。
UUID
是一种可能性。最后,您可以坚持使用原生SQL,同时受益于JPA/Hibernate将原生查询结果Map到表示视图数据的特定类。关于Spring Data 仓库
如果视图不自然地符合Spring Data Repository的要求,这可能意味着使用视图而不是表不一定适合。
事实上,Spring Data存储库类(如
CrudRepository
或JpaRepository
)旨在为特定实体类提供开箱即用的CRUD操作和一些额外的处理。在DBMS方面的视图不包括在您选择它时,但您不会直接更新,插入或删除视图中的任何行。
此外,将这样的Repository bean用于视图会有什么附加价值?您几乎不会使用Spring提供的生成的实现。
在您的情况下,如果您将视图定义为实体,我认为使用
JpaTemplate
更有意义。它只是JPA API之上的一层。
关于the documentation:
JpaTemplate可以被认为是使用本机JPA API的直接替代方案(通过共享的JPA API引用,如上所述)。主要优点是它可以自动转换为DataTemplate;主要缺点是它在本机JPA API之上引入了另一个薄层。注意,异常转换也可以通过AOP建议实现;请查看PersistenceExceptionTranslationPostProcessor