Play for Scala中的JPA查询会引发编译错误

时间:2017-09-08 03:29:27

标签: scala playframework playframework-2.0 playframework-2.5

我正在尝试在Play for Scala中实现JPA查询。我从here获取了信息,但由于这些例子是用Java编写的,我可能会弄错。这是代码:

SELECT
    Staff,
    CaseNumber,
    DENSE_RANK() OVER (ORDER BY Staff) StaffNo
FROM yourTable;

编译时出现以下错误:

  

重载方法值withTransaction with alternatives:[T](x $ 1:   String,x $ 2:Boolean,x $ 3:java.util.function.Supplier [T])T   (x $ 1:Runnable)单位[T](x $ 1:java.util.function.Supplier [T])T    [T](x $ 1:字符串,x $ 2:布尔值,x $ 3:   java.util.function.Function [javax.persistence.EntityManager,T])笔   [T](x $ 1:字符串,x $ 2:   java.util.function.Function [javax.persistence.EntityManager,T])笔   [T](X $ 1:   java.util.function.Function [javax.persistence.EntityManager,T])笔   无法应用于(javax.persistence.EntityManager⇒   列表[admin.manage.BankHib])

这段代码有什么问题?如何使查询工作?

2 个答案:

答案 0 :(得分:1)

这是因为play.db.jpa.JPAApi.withTransaction具有以下签名:

  1. withTransaction(java.util.function.Function<javax.persistence.EntityManager,T>)
  2. withTransaction(java.lang.String, java.util.function.Function<javax.persistence.EntityManager,T>)
  3. withTransaction(java.lang.String, boolean, java.util.function.Function<javax.persistence.EntityManager,T>)
  4. withTransaction(java.util.function.Supplier<T>)
  5. withTransaction(java.lang.Runnable)
  6. 最后withTransaction(java.lang.String, boolean, java.util.function.Supplier<T>)
  7. 但您传递的是(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
          }
        })
      }
    }
    

    此外,请注意,您不需要混合使用JPAApiJPA来获取EntityManager,因为JPAApi具有已将其提供给给定函数的方法。

答案 1 :(得分:0)

看看是否有效

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
      })
   }
}