Kotlinic模式使用Spring Data JPA的“查询范例”

Spring Data JPA引入了一个很好的function,即“通过示例查询”(QBE) 。 您通过构建实体的实例来expression您的搜索条件。

您不必编写JPQL。 它比存储库查询派生使用更少的“魔术”。 语法很好。 它防止琐碎的存储库代码的爆炸。 它很好地重构了重构。

但有一个问题:只有部分构建对象时,QBE才能正常工作。

这是我的实体:

@Entity @Table(name="product") data class Product( @Id val id: String, val city: String, val shopName: String, val productName: String, val productVersion: Short ) 

这里是我的存储库(空的!这是关于QBE的一件好事):

 @Repository interface ProductRepository : JpaRepository 

以下是您如何获取List – 某些商店中某些城市销售的所有产品:

 productRepository.findAll(Example.of(Product(city = "London", shopName="OkayTea"))) 

或者至少,这就是我想要做的。 有一个问题。 这是不可能的

 Product(city = "London", shopName="OkayTea") 

这是因为Product的构造函数要求定义所有的字段。 而事实上:这正是我大部分时间想要的。

Java中常见的折衷方案是:使用无参数构造函数构造实体,使所有variables可变,对完成性没有保证。

有没有一个很好的Kotlin模式来解决这个问题:

  • 通常要求所有参数在施工中被实例化
  • 提供了一些机制来生成部分构建的实例,以便与API一起使用

诚然,这些看起来完全相冲突的目标。 但也许有另一种方法来解决这个问题?

例如:也许我们可以做一个模拟/代理对象,这似乎是一个产品,但没有相同的建设约束?

因为主构造函数中的参数不是可选的,也不能为空。 您可以使参数为空,并为每个参数设置一个默认值,例如:

 @Entity @Table(name = "product") data class Product( @Id val id: String? = null, val city: String? = null, val shopName: String? = null, val productName: String? = null, val productVersion: Short? = null ) 

但是,您必须使用安全呼叫操作Product属性?. , 例如:

 val product = Product() // safe-call ---v val cityToLowerCase = product.city?.toLowerCase()