3

i have one REST API method :which will return Xml as response . Just for simplicity assume it throws simple Exception.

@RequestMapping(value = "machine/xmlData", method = RequestMethod.GET, produces = "application/xml")
    public ResponseEntity<String> getXml(HttpServletRequest request)
            throws Exception {
        return getDataFromService();

}

Now i am handling the Exception in REST Controller like this. This is generic Exception Handle method, for other API methods as well.(Xml or JSON Response)

 @ExceptionHandler(Exception.class)
        @ResponseStatus(value = HttpStatus.INTERNAL_SERVER_ERROR)
        public ResponseEntity HandleException(Exception ex, HttpServletRequest request) {
            ex.printStackTrace();
           // here logic to generate Custom error Object
            return new ResponseEntity<Object>(customErrorObject, HttpStatus.INTERNAL_SERVER_ERROR);
        }

Case 1: Accept :"application/xml" and valid Response from Service Everything works fine.

Case 2: Accept :"application/xml" and Exception from Service then i get 406 Not Representable

As per my understanding it is

because ResponseEntity from HandleException is JSON and accept header is "application/xml" thats why i am getting 406.

Is there anyway that i can send the error Response from HandleException method as xml and json ? I know on REST API methods we can define something like this produces={"application/json","application/xml"} i am struggling to put this on HandleException Method.

Any tip would be of great help.

Thanks.

2
  • remove @ResponseStatus in handleException and try Commented Dec 5, 2016 at 11:52
  • @kuhajeyan it does not help . i tried Commented Dec 5, 2016 at 14:16

1 Answer 1

2

You could take advantage of the spring-mvc HttpMessageConverters by using the @ResponseBody annotation( https://spring.io/blog/2013/05/11/content-negotiation-using-spring-mvc). This annotation is responsible for choosing the correct messageConverter for a given response type.

For your response to be xml or json compatible you need to do the following:

@XmlRootElement
@XmlAccessorType(XmlAccessType.FIELD)
public class WrappedExceptionResponse {
    public String respone;

    public String getRespone() {
        return respone;
    }

    public void setRespone(String respone) {
        this.respone = respone;
    }
}

And change your exception handler method to

    @ExceptionHandler(Exception.class)
    @ResponseStatus(value = HttpStatus.INTERNAL_SERVER_ERROR)
    public @ResponseBody WrappedExceptionResponse HandleException(Exception ex, HttpServletRequest request) {
//        ex.printStackTrace();
       // here logic to generate Custom error Object
        WrappedExceptionResponse resp=new WrappedExceptionResponse();
        resp.setRespone(ex.getMessage());
    return resp;

And then your exception response would be dependent on the content-type you give.

Sign up to request clarification or add additional context in comments.

7 Comments

but then its static , i cant use it for JSON MediaTypes. I would like to have some Generic Error Response.
Eddited my answer please check if it works as expected for both json and xml .
it does not help. @ResponseBody is not automatically using the right convertor.
If you change your rest endpoint to @RequestMapping(value = "machine/xmlData", method = RequestMethod.GET, produces = {"application/xml","application/json"}). Then the response type would be different with headers like Accept:application/json or Accept:application/xml. The response type is closely related to your Accept header for get requests.
Adding jackson xml dependency helped.
|

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.