# Spring Boot Jersey 教程

> 原文： [http://zetcode.com/springboot/jersey/](http://zetcode.com/springboot/jersey/)

Spring Boot Jersey 教程展示了如何在 Spring Boot 应用中使用 Jersey 建立一个简单的 RESTFul 应用。 Jersey 是使用`@RestController`创建的 Spring RESTFul 应用的替代方案。

Spring 是用于创建企业应用的流行 Java 应用框架。 Spring Boot 是 Spring 框架发展的下一步。 它有助于以最小的努力创建独立的，基于生产级的 Spring 应用。 它提倡在 XML 配置上使用约定而不是配置原则。

## RESTFul 应用

RESTFul 应用遵循 REST 架构样式，该样式用于设计网络应用。 RESTful 应用生成对资源执行 CRUD（创建/读取/更新/删除）操作的 HTTP 请求。 RESTFul 应用通常以 JSON 或 XML 格式返回数据。

## JAX-RS

RESTful Web 服务的 Java API（JAX-RS）是 Java 编程语言 API 规范，它提供了根据代表性状态传输（REST）架构模式创建 Web 服务的支持。 JAX-RS 使用注解来简化 Web 服务客户端和端点的开发和部署。 JAX-RS 是 Java EE 的正式组成部分。

## Jersey

Jersey 是用于用 Java 开发 RESTful Web 服务的开源框架。 它是 RESTful Web 服务 Java API（JAX-RS）规范的参考实现。

## Spring Boot `Jersey` 示例

以下应用是使用 Jersey 创建的 simpe Spring Boot RESTful 应用。

```java
$ tree
.
├── pom.xml
└── src
    ├── main
    │   ├── java
    │   │   └── com
    │   │       └── zetcode
    │   │           ├── Application.java
    │   │           ├── config
    │   │           │   └── JerseyConfig.java
    │   │           └── endpoint
    │   │               ├── HelloEndpoint.java
    │   │               └── ReverseReturnEndpoint.java
    │   └── resources
    └── test
        └── java
            └── com
                └── zetcode
                    └── ApplicationTests.java

```

这是项目结构。

`pom.xml`

```java
<?xml version="1.0" encoding="UTF-8"?>
<project xmlns="http://maven.apache.org/POM/4.0.0" 
         xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" 
         xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 
http://maven.apache.org/xsd/maven-4.0.0.xsd">

    <modelVersion>4.0.0</modelVersion>
    <groupId>com.zetcode</groupId>
    <artifactId>SpringBootJersey</artifactId>
    <version>1.0-SNAPSHOT</version>
    <packaging>jar</packaging>
    <properties>
        <project.build.sourceEncoding>UTF-8</project.build.sourceEncoding>
        <maven.compiler.source>1.8</maven.compiler.source>
        <maven.compiler.target>1.8</maven.compiler.target>
    </properties>

    <parent>
        <groupId>org.springframework.boot</groupId>
        <artifactId>spring-boot-starter-parent</artifactId>
        <version>1.5.9.RELEASE</version>
    </parent>   

    <dependencies>

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

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

    </dependencies>  

    <build>
        <plugins>
            <plugin>
                <groupId>org.springframework.boot</groupId>
                <artifactId>spring-boot-maven-plugin</artifactId>
            </plugin>            
        </plugins>
    </build>        

</project>

```

这是 Maven 构建文件。 Spring Boot 启动器是一组方便的依赖项描述符，可以极大地简化 Maven 配置。 `spring-boot-starter-parent`具有 Spring Boot 应用的一些常用配置。 `spring-boot-starter-jersey`是使用 JAX-RS 和 Jersey 构建 RESTful Web 应用的入门。 它是`spring-boot-starter-web`的替代方法。 `spring-boot-starter-test`是使用包含 JUnit，Hamcrest 和 Mockito 的库测试 Spring Boot 应用的入门程序。

`spring-boot-maven-plugin`在 Maven 中提供了 Spring Boot 支持，使我们可以打包可执行的 JAR 或 WAR 档案。 它的`spring-boot:run`目标运行 Spring Boot 应用。

`application.yml`

```java
server:
    port: 8086
    context-path: /api

spring: 
    main:
        banner-mode: "off"     

logging: 
    level: 
        org: 
            springframework: ERROR

```

在`application.yml`文件中，我们编写了 Spring Boot 应用的各种配置设置。 我们设置端口和上下文路径。 使用`banner-mode`属性，我们可以关闭 Spring 横幅。

我们将 spring 框架的日志记录级别设置为`ERROR`。 在`application.yml`文件位于中`src/main/resources`目录。

`JerseyConfig.java`

```java
package com.zetcode.config;

import com.zetcode.endpoint.HelloService;
import com.zetcode.endpoint.ReverseService;
import org.glassfish.jersey.server.ResourceConfig;
import org.springframework.context.annotation.Configuration;

@Configuration
public class JerseyConfig extends ResourceConfig {

    public JerseyConfig() {

        register(HelloService.class);
        register(ReverseService.class);
    }
}

```

`JerseyConfig`注册两个服务类别。

`HelloService.java`

```java
package com.zetcode.service;

import javax.ws.rs.GET;
import javax.ws.rs.Path;
import javax.ws.rs.Produces;
import org.springframework.stereotype.Service;

@Service
@Path("/hello")
public class HelloService {

    @GET
    @Produces("text/plain")
    public String hello() {
        return "Hello from Spring";
    }
}

```

这是`HelloService`。 `@Path`注解定义了服务类将响应的 URL。 Spring 的`@Service`也注解了`HelloService`以进行自动检测。 我们的服务方法仅返回`"Hello from Spring"`消息。

`HelloService.java`

```java
package com.zetcode.service;

import javax.validation.constraints.NotNull;
import javax.ws.rs.GET;
import javax.ws.rs.Path;
import javax.ws.rs.Produces;
import javax.ws.rs.QueryParam;
import org.springframework.stereotype.Service;

@Service
@Path("/reverse")
public class ReverseService {

    @GET
    @Produces("text/plain")
    public String reverse(@QueryParam("data") @NotNull String data) {
        return new StringBuilder(data).reverse().toString();
    }
}

```

`reverse()`服务方法返回一个反向的字符串。 它接受一个参数，不能为 null。 `@QueryParam`将 HTTP 查询参数的值绑定到资源方法参数。

`ApplicationTests.java`

```java
package com.zetcode;

import static org.assertj.core.api.Assertions.assertThat;
import org.junit.Test;
import org.junit.runner.RunWith;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.boot.test.context.SpringBootTest;
import org.springframework.boot.test.context.SpringBootTest.WebEnvironment;
import org.springframework.boot.test.web.client.TestRestTemplate;
import org.springframework.http.HttpStatus;
import org.springframework.http.ResponseEntity;
import org.springframework.test.context.junit4.SpringRunner;

@RunWith(SpringRunner.class)
@SpringBootTest(webEnvironment = WebEnvironment.RANDOM_PORT)
public class ApplicationTests {

    @Autowired
    private TestRestTemplate restTemplate;

    @Test
    public void hello() {
        ResponseEntity<String> entity = this.restTemplate.getForEntity("/hello",
                String.class);
        assertThat(entity.getStatusCode()).isEqualTo(HttpStatus.OK);
        assertThat(entity.getBody()).isEqualTo("Hello from Spring");
    }

    @Test
    public void reverse() {
        ResponseEntity<String> entity = this.restTemplate
                .getForEntity("/reverse?data=regit", String.class);
        assertThat(entity.getStatusCode()).isEqualTo(HttpStatus.OK);
        assertThat(entity.getBody()).isEqualTo("tiger");
    }

    @Test
    public void validation() {
        ResponseEntity<String> entity = this.restTemplate.getForEntity("/reverse",
                String.class);
        assertThat(entity.getStatusCode()).isEqualTo(HttpStatus.BAD_REQUEST);
    }
}

```

在`ApplicationTests`中，我们测试了两个端点。

`Application.java`

```java
package com.zetcode;

import org.springframework.boot.SpringApplication;
import org.springframework.boot.autoconfigure.SpringBootApplication;

@SpringBootApplication
public class Application {

    public static void main(String[] args) {
        SpringApplication.run(Application.class, args);
    }
}

```

`Application`设置 Spring Boot 应用。 `@SpringBootApplication`启用自动配置和组件扫描。

```java
$ mvn spring-boot:run

```

使用`mvn spring-boot:run`命令，运行应用。 该应用部署在嵌入式 Tomcat 服务器上。

```java
$ curl localhost:8086/api/hello
Hello from Spring

```

使用`curl`命令，我们连接到 hello 端点。

```java
$ curl localhost:8086/api/reverse?data=summer
remmus

```

夏天的字符是相反的。

在本教程中，我们使用 Jersey 借助 Spring Boot 创建了一个简单的 RESTFul 应用，它是 JAX-RS 规范的参考实现。 您可能也对相关教程感兴趣：

*   [Spring Boot REST XML 教程](/springboot/restxml/)
*   [带有嵌入式 Jetty 的 Jersey 应用](/articles/jerseyembeddedjetty/)
*   [Spring Boot H2 REST 教程](/articles/springbootresth2/)
*   [Spring Boot Thymeleaf 教程](/articles/springbootthymeleaf/)
*   [Jersey 应用中的 Web URL](/articles/url/)
*   [Spring Web 应用介绍](/articles/springwebfirst/)
*   [Spring Boot RESTFul 应用](/articles/springbootrestsimple/)