I would like to introduce IFormValidator and AbstractFormValidator
specific for validating Forms.
Currently we add multiple - reusable - validations to fields, but when
we have specific validations on a form level, we have to know about the
internals of the Form (which steps does it take in validation), and/ or
have to write a custom validation strategy (which certainly is not
straightforward to include form level validation). Because of the form
not supporting validation on a form level with an easy mechanism such as
there is for the form components, Wicket encourages to write
non-reusable, monolithic pieces of code, e.g. in the onSubmit method,
with all kinds of hacks like reversing the model updates and manually
setting error messages when something goes wrong. Note 'encourages'
here, as it *is* possible to do it neat, but that's just not what I see
in projects here, and it certainly isn't obvious how that should be done.
The way it must currently be done (though I just found a few bugs
preventing even this to work) using an example where I have a validate
method on object Product which returns a list of non-wicket validation
messages:
public IFormValidationStrategy getValidationStrategy()
{
final IFormValidationStrategy defaultStategy =
super.getValidationStrategy();
IFormValidationStrategy productStategy = new
IFormValidationStrategy()
{
public void validate(Form form)
{
defaultStategy.validate(form);
Product product = (Product)getModelObject();
List msgs = product.validate();
if (msgs != null && (!msgs.isEmpty()))
{
for (Iterator i = msgs.iterator(); i.hasNext();)
{
ValidationMessage msg =
(ValidationMessage)i.next();
Localizer localizer = form.getLocalizer();
String message =
localizer.getString(msg.getMessageKeyKey(), form);
form.error(message);
}
}
}
};
return productStategy;
}
Where getValidationStrategy overrides the super method (which means that
in order to validate a form you allways have to subclass)
In the new way, this could be:
class ProductFormValidator extends AbstractFormValidator
{
public void onValidate()
{
Product product = (Product)getForm().getModelObject();
List msgs = product.validate();
if (msgs != null && (!msgs.isEmpty()))
{
for (Iterator i = msgs.iterator(); i.hasNext();)
{
ValidationMessage msg = (ValidationMessage)i.next();
error(msg.getMessageKeyKey());
}
}
}
}
and just add(new ProductFormValidator()); to your form.
Not only is this shorter/ more obvious (same mechanism as FormFields) it
also supports reuse better.
Any objections? And should this be put in the 1.0 branch as well?
Eelco
-------------------------------------------------------
This SF.Net email is sponsored by: NEC IT Guy Games. How far can you shotput
a projector? How fast can you ride your desk chair down the office luge track?
If you want to score the big prize, get to know the little guy.
Play to win an NEC 61" plasma display: http://www.necitguy.com/?r=20
_______________________________________________
Wicket-develop mailing list
[email protected]
https://lists.sourceforge.net/lists/listinfo/wicket-develop