mqtt长连接报错32000

背景

项目需要使用mqtt协议建立长连接,我是客户端,需要连上服务端同学的提供的地址;客户端使用的是paho提供的客户端sdk,如下:


    org.eclipse.paho
    org.eclipse.paho.client.mqttv3
    1.2.5

建立连接代码也十分简单,和github上demo差不多:

public void createMqttConnection(){
        try {
            String ts = System.currentTimeMillis() + "";
            String password = "password";
            String clientId = "server_" + InetAddress.getLocalHost().getHostAddress() + "_" + ts;
            String broker = mqttConfig.getMqttHost();

            MemoryPersistence persistence = new MemoryPersistence();
            mqttClient = new MqttClient(broker, clientId, persistence);
            mqttClient.setCallback(new MqttCallback() {
                @Override
                public void connectionLost(Throwable cause) {
                    System.out.println("连接断开");
                    cause.printStackTrace();
                }

                @Override
                public void messageArrived(String topic, MqttMessage message) throws Exception {

                }

                @Override
                public void deliveryComplete(IMqttDeliveryToken token) {

                }
            });
            MqttConnectOptions connectOptions = new MqttConnectOptions();
            connectOptions.setUserName("server");
            connectOptions.setPassword(password.toCharArray());
            connectOptions.setAutomaticReconnect(true);
            connectOptions.setCleanSession(true);
            connectOptions.setKeepAliveInterval(20);

            log.info("Mqtt connection Initialization begin!");
            mqttClient.connect(connectOptions);
            log.info("Mqtt connection success!");
        } catch (Exception e) {
            log.error("Mqtt connection initialization error ", e);
        }
    }

问题

服务启动,并成功连接上过后,总是报错: 等待来自服务器的响应超时(32000),如下图

mqtt长连接报错32000

排查

打开wireshark抓包,结果如下,时间顺序是从下到上,发现,TCP三次握手建立连接后(362,363,364),并成功验证了username,password后(392,393,395,396),的确20s后( keepAliveInterval设置的20),客户端向服务器发送了心跳包(3456【PSH, ACK】),这个发送,是被【ACK】(3458)了,但是在接下来的20s内,服务器都没有返回心跳给客户端,在客户端看来,那么服务器就是挂了,所以断开连接,产生了接下来的【FIN ACK】(6136),四次挥手(6137,6138)断开了TCP连接(至于为什么四次挥手只抓到3个包,后文有补充);由于设置了 setAutomaticReconnect=true,又开始三次握手建立连接了。

mqtt长连接报错32000

结论

服务器没有返回心跳给客户端,客户端以为服务器挂了,就断开连接报错。需要让服务器端同学,修复一下心跳发送相关代码。

为什么四次挥手只有3个包
参考:Linux之TCP的实现,四次挥手
大概意思就是Linux中支持TCP的延迟ACK机制,发送ack的条件不能满足立即发送ack的条件,导致ack的发送被延时了,于是和下一个FIN合在一起发;包括本文中问题修复正常后,服务器端(Linux)返回的心跳也有这个ACK延迟

Original: https://www.cnblogs.com/rachel-aoao/p/16282083.html
Author: rachel_aoao
Title: mqtt长连接报错32000

原创文章受到原创版权保护。转载请注明出处:https://www.johngo689.com/601335/

转载文章受原作者版权保护。转载请注明原作者出处!

(0)

