给RestTemplate添加拦截器记录请求响应

简介: 给RestTemplate添加拦截器记录请求响应,还需解决流只读一次的问题

RestTemplate概述

RestTemplate是Spring提供的用于访问Rest服务的客户端,RestTemplate提供了多种便捷访问远程Http服务的方法,能够大大提高客户端的编写效率。

引入依赖:

使用RestTemplate需要引入spring-boot-starter-web;

  • 使用maven引入
<dependency>
            <groupId>org.springframework.boot</groupId>
            <artifactId>spring-boot-starter-web</artifactId>
            <version>2.3.12.RELEASE</version>
        </dependency>
  • 使用gradle:

compile 'org.springframework.boot:spring-boot-starter-web'

使用时可以在配置代码中实例化bean

添加配置注解:

@Configuration
@ConditionalOnWebApplication
public class CommonWebConfiguration {

}

@Bean
    public RestTemplate restTemplate() {
       
        RestTemplate restTemplate = new RestTemplate();
        return restTemplate;
    }

简单使用RestTemplate:

执行Get请求

        URI uri = UriComponentsBuilder.fromUriString(uriStr) //
                .queryParam("token", token) //
                .queryParam("id",id)
                .build().encode().toUri();
        HttpHeaders requestHeaders = new HttpHeaders();
        requestHeaders.setAccept(Collections.singletonList(MediaType.APPLICATION_JSON));
        HttpEntity<?> requestEntity = new HttpEntity(requestHeaders);
        ResponseEntity<String> responseEntity = restTemplate.exchange(uri, HttpMethod.GET, requestEntity,
                String.class);

给RestTemplate添加拦截器

有时候在对接调试时,经常需要记录一下接口请求和响应的数据;便于调试查找问题,这时可以通过拦截器,记录下请求响应信息;

  • 定义拦截器,继承ClientHttpRequestInterceptor

重写一下intercept方法

public class RestTemplateInterceptor implements ClientHttpRequestInterceptor {

    public static Logger logger = LoggerFactory.getLogger(RestTemplateInterceptor.class);

    @Override
    public ClientHttpResponse intercept(HttpRequest httpRequest, byte[] bytes, ClientHttpRequestExecution clientHttpRequestExecution) throws IOException {
     
        ClientHttpResponse response = clientHttpRequestExecution.execute(httpRequest,bytes);
       return  response;
    }
}
  • 记录请求和响应信息的方法:

记录信息::

请求地址,请求方法,请求header,body,
响应状态码,header body等
//记录请求
    private void recordRequest(HttpRequest httpRequest, byte[] bytes){
        logger.debug("请求地址:{},请求方法:{}",httpRequest.getURI(),httpRequest.getMethodValue());
        logger.debug("请求header:{}",httpRequest.getHeaders());
        logger.debug("请求body:{}",new String(bytes, StandardCharsets.UTF_8));
        logger.debug("请求开始---------------------------------");
    }
   
    public void  recordResponse(ClientHttpResponse response) throws  IOException{

        StringBuilder inputStringBuilder = new StringBuilder();
        BufferedReader bufferedReader = new BufferedReader(
                new InputStreamReader(response.getBody(),StandardCharsets.UTF_8));

        String line = bufferedReader.readLine();
        while (line!=null){
            inputStringBuilder.append(line).append("\n");
            line = bufferedReader.readLine();
        }
        logger.debug("Status code  : [{}]", response.getStatusCode());
        logger.debug("Status text  : [{}]", response.getStatusText());
        logger.debug("Headers      : [{}]", response.getHeaders());
        logger.debug("Response body: [{}]", inputStringBuilder);

    }
  • 除了可以记录信息,还可以给请求加点东西:
 //给请求加点东西
    private void handlerRequest(HttpRequest request){
        HttpHeaders headers = request.getHeaders();
        headers.add("my_key","my_value");
    }
  • 将记录的方法添加到intercept中:
@Override
    public ClientHttpResponse intercept(HttpRequest httpRequest, byte[] bytes, ClientHttpRequestExecution clientHttpRequestExecution) throws IOException {

        handlerRequest(httpRequest);
        recordRequest(httpRequest,bytes);
        ClientHttpResponse response = clientHttpRequestExecution.execute(httpRequest,bytes);
        recordResponse(response);
        return  response;
    }
  • 给RestTemplate配置一下拦截器;

可以再配置文件中,实例化一下bean

 @Bean
    public RestTemplateInterceptor restTemplateInterceptor(){
        return  new RestTemplateInterceptor();
    }
@Bean
    public RestTemplate restTemplate() {
       
        RestTemplate restTemplate = new RestTemplate();
        //restTemplate.getInterceptors().add(restTemplateInterceptor());
        return restTemplate;
    }
  • 发起请求,输出响应和请求数据;

有个问题

在RestTemplate测试时,发现没有响应信息,后来发现是,输出流只读一次的问题;

解决这个问题:

解决这个问题可以使用:BufferingClientHttpRequestFactory

 @Bean
    public RestTemplate restTemplate() {
        SimpleClientHttpRequestFactory requestFactory = new SimpleClientHttpRequestFactory();

        BufferingClientHttpRequestFactory simpleBufferingClientHttpRequest =
                new BufferingClientHttpRequestFactory(requestFactory);

        requestFactory.setConnectTimeout(5000);
        requestFactory.setReadTimeout(3500);
        RestTemplate restTemplate = new RestTemplate(simpleBufferingClientHttpRequest);
        restTemplate.getInterceptors().add(restTemplateInterceptor());
        return restTemplate;
    }
相关文章
|
5月前
|
前端开发 JavaScript
请求拦截器的使用
请求拦截器的使用
58 0
|
3天前
|
存储 缓存 Java
SpringBootWeb请求响应之前言及状态码的详细解析
SpringBootWeb请求响应之前言及状态码的详细解析
9 0
|
29天前
|
中间件
16_响应拦截器
16_响应拦截器
20 0
|
2月前
|
JSON 前端开发 Java
SpringMVC请求和响应
Spring MVC通过请求和响应的处理来实现Web应用程序的开发。请求通过控制器处理,响应通过视图渲染器生成最终的HTML响应,并返回给客户端。
43 4
|
3月前
|
存储
SpringMVC的请求和响应
SpringMVC的请求和响应
10 0
|
4月前
Axios 拦截器 请求拦截器 响应拦截器
Axios 拦截器 请求拦截器 响应拦截器
|
10月前
|
JSON Java 应用服务中间件
SpringMVC | 请求与响应
SpringMVC | 请求与响应
|
11月前
|
JSON 编解码 应用服务中间件
SpringMVC请求与响应(一)
SpringMVC请求与响应(一)
|
11月前
|
JSON 数据格式
SpringMVC请求与响应(二)
SpringMVC请求与响应(二)
|
前端开发 API
axios定制化设置请求响应拦截器,统一处理请求响应
设置拦截器的目的在于:可以定制化,设置请求头,公共api,超时时间。统一处理响应,对于前端获取的数据更加清晰。
368 0