【问题标题】:How to cache a JPA OneToMany relationship with Spring cache如何使用 Spring 缓存缓存 JPA OneToMany 关系
【发布时间】:2020-04-09 14:55:30
【问题描述】:

Product和ProductTag形成一对多的关系,如下图。

@Entity
public class Product {
    @Id
    Long id;

    @OneToMan(mappedBy = "product")
    List<ProductTag> productTags;
}

@Entity
public class ProductTag {
   @Id
   Long id;

   String content;

   @ManyToOne(fetch = FetchType.LAZY)
   @JoinColumn(name = "product_id")
   Product product;
}

现在我有一个 API 可以搜索产品,然后返回它们及其标签。每次我打电话给product.getProductTags(),Hibernate 都会触发一个 SQL 查询。由于 MySQL 服务器离应用服务器较远,所以我想缓存 product.getProductTags() 调用。我如何做到这一点?

【问题讨论】:

  • 不要。编写一个急切地获取标签的特定查询。

标签: spring hibernate jpa


【解决方案1】:

使用特定查询来获取标签并将它们存储在缓存中:

public TagRepository extends JpaRepository<Tag, Long> {

     @Cacheable("tagsByProducts")
     @Query("Select t from ProductTag t where t.product = ?product")
     List<Tag> findByProduct(Product product);

}

你需要一些方法来驱逐缓存:注解@CacheEvict("tagsByProducts")

但说实话:我怀疑将 JPA 实体存储在缓存中是个好主意!我认为这会导致许多奇怪的问题。所以最好只查询标签名称(或content)而不是标签实体。

public TagRepository extends JpaRepository<Tag, Long> {

     @Cacheable("tagsByProducts")
     @Query("Select t.content from ProductTag t where t.product = ?product")
     List<String> findTagContentByProduct(Product product);

}

【讨论】:

  • 当我使用 @Cacheable 注释接口方法时,IDE 会发出警告“spring 不鼓励使用 Cache* 注释接口”,您认为这值得关注吗?
  • @Chris Peng:Oliver Drotbohm(Spring Data 项目负责人)在stackoverflow.com/a/26283080/280244 中提出了相同的技术 - 所以我认为编写一个测试以确保它有效,然后忽略误导性的 IDE警告 - 还有一个官方 spring 数据示例 github.com/spring-projects/spring-data-examples/blob/master/jpa/… 以这种方式使用该缓存
【解决方案2】:
  @Entity
  public class Product {
   @Id
   Long product_id;

   @OneToMany(casacade=CascadeType.ALL, 
  fetch=FetchType.Eager,mappedBy = "product")
   @JsonManagedReference(value="product-tag")
    List<ProductTag> productTags;
   }

 @Entity
 public class ProductTag {
 @Id
  Long id;

  String content;

  @ManyToOne(fetch = FetchType.LAZY)
  @JoinColumn(name = "product_id")
  @JsonBackReference(value="product-tag")
   Product product;
  }

【讨论】:

    猜你喜欢
    • 2019-01-12
    • 2017-11-22
    • 1970-01-01
    • 2018-04-17
    • 1970-01-01
    • 1970-01-01
    • 2010-11-15
    • 2021-09-23
    • 1970-01-01
    相关资源
    最近更新 更多