Here's a JAX-RS end-point:

@Path("logout")
@POST
public void logout(@HeaderParam("X-AuthToken") String apiToken) {
    try {
        authenticationService.logout(apiToken);
    } catch (ExpiredApiTokenException exc) {
        throw new BadRequestException("API token has expired");
    } catch (InvalidApiTokenException exc) {
        throw new BadRequestException("API token is not valid");
    } catch (ApplicationException exc) {
        throw new InternalServerErrorException();
    }
}

When one of these BadRequestExceptions (HTTP 400) are thrown, GlassFish returns its own error page in the response body instead of the error message in my code. The response contains the correct HTTP code. Just the body is replaced.

I have tried creating an ExceptionMapper:

@Provider
public class ExceptionMapperImpl implements ExceptionMapper<Throwable> {

    @Override
    public Response toResponse(Throwable exception) {
        if (exception instanceof WebApplicationException) {
            return ((WebApplicationException) exception).getResponse();
        } else {
            logger.log(Level.SEVERE, "Uncaught exception thrown by REST service", exception);
            return Response.status(Response.Status.INTERNAL_SERVER_ERROR).build();
        }
    }

    private static final Logger logger = Logger.getLogger(ExceptionMapperImpl.class.getName());
}

And I tried adding the following ejb-jar.xml:

<?xml version="1.0" encoding="UTF-8"?>
<ejb-jar xmlns="http://xmlns.jcp.org/xml/ns/javaee"
         version="3.2"
         xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
         xsi:schemaLocation="http://xmlns.jcp.org/xml/ns/javaee http://xmlns.jcp.org/xml/ns/javaee/ejb-jar_3_2.xsd">
    <assembly-descriptor>
        <application-exception>
            <exception-class>javax.ws.rs.WebApplicationException</exception-class>
            <rollback>true</rollback>
        </application-exception>
    </assembly-descriptor>
</ejb-jar>

all to no avail.

What am I missing?

有帮助吗?

解决方案

In the toResponse method, I changed this

return exception.getResponse();

to this

return Response.status(exception.getResponse().getStatus())
               .entity(exception.getMessage())
               .build();

The problem is the when I do this:

throw new BadRequestException("Something is wrong!");

it doesn't populate the exception's Response's body with "Something is wrong!". GlassFish sees that the response body is empty and its status code is an error code, so it inserts its own response body. By populating the response body (a.k.a. entity) in the provider, this problem goes away.

许可以下: CC-BY-SA归因
不隶属于 StackOverflow
scroll top