Registering a custom out fault interceptor might do the trick and you
can handle both JAXWS and JAXRS exceptions from there...For ex, if the
in message has an application/soap content type then WSBaseException has
to be handled one way, otherwise it is a JAXRS service exception
Cheers, Sergey
-----Original Message-----
From: vickatvuuch [mailto:[email protected]]
Sent: 17 November 2009 20:38
To: [email protected]
Subject: Re: CXF jaxrs REST exception stack trace propagated to REST
client, can exception be wrapped up or filtered out or AOP intercepted?
In the end I wipped up something like this, which seem to be serving the
purpose.
Now I need to figure out how to do something similar on the Soap side.
public class RestExceptionMapper implements ExceptionMapper<Exception>
{
private static Log logger =
LogFactory.getLog(RestExceptionMapper.class);
private static final ResourceBundle BUNDLE =
BundleUtils.getBundle(WebApplicationExceptionMapper.class);
public Response toResponse(Exception exception)
{
logger.error("REST exception: ", exception);
if (exception instanceof WSAuthException)
{
// do not give details on auth failure
return Response.status(Response.Status.FORBIDDEN).build();
}
else if (exception instanceof WSBaseException)
{
// let custom port exception out
return
Response.status(Response.Status.INTERNAL_SERVER_ERROR).type(MediaType.TE
XT_PLAIN).entity(
exception.getLocalizedMessage()).build();
}
else if (exception instanceof WebApplicationException)
{
return toResponse2((WebApplicationException) exception);
}
//TODO: add one more for platform level exceptions
// the rest are server errors..
return
Response.status(Response.Status.INTERNAL_SERVER_ERROR).build();
}
public Response toResponse2(WebApplicationException ex)
{
if (logger.isWarnEnabled())
{
String message = ex.getCause() == null ? ex.getMessage() :
ex.getCause().getMessage();
if (message == null)
{
if (ex.getCause() != null)
{
message = "cause is " + ex.getCause().getClass().getName();
}
else
{
message = "no cause is available";
}
}
org.apache.cxf.common.i18n.Message errorMsg =
new org.apache.cxf.common.i18n.Message("WEB_APP_EXCEPTION",
BUNDLE, message);
logger.warn(errorMsg.toString());
}
Response r = ex.getResponse();
if (r == null)
{
String message = null;
if (ex.getCause() == null)
{
message = new
org.apache.cxf.common.i18n.Message("DEFAULT_EXCEPTION_MESSAGE",
BUNDLE).toString();
}
else
{
message = ex.getCause().getMessage();
if (message == null)
{
message = ex.getCause().getClass().getName();
}
}
r =
Response.status(Response.Status.INTERNAL_SERVER_ERROR).type(MediaType.TE
XT_PLAIN).entity(message).build();
}
return r;
}
}
Sergey Beryozkin-2 wrote:
Hi
I updated the exception handling section with few extra details, I
added a
link to a simple exception mapper used by Spring Security
tests and also linked to a custom CXF out fault interceptor.
So in summary here're the options for catching all the exceptions :
- register a mapper like ExceptionMapper<Throwable>
- register a custom out Fault Interceptor
- register a custom Servlet filter (provided that the propogation is
not
turned off)
Finally, if you'd like no exception traces reported with HTTP
responses
then just disable the propogation.
Also, I wonder
if you can tell why spring AOP is not working on the CXF impls? Tried
to
debug it, but have no clear picture yet. It seems like injection
hicks
up
on the wsContext member of the base class of my Impl class.
... 39 more
Caused by: java.lang.IllegalArgumentException
at
sun.reflect.UnsafeFieldAccessorImpl.ensureObj(UnsafeFieldAccessorImpl.ja
va
:37)
at
sun.reflect.UnsafeObjectFieldAccessorImpl.set(UnsafeObjectFieldAccessorI
mp
This exception trace looks similar. If you have a JAXWS
WebServiceContext
field then use a setter instead. Similarly for JAXRS
MessageContext
hope it helps, Sergey
Hi Mustafa!
Yes, I need to be able to have a centrally controller backstop for
all
exceptions coming out of my mackages, mostly .*Impl classes and
custom
interceptors such as i.e. Auth interceptor. Soap already kind of does
it
for
me by wrapping it into a generic Fault (I actually wanted MyException
class
instead, but I can live with Fault for unexpected errors on the Soap
side.
The jaxrs REST side behaves differently by exposing full stack
traces,
which
is what I don't want clients to see - there is log file for that
purpose..
The mapper sounds like what I could use, do you have an example how
to
intercept or map a Exception and rethrow MyException instead? Also, I
wonder
if you can tell why spring AOP is not working on the CXF impls? Tried
to
debug it, but have no clear picture yet. It seems like injection
hicks
up
on the wsContext member of the base class of my Impl class.
Mustafa Sezgin-2 wrote:
From my understanding you basically want a centralised place to
handle
exceptions and a way to control what is returned to the client? We
use
an
exception mapper which receives all possible exceptions and you can
then
return the desired response object based on the exception. We have a
many
to one mapping between exceptions and the status codes we return in
XML
format and are able to handle all exceptions ensuring that not
undesired
responses get sent back to the client.
Have a look at
http://cwiki.apache.org/CXF20DOC/jax-rs.html#JAX-RS-Exceptionhandling
-----Original Message-----
From: vickatvuuch [mailto:[email protected]]
Sent: Tuesday, 17 November 2009 9:30 AM
To: [email protected]
Subject: CXF jaxrs REST exception stack trace propagated to REST
client,
can exception be wrapped up or filtered out or AOP intercepted?
Hi All,
Is there a way to Not propagate unchecked exception stack traces
back to
the
client?
Use case: I have a port, that expects certain parameters, if one of
them
is
null
it may throw unchecked IllegalArgumentException, which could be
rectified
if
it was
all under my control.
Imagine that other team members adding new ports and not wrapping it
up
completely.
What I wanted was to have a way to control what goes out to the
client
hopefully in one place.
For instance I have defined WSBaseException from which all other WS
layer
exceptions
should be derived and thrown out of the WS layer (annotated with
WebFault).
First thing I did, I tried try AOP "after-throwing" pointcut, which
is
where
I was hoping to intercept all outgoing exceptions and wrap them up
in
the
WSBaseException for anything
that would come out unless it was already WSBaseException, but that
didn't
work, still debugging why it fails, btw AOP config and exception is
below:
But my question is mostly about how to do this without
extra AOP, does CXF has a way of dealing with this situation
already,
may
be
I'm missing something?
Thanks,
-Vitaly
<bean id="wsExceptionInterceptorAspect"
class="com.foo.webservices.v1.WSExceptionTranslator"/>
<aop:config>
<aop:pointcut id="wsServiceOperation"
expression="execution(*
com.foo.webservices.v1.ports.auth.MyServiceImpl*.(..))"/>
<aop:aspect id="wsAfterThrowing"
ref="wsExceptionInterceptorAspect">
<aop:after-throwing pointcut-ref="wsServiceOperation"
throwing="exception" method="afterThrowing"/>
</aop:aspect>
</aop:config>
The above blows up on server startup, when it is loading the Imlp on
which
I
have a pointcut:
jaxws.EndpointImpl---1853031827,org.apache.cxf.jaxrs.spring.JAXRSServerF
ac
toryBeanDefinitionParser$SpringJAXRSServerFact
oryBean--1917449182,org.apache.cxf.jaxws.EndpointImpl--1050608923,org.ap
ac
he.cxf.jaxws.EndpointImpl--880314741,wsExcepti
onInterceptorAspect,org.springframework.aop.config.internalAutoProxyCrea
to
r,wsServiceOperation,org.springframework.aop.a
spectj.AspectJPointcutAdvisor#0]; root of factory hierarchy
- Context initialization failed
org.springframework.beans.factory.BeanCreationException: Error
creating
bean
with name 'org.apache.cxf.jaxws.EndpointImp
l---1687321673': Invocation of init method failed; nested exception
is
javax.xml.ws.WebServiceException: Creation of End
point failed
at
org.springframework.beans.factory.support.AbstractAutowireCapableBeanFac
to
ry.initializeBean(AbstractAutowireC
apableBeanFactory.java:1338)
at
org.springframework.beans.factory.support.AbstractAutowireCapableBeanFac
to
ry.doCreateBean(AbstractAutowireCap
ableBeanFactory.java:473)
at
org.springframework.beans.factory.support.AbstractAutowireCapableBeanFac
to
ry$1.run(AbstractAutowireCapableBea
nFactory.java:409)
at java.security.AccessController.doPrivileged(Native
Method)
at
org.springframework.beans.factory.support.AbstractAutowireCapableBeanFac
to
ry.createBean(AbstractAutowireCapab
leBeanFactory.java:380)
at
org.springframework.beans.factory.support.AbstractBeanFactory$1.getObjec
t(
AbstractBeanFactory.java:264)
at
org.springframework.beans.factory.support.DefaultSingletonBeanRegistry.g
et
Singleton(DefaultSingletonBeanRegis
try.java:222)
at
org.springframework.beans.factory.support.AbstractBeanFactory.doGetBean(
Ab
stractBeanFactory.java:261)
at
org.springframework.beans.factory.support.AbstractBeanFactory.getBean(Ab
st
ractBeanFactory.java:185)
at
org.springframework.beans.factory.support.AbstractBeanFactory.getBean(Ab
st
ractBeanFactory.java:164)
at
org.springframework.beans.factory.support.DefaultListableBeanFactory.pre
In
stantiateSingletons(DefaultListable
BeanFactory.java:429)
at
org.springframework.context.support.AbstractApplicationContext.finishBea
nF
actoryInitialization(AbstractApplic
ationContext.java:728)
at
org.springframework.context.support.AbstractApplicationContext.refresh(A
bs
tractApplicationContext.java:380)
at
org.springframework.web.context.ContextLoader.createWebApplicationContex
t(
ContextLoader.java:255)
at
org.springframework.web.context.ContextLoader.initWebApplicationContext(
Co
ntextLoader.java:199)
at
org.springframework.web.context.ContextLoaderListener.contextInitialized
(C
ontextLoaderListener.java:45)
at
org.apache.catalina.core.StandardContext.listenerStart(StandardContext.j
av
a:3934)
at
org.apache.catalina.core.StandardContext.start(StandardContext.java:4429
)
at
org.apache.catalina.core.ContainerBase.addChildInternal(ContainerBase.ja
va
:791)
at
org.apache.catalina.core.ContainerBase.addChild(ContainerBase.java:771)
at
org.apache.catalina.core.StandardHost.addChild(StandardHost.java:526)
at
org.apache.catalina.startup.HostConfig.deployWAR(HostConfig.java:850)
at
org.apache.catalina.startup.HostConfig.deployWARs(HostConfig.java:724)
at
org.apache.catalina.startup.HostConfig.deployApps(HostConfig.java:493)
at
org.apache.catalina.startup.HostConfig.start(HostConfig.java:1206)
at
org.apache.catalina.startup.HostConfig.lifecycleEvent(HostConfig.java:31
4)
at
org.apache.catalina.util.LifecycleSupport.fireLifecycleEvent(LifecycleSu
pp
ort.java:119)
at
org.apache.catalina.core.ContainerBase.start(ContainerBase.java:1053)
at
org.apache.catalina.core.StandardHost.start(StandardHost.java:722)
at
org.apache.catalina.core.ContainerBase.start(ContainerBase.java:1045)
at
org.apache.catalina.core.StandardEngine.start(StandardEngine.java:443)
at
org.apache.catalina.core.StandardService.start(StandardService.java:516)
at
org.apache.catalina.core.StandardServer.start(StandardServer.java:710)
at
org.apache.catalina.startup.Catalina.start(Catalina.java:583)
at sun.reflect.NativeMethodAccessorImpl.invoke0(Native
Method)
at
sun.reflect.NativeMethodAccessorImpl.invoke(NativeMethodAccessorImpl.jav
a:
39)
at
sun.reflect.DelegatingMethodAccessorImpl.invoke(DelegatingMethodAccessor
Im
pl.java:25)
at java.lang.reflect.Method.invoke(Method.java:585)
at
org.apache.catalina.startup.Bootstrap.start(Bootstrap.java:288)
at
org.apache.catalina.startup.Bootstrap.main(Bootstrap.java:413)
Caused by: javax.xml.ws.WebServiceException: Creation of Endpoint
failed
at
org.apache.cxf.jaxws.JaxWsServerFactoryBean.init(JaxWsServerFactoryBean.
ja
va:181)
at
org.apache.cxf.jaxws.JaxWsServerFactoryBean.create(JaxWsServerFactoryBea
n.
java:168)
at
org.apache.cxf.jaxws.EndpointImpl.getServer(EndpointImpl.java:346)
at
org.apache.cxf.jaxws.EndpointImpl.doPublish(EndpointImpl.java:259)
at
org.apache.cxf.jaxws.EndpointImpl.publish(EndpointImpl.java:209)
at
org.apache.cxf.jaxws.EndpointImpl.publish(EndpointImpl.java:404)
at sun.reflect.NativeMethodAccessorImpl.invoke0(Native
Method)
at
sun.reflect.NativeMethodAccessorImpl.invoke(NativeMethodAccessorImpl.jav
a:
39)
at
sun.reflect.DelegatingMethodAccessorImpl.invoke(DelegatingMethodAccessor
Im
pl.java:25)
at java.lang.reflect.Method.invoke(Method.java:585)
at
org.springframework.beans.factory.support.AbstractAutowireCapableBeanFac
to
ry.invokeCustomInitMethod(AbstractA
utowireCapableBeanFactory.java:1414)
at
org.springframework.beans.factory.support.AbstractAutowireCapableBeanFac
to
ry.invokeInitMethods(AbstractAutowi
reCapableBeanFactory.java:1375)
at
org.springframework.beans.factory.support.AbstractAutowireCapableBeanFac
to
ry.initializeBean(AbstractAutowireC
apableBeanFactory.java:1335)
... 39 more
Caused by: java.lang.IllegalArgumentException
at
sun.reflect.UnsafeFieldAccessorImpl.ensureObj(UnsafeFieldAccessorImpl.ja
va
:37)
at
sun.reflect.UnsafeObjectFieldAccessorImpl.set(UnsafeObjectFieldAccessorI
mp
l.java:57)
at java.lang.reflect.Field.set(Field.java:656)
at
org.apache.cxf.common.injection.ResourceInjector.injectField(ResourceInj
ec
tor.java:283)
at
org.apache.cxf.common.injection.ResourceInjector.visitField(ResourceInje
ct
or.java:167)
at
org.apache.cxf.common.annotation.AnnotationProcessor.processFields(Annot
at
ionProcessor.java:101)
at
org.apache.cxf.common.annotation.AnnotationProcessor.processFields(Annot
at
ionProcessor.java:95)
at
org.apache.cxf.common.annotation.AnnotationProcessor.accept(AnnotationPr
oc
essor.java:69)
at
org.apache.cxf.common.injection.ResourceInjector.inject(ResourceInjector
.j
ava:81)
at
org.apache.cxf.jaxws.JaxWsServerFactoryBean.injectResources(JaxWsServerF
ac
toryBean.java:221)
at
org.apache.cxf.jaxws.JaxWsServerFactoryBean.init(JaxWsServerFactoryBean.
ja
va:175)
... 51 more
Nov 16, 2009 5:23:23 PM org.apache.catalina.core.StandardContext
start
--
View this message in context:
http://old.nabble.com/CXF-jaxrs-REST-exception-stack-trace-propagated-to
-R
EST-client%2C-can-exception-be-wrapped-up-or-filtered-out-or-AOP-interce
pt
ed--tp26379915p26379915.html
Sent from the cxf-user mailing list archive at Nabble.com.
--
View this message in context:
http://old.nabble.com/CXF-jaxrs-REST-exception-stack-trace-propagated-to
-REST-client%2C-can-exception-be-wrapped-up-or-filtered-out-or-AOP-inter
cepted--tp26379915p26384165.html
Sent from the cxf-user mailing list archive at Nabble.com.
--
View this message in context:
http://old.nabble.com/CXF-jaxrs-REST-exception-stack-trace-propagated-to
-REST-client%2C-can-exception-be-wrapped-up-or-filtered-out-or-AOP-inter
cepted--tp26379915p26396467.html
Sent from the cxf-user mailing list archive at Nabble.com.