JAX-RS简介

什么是JAX-RS

JAX-RS 是 JAVA EE6 引入的一个新技术。 JAX-RS 即 Java API for RESTful Web Services,是一个 Java 编程语言的应用程序接口,支持按照表述性状态转移 (REST)架构风格创建 Web 服务。JAX-RS 使用了 Java SE5 引入的 Java 注解来 简化 Web 服务的客户端和服务端的开发和部署。 其实就是类似于 Servlet 规范来接收用户请求的一个范。

JAX-RS 是代表restful web service的一套规范API,JAX-RS规范基于JAVA编程语言,它是用来创建Restful 风格的web services服务的。Jax-rs使用一系列注解来简化java开发。

JAX-RS也称jsr339 (全称java specifications requests java规范提案第339个),由jcp(java community process)组织经过投票通过。

为了加深对jsr的理解,举一个简单的例子,jsr 330标准就是依赖注入的提案,已经通过。

规范说明

规范定义了一些常见的注解(见下表),用来标注一种资源文件为restfun风格的资源文件

序号 注解 描述
1 @Path 类或者方法的相对地址,标注在类或者方法上
2 @GET HTTP GET请求用,用来获取资源
3 @PUT HTTP PUT 请求,用来创建资源
4 @POST HTTP POST 请求, 用来创建或者更新资源
5 @DELETE HTTP DELETE请求, 用来删除资源
6 @HEAD HTTP HEAD请求, 用来获取一个接口是否可用的状态
7 @Produces 返回数据的格式比如APPLICATION/XML, TEXT/HTML, APPLICATION/JSON
8 @Consumes 请求数据格式 , 如json
9 @PathParam 绑定url里面的参数
10 @QueryParam 绑定url后面的参数(?后面的)
11 @MatrixParam 绑定包含多个 property (属性)=value(值) 方法参数表达式
12 @HeaderParam 给header里面传参
13 @CookieParam 给cookie里面传参
14 @FormParam 给form传参
15 @DefaultValue 给参数一个默认值
16 @Context 可以注入HttpRequest,HttpResponse用

规范实现

POM引入依赖

<dependency>
    <groupId>org.springframework.boot</groupId>
    <artifactId>spring-boot-starter-jersey</artifactId>
</dependency>

配置类

创建JerseyConfig
@Configuration
public class JerseyConfig {

	@Bean
	public ServletRegistrationBean jerseyServlet() {
        //手动注册servlet
		ServletRegistrationBean registrationBean = new ServletRegistrationBean(new ServletContainer(), "/rest/*");
		registrationBean.addInitParameter(ServletProperties.JAXRS_APPLICATION_CLASS,JerseyResourceConfig.class.getName());

		return registrationBean;
	}
}
创建JerseyResourceConfig
public class JerseyResourceConfig extends ResourceConfig {

    public JerseyResourceConfig() {
        /*
         * Servlet Filter that exposes the request to the current thread, through both org.springframework.context.i18n.LocaleContextHolder and RequestContextHolder. To be registered as filter in web.xml.<br/>
           Alternatively, Spring's org.springframework.web.context.request.RequestContextListener and Spring's org.springframework.web.servlet.DispatcherServlet also expose the same request context to the current thread.<br/>
           This filter is mainly for use with third-party servlets, e.g. the JSF FacesServlet. Within Spring's own web support, DispatcherServlet's processing is perfectly sufficient.<br/>
         */
        register(RequestContextFilter.class);

        // 加载资源文件,这里直接扫描com.example.demo.controller下的所有api
        packages("com.demo.controller");
        //register(HelloController.class);  //@wjw_note: 这种是注册单个的 JAX-RS component!
    }
}

创建接口

@Path("/user/")
public class HelloController {
    @Path("{id}")
    @GET
    @Produces(MediaType.APPLICATION_JSON)
    public User hello(@PathParam("id") String id) {
        User user = new User();
        user.setId(id);
        user.setUsername("mvc JAX-RS 测试");

        return user;
    }
}

测试访问

启动Spring Boot程序

http://localhost:8080/rest/user/123456

返回 {"id":"123456","username":"mvc JAX-RS 测试"}

JAX-RS常用注解介绍

@GET

http请求方式里面的get请求,标记这个请求方式为get

/**
  *  http://localhost:8080/rest/province/city/1
  *
  * @param id
  * @return
  */
@Path("city/{id}")
@GET
@Produces(MediaType.APPLICATION_JSON) //表示输出json
@Consumes(MediaType.APPLICATION_JSON) //表示输入为json
public Result<Boolean> getCity(@PathParam("id") Long id) {

    return new Result<>();
}

@PUT

http请求方式里面的get请求,标记这个请求方式为put

一般用来创建一个资源

@Path("city/{id}")
@PUT
@Produces(MediaType.APPLICATION_JSON)
@Consumes(MediaType.APPLICATION_JSON)
public Result<Boolean> putCity(@PathParam("id") Long id) {

    return new Result<>();
}

@POST

http请求方式里面的get请求,标记这个请求方式为post

一般用来创建和更新

@Path("city/{id}")
@POST
@Produces(MediaType.APPLICATION_JSON)
@Consumes(MediaType.APPLICATION_JSON)
public Result<Boolean> postCity(@PathParam("id") Long id) {

  return new Result<>();
}

@DELETE

http请求方式里面的get请求,标记这个请求方式为delete

一般用来删除一个资源

