I am working on REST API with CXF framework. Anybody can explain to me more detail about what's different between InFaultInterceptor vs. OutFaultInterceptor? They seems belong to different phase of interceptor. But Do we should put what logic into different Fault Interceptor? I need to abort interceptor chain and response custom response message. I cannot see different on InFaultInterceptor and OutFaultInterceptor for my scenario. What's your typical error handler interceptor? Could you brief introduce your error handling structure of CXF if convenient?
The concept in the interceptor chain is pretty straightforward, in is coming in, out is going out.
For instance, if you want to change the way faults are populated in a SOAP Fault, say to get some variable you are putting in the exception you are throwing, you would use say the Soap12FaultOutInterceptor to modify the fault you are generating. The Soap12FaultInInterceptor would be used to handle incoming faults.
My real question is why do you want to use the interceptor chain, and what is your use case? This is not unusual, but many times unnecessary especially with Spring and aspecting, IMO.
Related
I have the following question. I find myself in using ResponseEntity inside a RestController in Spring whenever I want to manipulate the HTTP response coming back from my controller.
Let's say now that the outcome of this response depends indeed on what happens on the business layer below. Let's say this layer makes an http call, if it goes right I forward back above a positive message, instead I forward a negative message.
My controller now receives a message, but it would be nice to analyze whetever what happened down below was successful or not. So, can I return from the business level a ResponseEntity and mark it already as 400 or 200 (depending on what happens down there) or there is another better practice?
Sure you can. Technically ResponseEntity is a class like any other, you can return an instance of it from any layer.
The question you should ask yourself though, is this a good practise to return object of that class from a method that suppose to perform some business logic? For me it does not feel right. You introduce layers to separate concerns. Your domain layer should be totally agnostic of off communication protocol your application offer.
If you design domain layer right you'll know what went wrong based on thrown exception. Then you'll also know which HTTP status you should return.
This violates the concept of separation of layers: It is the controller's only job, and only the controller's job, to translate between the language of HTTP and your application's internal language (API). What if, in the future, you want to change how your HTTP API works but support multiple versions at the same time?
Instead, this is exactly what exceptions are for: Throw a sensible exception from your business methods. I frequently create subclasses of exception types such as IllegalStateException to represent application-specific errors, and sometimes I use the existing exception classes directly.
Normally I try to use exceptions only for "exceptional" conditions ("Effective Java ", Issue 69). My personal interpretation is:
if I hit a condition in a specific part in code (normally a method or constructor) where I can't give a meaningful answer or outcome anymore I throw an exception and whoever called the piece of code has to handle it.
In the special case of HTTP endpoints I can always give a meaningful answer - a response with a status code.
Handling bad requests thus belongs to normal program flow of endpoint methods and should not raise new exception.
E.g. an endpoint that returns a resource should just return 404 in case the resource is not found. In my opinion it would be bad practice to raise a "SomethingNotFoundExcetion" (that could be handled by an error handler and create 404 response)
My question is: It is bad practice to use Spring Boot's error handling mechanism for bad requests (4xy) that relies on exceptions to create specific HTTP responses. (It is really fine for all uncovered errors yielding 500)
(I am just writing a review of code and I am not sure if I should suggest to not use error handler for "normal" API interaction)
Answer/Comment to current answers
It seems that the most of you missed the important part of my reasoning:
(citing Effective Java, Item 69):
Use exceptions only for exceptional
conditions ...
this reasoning:
• Because exceptions are designed for exceptional circumstances, there is little
incentive for JVM implementors to make them as fast as explicit tests.
• Placing code inside a try-catch block inhibits certain optimizations that
JVM implementations might otherwise perform.
The main point for me is:
A well-designed API
must not force its clients to use exceptions for ordinary control flow.
Especially in case of rest API. It should be easy to use any API in a way to avoid exceptions at all. This means for me. No correct (defined e.g. in Open API) usage of a Rest API should raise an exception.
To put another point: The standard for SOAP (another http based API stuff) forbids to use "SOAP fault" for correct (defined by WSDL) requests.
For me raising exception in remote APIs on not exceptional cases are even worse then in classic API (via dependency).
It depends on your project, it's really a matter of opinion/architectural decision. I'd say either-or.
The advantage of using specific Exceptions and then using a Spring handler to map them is that it removes the tedious construction of responses with the correct code from the actual application logic code (it's not dissimilar from aspects in that respect): just throw the correct exception and be done with it.
OTOH, the distance to the error handling code means that 1. if something doesn't work, it may be difficult to track down the issue 2. you need to know what exceptions to throw, and that is not immediately obvious and needs to be documented well.
It is not a bad practice, but a matter of architectural decision. It could be good to have an error handler that will produce a 4xx response and will do some additional error handling work, such as logging, and/or sending a notification by mail or queue or (like in my project) write errors in the table so they could be reviewed by user using GUI component of an application and may be even edited and re-submitted if it makes sense. It also unifies the error handling to a single code (code re-use). But if you really just need to send a 4xx response and nothing else, then its OK not raise exception and just do it in your code. Raising exception is expensive performance-wise and shouldn't be done just for the sake of raising exception alone. But in this particular case my opinion is to use Exception/Spring boot Error handling mechanism
I need to handle the exceptions in My rest API.
I have a layered architecture, composed by Entities, DAOs, Services and controllers.
In my services I have the model Exceptions, and I need to know the best way to translate these exceptions to send responses in HTTP.
I read about Exception handler and Controller advice but I'm not sure how is the best form to do this.
Anyone can iluminate me?
Thanks
I would go with #ControllerAdvice for most of the exceptions, for instance, validation error, system errors etc. On the other hand, you could use error handlers for specific cases in your controllers.
This way you have generalized error handler with the possibility to overwrite the default error handling.
One way is by the use of spring ExceptionHandler (there are several variants possible depending on spring version).
Some good documentation here
best way is to create your own custom exception class and dont handle any excpetion in dao & services instead of just throw custom exception from there
and handle all excpetion in controller and response back meaning full message to client from controller.
I have CXF Interceptor that checks field in SOAP header. I want to skip this check for a single method.
Is it possible to do it without parsing soap and checking for method name (for example, annotation).
Thank you!
If you put your interceptor fairly late in the chain (USER_LOGICAL for example), you can grab the BindingOperationInfo object from the exchange to determine which operation was used to process the body. From there, decide wether to look at the SOAP headers or not.
An interceptor gets executed even before CXF has started parsing the xml message (actually I use them to change the xml parser secure factory implementation class :P ), so I think what you need is not supported by the architecture (or at least I am unable to find it, if someone wants to bring some light here I will thank it too).
http://cxf.apache.org/docs/interceptors.html
May you separe your functionality in 2 webservices, each one with different interceptors and validation levels?
I know a lot has been discussed around exception handling, however I need some advice specific to my situation.
I am currently working on a Spring MVC application with Controller->Services->DAO layers. The service classes catch mainly two kinds of exceptions HibernateException and IOException.
HibernateException because service needs to perform rollback if a transaction did not succeed and IOException since it is an unchecked exception and needs to be caught or thrown and I prefer the first option.
Now what would be a better way of handling these further up in the stack :
Should I rethrow these exceptions to the controller and in the
ExceptionHandler of the controller send a HTTP error-code 500
Or in the catch block create the normal JSON response object, setting status=failure and the appropriate error message and return this to the Controller?
Exception Handling convensions:
There is a saying that, best way of handling Exception is not to handle it!
For Spring's convention of controller<->service<->dao layers, Exception handling mechanism is known as Bubble up. Any exception occurs in the dao or service layer, you should pop it up to the controller layer (by adding throws XXXException in dao and service layer's method signature, is the most common way). Only controller layer should handle Exceptions.
Here is a nice tutorial of how you can handle exceptions for REST with spring.
Send HTTP Status code 500 or JSON object with status:
Sounds like you are writing API with Spring MVC. Look, when you are writing API's you should follow the proper conventions. It is Globally accepted that for internal server errors you send HTTP response with code 500, that means internal server errors.
There are number of causes for what you should not send JSON response in this case. One of the main cause is the implicit assumption of your API client. That is HTTP response with code 200 with a JSON object means every thing went normal. And thus the client side business logic may reflect that assumption which is wrong eventually.
Here you can see some API error code conventions for some well-known organizations:
twitter
LinkedIn
Facebook Graph API
I assume that you have not come so far yet as to create a client and therefor can pick 100% for yourself.
If so I would also recommend to use 1, for the main reason that using the correct status codes can go a long way in your API, as well as it's a very easy solution to your problem. You can write some neat code for your error handling.
Another major reason why you should use your first point is because you can easily re-use the error handling for other APIs, resources or webapps.
For example an enum with all your errors, and what status code you consider them to be, and you can also include what log level you want them to be.
public enum ExceptionMapping {
IllegalArgumentException(IllegalArgumentException.class, 400, LogLevel.ERROR),
If your goal is to build a neat API for unknown clients I would recommend reading more about REST level 3 (http://martinfowler.com/articles/richardsonMaturityModel.html) where you includes hypermedia links to create an API which allows the client to "browse" your full API. It's more work for the client since they have to be smarter but it can provide you with very nice features such as breaking a large part of your API without the client even noticing.