RestTemplate的exchange()方法,解决put和delete请求拿不到返回值的问题
嗷嗷待哺的controller(被调用provider的controller方法)
//测试get少量参数
@RequestMapping(value = "detailsGetD",method = RequestMethod.GET)
public String test05(Integer id,String name){
System.out.println("GET-"+id+"-"+name);
return "error";
}
//测试post
@RequestMapping(value = "detailsPostD",method = RequestMethod.POST)
public String test06(Integer id,String name){
System.out.println("POST-"+id+"-"+name);
return "error";
}
//测试put
@RequestMapping(value = "detailsPutD",method = RequestMethod.PUT)
public String test07(Integer id,String name){
System.out.println("PUT-"+id+"-"+name);
return "error";
}
//测试delete
@RequestMapping(value = "detailsDeleteD",method = RequestMethod.DELETE)
public String test08(Integer id,String name){
System.out.println("DELETE-"+id+"-"+name);
return "error";
}
consumer的调用传参(url拼接少量参数)
//get传递单参
ResponseEntity<String> resp = restTemplate.exchange("http://localhost:8080/detailsGetD?id={id}&name={name}", HttpMethod.GET, null, String.class,1,"zsw");
//post传递单参
ResponseEntity<String> resp = restTemplate.exchange("http://localhost:8080/detailsPostD?id={id}&name={name}", HttpMethod.POST, null, String.class,1,"zsw");
//put传递单参
Map<String,Object> map=new HashMap<>();
map.put("id",1);
map.put("name","zsw");
ResponseEntity<String> resp = restTemplate.exchange("http://localhost:8080/detailsPutD?id={id}&name={name}", HttpMethod.PUT, null, String.class,map);
//delete传递单参
Map<String,Object> map=new HashMap<>();
map.put("id",1);
map.put("name","zsw");
ResponseEntity<String> resp = restTemplate.exchange("http://localhost:8080/detailsDeleteD?id={id}&name={name}", HttpMethod.DELETE, null, String.class,map); //返回内容
String result = resp.getBody();
System.out.println(result);
使用map和直接写参数都可以。
再介绍一下传json对象。
首先登场的是provider方controller。
//测试get
@RequestMapping(value = "detailsGet",method = RequestMethod.GET)
public String test01(@RequestBody Detail detail){
System.out.println("GET-"+detail);
return "error";
}
//测试post
@RequestMapping(value = "detailsPost",method = RequestMethod.POST)
public String test02(@RequestBody Detail detail){
System.out.println("POST-"+detail);
return "error";
}
//测试put
@RequestMapping(value = "detailsPut",method = RequestMethod.PUT)
public String test03(@RequestBody Detail detail){
System.out.println("PUT-"+detail);
return "error";
}
//测试delete
@RequestMapping(value = "detailsDelete",method = RequestMethod.DELETE)
public String test04(@RequestBody Detail detail){
System.out.println("DELETE-"+detail);
return "error";
}
我们再来看consumer的选手,传参json对象。
        String json = "{\"author\":\"zsw\",\"createdate\":1582010438846,\"id\":1,\"summary\":\"牡丹\",\"title\":\"菏泽\"}";
        HttpHeaders headers = new HttpHeaders();
        headers.setContentType(MediaType.APPLICATION_JSON);
        HttpEntity<String> entity = new HttpEntity<>(json,headers);
        ResponseEntity<String> resp = restTemplate.exchange("http://localhost:8080/detailsPost", HttpMethod.POST, entity, String.class);
        HttpStatus statusCode = resp.getStatusCode(); // 获取响应码
        int statusCodeValue = resp.getStatusCodeValue(); // 获取响应码值
        HttpHeaders headers1 = resp.getHeaders(); // 获取响应头
        System.out.println("statusCode:" + statusCode);
        System.out.println("statusCodeValue:" + statusCodeValue);
        System.out.println("headers:" + headers1);
        //或者直接传对象,底层自己处理
        Detail detail=new Detail();
        detail.setId(1L);
        detail.setSummary("牡丹");
        detail.setTitle("菏泽");
        detail.setAuthor("zsw");
        detail.setCreatedate(new Timestamp(new Date().getTime()));
        HttpHeaders headers = new HttpHeaders();
        headers.setContentType(MediaType.APPLICATION_JSON);
        HttpEntity<Detail> entity = new HttpEntity<>(detail,headers);
        ResponseEntity<String> resp = restTemplate.exchange("http://localhost:8080/detailsDelete", HttpMethod.DELETE, entity, String.class);
        //拿到返回值
        String result = resp.getBody();
        System.out.println(result);
        return result;
  post、put、delete请求都可以用这种方法。但是测试get时就不行了直接报错:org.springframework.web.client.HttpClientErrorException: 400 null(错误请求,服务器不理解请求的语法),get请求不支持这种方式的传参,get请求只能将请求参数拼接URI后边,而不能单独传递request body参数,除非你改用POST。如果用resuful风格,必须要get传参对象,也不是没有办法的。根据(https://blog.belonk.com/c/http_resttemplate_get_with_body.html)这篇文章,小弟把情况摸清楚了,上手!
import com.alibaba.fastjson.JSON;
import com.github.pagehelper.PageInfo;
import com.zhou.entity.Detail;
import org.apache.http.client.methods.HttpEntityEnclosingRequestBase;
import org.apache.http.client.methods.HttpUriRequest;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.http.*;
import org.springframework.http.client.HttpComponentsClientHttpRequestFactory;
import org.springframework.stereotype.Repository;
import org.springframework.web.client.RestTemplate; import java.net.URI;
import java.util.HashMap;
import java.util.List;
import java.util.Map; @Repository
public class DetailMapper { public String test(){
RestTemplate restTemplate1 = new RestTemplate();
restTemplate1.setRequestFactory(new HttpComponentsClientHttpRequestWithBodyFactory()); String json = "{\"author\":\"zsw\",\"createdate\":1582010438846,\"id\":1,\"summary\":\"牡丹\",\"title\":\"菏泽\"}";
HttpHeaders headers = new HttpHeaders();
headers.setContentType(MediaType.APPLICATION_JSON);
HttpEntity<String> entity = new HttpEntity<>(json,headers);
ResponseEntity<String> resp = restTemplate1.exchange("http://localhost:8080/detailsGet", HttpMethod.GET, entity, String.class); String result = resp.getBody();
System.out.println(result);
return result;
}
private static final class HttpComponentsClientHttpRequestWithBodyFactory extends HttpComponentsClientHttpRequestFactory {
@Override
protected HttpUriRequest createHttpUriRequest(HttpMethod httpMethod, URI uri) {
if (httpMethod == HttpMethod.GET) {
return new HttpGetRequestWithEntity(uri);
}
return super.createHttpUriRequest(httpMethod, uri);
}
}
private static final class HttpGetRequestWithEntity extends HttpEntityEnclosingRequestBase {
public HttpGetRequestWithEntity(final URI uri) {
super.setURI(uri);
} @Override
public String getMethod() {
return HttpMethod.GET.name();
}
}
}
大致就是这个样子。对于没接触过httpclient的我,有些类不能导包,属实有的懵。百度百度百度。。。 找到httpclient的maven的依赖,下载导包,成功!启动项目:无法访问org.apache.http.annotation.ThreadSafe,找不到org.apache.http.annotation.ThreadSafe的类文件 ???,我记忆中没有用过这个类,全局搜索一下也找不到(ctrl+shift+f - 查询自己写的代码)。继续百度,说httpclient4.5.2版本和httpcore4.4.4版本更配哦,maven自动下载的httpcore4.4.13,今天这个maven咋回事(好感-1),参考(https://www.jianshu.com/p/f35eac56c334)文章,最终的pom文件:
<?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 https://maven.apache.org/xsd/maven-4.0.0.xsd">
<modelVersion>4.0.0</modelVersion>
<parent>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-parent</artifactId>
<version>2.1.12.RELEASE</version>
<relativePath/> <!-- lookup parent from repository -->
</parent>
<groupId>com.zhou</groupId>
<artifactId>news-consumer</artifactId>
<version>0.0.1-SNAPSHOT</version>
<name>news-consumer</name>
<description>Demo project for Spring Boot</description> <properties>
<java.version>1.8</java.version>
</properties> <dependencies>
<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>
<optional>true</optional>
</dependency>
<dependency>
<groupId>org.projectlombok</groupId>
<artifactId>lombok</artifactId>
<optional>true</optional>
</dependency>
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-test</artifactId>
<scope>test</scope>
</dependency>
<!-- 分页 -->
<dependency>
<groupId>com.github.pagehelper</groupId>
<artifactId>pagehelper-spring-boot-starter</artifactId>
<version>1.2.3</version>
</dependency> <dependency>
<groupId>com.alibaba</groupId>
<artifactId>fastjson</artifactId>
<version>1.2.13</version>
</dependency> <!-- Apache Commons IO -->
<dependency>
<groupId>org.apache.httpcomponents</groupId>
<artifactId>httpclient</artifactId>
<version>4.5.2</version>
</dependency>
<!-- Apache Commons IO -->
<dependency>
<groupId>org.apache.httpcomponents</groupId>
<artifactId>httpcore</artifactId>
<version>4.4.4</version>
</dependency> </dependencies> <build>
<plugins>
<plugin>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-maven-plugin</artifactId>
</plugin>
</plugins>
</build> </project>
重新启动,访问,拿到参数。
附上github地址:https://github.com/wwck-zsw/RestTemplate
参考链接:
https://segmentfault.com/a/1190000021123356
https://www.cnblogs.com/jnba/p/10522608.html(灵感来源)
RestTemplate的exchange()方法,解决put和delete请求拿不到返回值的问题的更多相关文章
- SpringBoot 使用 RestTemplate 调用exchange方法 显示错误信息
		SpringBoot使用RestTempate SpringBoot使用RestTemplate摘要认证 SpringBoot使用RestTemplate基础认证 SpringBoot使用RestTe ... 
- Spring RestTemplate 之exchange方法
		●exchange方法提供统一的方法模板进行四种请求:POST,PUT,DELETE,GET (1)POST请求 String reqJsonStr = "{\"code\&quo ... 
- 自定义HttpMessageConverter实现RestTemplate的exchange方法返回自定义格式数据
		一 概述 实现如下效果代码,且可正常获取到返回数据: ResponseEntity<JsonObject> resEntity = restTemplate .exchange(url, ... 
- 利用jquery的$.Deferred方法在一个函数内获取另一个函数的返回值
		使用场景:方法B需要方法A执行完成之后再执行,比如方法B中有用到方法A的变量:(需要引入jQuery1.5以后的版本) function A(){ var deffered = new $.Defer ... 
- Java--FutureTask原理与使用(FutureTask可以被Thread执行,可以被线程池submit方法执行,并且可以监控线程与获取返回值)
		package com; import java.util.concurrent.Callable; import java.util.concurrent.ExecutionException; i ... 
- angularJS  条件查询 品优购条件查询品牌(条件查询和列表展示公用方法解决思路 及 post请求混合参数提交方式)
		Brand.html <!DOCTYPE html> <html> <head> <meta charset="utf-8"> &l ... 
- 资料汇总--Ajax中Put和Delete请求传递参数无效的解决方法(Restful风格)【转】
		开发环境:Tomcat9.0 在使用Ajax实现Restful的时候,有时候会出现无法Put.Delete请求参数无法传递到程序中的尴尬情况,此时我们可以有两种解决方案:1.使用地址重写的方法传递参数 ... 
- Ajax中Put和Delete请求传递参数无效的解决方法(Restful风格)
		本文装载自:http://blog.csdn.net/u012737182/article/details/52831008 感谢原文作者分享 开发环境:Tomcat9.0 在使用Ajax实现R ... 
- CURL 支持 GET、PUT、POST、DELETE请求
		一个方法解决所有的 curl 请求的问题. <?php function curlTypeData( $method, $url, $data=false, $json=false ) { $d ... 
随机推荐
- properties 文件解析
			1.提供properties文件 jdbc.driver=com.mysql.jdbc.Driver jdbc.url=jdbc:mysql://localhost:3306/future?useUn ... 
- js--数组的 Array.of() 和 Array.from() 方法的使用总结
			前言 JavaScript 中数组的本质是一个对象,它存在的 length 属性值随数组元素的长度变化,但是开发中经常会遇到拥有 length 属性和若干索引属性的对象,被称为类数组对象,类数组对象和 ... 
- .net core api 请求实现接口幂等性
			简单实现接口幂等性,根据参数的hascode实现: 参数介绍 WaitMillisecond : 请求等待毫秒数 CacheMillisecond:请求结果缓存毫秒数 参数具体使用场景 WaitMi ... 
- SVN错误:Attempted to lock an already-locked dir svn: Working copy locked
			VN错误:Attempted to lock an already-locked dir update D:/workspace20/SC_200/metadata -r 3398 --force ... 
- 常见yaml写法-job
			apiVersion: batch/v1 kind: Job metadata: name: job-demo spec: template: metadata: name: job-demo spe ... 
- Part 28 AngularJS default route
			At the moment the problem is that, if you try to navigate to a route that is not configured, you wil ... 
- requests_cookie登陆古诗文网。session的使用
			通过登录失败,快速找到登录接口 获取hidden隐藏域中的id的value值 # 通过登陆 然后进入到主页面 # 通过找登陆接口我们发现 登陆的时候需要的参数很多 # _VIEWSTATE: /m1O ... 
- NFS导致df -h卡主解决
			NFS导致df -h无法使用解决 NFS服务意外断开,导致挂载的客户端"df -Th"命令无法使用,及挂载目录无法"cd""ls"解决思路: ... 
- [hdu6973]Bookshop
			将询问拆成$x$到$lca$和$lca$($lca$靠近$y$的儿子)到$y$两部分,分别处理(后者以前者的答案为基础) 两者是类似地,不妨仅考虑前者:用树剖将该询问拆成dfs序上若干个 ... 
- [gym102268E]Expected Value
			令$X$为移动次数,答案即$\sum_{i=0}^{\infty}P(X>i)$,后者记作$S_{i}$ 关于$S_{i}$,令$f_{i,j}$表示走了$i$步后位于$j$且未到达过$k$的概 ... 
