Hi, Derek,

Have you considered making ScalaEntityManager a trait that can be mixed into
something that provides an EntityManager, rather than an abstract class
decorating one? I've taken that approach with good results; I think it makes
it a bit more flexible with respect to how the underlying EntityManager is
created.

I've attached the version I've been working with.

Kris

On Fri, Dec 12, 2008 at 4:28 PM, Derek Chen-Becker <[email protected]>wrote:

> I've reworked it a little and put it into its own project:
>
> http://github.com/dchenbecker/scalajpa/tree/master
>
> I've broken things down just a bit and added some more abstract classes to
> make it easier to use. In particular, now there's a LocalEM class that uses
> java.persistence.Persistence to retrieve the EM, and a JndiEM class that
> uses JNDI. Under the test source directory is an example of how to integrate
> with Lift, similar to how it's been done up to now. One thing I'm thinking
> about doing is reworking it a bit so that ScalaEntityManager becomes a
> per-instance usage, in case people want to use these classes outside of
> Lift. Right now it's very geared toward using a singleton accessor and using
> a per-thread management of instances. Please send me any questions or
> comments.
>
> Cheers,
>
> Derek
>
> PS - I'm going to talk to David B. to see if this can be hosted as a maven
> module on scala-tools.org so that you can just drop it in your POM in the
> future.
>
> >
>

--~--~---------~--~----~------------~-------~--~----~
You received this message because you are subscribed to the Google Groups 
"Lift" group.
To post to this group, send email to [email protected]
To unsubscribe from this group, send email to 
[email protected]
For more options, visit this group at 
http://groups.google.com/group/liftweb?hl=en
-~----------~----~----~----~------~----~------~--~---

package com.gaiam.gcsi.model

import java.util.{Date,Calendar}
import javax.persistence._

import net.liftweb.http.RequestVar
import net.liftweb.util.{Can,Full,Empty}

import scala.collection.jcl.IterableWrapper
import scala.collection.jcl.Conversions._

object JPA {
  implicit def collToWrapper[A](coll : java.util.Collection[A]) = new IterableWrapper[A] {
    override def underlying = coll
  }

  def findToCan[A](f: => A): Can[A] = 
  try {
    f match {
      case null => Empty
      case _ => Full(f)
    }
  } catch {
    case e: NoResultException => Empty
  }
}

trait ScalaEntityManager {
  def em : EntityManager

  // value added methods
  def findOne[A](clazz: Class[A], id: Any) = JPA.findToCan[A](em.find[A](clazz, id).asInstanceOf[A])

  def createQuery[A](queryString : String, params : Pair[String,Any]*) : ScalaQuery[A] = {
    val q = new ScalaQuery[A](em.createQuery(queryString))
    params.foreach(param => q.setParameter(param._1, param._2))
    q
  }

  def createPageQuery[A](page : Int, pageSize : Int, queryString : String, params : Pair[String,Any]*) : ScalaQuery[A] = {
    val q = createQuery[A](queryString, params : _*)
    q.setMaxResults(pageSize)
    q.setFirstResult(pageSize * page)
    q
  }

  def createNamedQuery[A](queryName : String, params : Pair[String,Any]*) : ScalaQuery[A] = {
    val q = new ScalaQuery[A](em.createNamedQuery(queryName))
    params.foreach(param => q.setParameter(param._1, param._2))
    q
  }

  // methods defined on Entity Manager
  def persist(entity: AnyRef) = em.persist(entity)
  def merge[T](entity: T): T = em.merge(entity)
  def remove(entity: AnyRef) = em.remove(entity);
  def find[A](clazz: Class[A], id: Any) = em.find[A](clazz, id).asInstanceOf[A]
  def flush() = em.flush()
  def setFlushMode(flushModeType: FlushModeType) = em.setFlushMode(flushModeType)
  def refresh(entity: AnyRef) = em.refresh(entity)
  def getFlushMode() = em.getFlushMode()
  def createNativeQuery[A](sqlString: String) = new ScalaQuery[A](em.createNativeQuery(sqlString))
  def createNativeQuery[A](sqlString: String, clazz: Class[A]) = new ScalaQuery[A](em.createNativeQuery(sqlString, clazz))
  def createNativeQuery[A](sqlString: String, resultSetMapping: String) = new ScalaQuery[A](em.createNativeQuery(sqlString, resultSetMapping))
  def close() = em.close()
  def isOpen() = em.isOpen()
  def getTransaction() = em.getTransaction()
  def joinTransaction() = em.joinTransaction()
  def clear() = em.clear()
  def getDelegate() = em.getDelegate()
  def getReference[A](clazz: Class[A], primaryKey: Any) = em.getReference[A](clazz, primaryKey)
  def lock(entity: AnyRef, lockMode: LockModeType) = em.lock(entity, lockMode)
  def contains(entity: AnyRef) = em.contains(entity)
}

class ScalaQuery[A](val query: Query) {
  // value added methods
  def findAll = getResultList()
  def findOne = JPA.findToCan[A](query.getSingleResult.asInstanceOf[A])
  def setParams(params : Pair[String,Any]*) = {params.foreach(param => query.setParameter(param._1, param._2)); this}

  // methods defined on Query
  def getResultList() = query.getResultList.asInstanceOf[java.util.List[A]].toList
  def getSingleResult() = query.getSingleResult.asInstanceOf[A]
  def executeUpdate() = query.executeUpdate()
  def setMaxResults(maxResult: Int) = {query.setMaxResults(maxResult);this}
  def setFirstResult(startPosition: Int) = {query.setFirstResult(startPosition); this}
  def setHint(hintName: String, value: Any) = {query.setHint(hintName, value); this}
  def setParameter(name: String, value: Any) = {query.setParameter(name, value); this}
  def setParameter(position: Int, value: Any) = {query.setParameter(position, value); this}
  def setParameter(name: String, value: Date, temporalType: TemporalType) = {query.setParameter(name, value, temporalType); this}
  def setParameter(position: Int, value: Date, temporalType: TemporalType) = {query.setParameter(position, value, temporalType); this}
  def setParameter(name: String, value: Calendar, temporalType: TemporalType) = {query.setParameter(name, value, temporalType); this}
  def setParameter(position: Int, value: Calendar, temporalType: TemporalType) = {query.setParameter(position, value, temporalType); this}
  def setFlushMode(flushMode: FlushModeType) = {query.setFlushMode(flushMode); this}
}



Reply via email to