【问题标题】:Spring Boot - configuring restTemplate for content-type application/jsonSpring Boot - 为内容类型应用程序/json配置restTemplate
【发布时间】:2017-10-08 09:56:40
【问题描述】:

我正在尝试使用本教程使用 RESTful Web 服务: Consuming a RESTful Web Service

但是在调用 restTemplate 时出现以下错误

org.springframework.web.client.RestClientException: Could not extract response: no suitable HttpMessageConverter found for response type [class [cukamart.cvut.fel.cz.dto.Flight;] and content type [text/html;charset=UTF-8]

我不明白为什么内容类型设置为 text/html。它应该是 application/json 因为我添加了 jackson 依赖项到我的 pom.xml 并且 spring-boot 应该为我配置它对吗?

因为 Jackson JSON 处理库在类路径中,RestTemplate 将使用它(通过消息转换器)来转换传入的 JSON 数据

这是我的 restTemplate bean

@Configuration
public class AosClientConfig extends WebMvcConfigurerAdapter{

    @Bean
    public RestTemplate restTemplate(RestTemplateBuilder builder) {
        return builder.build();
    }
}

带有杰克逊依赖的pom.xml

<?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>cukamart.cvut.fel.cz</groupId>
    <artifactId>aosclient</artifactId>
    <version>0.0.1-SNAPSHOT</version>
    <packaging>war</packaging>

    <name>aosclient</name>
    <description>Demo project for Spring Boot</description>

    <parent>
        <groupId>org.springframework.boot</groupId>
        <artifactId>spring-boot-starter-parent</artifactId>
        <version>1.5.3.RELEASE</version>
        <relativePath/> <!-- lookup parent from repository -->
    </parent>

    <properties>
        <project.build.sourceEncoding>UTF-8</project.build.sourceEncoding>
        <project.reporting.outputEncoding>UTF-8</project.reporting.outputEncoding>
        <java.version>1.8</java.version>
    </properties>

    <dependencies>
        <dependency>
            <groupId>com.fasterxml.jackson.core</groupId>
            <artifactId>jackson-databind</artifactId>
        </dependency>
        <dependency>
            <groupId>org.springframework.boot</groupId>
            <artifactId>spring-boot-starter-thymeleaf</artifactId>
        </dependency>
        <dependency>
            <groupId>org.springframework.boot</groupId>
            <artifactId>spring-boot-starter-web</artifactId>
        </dependency>

        <dependency>
            <groupId>org.springframework.boot</groupId>
            <artifactId>spring-boot-devtools</artifactId>
            <scope>runtime</scope>
        </dependency>
        <dependency>
            <groupId>org.springframework.boot</groupId>
            <artifactId>spring-boot-starter-tomcat</artifactId>
            <scope>provided</scope>
        </dependency>
        <dependency>
            <groupId>org.springframework.boot</groupId>
            <artifactId>spring-boot-starter-test</artifactId>
            <scope>test</scope>
        </dependency>
        <dependency>
            <groupId>org.springframework.boot</groupId>
            <artifactId>spring-boot-starter-security</artifactId>
        </dependency>
</dependencies>

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

尝试使用 RESTful Web 服务的控制器

@Controller
@RequestMapping(value = "/flight")
public class FlightController {

    @Value("${endpoint.url}")
    private String url;

    @Autowired
    private RestTemplate restTemplate;

    @GetMapping(value = "/preview")
    public String showAllFlights() {

        restTemplate.getForObject(url,  Flight[].class); //throw exception

        ....
        return "flights";
    }
}

知道我做错了什么或如何告诉 restTemplate 使用内容类型 application/json 吗?

我也试过了,但我得到了同样的错误

@GetMapping(value = "/preview")
    public String showAllFlights() {
        HttpHeaders headers = new HttpHeaders();
        headers.setAccept(Collections.singletonList(MediaType.APPLICATION_JSON));

        HttpEntity<String> entity = new HttpEntity<String>("parameters", headers);

        restTemplate.exchange(url, HttpMethod.GET, entity, Flight[].class);

        return "flights";
    }

【问题讨论】:

    标签: json spring-boot content-type resttemplate


    【解决方案1】:

    我认为问题可能出在这一行:

    restTemplate.exchange(url, HttpMethod.GET, entity, Flight[].class);

    当 httpmethod 为 GET 时,resttemplate 会忽略正文,因此不会包含您的实体。将 httpmethod 更改为 POST 并查看目标服务是否接收到有效负载。如果您控制它,您可能必须对目标服务进行更改才能接受 POST。

    【讨论】:

      【解决方案2】:

      看起来响应中的“Content-Type”标头没有设置。您可以使用Postman(Chrome Extension) 或类似的 REST 客户端向该 URL 发送请求吗?这将帮助您查看 REST 端点是否实际返回带有“Content-Type: application/json”响应标头的数据。

      http://blog.getpostman.com/2015/06/13/debugging-postman-requests/ 解释了如何使用 Postman 检查响应标头。

      【讨论】:

      • 谢谢,但我已经尝试通过高级休息客户端请求,我得到了 json 和 xml 中的响应。我也是服务器端的作者,我已经设置了 -produces = {MediaType.APPLICATION_JSON_VALUE, MediaType.APPLICATION_XML_VALUE}
      • 如果您同时生成 json 和/或 xml 类型的响应,您还应该在请求中传递一个“Accept: application/json”标头,以确保您获得正确的响应格式。这是一个如何做到这一点的例子stackoverflow.com/questions/19238715/…
      • 我已经尝试过了(请参阅我的问题 - 最后一个 sn-p)但是我不理解这一行 HttpEntity entity = new HttpEntity("parameters", headers);什么是“参数”?
      猜你喜欢
      • 2018-09-05
      • 1970-01-01
      • 2019-06-23
      • 1970-01-01
      • 2015-06-07
      • 2019-12-07
      • 1970-01-01
      • 1970-01-01
      • 2016-08-22
      相关资源
      最近更新 更多