@Path("city/{id}")
@DELETE
@Produces(MediaType.APPLICATION_JSON)
@Consumes(MediaType.APPLICATION_JSON)
public Result<Boolean> deleteCity(@PathParam("id") Long id) {
    return new Result<>();
}

@PathParam

一般url里面的参数用PathParam

/**
  *  http://localhost:8080/rest/province/city/1
  *
  * @param id
  * @return
  */
@Path("city/{id}")
@GET
@Produces(MediaType.APPLICATION_JSON) //表示输出json
@Consumes(MediaType.APPLICATION_JSON) //表示输入为json
public Result<Boolean> getCity(@PathParam("id") Long id) {

    return new Result<>();
}

@QueryParam

可以输出url后面的参数

/**
  * http://localhost:8080/rest/queryCity/1?name=wh
  *
  * @param id
  * @param name
  * @return
  */
@Path("queryCity/{id}")
@GET
@Produces(MediaType.APPLICATION_JSON)
@Consumes(MediaType.APPLICATION_JSON)
public Result<Boolean> queryCity(@PathParam("id") Long id, @QueryParam("name") String name) {
    System.out.println(name);
    return new Result<>();
}

@HeaderParam

/**
  * http://localhost:8080/rest/queryCity/1?name=wh
  *
   * @param authKey
   * @param id
   * @param name
   * @return
   */
@Path("queryCity/{id}")
@GET
@Produces(MediaType.APPLICATION_JSON)
@Consumes(MediaType.APPLICATION_JSON)
public Result<Boolean> queryHeaderCity(@HeaderParam("auth") String authKey, @PathParam("id") Long id, @QueryParam("name") String name) {
    System.out.println(name);
    System.out.println(authKey);
    return new Result<>();
}

@CookieParam

/**
  * http://localhost:8080/rest/queryCity/1?name=wh
  * @param sessionId
  * @param authKey
  * @param id
  * @param name
  * @return
  */
@Path("queryCity/{id}")
@GET
@Produces(MediaType.APPLICATION_JSON)
@Consumes(MediaType.APPLICATION_JSON)
public Result<Boolean> queryCookieCity(@CookieParam("__utma") String sessionId, @HeaderParam("auth") String authKey, @PathParam("id") Long id, @QueryParam("name") String name) {
    System.out.println(name);
    System.out.println(sessionId);
    System.out.println(authKey);
    return new Result<>();
}

注: _utma是postman里面自带的一个cookie,所以直接调用就可以拿到值,不用额外设置

@MatrixParam

matrixParam一般是用来分离参数的,一般和分号一起使用,下例中,分号后面的from被成功识别打印

/**
  * http://localhost:8080/rest/queryCity/1;from=wh?name=sh
  *
  * @param from
  * @param sessionId
  * @param authKey
  * @param id
  * @param name
  * @return
  */
@Path("queryCity/{id}")
@GET
@Produces(MediaType.APPLICATION_JSON)
@Consumes(MediaType.APPLICATION_JSON)
public Result<Boolean> queryMatrixCity(@MatrixParam("from") String from, @CookieParam("__utma") String sessionId, @HeaderParam("auth") String authKey, @PathParam("id") Long id, @QueryParam("name") String name) {
    System.out.println(id);
    System.out.println(name);
    System.out.println(sessionId);
    System.out.println(authKey);
    System.out.println(from);
    return new Result<>();
}

@FormParam

postman里面改为post请求,表单中添加age参数,得到输出

/**
  * http://localhost:8080/rest/city/1?name=%22%E5%B0%8F%E6%98%8E%22
  *
  * @param age
  * @param id
  * @param name
  * @return
  */
@POST
@Path("city/{id}")
@Consumes(MediaType.APPLICATION_FORM_URLENCODED)
@Produces(MediaType.APPLICATION_JSON)
public Result<Boolean> addBook(@FormParam("age") Integer age, @PathParam("id") String id, @QueryParam("name") String name) {
    System.out.println(id);
    System.out.println(name);
    System.out.println(age);
    return new Result<>();
}

@DefaultValue

/**
  * http://localhost:8080/rest/queryCity/1?name=wh
  *
  * @param id
  * @param name
  * @return
  */
@Path("queryCity/{id}")
@GET
@Produces(MediaType.APPLICATION_JSON)
@Consumes(MediaType.APPLICATION_JSON)
public Result<Boolean> queryDefaultValueCity(@PathParam("id") Long id, @DefaultValue("sh") @QueryParam("name") String name) {
    System.out.println(name);
    return new Result<>();
}

@Context

The @Context 注解允许你注入下面这些类

  • javax.ws.rs.core.HttpHeaders
  • javax.ws.rs.core.UriInfo
  • javax.ws.rs.core.Request
  • javax.servlet.http.HttpServletRequest
  • javax.servlet.http.HttpServletResponse
  • javax.servlet.ServletConfig
  • javax.servlet.ServletContext
  • javax.ws.rs.core.SecurityContext

在filter中使用较多

@Encoded and encoding

/**
  * http://localhost:8080/rest/en_city/小明
  *
  * @param name
  * @return
  */
@Path(value = "en_city/{name}")
@GET
@Produces(MediaType.APPLICATION_JSON)
@Consumes(MediaType.APPLICATION_JSON)
public Result<Boolean> getCity(@PathParam("name") @Encoded String name) {
    System.out.println(name);
    return new Result<>();
}