rest.resteasy.crud.ExceptionHandler.java Source code

Java tutorial

Introduction

Here is the source code for rest.resteasy.crud.ExceptionHandler.java

Source

/*
This file is part of resteasy-crud-play-module.
    
Copyright Lunatech Research 2010
    
resteasy-crud-play-module is free software: you can redistribute it and/or modify
it under the terms of the GNU Lesser General Public License as published by
the Free Software Foundation, either version 3 of the License, or
(at your option) any later version.
    
resteasy-crud-play-module is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
GNU Lesser General Public License for more details.
    
You should have received a copy of the GNU General Lesser Public License
along with resteasy-crud-play-module.  If not, see <http://www.gnu.org/licenses/>.
*/
package rest.resteasy.crud;

import java.net.HttpURLConnection;
import java.util.List;

import javax.ws.rs.WebApplicationException;
import javax.ws.rs.core.Context;
import javax.ws.rs.core.MediaType;
import javax.ws.rs.core.Request;
import javax.ws.rs.core.Response;
import javax.ws.rs.core.Variant;
import javax.ws.rs.ext.ExceptionMapper;
import javax.ws.rs.ext.Provider;

import org.hibernate.PropertyValueException;
import org.hibernate.validator.InvalidStateException;
import org.hibernate.validator.InvalidValue;
import org.jboss.resteasy.spi.Failure;

import play.Logger;
import play.modules.resteasy.crud.InvalidResponse;

/**
 * Maps RESTEasy failures to responses, finds Hibernate Validation exceptions
 * and maps them to InvalidResponse and tries to unwrap exceptions generally.
 * @author Stphane pardaud <stef@epardaud.fr>
 */
@Provider
public class ExceptionHandler implements ExceptionMapper<Throwable> {

    @Context
    private Request request;

    public Response toResponse(Throwable t) {
        Logger.debug("Exception mapper called");
        InvalidValue[] invalidValues = findInvalidValues(t);
        if (invalidValues != null) {
            InvalidResponse r = new InvalidResponse();
            if (invalidValues != null) {
                for (InvalidValue val : invalidValues) {
                    r.addError(val.getPropertyName(), val.getMessage());
                }
            }
            List<Variant> variants = Variant.mediaTypes(MediaType.APPLICATION_JSON_TYPE,
                    MediaType.APPLICATION_XML_TYPE, MediaType.valueOf("application/*+xml"), MediaType.TEXT_XML_TYPE)
                    .build();
            Variant variant = request.selectVariant(variants);
            return Response.status(HttpURLConnection.HTTP_BAD_REQUEST).entity(r).variant(variant).build();
        }
        // also handle "normal" JAX-RS exceptions
        WebApplicationException wx = findWebApplicationException(t);
        if (wx != null) {
            return wx.getResponse();
        }
        // handle security checks as well
        /* FIXME: play port: fix auth
        if (t instanceof AuthorizationException) {
           return Response.status(HttpURLConnection.HTTP_FORBIDDEN).entity(
           t.getMessage()).build();
        }
        */
        // and RESTEasy failures (grrr)
        if (t instanceof Failure) {
            Failure f = (Failure) t;
            if (f.getResponse() != null)
                return f.getResponse();
            if (f.getErrorCode() != -1)
                return Response.status(f.getErrorCode()).entity(f.getMessage()).build();
            // fall through
        }
        Logger.error(t, "Uncaught exception");
        return Response.serverError().build();
    }

    private WebApplicationException findWebApplicationException(Throwable t) {
        if (t instanceof WebApplicationException)
            return (WebApplicationException) t;
        if (t.getCause() != null)
            return findWebApplicationException(t.getCause());
        return null;
    }

    private InvalidValue[] findInvalidValues(Throwable t) {
        if (t instanceof InvalidStateException)
            return ((InvalidStateException) t).getInvalidValues();
        if (t instanceof PropertyValueException) {
            PropertyValueException x = (PropertyValueException) t;
            // watch it, keep this in sync with exception handling
            InvalidValue invalidValue = new InvalidValue(x.getMessage(), null, x.getPropertyName(), null, null);
            InvalidValue[] invalidValues = new InvalidValue[1];
            invalidValues[0] = invalidValue;
            return invalidValues;
        }
        if (t.getCause() != null)
            return findInvalidValues(t.getCause());
        return null;
    }

}