假设一个Car
模型对象(如case class
),不可变且使用构建器模式创建。 (由Joshua Bloch制作的模式)。Play Framework 2 /冗余对象验证
其build
方法调用CarValidator
对象,以便允许创建或不相关的Car
。否则,它会抛出一个IllegalStateException
,其中包含意外的字段。
因此,在运行时,任何人都无法创建陈旧或无效的Car
,太棒了!
现在假设一个web表单创建一个Car
。 Play的控制器将含有这种形式的映射:
val carForm = Form( //this is a conceptual sample
mapping(
"brand" -> nonEmptyText,
"description" -> nonEmptyText,
"maxSpeed" -> number
"complexElement" -> number.verifying(........) //redundant validation here
)(Car.apply)(Car.unapply)
)
在这个例子中,有一些基础领域,但想象的复杂领域,要求复杂的业务验证喜欢这里的complexeElement
。
我真的有这样的感觉,我很容易打破干(不要重复自己)。
事实上,无论表单验证会带来什么结果,这将由我的Car
构建器的验证器提供,因为对模型的验证是最重要的验证位置,不应该依赖于其他任何内容。
我想象一下Helper
类的解决方案,该类接近我的Controller
,处理与构建器使用的相同验证器对象。然而,它迫使我得到所有验证方法public
,以便在我的Web表单的任何验证步骤(如上面的代码段中)独立调用。
保持这个建设者的原则,同时避免打破DRY会是一个很好的做法吗?
如果我没有直接在映射中进行直接验证,我怎么能在映射表单时使用由Play提供的错误通知机制? – Mik378 2013-02-18 00:43:02
您可以使用Form'类的'withError'方法 – EECOLOR 2013-02-18 10:40:52
最后,我选择在模型和表单之间共享一个Validator。这个验证器返回一些'ValidationNEL'(从scalaz),我不得不将它们调整为'Constraint',以便设置它们来验证我的表单的方法。第一个建议的解决方案并不是最佳的,因为有了它,我们永远无法在一个步骤中显示整个错误列表。 – Mik378 2013-02-21 21:32:54