2012-08-29 12 views
0

Squeryl에서 사용자 정의 필드 유형을 만들려고합니다. 이 필드는 Isin code을 나타내므로 문자열 필드로 백업됩니다. example on the documentation 다음, 나는 새로운 ISIN를 작성하기 전에 간단한 유효성 검사를 추가 한 (AN 이신 코드가 무엇인지 신경 쓰지 또는 검증 절차는 어떻게 작동하는지 절대) :Squeryl 사용자 정의 필드 유형

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

내가 무슨 일이 일어나고 있는지 알아 일부 println을 추가 한 . 나는 예외가 (유효한 ISIN) Asset.create("US0378331005")를 호출 할 때 나는 지금

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

같은 모델 내에서이 필드를 사용합니다. 스택 트레이스 그것은이 예외로 인해 아마 checkIsin에 전달되는 null 값에 init 메소드를 호출하는 것으로 나타났다. 실제로, println 문은

calling validate with US0378331005 
Instantiating Isin 
calling validate with 

를 인쇄 그래서는 validate 방법은 실제로 두 번 호출 될 것 같다,하지만 두 번째 시간은이 null 값을 가져옵니다.

잘못에 무엇 이죠? 몇 가지 문제는 여기에있다

답변

1

있습니다. 첫째로, Lift Record를 사용하고있는 것처럼 보입니다. 그렇다면 유효성 검사 논리를 잘못 구현하는 것입니다. 레코드 필드의 유효성을 확인하는 올바른 방법은 ValidationFunction이 유형의 별칭

type ValidationFunction = ValueType => List[FieldError] 

및 귀하의 경우 치형 == 문자열에에게 있습니다

def validations: List[ValidationFunction] 

을 무시하는 것입니다.

다음 문제는 도메인의 특성이다. validate에 대한 호출이 클래스 정의로 인라인되기 때문에 필드가 생성 될 때 호출됩니다. 분명히 그 시점에 설정된 값이 없기 때문에 빈 값을 참조하는 println을 보게됩니다. 내가 본 순서는 애플리케이션 흐름과 관련이 있다고 상상해보십시오. 유효성이 검증 된 기존 레코드가 있고 그 다음에 다음 2 개의 println 문을 트리거하는 새 레코드가 작성됩니다.

관련 문제