RestTemplate实时接收Chunked编码传输的HTTP Response

学习调用AI接口的时候,流式响应都是使用的 Transfer-Encoding: chunked,图方便想用RestTemplate,但是平时用到的都是直接返回响应对象的类型。使用bing搜索到一种方式,使用下面的代码来读取,于是掉这个坑里了,浪费了我好长时间。

java 复制代码
ResponseEntity<Resource> responseEntity = restTemplate.exchange(apiUrl, HttpMethod.POST, requestEntity, org.springframework.core.io.Resource.class);
PrintWriter writer = httpServletResponse.getWriter();
BufferedReader bufferedReader;
try {
    bufferedReader = new BufferedReader(new InputStreamReader(responseEntity.getBody().getInputStream()));
    String line;
    while ((line = bufferedReader.readLine()) != null && !(ChatGpt3dot5Request.STREAM_MESSAGE_PREFIX + "[DONE]").equals(line)) {
        String message = getMessageFromLine(line, ChatGpt3dot5Request.STREAM_MESSAGE_PREFIX);
        writer.write(message);
        writer.flush();
    }
} catch (IOException e) {
    throw new RuntimeException(e);
}

注意,上面的代码是错误的,并不会实时读取到数据,而是会等到响应全结束之后才能读取到数据。


下面的才是正解:

java 复制代码
restTemplate.execute(apiUrl, HttpMethod.POST, restTemplate.httpEntityCallback(requestEntity), new ResponseExtractor<ClientHttpResponse>() {
    @Override
    public ClientHttpResponse extractData(ClientHttpResponse response) throws IOException {
        InputStream inputStream = response.getBody();
        /*
         * 在这个地方从inputStream中读取数据,或者调用自己的方法读取inputStream来处理数据
        */
        return response;
    }
});
相关推荐
下次再写7 小时前
互联网大厂Java面试三轮技术问答及详解——涵盖Spring Boot与微服务
java·springboot·microservices·interview
吕永强1 天前
基于SpringBoot+Vue校园报修系统的设计与实现(源码+论文+部署)
vue·毕业设计·springboot·毕业论文·报修系统·校园报修
Flittly3 天前
【SpringSecurity新手村系列】(3)自定义登录页与表单认证
java·笔记·安全·spring·springboot
C雨后彩虹3 天前
Java Lambda & Stream 避坑指南:20个高频错误案例分析与修复
java·stream·lambda·并行流
Flittly4 天前
【SpringSecurity新手村系列】(2)整合 MyBatis 实现数据库认证
java·安全·spring·springboot·安全架构
极光代码工作室4 天前
基于SpringBoot的在线考试系统
java·springboot·web开发·后端开发
YDS8295 天前
大营销平台 —— 抽奖规则决策树
java·springboot·ddd
码农张36 天前
自定义跨字段校验必填注解
springboot
格鸰爱童话6 天前
向AI学习项目技能(七)
学习·springboot
代码漫谈6 天前
微服务 vs 单体架构:架构选型、实战拆解与决策指南
java·微服务·springboot·springcloud