Reputation: 1688
In the Scala Lift framework, how do I make a trait that I can mix into mapped fields to that I don not have to override the same properties for many fields in a database?
I would like to eliminate some redundancy in the code below. Specifically, I do not want to have to repeatedly add:
override def writePermission_? = false
override def readPermission_? = false
override def shouldDisplay_? = false
override def show_? = false
override def dbDisplay_? = false
for the several db fields. I am thinking that the way to go about this would be to write a trait that looks something like this:
trait PrivateField extends ...??? {
override def writePermission_? = false
override def readPermission_? = false
override def shouldDisplay_? = false
override def show_? = false
override def dbDisplay_? = false
}
and then mix this into the object overrides as follows:
object owner extends MappedLongForeignKey(this, User) with PrivateField
object status extends MappedInt(this) with PrivateField
etc. Is this a good way to approach the problem? If so, any suggestions on how to write the trait? Below is the code for which I want to reduce the redundancy.
class Mytable extends LongKeyedMapper[Mytable] with IdPK {
def getSingleton = Myclass
object owner extends MappedLongForeignKey(this, User) {
override def writePermission_? = false
override def readPermission_? = false
override def shouldDisplay_? = false
override def show_? = false
override def dbDisplay_? = false
}
object description extends MappedString(this, 140)
object name extends MappedString(this, 140)
object status extends MappedInt(this) {
override def writePermission_? = false
override def readPermission_? = false
override def shouldDisplay_? = false
override def show_? = false
override def dbDisplay_? = false
}
object entry_number extends MappedInt(this) {
override def writePermission_? = false
override def readPermission_? = false
override def shouldDisplay_? = false
override def show_? = false
}
object quanitity extends MappedDecimal(this, MathContext.DECIMAL64, 2) {
override def writePermission_? = false
override def readPermission_? = false
override def shouldDisplay_? = false
override def show_? = false
override def dbDisplay_? = false
}
}
object Mytable extends Mytable with LongKeyedMetaMapper[Mytable] with CRUDify[Long, Mytable] {
override def editMenuLoc:Box[Menu] = Empty
override def deleteMenuLoc:Box[Menu] = Empty
override def viewMenuLoc:Box[Menu] = Empty
override def createMenuLocParams: List[Loc.AnyLocParam] = List(If(User.loggedIn_? _, "Not logged in"))
override def showAllMenuLocParams: List[Loc.AnyLocParam] = List(If(User.loggedIn_? _, "Not logged in"))
override def findForList(start: Long, cnt: Int): List[Mytable] =
findAll(StartAt(start), MaxRows(cnt), By(owner, User.currentUser))
override def findForParam(in: String): Box[Mytable] =
for {
user <- User.currentUser
id <- Helpers.asLong(in)
mytable <- find(By(this.id, id), By(owner, user))
} yield mytable
}
Thanks,
Upvotes: 0
Views: 32
Reputation: 159955
The simplest way is probably to use a self type annotation:
trait PrivateField[FieldType <: Any, OwnerType <: Mapper[OwnerType]] {
self: MappedField[FieldType, OwnerType] =>
override def writePermission_? = false
override def readPermission_? = false
override def shouldDisplay_? = false
override def show_? = false
}
Then you can use it in this manner:
MappedInt(this) with PrivateField[Int, Mytable]
Upvotes: 1