OkHttp Address already in use: no further information异常

这篇具有很好参考价值的文章主要介绍了OkHttp Address already in use: no further information异常。希望对大家有所帮助。如果存在错误或未考虑完全的地方,请大家不吝赐教,您也可以点击"举报违法"按钮提交疑问。

  说下场景,我的程序在多线程场景下一个循环体中处理业务数据,其中需要调用一个外部http接口去获取一些数据,程序总会在在本地执行一段时间后会抛出Address already in use: no further information错误。

  这是大量并发场景下出现的问题,经过查阅原因是OkHttp的链接没有被有效回收和复用导致的端口资源占用,okHttp在发起请求调用外部接口时也会占用本地的端口资源,因为okHttp需要建立Socket链接来和对方通信,端口是本地一个随机的未被使用的端口,okHttp会尽量复用这些资源以减少服务器消耗,但如果在短时间内出现大量的请求都在创建新的okHttp对象去发起请求,那么每个okHttp对象的资源占用都不会共享,导致资源被浪费,亦或者没有及时关闭响应体,比如response.close()。最终,资源被耗尽,出现 Address already in use: no further information。而我的调用代码就是为了图方便简单的每次请求创建一个新的OkHttpClient

  解决方式很简单,使用单例的OkHttpClient并配置好超时时间,同时注意资源关闭,如果是在Spring环境下做个配置就行,其中线程数和连接回收时间根据自己情况进行调整:

@Configuration
public class HttpClientConfiguration {
    @Bean
    public OkHttpClient httpClient(){
        return  new OkHttpClient().newBuilder()
                //设置线程池              最大200线程     最大保持10秒连接既自动回收
                .connectionPool(new ConnectionPool(200, 10, TimeUnit.SECONDS))
                //设置超时时间
                .connectTimeout(5, TimeUnit.SECONDS).readTimeout(5,TimeUnit.SECONDS)
                .writeTimeout(5,TimeUnit.SECONDS).build();
    }
}
 
 
class Test{
 
  @Autowired
  private OkHttpClient httpClient;
 
  public JsonNode getFieldData(String token){
        String body = "{xxx}";
 
        RequestBody requestBody = RequestBody.create(MediaType.parse("application/json"),body);
        Request request = new Request.Builder().url("http://xxxx").post(requestBody).header("token",token).build();
 
        //请求成功结果正常则返回数据
        try (Response response = httpClient.newCall(request).execute()){
            if(response.isSuccessful()){
                String resultJsonStr = response.body().string();
                JsonNode resJson = objectMapper.readTree(resultJsonStr);
                return resJson.get("result");
            }
        }catch (Exception e){
            logger.error(e.getMessage(),e);
        }
        return objectMapper.createObjectNode();
    }
}

另外,根据找到的资料,单例模式下的OkHttp性能也会更好:

如果okhttp客户端不是单例的,那么每次发送请求时都会创建一个新的客户端对象,这样会导致资源浪费和性能下降,而且可能会导致内存泄漏。okhttp客户端是设计成单例的,它可以共享连接池、响应缓存和配置。因此,建议使用单例模式来创建和管理okhttp客户端,或者至少为每个主机名保持一个客户端实例。文章来源地址https://www.toymoban.com/news/detail-412505.html

到了这里,关于OkHttp Address already in use: no further information异常的文章就介绍完了。如果您还想了解更多内容,请在右上角搜索TOY模板网以前的文章或继续浏览下面的相关文章,希望大家以后多多支持TOY模板网!

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处: 如若内容造成侵权/违法违规/事实不符,请点击违法举报进行投诉反馈,一经查实,立即删除!

领支付宝红包 赞助服务器费用

