繁体   English   中英

在 Spring 中使用 class 进行查询

[英]Querying using class in Spring

我正在尝试执行此查询

List<Product> findProductByCategory_CategoryNameAndPriceBetween(String category, double min, double max);

但查询的返回是一个空列表。 我究竟做错了什么? 我也试过没有类别和类别名称之间的下划线。 这是 class 类别和产品:

@Entity
public class Category {
    @Id
    @GeneratedValue(strategy = GenerationType.AUTO)
    @Column(name="ID")
    private Long id;

    @Column(name = "NAME")
    private String categoryName;
    
    @OneToMany(mappedBy = "category", fetch = FetchType.EAGER)
    private List<Product> products;

...
}
@Entity
@Table(name="PRODUCT")
public class Product {

    @Id
    @GeneratedValue(strategy = GenerationType.AUTO)
    @Column(name="ID")
    private Long id;

    @Column(name="PRICE")
    private Double price;

    @Column(name="BRAND")
    private String brand;

    @Column(name="MODEL")
    private String model;

    //@Lob
    @Column(name="DESCRIPTION")
    private String description;

    @Column(name = "IMAGE_URL")
    private String imageUrl;

    @ManyToOne
    @JoinColumn(name = "CATEGORY_ID", referencedColumnName = "ID")
    private Category category;

这就是我实现存储库的方式:

@Repository
public interface ProductDao extends JpaRepository<Product,Long> {
...

通过下面的实现,您的查询运行良好。

请注意,我添加了一个替代实现:

List<Product> findByCategoryAndPriceBetween(Category category, double min, double max);

我怀疑当您对此进行测试时,您没有保存任何产品,因为您的代码在Category class 中缺少级联。 因此,我添加了在测试期间使用的实现。

类别 class

package no.mycompany.myapp.misc;

import lombok.Data;

import javax.persistence.*;
import java.util.ArrayList;
import java.util.List;

@Data
@Entity
public class Category {
    @Id
    @GeneratedValue(strategy = GenerationType.AUTO)
    @Column(name = "ID")
    private Long id;

    @Column(name = "NAME")
    private String categoryName;

    @OneToMany(mappedBy = "category", cascade = {CascadeType.PERSIST, CascadeType.MERGE})
    private List<Product> products = new ArrayList<>();
}

产品 class

package no.mycompany.myapp.misc;

import lombok.Getter;
import lombok.Setter;

import javax.persistence.*;

// cannot use @Data here because of circular ref
@Getter
@Setter
@Entity
@Table(name="PRODUCT")
public class Product {

    @Id
    @GeneratedValue(strategy = GenerationType.AUTO)
    @Column(name="ID")
    private Long id;

    @Column(name="PRICE")
    private Double price;

    @Column(name="BRAND")
    private String brand;

    @Column(name="MODEL")
    private String model;

    //@Lob
    @Column(name="DESCRIPTION")
    private String description;

    @Column(name = "IMAGE_URL")
    private String imageUrl;

    @ManyToOne
    @JoinColumn(name = "CATEGORY_ID", referencedColumnName = "ID")
    private Category category;
}

产品道

public interface ProductDao extends JpaRepository<Product, Long> {
    List<Product> findProductByCategory_CategoryNameAndPriceBetween(String category, double min, double max);
    List<Product> findByCategoryAndPriceBetween(Category category, double min, double max);
}

让我们为此添加几个测试:

package no.mycompany.myapp.misc;

import org.junit.jupiter.api.Test;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.boot.test.autoconfigure.orm.jpa.DataJpaTest;
import org.springframework.boot.test.autoconfigure.orm.jpa.TestEntityManager;
import org.springframework.test.context.ActiveProfiles;

import static org.assertj.core.api.AssertionsForClassTypes.assertThat;

@DataJpaTest
public class ProductDaoTest {

    @Autowired
    ProductDao productDao;

    @Autowired
    TestEntityManager testEntityManager;

    @Test
    public void findByCategoryAndPriceBetween_singleCategoryWithSingleProductInDb_expectSingleProduct() {
        var category = createCategoryWithSingleProduct();
        testEntityManager.persist(category);
        var result = productDao.findByCategoryAndPriceBetween(category, 0.0, 2.0);
        assertThat(result.size()).isEqualTo(1);
    }

    @Test
    public void findByCategoryAndPriceBetween_singleCategoryWithSingleProductInDb_expectEmptyResult() {
        var category = createCategoryWithSingleProduct();
        testEntityManager.persist(category);
        var result = productDao.findByCategoryAndPriceBetween(category, 5.0, 6.0);
        assertThat(result.size()).isEqualTo(0);
    }

    @Test
    public void findProductByCategory_CategoryNameAndPriceBetween_singleCategoryWithSingleProductInDb_expectSingleProduct() {
        var category = createCategoryWithSingleProduct();
        testEntityManager.persist(category);
        var result = productDao.findProductByCategory_CategoryNameAndPriceBetween(category.getCategoryName(), 0.0, 2.0);
        assertThat(result.size()).isEqualTo(1);
    }

    private static Category createCategoryWithSingleProduct() {
        Product product = new Product();
        product.setPrice(1.00);

        Category category = new Category();
        category.setCategoryName("test");
        category.getProducts().add(product);
        product.setCategory(category);

        return category;
    }
}

根据文档,您的方法应该是:

List<Product> findProductByCategoryNameAndPriceBetween(String category, double min, double max)

前提是 categoryName 和 price 在类别 class 中定义。

暂无
暂无

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM