解决okhttp3提示java.lang.IllegalStateException:closed异常问题

 更新时间:2025年07月16日 08:42:46   作者:一缕纯氧  
使用OkHttp3时,response.body().string()只能调用一次,重复调用会导致流关闭异常,解决方法是保存响应体内容到变量或重新构建Response对象,避免多次读取

okhttp3提示java.lang.IllegalStateException:closed异常

使用okhttp3的response.body().string()时候提示java.lang.IllegalStateException: closed异常

原因为okhttp3请求回调中response.body().string()只能有效调用一次,而我使用了两次,所以在第二次时调用时提示已关闭流的异常。

		Response response = httpClient.newCall(request).execute();
        logger.info(response.body().string()); //一次
        Map<String,Object> resMap=objectMapper.readValue(response.body().string(),Map.class); //两次

解决办法

将返回的值保存在对象中,重复使用对象即可。(或者重新builder一个Response对象)

    public void pushOrder(RecordPushRequest pushRequest) throws Exception {
        //TODO:构造builder
        Request.Builder builder = new Request.Builder()
                .url(URL)
                .header("Content_Type", "application/json");
        //TODO:构造请求体
        RequestBody requestBody = RequestBody.create(MediaType.parse("application/json"),
                objectMapper.writeValueAsString(pushRequest));
        //TODO:构造请求
        Request request = builder.post(requestBody).build();
        //TODO:发起请求
        Response response = httpClient.newCall(request).execute();
        String res = response.body().string();
//        logger.info(response.body().string()); //打印时重复使用了一次
        Map<String,Object> resMap=objectMapper.readValue(res,Map.class);
        logger.info("得到的响应解析结果:{} ",resMap);
    }

深扒response.body().string()问题原因

查看源码Response.class:

private final ResponseBody body;

发现body是一个ResponseBody 对象。继续查看ResponseBody 类的源码:

public abstract class ResponseBody implements Closeable 

ResponseBody类实现Closeable接口,感觉有点找到问题的源泉了,继续点进去看看Closeable接口是干嘛的:

public interface Closeable extends AutoCloseable {

    /**
     * Closes this stream and releases any system resources associated
     * with it. If the stream is already closed then invoking this
     * method has no effect.
     *
     * <p> As noted in {@link AutoCloseable#close()}, cases where the
     * close may fail require careful attention. It is strongly advised
     * to relinquish the underlying resources and to internally
     * <em>mark</em> the {@code Closeable} as closed, prior to throwing
     * the {@code IOException}.
     *
     * @throws IOException if an I/O error occurs
     */
    public void close() throws IOException;
}

Closeable接口继承AutoCloseable类,有一个close方法,官方标注:“关闭此流并释放与之关联的任何系统资源。

如果流已关闭,则调用此方法无效。”大概就是这个原因了。所以不要多次调用response.body().string();语句。

总结

以上为个人经验,希望能给大家一个参考,也希望大家多多支持脚本之家。

相关文章

  • 配置了jdk的环境idea却提示找不到jdk解决办法

    配置了jdk的环境idea却提示找不到jdk解决办法

    在使用Java编程语言进行开发时,IDEA是一个非常流行和强大的集成开发环境,这篇文章主要给大家介绍了关于配置了jdk的环境idea却提示找不到jdk的解决办法,需要的朋友可以参考下
    2023-12-12
  • 服务性能优化之mybatis-plus开启与关闭SQL日志打印方法

    服务性能优化之mybatis-plus开启与关闭SQL日志打印方法

    这篇文章主要介绍了在Mybatis-plus中开启和关闭控制台SQL日志打印,在`application.properties`文件中,可以通过配置来实现SQL日志的开启和关闭,文中通过代码介绍的非常详细,需要的朋友可以参考下
    2024-12-12
  • 浅谈SpringBoot @Autowired的两种注入方式

    浅谈SpringBoot @Autowired的两种注入方式

    本文主要介绍了两种SpringBoot @Autowired注入方式,具有一定的参考价值,需要的朋友们下面随着小编来一起学习学习吧
    2021-06-06
  • Java泛型与注解全面分析讲解

    Java泛型与注解全面分析讲解

    Java 泛型(generics)是 Jdk 5 中引入的一个新特性, 泛型提供了编译时类型安全检测机制,该机制允许程序员在编译时检测到非法的类型。Annotation(注解)是JDK1.5及以后版本引入的。它可以用于创建文档,跟踪代码中的依赖性,甚至执行基本编译时检查。需要的可以参考一下
    2022-08-08
  • Java中ArrayList和LinkedList有什么区别举例详解

    Java中ArrayList和LinkedList有什么区别举例详解

    这篇文章主要介绍了Java中ArrayList和LinkedList区别的相关资料,包括数据结构特性、核心操作性能、内存与GC影响、扩容机制、线程安全与并发方案,以及工程实践场景,文中通过代码介绍的非常详细,需要的朋友可以参考下
    2025-02-02
  • Java中的ScheduledThreadPoolExecutor定时任务详解

    Java中的ScheduledThreadPoolExecutor定时任务详解

    这篇文章主要介绍了Java中的ScheduledThreadPoolExecutor详解,  ScheduledThreadPoolExecutor 继承自 ThreadPoolExecutor,它主要用来在给定的延迟之后运行任务,或者定期执行任务,ScheduledThreadPoolExecutor 的功能与 Timer 类似<BR>,需要的朋友可以参考下
    2023-12-12
  • 使用IDEA创建java项目的步骤详解(hello word)

    使用IDEA创建java项目的步骤详解(hello word)

    这篇文章主要介绍了使用IDEA创建java项目的步骤详解(hello word),本文分步骤通过图文并茂的形式给大家介绍的非常详细,对大家的学习或工作具有一定的参考借鉴价值,需要的朋友可以参考下
    2020-12-12
  • Java中的Semaphore信号量简单使用代码实例

    Java中的Semaphore信号量简单使用代码实例

    这篇文章主要介绍了Java中的Semaphore信号量简单使用代码实例,Semaphore是用来保护一个或者多个共享资源的访问,Semaphore内部维护了一个计数器,其值为可以访问的共享资源的个数,一个线程要访问共享资源,需要的朋友可以参考下
    2023-12-12
  • 简单讲解Android开发中触摸和点击事件的相关编程方法

    简单讲解Android开发中触摸和点击事件的相关编程方法

    这篇文章主要介绍了Android开发中触摸和点击事件的相关编程方法,包括事件侦听器等安卓开发中常用的接口的基本使用方法,需要的朋友可以参考下
    2015-12-12
  • SpringBoot松散绑定/宽松绑定(Relaxed Binding)的实现

    SpringBoot松散绑定/宽松绑定(Relaxed Binding)的实现

    本文主要介绍了SpringBoot松散绑定/宽松绑定(Relaxed Binding)的实现,文中通过示例代码介绍的非常详细,对大家的学习或者工作具有一定的参考学习价值,需要的朋友们下面随着小编来一起学习学习吧
    2025-08-08

最新评论