相关文章

  • Caused by: java.net.BindException: Address already in use: bind

    一,换端口号 这个比较简单,就是把tomcat的端口号改一下,换一个没用的端口号就行了。 1,找到找到server.xml文件 去tomcat的安装目录下的conf文件夹就可以找到 2,修改端口号 找到Connector标签,红方框中8080位置就是端口号,修改这个端口号即可,之后重启服务器 二,杀掉占

    2024年02月11日
    浏览(38)
  • Error running ‘Tomcat 8.5.29‘ Address localhost:1099 is already in use

    原因:端口1099被占用了。 2.1 解决方法一-结束该端口1099占用 具体命令 : 截图: 2.2 解决方法二-修改端口号1099为其他端口 使用 方法一 或者 方法二 解决问题后, 再次启动Tomcat ,便不会再报此 端口占用 错误。

    2024年02月11日
    浏览(24)
  • Linux Server 终止后立即重启报错 bind error: Address already in use

    先启动Server,再启动Client,然后使用Ctrl+C关闭Server,马上再运行Server,会得到以下结果: 这是因为,虽然Server的应用程序终止了,但TCP协议层的连接并没有完全断开,因此Server不能再监听同样的端口 使用netstat命令可以查看,Server终止时,Socket描述符会自动关闭并发FIN段给

    2024年02月07日
    浏览(40)
  • nginx: [emerg] bind() to 0.0.0.0:80 failed (98: Address already in use)

    原因就是80 端口被占用了可能是你的centos安装了Apache中间件,然后它俩都用的80 端口所以导致占用了,这时候关闭端口即可!用到命令fuser fuser 是Linux上的一个命令,用以由文件或设备去找出使用文件、或设备的进程,该命令列出本地进程的进程号,那些本地进程使用File 参数

    2024年02月09日
    浏览(31)
  • 【Kafka】ZooKeeper启动失败报错java.net.BindException: Address already in use: bind

    Kafka 2.8.1 ZooKeeper启动失败。 2181端口被占用。 打开cmd。 无结果返回,找不到占用2181端口的程序。 修改config/zookeeper.properties 找到: 改为: 重新启动ZooKeeper,启动成功。 记得修改config/server.properties,不然Kafka Server无法连接。 找到: 改为: 在解决端口被占用的问题时,首先需

    2024年02月09日
    浏览(49)
  • nginx报错 nginx: [emerg] bind() to 0.0.0.0:80 failed (98: Address already in use)

    今天重新优化nginx管理以后,检查配置文件是配置正确的,但启动nginx确报错了 报错显示nginx: [emerg] bind() to 0.0.0.0:80 failed (98: Address already in use) 查看nginx的端口(nginx使用的端口为80)   发现可能是之前的nginx服务自己占用80端口,导致不能启动,把他的进程全部杀掉,再重启服

    2024年02月16日
    浏览(37)
  • 【nginx启动出错】nginx: [emerg] bind() to 0.0.0.0:80 failed (98: Address already in use)

    问题:nginx: [emerg] bind() to 0.0.0.0:80 failed (98: Address already in use) 启动过程: 在ubuntu上下载好nginx后,首先进入 sbin/ 目录下输入以下测试命令查看nginx配置情况 测试成功后,输入命令 启动nginx,但是遇到问题 nginx: [emerg] bind() to 0.0.0.0:80 failed (98: Address already in use) 错误原因:80端口

    2024年02月09日
    浏览(27)
  • nginx启动提示:nginx: [emerg] bind() to 0.0.0.0:8080 failed (98: Address already in use)

    解决方法两种:          第一种:更换端口          第二种:杀死占用的端口 我们先来看第一种方法: 再来看第二种方法: 欢迎大家纠错讨论!!!

    2024年02月15日
    浏览(35)
  • Redis端口占用 Could not create server TCP listening socket *:6379: bind: Address already in use

    在使用redis-server命令时发现启动redis失败,说端口号6379已经在使用了。 10503:M 16 Nov 2022 17:29:01.118 # Warning: Could not create server TCP listening socket *:6379: bind: Address already in use 10503:M 16 Nov 2022 17:29:01.118 # Failed listening on port 6379 (TCP), aborting.  1. 使用命令ps -ef | grep redis 查看被占用的端口

    2024年02月11日
    浏览(48)
  • Error starting userland proxy: listen tcp 0.0.0.0:80: bind: address already in use.的解决办法

    docker映射端口报下面这个错误: Error starting userland proxy: listen tcp 0.0.0.0:80: bind: address already in use. 大概意思就是端口被占用了,我们只要将被占用的端口杀死即可。 解决方案: 1、首先先查看当前占用端口的命令 2、杀死进程 3、删除后再运行docker run命令再次创建docker容器即可

    2024年02月21日
    浏览(34)

觉得文章有用就打赏一下文章作者

支付宝扫一扫打赏

博客赞助

微信扫一扫打赏

请作者喝杯咖啡吧~博客赞助

支付宝扫一扫领取红包,优惠每天领

二维码1

领取红包

二维码2

领红包