We're using Dropwizard as a platform for our REST service and make use of its exception mappers to deal with any exceptions thrown during the user journey. We're using google guice for dependency injection.
In one of our use cases, when an exception is thrown, we need to attach some extra information to the response that is not available at the point where exception is thrown.
The following flow diagram highlights the use case.
Object A -> Object b -> Object C
Object A has the main input available which has the extra information and Object C is where the exception is thrown. Also, Object C is an adapter that talks to an external system and at the moment we don't have the option to carry our input from Object A through C.
When exception is thrown, the thread goes into an exception mapper from where the Response is returned.
Is there a way to make the input available in the exception mapper via some dropwizard/jersey/guice annotation magic ?
I've been able to do this by defining a RequestScoped (#RequestScoped) bean that can hold intermediary result and then injecting it into the dropwizard exception mapper using #Inject. Google Guice magic.
Related
I am using BeanValidation (with DropWizzard). Now if a form contains a field annotated with #NotEmpty, but is empty, I'll get an InternalServer ErrorException with Status Code 500.
I'd like to log a RuntimeException for this and forward the user to an error page.
Is it possible to catch all ValidationException in one place, log them and do something like forwarding the user?
You can build your own exception mapper for the ValidationException. Jersey have its own ValidationExceptionMapper implementation that will return a bad request if the element is a parameter that is validated or a internal server error if the validation occur on a return value. Latest version of Dropwizard should configure these mappers by default.
To build your own exception mapper you should implement the interface javax.ws.rs.ext.ExceptionMapper and register it in the jersey context of Dropwizard ieenvironment.jersy().register(MyExceptionMapper.class)if you use Dropwizard 0.8 or later
I have a web application in which I throw some custom exceptions(application exceptions annotated with #ApplicationException) and there is an exception mapper(provider annotated with #Provider) for each. Recently I forgot to annotate an exception with #ApplicationException and still the mapper is able to identify the exception and format the response properly.
Then I checked the documentation and I understood that the annotation will be inherited by its child class by default. So I removed the annotation from the super class and checked. The mapper still identified the exception and formatted the response.
Then I went even forward and tried throwing java.lang.IllegalArgumentException and wrote a mapper class for it. It also worked properly. Is javax.ws.rs.ext.ExceptionMapper independent of the exception being thrown. Will it not check if whether thrown exception is really annotated with #ApplicationException?
#Provider
public class IllegalArgumentExceptionMapper implements ExceptionMapper<java.lang.IllegalArgumentException> {
#Override
public Response toResponse(java.lang.IllegalArgumentException exception) {
return Response.status(Status.BAD_REQUEST).entity(exception.getMessage()).build();
}
}
Somewhere in my service class:
throw new java.lang.IllegalArgumentException("Problem with the payload. Please check the payload you are sending");
The answer is no, it will not check if whether thrown exception is really annotated with #ApplicationException.
The exception mapper is independent of the #ApplicationException.
All the exception mapper knows is, if there's no exception caught until the almost last layer, it will be processed here, if it find a matching provider.
You can also actually create a provider for RuntimeException and all exception happened in the REST request will land here (but this is not good practice, we should always throw custom exception and catch them with the provider and convert them to good error response).
When you annotate the exception with #ApplicationException you can control things like whether the transaction should be rollback, and whether it will be wrapped by EJBException etc etc.
I have heard that it is possible to log (or do something else) Exceptions with Spring in my web-App, so I don't have to manually insert in every "catch(){}" block the Log-function.
Does anyone have experience with Spring-overall-logging? I just want to get informed when an error appears
ExceptionHandler is the central point for handling unexpected Exceptions that are thrown during the Faces lifecycle. The ExceptionHandler must not be notified of any Exceptions that occur during application startup or shutdown.
See the specification prose document for the requirements for the default implementation. Exceptions may be passed to the ExceptionHandler in one of two ways:
1.)By ensuring that Exceptions are not caught, or are caught and re-thrown.
This approach allows the ExceptionHandler facility specified in section JSF.6.2 to operate on the Exception.
2.)By using the system event facility to publish an ExceptionQueuedEvent that wraps the Exception.
This approach requires manually publishing the ExceptionQueuedEvent, but allows more information about the Exception to be stored in the event. The following code is an example of how to do this.
Global Exception Handler – Exception Handling is a cross-cutting concern, it should be done for all the pointcuts in our application. We have already looked into Spring AOP and that’s why Spring provides #ControllerAdvice annotation that we can use with any class to define our global exception handler.
The handler methods in Global Controller Advice is same as Controller based exception handler methods and used when controller class is not able to handle the exception.
Sample Code
#ExceptionHandler(Exception.class)
public ModelAndView getExceptionPage(Exception e, HttpServletRequest request) {
request.setAttribute("errorMessageObject", e.toString());
return model;
}
** Here we can catch the base exception class Exception.class or any other exception class. Also we can throw and catch our own custom defines exception class.
I have a default catch exception strategy for my entire flow/subflows. However, I'd like to be able to tell what component/endpoint threw an exception so I can try to restart the flow at that point (I have yet to figure out how to do that as well.)
Is there any easy way to tell what component/endpoint threw the exception, and be able to tell if it was in a foreach, and at what point (by looking at the "counter" variable.)
Thanks!
You can set a variable at the start of flow like this:
<set-variable variableName="flowName" value="Your_flow_name"/>
And the get the flow name like #[flowName] in your exception strategy.
EDIT:
To trigger a flow, create a java component implementing Callable interface, from the context get the MuleClient and use send or dispatch method to send payload to flow. Send causes MuleClient to wait for response while dispatch doesn't.
More info here: http://www.mulesoft.org/documentation/display/current/Using+the+Mule+Client
I have error_messages table, which contains the site-wide error messages.
I use the error messages across application. So, I created singleton bean of error messages (ErrorMessagesLoad.java)
ErrorMessagesLoad uses ErrorMessageDao to retrieve the error messages from database.
Should I create static variable in ErrorMessagesLoad to hold all the error messages and use it in all classes? or is there better way of doing it?
Thanks,
Satya
You should use your own implementation of MessageSource in Spring to resolve any messages. Here is a good point to start.
When implemented, you just wire your bean to any service or controller and it handles messages for you, with ability to iternationalize them.
In general global static variables should be avoided. Error handling can get tricky. Many applications try to put a global catch handler somewhere near the top (e.g. web applications the top would be filters) which has the ErrorMessagesLoad injected into it. That handler catches underlying exceptions, translates them into something user readable and then throws that higher.
Some examples include Spring's exception translation filter and Jersey's exception mapping mechanism.