简体   繁体   中英

Custom Annotation Spring MVC ResultBinding

I have a simple MVC controller that I annotate with my custom annotation:

@PreAuthorize("hasRole('GESTION_BENEFICIAIRE')")
@AuthentificationForte(otp = "#{args[0]}",transactionId="#{args[1]}")
@RequestMapping(value = "/ajouter", method = { RequestMethod.POST, RequestMethod.GET })
public String addBeneficiaire(@ModelAttribute("beneficiaireForm") BeneficiaireForm beneficiaireForm,
                              BindingResult result, Model model, Principal principal) {
  [...]
}

My custom annotation is linked with an aspect that throws a RuntimeException when the validation doesn't succeed.

@Around(value = "@annotation(annotation)")
public Object verifyOtp(final ProceedingJoinPoint jointPoint,
                        final AuthentificationForte annotation) throws Throwable {
  try {
    if (authentificationForteEnabled) {
      [...]
    } else {
      throw new AuthentificationForteException();
    }
    } else {
      return jointPoint.proceed();
    }
  } finally {

  }
}

So now the behavior is that when the validation fails, I am redirected to a 500 Error page. My goal is to stay in the same page and add a rejected message to the BindingResult :

 result.rejectValue("suiteRib", "BeneficiaireForm.InvalidRib");

I haven't found a way to do that, the only way that I've found is to change all my logic and not use the annotation, while using a validation service with a try/catch in the controller code.

Is there any way to handle this and to access the binding result and add the error message when the aspect throws this exception?

Most definitely.

There is an example here of manipulating args: Aspectj overwrite an argument of a method

You can also autowire services into the aspect class (remember to mark it @Configurable).

If you know the arguments before hand, then I think they can be included into the point cut definition, in which case they can be referred to directly in the around method. This is much nicer was as the arguments come strongly type.

You can read more here: http://docs.spring.io/spring/docs/current/spring-framework-reference/html/aop.html

May be its too late to answer your question but there are two ways you can handle it :

  1. Have a try catch around proceed() in your aspect and when you get runtime exception you can either return the response from the aspect ( like a generic JSP showing the cause of error or generic JSON with error message.)
  2. Second option could be to use Spring Exception Handler Controller advice. Spring MVC provides nice exception handler controller mechanism to call specific handler method for given type of exception class. ( Here is the blog link : https://spring.io/blog/2013/11/01/exception-handling-in-spring-mvc )

We currently have an application where we use mix of this approach to handle exception.

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM