zoukankan      html  css  js  c++  java
  • Jersey中的异常统一处理

    Jersey中,对rest资源进行处理时,正常情况下会返回一个成功的Response,例如flag=1或者一个json。

    public Response get(@PathParam("p") String p) throws MyException {
            logger.info("rest/test ...");
            if ("1".equals(p)) {
                throw new MyException("test myException..");
            }
            return Response.status(Response.Status.OK).type(MediaType.APPLICATION_JSON).build();
        }

    但有时候因为各种原因:例如参数错误或者业务要求,需要抛出runtimeException或者自定义异常(权限不够等),我们的代码如果对每个异常都进行处理并返回的话,程序就会显得很拖沓。

    如果不处理异常,任由系统抛出的话,前端就会得到http status 404之类的返回,而前端的兄弟是希望任何时间都应该得到一个code,而不是http 404之类的返回。

    这个时候,我们就需要对异常进行统一处理,避免到处都是处理异常的代码。

    首先是Jersey的配置

    maven

    <!--jersey-->
    <dependency>
        <groupId>org.glassfish.jersey.containers</groupId>
        <artifactId>jersey-container-servlet-core</artifactId>
        <version>2.0</version>
    </dependency>
    
    <!--JAXB API-->
    <dependency>
        <groupId>javax.xml.ws</groupId>
        <artifactId>jaxws-api</artifactId>
        <version>2.1</version>
    </dependency>
    
    <!-- Json支持 -->
    <dependency>
        <groupId>org.codehaus.jackson</groupId>
        <artifactId>jackson-core-asl</artifactId>
        <version>1.9.12</version>
    </dependency>
    <dependency>
        <groupId>org.codehaus.jackson</groupId>
        <artifactId>jackson-mapper-asl</artifactId>
        <version>1.9.12</version>
    </dependency>
    <dependency>
        <groupId>org.codehaus.jackson</groupId>
        <artifactId>jackson-jaxrs</artifactId>
        <version>1.9.12</version>
    </dependency>
    
    <dependency>
        <groupId>com.fasterxml.jackson.jaxrs</groupId>
        <artifactId>jackson-jaxrs-json-provider</artifactId>
        <version>2.4.1</version>
    </dependency>

    web.xml

        <!-- RestServiceServlet -->
        <servlet>
            <servlet-name>RestfulContainer</servlet-name>
            <servlet-class>org.glassfish.jersey.servlet.ServletContainer</servlet-class>
            <init-param>
                <param-name>javax.ws.rs.Application</param-name>
                <param-value>com.sharp.controller.rest.MyApplication</param-value>
            </init-param>
            <init-param>
                <param-name>com.sun.jersey.api.json.POJOMappingFeature</param-name>
                <param-value>true</param-value>
            </init-param>
            <load-on-startup>1</load-on-startup>
        </servlet>
        <servlet-mapping>
            <servlet-name>RestfulContainer</servlet-name>
            <url-pattern>/rest/*</url-pattern>
        </servlet-mapping>

    注意其中的MyApplication...

     自定义异常

    public class MyException extends RuntimeException {
    
        /**  */
        private static final long serialVersionUID = -9095798995958029993L;
    
        private String            msg;
    
        /**
         * Getter method for property <tt>msg</tt>.
         * 
         * @return property value of msg
         */
        public String getMsg() {
            return msg;
        }
    
        /**
         * Setter method for property <tt>msg</tt>.
         * 
         * @param msg value to be assigned to property msg
         */
        public void setMsg(String msg) {
            this.msg = msg;
        }
    
        public MyException(String msg) {
            this.msg = msg;
        }
    }

    异常mapper

    @Provider
    public class MyExceptionMapper implements ExceptionMapper<MyException> {
    
        /** 
         * @see javax.ws.rs.ext.ExceptionMapper#toResponse(java.lang.Throwable)
         */
        public Response toResponse(MyException ex) {
            return Response.status(Response.Status.OK).entity(ex.getMsg())
                .type(MediaType.APPLICATION_JSON).build();
        }
    
    }

    注册初始化,这个文件要与web.xml中相对应。

    public class MyApplication extends ResourceConfig {
        public MyApplication() {
            // register(HelloResource.class);
            packages("com.sharp.controller.rest");
            // register(RestTestController.class);
        }
    }

    最后就是rest的入口

    @Path("/test")
    public class RestTestController {
        private final Log logger = LogFactory.getLog(getClass());
    
        @GET
        @Path("/get/{p}")
        @Produces(MediaType.TEXT_PLAIN)
        @Consumes(MediaType.APPLICATION_JSON)
        public Response get(@PathParam("p") String p) throws MyException {
            logger.info("rest/test ...");
            if ("1".equals(p)) {
                throw new MyException("test myException..");
            }
            return Response.status(Response.Status.OK).type(MediaType.APPLICATION_JSON).build();
        }
    
    }

    这里我们的业务就是如果传入的参数是1的话,就抛出异常,否则就是一个正常的结果。

    最后访问http://127.0.0.1:8080/batis/rest/test/get/1 ,就可以看到虽然抛出了一个异常,但前端还是得到了一个http status 200的正确返回,只不过返回数据显示有个异常。

    这样的话,我们在rest的service中就可以只考虑业务流程,而不需要使用try catch 对业务进行包围处理了。

  • 相关阅读:
    C# 特性(Attribute)学习
    ASP.NET Request.MapPath() 与 Server.MapPath()
    Asp.net对http request 处理的全过程!
    保存网址
    寻找silverlight高手帮忙解决问题,谢谢,
    基于.Net Framework的N层分布式应用开发
    VB.NET 代码转为C#
    刚刚开通博客噢 。欢迎大家光临啊
    配置本地服务器的几种方式
    前端必备工具 (记录)
  • 原文地址:https://www.cnblogs.com/malaya/p/6365419.html
Copyright © 2011-2022 走看看