Java RESTful Web Service实战(第2版) 2.4 连通性

简介:

2.4 连通性

REST的一个重要的特性就是连通性。Web Link和HATEOAS以不同方式实现了REST式服务的联通性。

Web Link定义在IETFRFC 5988(Web Linking),是通过在HTTP头中定义链接信息,以描述当前页面与链接页面之间的关系。Web Link是一种过渡型链接(Transitional Links)。JAX-RS 2.0引入了javax.ws.rs.core.Link类,用来处理Web Link的表述。

HATEOAS(Hypermedia as the Engine of Application State,超媒体作为应用程序状态引擎)。HATEOAS的形式是包含链接信息的超媒体文档,HATEOAS的核心是“引擎”,该引擎的目的是通过请求的响应实体将超媒体信息返回给客户端,超媒体信息可以告诉用户,如果接下来选择去往某个链接(或者链接列表中的某个链接),应用的状态就会如超媒体描述的那样发生转变。HATEOAS是一种结构型链接(Structural Links)。Jersey2中可以使用XML实现HATEOAS的结构要求。

下面讲述在Jersey中如何实现Web Link和HATEOA这两种REST连通性实践方式。

阅读指南

本节示例源代码地址:https://github.com/feuyeux/jax-rs2-guide-II/tree/master/2.simple-service-3。

相关包:com.example.link。

2.4.1 过渡型链接

Web Link通过使用HTTP的头信息来传递操作链接,在Jersey中使用javax.ws.rs.core.Link类可以非常简洁地实现支持Web Link的资源类,示例代码如下。

@Path("weblink-resource")

public class WebLinkResource {

  @Context

  UriInfo uriInfo;

 

  @POST

  @Produces(MediaType.APPLICATION_XML)

  @Consumes({ MediaType.APPLICATION_JSON,

    MediaType.APPLICATION_XML, MediaType.TEXT_XML })

  public Response saveBook(final Book book) {

      final long newId = System.nanoTime();

      book.setBookId(newId);

      LinkCache.map.put(newId, book);

      //关注点1:通过UriInfo实例获取资源路径

      final UriBuilder ub = uriInfo.getAbsolutePathBuilder();

      final URI location = ub.path("" + newId).build();

      //关注点2:通过模板获取资源路径

      final String uriTemplate = "http://{host}:{port}/{path}/{param}";

      final URI location2 = UriBuilder.fromUri(uriTemplate)

      .resolveTemplate("host", "localhost").resolveTemplate("port", "9998")

      .resolveTemplate("path", "weblink-resource")

      .resolveTemplate("param", newId).build();

      //关注点3:通过模板方法获取资源路径

      final UriBuilder ub3 = uriInfo.getAbsolutePathBuilder();

      final URI location3 = ub3.scheme("http").host("localhost").port(9998)

      .path("weblink-resource").path("" + newId).build();

      //关注点4:为响应实例添加路径信息

      return Response.created(location).link(location2, "view1")

      .link(location3, "view2").entity(book).build();

    }

}

在这段代码中,使用了3种方式构建URI实例。第一种方式是通过调用UriInfo实例的getAbsolutePathBuilder()方法可以获取当前请求的绝对路径,然后基于此路径添加资源id信息,见关注点1;第二种方式是为UriBuilder提供路径模板,然后链式调用resolveTemplate()方法传递并解析模板参数,最后通过UriBuilder的build方法生成URI实例,见关注点2;第三种方式和第二种类似,不同的是模板信息被具体方法替代。最后,这3个与Link相关的URI实例由Response构建,作为返回值响应给客户端,见关注点4。

2.4.2 结构型链接

HATEOAS用以代替聚集数据并避免描述膨胀,通常使用 Atom格式在实体字段中提供链接信息。本例使用XML格式来支持HATEOAS,折中的设计是在POJO中额外定义一个链接字段。支持HATEOAS的资源类示例如下。

@Path("hateoas-resource")

public class HATEOASResource {

  @Context

  UriInfo uriInfo;

 

  @POST