大家都在看

  • Mysql的读写分离中间件该怎么写?听我来说。

    网上有很多读写分离的中间件,像proxy,mycat等等,由于本人比较懒,懒得去读各种开源的东西,还是想造轮子来得快。 1、了解mysql通信协议,其中有分4.1之前和4.1版本的…

    数据库 2023年5月24日
    0129
  • 在windows上用docker desktop安装StoneDB

    自6月底开源以来,许多热心的社区用户都对StoneDB进行了编译和测试,也有一些用户询问StoneDB是否会支持Windows。虽然适配Windows版本的StoneDB尚未进入研…

    数据库 2023年5月24日
    0113
  • zabbix模板,角色,用户,权限管理

    用户管理 用户组 用户角色 用户 模板管理 模板组 模板 posted @2022-09-07 22:22 溜溜威 阅读(16 ) 评论() 编辑 Original: https:…

    数据库 2023年6月14日
    0107
  • MySQL多表查询

    多表查询 案列说明 笛卡尔积的理解 select id,department_name from employees,departments;#错的 select id,depar…

    数据库 2023年5月24日
    083
  • Redis学习笔记一

    ============================= Redis学习笔记一 注:笔记旨在记录 一、redis简介: 高性能的 key-value 数据库 特点: 支持数据持久…

    数据库 2023年6月16日
    073
  • BeautifulSoup4的使用

    Beautiful Soup 主要是用来解析提取 HTML 和 XML 文件中的数据。 现在官网推荐使用 Beautiful Soup 4 ,已经被移植到了BS4中。 安装 Bea…

    数据库 2023年6月9日
    0101
  • mysql事务、触发器、存储过程

    一、mysql事务 数据库中的事务是指对数据库执行一批操作,在同一个事务当中,这些操作最终要么全部执行成功,要么全部失败,不会存在部分成功的情况。MySQL 事务主要用于处理操作量…

    数据库 2023年5月24日
    085
  • Redis的五大数据类型(简单使用)

    redis是基于内存的,内存的读写速度非常快 ; redis是单线程的,省去了很多上下文切换线程的时间; *redis因为是基于内存的 不涉及io操作 所以单线程效率是最高的 回归…

    数据库 2023年6月6日
    0102
  • 翻译 | Kubernetes 将改变数据库的管理方式

    作者:Álvaro Hernández 当技术决策人考虑在 Kubernetes 上部署数据库时,面临的第一个问题就是:” Kubernetes 有应对有状态服务的能力…

    数据库 2023年5月24日
    0127
  • 简析XDP的重定向机制

    GreatSQL社区原创内容未经授权不得随意使用,转载请联系小编并注明来源。 GreatSQL是MySQL的国产分支版本,使用上与MySQL一致。 一. XDP Socket示例解…

    数据库 2023年6月11日
    089
  • MySQL select语句中where条件的提取过程

    select语句中where条件的提取过程 孔个个依然,在整理where条件提取过程时,发现中文互联网上关于这一块的知识要么是存在错误自相矛盾的,要么是版本过老,遂自己整理了一版。…

    数据库 2023年6月16日
    093
  • [LeetCode]20. 有效的括号

    给定一个只包括 ‘(‘,’)’,'{‘,’}’,'[‘,’]&#8217…

    数据库 2023年6月9日
    0124
  • Shell第三章《for循环》

    语法结构: for 变量名 [ in 取值列&a…

    数据库 2023年6月14日
    095
  • MySQL45讲之幻读

    前言 本文介绍了什么是虚读,虚读存在的问题和解决方法,以及间隙锁带来的麻烦。 [En] This paper introduces what is phantom reading,…

    数据库 2023年5月24日
    086
  • Linux下Oracle单实例配置多监听

    Oracle单实例配置多监听 一、前言 有时候我们项目中需要使用Oracle数据库,同时要需要不同的数据源,而Oracle不像Mysql那样直接建个库即可,Oracle是以账号为单…

    数据库 2023年6月16日
    0135
  • sed与awk命令

    1.1 sed命令语法 在看单个命令以前,需要回顾一下关于所有sed命令的两点语法。在上一个章中,我们介绍了其大部分内容。行地址对于任何命令都是可选的。它可以使一个模式,被描述为由…

    数据库 2023年6月14日
    0107
亲爱的 Coder【最近整理,可免费获取】👉 最新必读书单  | 👏 面试题下载  | 🌎 免费的AI知识星球