如何使用Jpa存储库实现ligh Entity版本? [英] How to implement ligh Entity version with Jpa repository?
问题描述
具有完整实体"类:
@Entity(name = "vacancy_dec_to_words")
public class VacancyDescriptionToWords {
@Id
@Column(name = "id")
@GeneratedValue(strategy = GenerationType.IDENTITY)
private long id;
@JoinColumn(name = "vacancy_description_id")
@ManyToOne(cascade = CascadeType.ALL)
private VacancyDescription vacancyDescription;
@JoinColumn(name = "words_id")
@ManyToOne
private Words words;
@Column(name = "qty")
private int qty;
@Column(name = "create_date")
private Date date;
//...getters and setters
在某些方法中,我只需要使用此数据库中的2列:word_id
和qty
In some methods I need use only 2 column from this database: word_id
and qty
我尝试以下方法:
投影 https://docs.spring .io/spring-data/jpa/docs/2.1.2.RELEASE/reference/html/#projections
public interface QtyWords {
Long getWords();
Integer getQty();
}
Jpa存储库:
*查询,我使用了经过测试且可行的查询,我在JpaRepository
中使用了他:
*Query, that I use tested and it workable, I use him in JpaRepository
:
@Repository
public interface SmallVDTWRepository extends JpaRepository<VacancyDescriptionToWords, Long> {
@Query(nativeQuery = true,
value = "SELECT sum(qty), words_id FROM vacancy_desc_to_words WHERE vacancy_description_id IN (" +
"SELECT id FROM vacancy_description WHERE vacancy_id IN (" +
"SELECT id FROM vacancy WHERE explorer_id = :exp))" +
"GROUP BY words_id")
List<QtyWords> getDistinctWordsByExplorer(@Param("exp") long exp);
}
但是当我获得实体列表时,我得到一些有趣的结果:
But I get some interesting result when I get list of entities:
List<QtyWords> list = vdtwService.getByExplorerId(72);
我没有任何例外,但是我有一个带有unknowns对象的列表.该对象包含我需要的数据(qty
和words_id
),但是我无法从他那里获取它们.
I am not get any exceptions, but I have the list with are unknowns objects. This objects contains my data, which I need(qty
and words_id
), but I cannot get them from him.
我可以使用此方法(Projection
)来执行此任务,并且在这种情况下,通常如何正确地实现轻型实体"?
Can I use this method (Projection
) to implement this task and, in general, how to correctly implement the 'Light Entity' in this case?
推荐答案
Spring提供了两种机制,可用于限制要提取的数据.
Spring provides two mechanisms that can be used to limit data to be fetched.
通过设置确切要获取的属性,投影可以帮助您减少从数据库检索的数据.
Projections can help you to reduce data, retrieved from database, by setting what exactly attributes you want to fetch.
@Entity
class Person {
@Id UUID id;
String firstname, lastname;
@OneToOne
Address address;
}
@Entity
static class Address {
@Id UUID id;
String zipCode, city, street;
}
interface NamesOnly {
String getFirstname();
String getLastname();
}
@Repository
interface PersonRepository extends Repository<Person, UUID> {
Collection<NamesOnly> findByLastname(String lastname);
}
实体图
注释EntityGraph
通过设置需要获取的确切相关实体,可以帮助您减少对数据库的查询量.
Entity graph
Annotation EntityGraph
can help you to reduce amount of queries to database, by setting what exactly related entities you need to fetch.
@Entity
@NamedEntityGraph(name = "GroupInfo.detail", attributeNodes = @NamedAttributeNode("members"))
public class GroupInfo {
@Id UUID id;
@ManyToMany //default fetch mode is lazy.
List<GroupMember> members = new ArrayList<GroupMember>();
}
@Repository
public interface GroupRepository extends CrudRepository<GroupInfo, String> {
@EntityGraph(value = "GroupInfo.detail", type = EntityGraphType.LOAD)
GroupInfo getByGroupName(String name); //Despite of GroupInfo.members has FetchType = LAZY, it will be fetched because of using EntityGraph
}
EntityGraph
有两种类型:
-
EntityGraphType.LOAD
-用于指定实体图,将由实体图的属性节点指定的属性视为FetchType.EAGER
,将未指定的属性根据其指定的或默认的FetchType
处理. -
EntityGraphType.FETCH
-用于指定实体图,将由实体图的属性节点指定的属性视为FetchType.EAGER
,将未指定的属性视为FetchType.LAZY
.
EntityGraphType.LOAD
- is used to specify an entity graph, attributes that are specified by attribute nodes of the entity graph are treated asFetchType.EAGER
and attributes that are not specified are treated according to their specified or defaultFetchType
.EntityGraphType.FETCH
- is used to specify an entity graph, attributes that are specified by attribute nodes of the entity graph are treated asFetchType.EAGER
and attributes that are not specified are treated asFetchType.LAZY
.
PS:另外请记住,您可以设置延迟获取类型:@ManyToOne(fetch = FetchType.LAZY)
,并且在获取父对象时,JPA不会获取子实体.
PS: Also remember that you can set lazy fetch type: @ManyToOne(fetch = FetchType.LAZY)
and JPA will not fetching child entities when parent is being fetched.
这篇关于如何使用Jpa存储库实现ligh Entity版本?的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!