  @Produces({ MediaType.APPLICATION_XML })

  @Consumes({ MediaType.APPLICATION_XML })

  public BookWrapper saveBook(final Book book) {

      final long newId = System.nanoTime();

      book.setBookId(newId);

      LinkCache.map.put(newId, book);

      //关注点1:通过UriInfo实例获取资源路径

      final UriBuilder ub = uriInfo.getAbsolutePathBuilder();

      final URI uri = ub.path("" + newId).build();

      BookWrapper b = new BookWrapper();

      b.setBook(book);

      //关注点2:将资源路径赋给资源实体

      b.setLink(uri.toString());

      return b;

  }

}

在这段代码中,URI实例由上下文UriInfo中获取的绝对路径和资源ID组成,见关注点1;该链接信息被赋值到POJO实例的link属性中,以实现HATEOAS,见关注点2。

阅读指南

REST连通性的实践手段非常多,推荐读者从成熟的产品中学习其设计。如果有可能,这里推荐Jenkins和RallyDev两个敏捷开发中常用的平台,它们提供了比较舒适的连通性设计。比如在RallyDev中,为一个测试用例结果添加测试用例属性(该属性是必输项),其内容并不是对应测试用例的实例,而是该测试用例的引用地址字符串。这样的设计不但减少了网络传输的负载,还方便在调试和维护时排错。

相关文章
|
3天前
|
Java 应用服务中间件 测试技术
深入探索Spring Boot Web应用源码及实战应用
【5月更文挑战第11天】本文将详细解析Spring Boot Web应用的源码架构,并通过一个实际案例,展示如何构建一个基于Spring Boot的Web应用。本文旨在帮助读者更好地理解Spring Boot的内部工作机制,以及如何利用这些机制优化自己的Web应用开发。
14 3
|
12天前
|
SQL Java
20:基于EL与JSTL的产品管理页-Java Web
20:基于EL与JSTL的产品管理页-Java Web
21 5
|
17小时前
|
存储 人工智能 测试技术
python自动化测试实战 —— CSDN的Web页面自动化测试
python自动化测试实战 —— CSDN的Web页面自动化测试
5 0
|
3天前
|
JSON Go 数据格式
golang学习7,glang的web的restful接口结构体传参
golang学习7,glang的web的restful接口结构体传参
|
3天前
|
JSON Go 数据格式
golang学习6,glang的web的restful接口传参
golang学习6,glang的web的restful接口传参
|
3天前
|
JSON Go 数据格式
golang学习5,glang的web的restful接口
golang学习5,glang的web的restful接口
|
5天前
|
前端开发 JavaScript Java
Java与Web开发的结合:JSP与Servlet
Java与Web开发的结合:JSP与Servlet
10 0
|
6天前
|
监控 安全 Shell
记一次应急靶场实战--web1
本次应急靶机题目训练主要是为了应对接下来的护网面试和比赛,顺便提高一下自己对应急和溯源的实战能力,这里有两个逗比的事情发生,一是用D盾分析的时候,电脑环境监测到了,把要分析的马杀了,二是,发现无法使用脚本,在自己本机实验,电脑差点搞崩,还好佬在制作时候只是单次运行会占用.切记不要本机实验,一定要在虚拟机中进行测试.
|
7天前
|
存储 监控 安全
JVM工作原理与实战(十六):运行时数据区-Java虚拟机栈
JVM作为Java程序的运行环境,其负责解释和执行字节码,管理内存,确保安全,支持多线程和提供性能监控工具,以及确保程序的跨平台运行。本文主要介绍了运行时数据区、Java虚拟机栈等内容。
11 0
|
8天前
|
Java
Java中的多线程编程:基础知识与实战技巧
【5月更文挑战第6天】多线程编程是Java中的一个重要特性,它允许我们在一个程序中同时执行多个任务。本文将介绍Java多线程的基础知识,包括线程的创建、启动、同步和通信,以及如何在Java中实现多线程编程。通过实例代码和解析,帮助读者深入理解Java多线程编程的概念和应用。