users@jersey.java.net

Re: [Jersey] Doh! Re: [Jersey] ExceptionMapper and Viewable

From: Paul Sandoz <Paul.Sandoz_at_Sun.COM>
Date: Fri, 16 Oct 2009 11:38:08 +0200

Hi Jordi,

Well done! Thanks for your patience and persistence. I have logged a
number of issues which should hopefully resolve all the
inconsistencies you have found.

I am glad i made it possible to allow Viewable instances to be
declared in this manner (another developer wanted to do that, reported
an issue and I fixed it) :-)

In 1.1.2 i added an EJB exception mapper. The reason i had to do this
was because of the way runtime exceptions thrown from EJBs are wrapped
by the EJB runtime in an EJBException:

public class EJBExceptionMapper implements
ExceptionMapper<EJBException> {

     private final Providers providers;

     public EJBExceptionMapper(@Context Providers providers) {
         this.providers = providers;
     }

     public Response toResponse(EJBException exception) {
         final Exception cause = exception.getCausedByException();
         if (cause != null) {
             final ExceptionMapper mapper =
providers.getExceptionMapper(cause.getClass());
             if (mapper != null) {
                 return mapper.toResponse(cause);
             } else if (cause instanceof WebApplicationException) {
                 return ((WebApplicationException)cause).getResponse();
             }
         }

         return Response.serverError().build();
     }
}

I think there is an issue with JAX-RS that it is not possible to re-
throw exceptions from an ExceptionMapper to be propagated to the
container. I think i need to add a Jersey-specific feature to allow
this. Issue logged:

   https://jersey.dev.java.net/issues/show_bug.cgi?id=390

I have also logged an issue with MappableContainerException to re-
throw the cause instead:

   https://jersey.dev.java.net/issues/show_bug.cgi?id=391

BTW i have also dug further into result 3) and i think it may be
possible to fix. Issue logged:

   https://jersey.dev.java.net/issues/show_bug.cgi?id=389



> Sorry for the delay, i got a bit crazy with maven and failures
> deploying the app with an EJB (your web.xml was 2.4 version and I
> didnt noticed :)) )


I created the project from a maven archetype. Issue has been logged:

   https://jersey.dev.java.net/issues/show_bug.cgi?id=388

Paul.


On Oct 16, 2009, at 11:12 AM, Jordi Domingo wrote:

> Hi there :)
>
> I made i little hack (following your example for the 500 :) ) to
> solve the 404 error:
>
> public class HackDumpFilter implements ContainerResponseFilter{
>
> private final static Logger logger =
> LoggerFactory.getLogger(HackDumpFilter.class);
>
> public ContainerResponse filter(ContainerRequest
> request,ContainerResponse response){
>
> if(response.getStatus() == 500){
> response.setEntity(null);
> response.getHttpHeaders().put("Content-Type",null);
> }else if(response.getStatus() == 404){
> response.setEntity(new Viewable("/jsp/
> notFound.jsp",null));
> }
> return response;
> }
> }
>
> Hope it helps somebody else :)
>
> Jordi
>
> From: noseya_at_hotmail.com
> To: users_at_jersey.dev.java.net
> Date: Fri, 16 Oct 2009 11:02:05 +0200
> Subject: RE: [Jersey] Doh! Re: [Jersey] ExceptionMapper and Viewable
>
> Great test Paul!
>
> But, did you try to turn your resource into an EJB ? :)
>
> Results change:
>
> 1) Now Fails with a complete dump, escaping the servlet container
> 2) Same like not ejb
> 3) Same like not ejb
>
> My resource's are Stateless beans :(
>
> Sorry for the delay, i got a bit crazy with maven and failures
> deploying the app with an EJB (your web.xml was 2.4 version and I
> didnt noticed :)) )
>
> Thanks,
>
> Jordi
>
> Date: Thu, 15 Oct 2009 12:50:44 +0200
> From: Paul.Sandoz_at_Sun.COM
> To: users_at_jersey.dev.java.net
> Subject: Re: [Jersey] Doh! Re: [Jersey] ExceptionMapper and Viewable
>
> H Jordi,
>
> I have attached a very simple project that exercises many of the
> possible ways of mapping exceptions.
>
> Hopefully it should be fairly intuitive to understand. The main
> index.jsp provides links to click on that results in various forms
> of error pages.
>
> Results of investigation:
>
> 1) Jersey will propagate runtime exceptions to the servlet layer if
> those exceptions are not mapped by
> an ExceptionMapper. Those exceptions can then be mapped using
> an error page.
> See the error page SecurityExceptionErrorPage.jsp and the link:
>
> http://localhost:8080/exceptions/webresources/myresource/runtime?ex=java.lang.SecurityException
>
> supported by the following resource method:
>
> @Path("runtime")
> @GET
> @Produces("text/plain")
> public String runtimeException(@QueryParam("ex") String
> className)
> throws ClassNotFoundException, InstantiationException,
> IllegalAccessException {
> Class c = Class.forName(className, true,
> this.getClass().getClassLoader());
> RuntimeException re = (RuntimeException)c.newInstance();
> if (true) throw re;
> return "Hi there!";
> }
>
>
> 2) Jersey will propagate checked exceptions wrapped in a
> MappableContainerException to the servlet layer.
> That exception can then be mapped using an error page and the
> cause can be extracted.
> See the error page MappableContainerException.jsp and the links:
>
> http://localhost:8080/exceptions/webresources/myresource/checked/ioexception
> http://localhost:8080/exceptions/webresources/myresource/checked/myexception
>
> supported by the following resource methods:
>
> @Path("checked/ioexception")
> @GET
> @Produces("text/plain")
> public String checkedIOException() throws IOException {
> if (true) throw new IOException();
> return "Hi there!";
> }
>
> public static class MyException extends Exception {
> }
>
> @Path("checked/myexception")
> @GET
> @Produces("text/plain")
> public String checkedMyException() throws MyException {
> if (true) throw new MyException();
> return "Hi there!";
> }
>
>
> 3) If Jersey sets the status code in the servlet response it is not
> possible for error pages to be mapped to the
> status code.
> See the links:
>
> http://localhost:8080/exceptions/404
> http://localhost:8080/exceptions/webresources/404
>
> The first link is mapped to the 404 bound error page,
> NotFound.jsp. The the second link returns the default
> GF 404 error page. The first works because the Jersey servlet is
> not invoked.
>
> I verified i get the same behavior with a simple servlet if one
> only sets the status code to 404.
> However, i could get this to work if instead of calling
> HttpServletResponse.setStatus i call
> HttpServletResponse.sendError.
>
>
> Conclusions:
>
> Result 1 is working correctly.
>
> Result 2 could be improved by unwrapping the cause in the
> MappableContainerException and re-throwing the cause wrapped in
> ServletException.
>
> Result 3 might be a bug in the servlet container. I am not quite
> sure how to work around it. For example if using sendError then any
> headers that have been added are ignored. It seems to me the correct
> behavior would be to map status codes if no entity is present (nor
> no bytes have been written to the response output stream).
>
> Paul.
>
>
>
>
> En tu material escolar no puede faltar el nuevo Pack de Emoticonos
> Vuelta al Cole ¡Descárgatelo gratis! Es muy divertido
> En tu material escolar no puede faltar el nuevo Pack de Emoticonos
> Vuelta al Cole ¡Descárgatelo gratis! Es muy divertido