I am trying to create a custom field type in Squeryl. This field represents an Isin code, so it is backed up by a string field. Following the example on the documentation, I have added a simple validation before creating a new isin (never mind what an Isin code is or how the validation procedure works):
trait Domain[A] { self: CustomType[A] =>
def validate(a: A): Unit
validate(value)
}
class Isin(v: String) extends StringField(v) with Domain[String] {
println("instantiating Isin")
override def validate(s: String) {
println("calling validate with " + s)
assert(checkIsin(s))
}
private def checkIsin(isin: String): Boolean = {
// never mind the exact procedure
}
}
I have added some println
to find out what is going on. I use this field inside a model like
case class Asset(
val id: Long = 0,
val isin: Isin
) extends KeyedEntity[Long]
object Asset {
import Database.assets
def create(isinCode: String) {
inTransaction {
assets.insert(new Asset(isin = new Isin(isinCode)))
}
}
}
Now, when I call Asset.create("US0378331005")
(a valid ISIN) I get an exception. In the stacktrace it turns out that this exception is due to a call to the init
method on a null
value, which is supposedly passed to checkIsin
. Indeed, the println
statements print
calling validate with US0378331005
Instantiating Isin
calling validate with
So it seems that the validate
method is actually invoked twice, but the second time it gets a null
value.
What is going on wrong?