Play for Scala 中的 JPA 查询抛出编译错误
JPA query in Play for Scala throws compilation error
我正在尝试在 Play for Scala 中实现 JPA 查询。我从 here 中获取信息,但由于示例在 Java 中,所以我可能弄错了。这是代码:
class ManageBanks @Inject() (jpaApi: JPAApi) extends Controller {
@Transactional
def readMany = {
val em = jpaApi.em
jpaApi.withTransaction( (em: EntityManager) => { // <-- error in this line
val query = em.createQuery("from BankHib order by name")
val list = query.getResultList.asScala.toList.map(_.asInstanceOf[BankHib])
list
})
}
}
编译时出现如下错误:
overloaded method value withTransaction with alternatives: [T](x:
String, x: Boolean, x: java.util.function.Supplier[T])T
(x: Runnable)Unit [T](x: java.util.function.Supplier[T])T
[T](x: String, x: Boolean, x:
java.util.function.Function[javax.persistence.EntityManager,T])T
[T](x: String, x:
java.util.function.Function[javax.persistence.EntityManager,T])T
[T](x:
java.util.function.Function[javax.persistence.EntityManager,T])T
cannot be applied to (javax.persistence.EntityManager ⇒
List[admin.manage.BankHib])
这段代码有什么问题?如何使查询工作?
看看这是否有效
class ManageBanks @Inject() (jpaApi: JPAApi) extends Controller {
@Transactional
def readMany = {
jpaApi.withTransaction( () => { // <-- error in this line
val em = JPA.em() // or jpaApi.em
val query = em.createQuery("from BankHib order by name")
val list = query.getResultList.asScala.toList.map(_.asInstanceOf[BankHib])
list
})
}
}
这是因为 play.db.jpa.JPAApi.withTransaction
具有以下签名:
withTransaction(java.util.function.Function<javax.persistence.EntityManager,T>)
withTransaction(java.lang.String, java.util.function.Function<javax.persistence.EntityManager,T>)
withTransaction(java.lang.String, boolean, java.util.function.Function<javax.persistence.EntityManager,T>)
withTransaction(java.util.function.Supplier<T>)
withTransaction(java.lang.Runnable)
- 最后
withTransaction(java.lang.String, boolean, java.util.function.Supplier<T>)
。
但是您传递的是 (javax.persistence.EntityManager ⇒ List[admin.manage.BankHib])
类型的 Scala 函数。因此,错误的类型和编译器抱怨说它无法找到替代方案。
正确的方法是使用 java.util.function.Function[EntityManager, List]
:
class ManageBanks @Inject()(jpaApi: JPAApi) extends Controller {
def readMany = {
jpaApi.withTransaction(new java.util.function.Function[EntityManager, List[BankHib]] {
override def apply(em: EntityManager): List[BankHib] = {
val query = em.createQuery("from BankHib order by name")
query.getResultList.asScala.map(_.asInstanceOf[BankHib]).toList
}
})
}
}
此外,请注意,您不需要混合使用 JPAApi
和 JPA
来获得 EntityManager
,因为 JPAApi
的方法已将其提供给给定的功能。
我正在尝试在 Play for Scala 中实现 JPA 查询。我从 here 中获取信息,但由于示例在 Java 中,所以我可能弄错了。这是代码:
class ManageBanks @Inject() (jpaApi: JPAApi) extends Controller {
@Transactional
def readMany = {
val em = jpaApi.em
jpaApi.withTransaction( (em: EntityManager) => { // <-- error in this line
val query = em.createQuery("from BankHib order by name")
val list = query.getResultList.asScala.toList.map(_.asInstanceOf[BankHib])
list
})
}
}
编译时出现如下错误:
overloaded method value withTransaction with alternatives: [T](x: String, x: Boolean, x: java.util.function.Supplier[T])T (x: Runnable)Unit [T](x: java.util.function.Supplier[T])T [T](x: String, x: Boolean, x: java.util.function.Function[javax.persistence.EntityManager,T])T [T](x: String, x: java.util.function.Function[javax.persistence.EntityManager,T])T [T](x: java.util.function.Function[javax.persistence.EntityManager,T])T cannot be applied to (javax.persistence.EntityManager ⇒ List[admin.manage.BankHib])
这段代码有什么问题?如何使查询工作?
看看这是否有效
class ManageBanks @Inject() (jpaApi: JPAApi) extends Controller {
@Transactional
def readMany = {
jpaApi.withTransaction( () => { // <-- error in this line
val em = JPA.em() // or jpaApi.em
val query = em.createQuery("from BankHib order by name")
val list = query.getResultList.asScala.toList.map(_.asInstanceOf[BankHib])
list
})
}
}
这是因为 play.db.jpa.JPAApi.withTransaction
具有以下签名:
withTransaction(java.util.function.Function<javax.persistence.EntityManager,T>)
withTransaction(java.lang.String, java.util.function.Function<javax.persistence.EntityManager,T>)
withTransaction(java.lang.String, boolean, java.util.function.Function<javax.persistence.EntityManager,T>)
withTransaction(java.util.function.Supplier<T>)
withTransaction(java.lang.Runnable)
- 最后
withTransaction(java.lang.String, boolean, java.util.function.Supplier<T>)
。
但是您传递的是 (javax.persistence.EntityManager ⇒ List[admin.manage.BankHib])
类型的 Scala 函数。因此,错误的类型和编译器抱怨说它无法找到替代方案。
正确的方法是使用 java.util.function.Function[EntityManager, List]
:
class ManageBanks @Inject()(jpaApi: JPAApi) extends Controller {
def readMany = {
jpaApi.withTransaction(new java.util.function.Function[EntityManager, List[BankHib]] {
override def apply(em: EntityManager): List[BankHib] = {
val query = em.createQuery("from BankHib order by name")
query.getResultList.asScala.map(_.asInstanceOf[BankHib]).toList
}
})
}
}
此外,请注意,您不需要混合使用 JPAApi
和 JPA
来获得 EntityManager
,因为 JPAApi
的方法已将其提供给给定的功能。