java - Hibernate 6 Left Join 集合的最新成员

标签 java spring-boot hibernate

在 Hibernate 6.2 中,如果有匹配的书籍,我希望获得具有最新 BookAuthor 实体,并进入 Dto 投影 - AuthorBookDto:

作者

public class Author {
@Id
@GeneratedValue(strategy = SEQUENCE, generator = "author_seq")
private Long id;

@JsonBackReference
@OneToMany(cascade = CascadeType.ALL, orphanRemoval = true, mappedBy = "author")
private List<Book> listBook = new ArrayList<>();

// other fields
// getters and setters

预订

public class Book {

@Id
@GeneratedValue(strategy = SEQUENCE, generator = "book_seq")
private Long id;

@JsonManagedReference
@ManyToOne(fetch = FetchType.EAGER, optional = false)
private Author author;    

private LocalDateTime publishedDateTime;

我想要投影到的 Dto 包含来自 Author 的一些字段以及 Book 集合中最新的 Book:

AuthorBookDto

public class AuthorBookDto {

// Selected fields from Author plus a book entity (the newest one)
public Long authorId;
public Long bookId;
public Book newestBook;

我编写了一个查询,它最多选择一个Author,并且可以从Book检索单个字段,但不能检索整个图书实体(下面的查询无法正确投影)至上述实体):

    public Test customQuery3(Long id) {
    return (Test) entityManager.createQuery(
                    "SELECT NEW com.view.Test(a.id, a.name, y.pub_max_date) FROM Author a " +
                            "LEFT JOIN(SELECT book.id as book_id, MAX(book.pubDateTime) as pub_max_date, book.author.id as bid FROM Book b WHERE book.author.id=:id) as y " +
                            "ON a.id=y.bid " +
                            "WHERE a.id=:id GROUP BY a.id, y.book_id ORDER BY y.pub_max_date DESC LIMIT 1")
            .setParameter("id", id)
            .getSingleResult();

结果应如下所示:

{
    "id": 1,
    "name": "Steven King",
        Book {"id": "1",
              "title":"The Shining",
              "publishedDateTime":"2023-01-01 13:00"
              }
 }

这可以在一个 HQL 查询中实现吗? (注:有些作者可能没有出版过任何书籍)

最佳答案

此查询有效:

@Override
public Test customQuery3(Long id) {
    return (Test) entityManager.createQuery(
                    "SELECT NEW com.view.Test(a.id, b) FROM Author a " +
                            "LEFT JOIN Book b ON b.author.id=a.id " +
                            "WHERE b.id=:id " +
                            "GROUP BY a, b ORDER BY b.newestBook DESC LIMIT 1")
            .setParameter("id", id)
            .getSingleResult();
}

订购b.newestBook将最新的放在顶部,.getSingleResult()LIMIT 1两者都确保只返回 1 个结果。

关于java - Hibernate 6 Left Join 集合的最新成员,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/77005546/

相关文章:

java - Hibernate查询异常: unexpected token inside a number

java - 如何正确使用hybris1905的服务?

java - 使用 AngularJS、Spring 和 Hibernate 保存房间预订

java - JOptionPane 并从输入中获取文本

java - 将字段从一个对象映射到另一个对象的设计模式

java - 为什么我的矩阵乘法器不起作用?

hibernate - JPA/Hibernate 中的条件/复合 JoinColumn

java - Spring Data (Hibernate) 动态 WHERE 子句

spring - 如何从 src/main/resources 文件夹中读取 Freemarker 模板文件?

java - 无法使用@IdClass 转换实体中的请求元素