0

We have the validate() method directly available in our action classes in which we can put our own logic to perform some kind of validations we need.

For example, if I need to validate two fields regarding date-time, I can put my own logic in the validate() method something like the following.

public final class DiscountAction extends ActionSupport implements ValidationAware, ModelDriven<Discount>
{
    private Discount entity=new Discount();

    @Override
    public Discount getModel() {
        return entity;
    }

    @Override
    public void validate()
    {
        if(entity.getDiscountStartDate()!=null&&entity.getDiscountEndDate()!=null)
        {
            final int period=30;
            final DateTime startDate=entity.getDiscountStartDate().withZone(DateTimeZone.forID("Asia/Kolkata")).withMillisOfSecond(0);
            final DateTime endDate=entity.getDiscountEndDate().withZone(DateTimeZone.forID("Asia/Kolkata")).withMillisOfSecond(0);
            final DateTime currentDate=new DateTime(DateTimeZone.forID("Asia/Kolkata"));
            final int daysBetween = Days.daysBetween(startDate, endDate).getDays();

            if(startDate.isAfter(endDate))
            {
                addFieldError("discountStartDate", "The start date must be earlier than the end date.");
            }
            else if(startDate.equals(endDate))
            {
                addFieldError("discountEndDate", "Both the dates can not be same.");
            }
            else if(DateTimeComparator.getDateOnlyInstance().compare(currentDate, endDate)==0 || endDate.isBefore(currentDate))
            {
                addFieldError("discountEndDate", "Can not be today's date or any day before today.");
            }
            else if(Days.daysBetween(startDate, endDate).getDays()<1)
            {
                addFieldError("discountEndDate", "There must be an interval of at least one day.");
            }
            else if(daysBetween>period)
            {
                addFieldError("discountEndDate", "The discount period is valid only upto "+period+(period==1?" day":" days")+" period which it excceds. The actual difference is "+daysBetween);
            }
        }
    }
}

Assuming entity is an instance of the model class.

Why do we need a custom validator here? I have not yet tried a custom validator, since it is not needed yet.

Could you please show me a real situation/example where a custom validator is precisely need?

Tiny
  • 27,221
  • 105
  • 339
  • 599
  • 2
    I strongly against using `validate` method, if you seriously want to validate your entities or data either use build in validator framework of Struts2 or use other plugin like Struts2-JSR303 which are more powerful and flexible – Umesh Awasthi Jan 30 '14 at 05:43
  • 1
    If you need to do this validation in different action classes, then custom validator is perfect solution. – Aleksandr M Jan 30 '14 at 09:22
  • A real situation where the custom validator is precisely need. See http://stackoverflow.com/q/20835110/573032 – Roman C Jan 30 '14 at 20:22

2 Answers2

3

Custom validators are used when:

  • You want to use annotation- or XML-based validation
  • You want to re-use the same validation across many actions, with the caveat that...
  • ...if the validation already exists in external logic, which it should anyway, you can re-use it in validate methods as well

The business logic for custom validators should already exist as a separate entity. It should not exist as code embedded in an action; it makes both the action, and the validation, much harder to test.

When the logic is located in its appropriate place, it's easy to use in either a validator or a validate method. The advantage is easy re-use in XML and/or annotations.

Dave Newton
  • 158,873
  • 26
  • 254
  • 302
1

In such point-of-view, I can also claim that Struts2 is not needed too because I can implement my web application using C++. Could you accept? I think no, because using an MVC pattern such Struts2 makes your application more clean and maintainable. Also, you do not have to redo things again yourself when they're implemented already.

In same way, if you want to use already implemented and tested best practices and also if you would like to save time and money by not doing things from scratch, and if you like maintainable codes using separated concerns ... then you need to use Struts2 custom validators instead of that ugly validate method (It's ugly because aspects such validations should not mixed with business logic - see AOP).

Yasser Zamani
  • 2,380
  • 21
  • 18