默认
发表评论 3
想开发IM:买成品怕坑?租第3方怕贵?找开源自已撸?别走弯路了... 找站长给点建议
[已解决] MobileIMSDK开发的IM消息接收方客户端断网导致消息没存离线的问题
阅读(242) | 评论(3 收藏 淘帖1 2
在一般情况,如果客户端ws在线,则直接转发消息,如果ws断开则走离线消息,把消息存到缓存中,客户端重连的时候通过http去拉取离线消息。但是现在遇到一个问题,接收方如果是断网的情况下,发送方发送消息,通过sendData()方法 不知道什么原因,发送成功了,但实际上接收方并没有收到消息,由于服务端认为消息发送成功,所以也没存消息到缓存中 导致断网情况下消息丢失,这种情况应该怎么办呢?

即时通讯网 - 即时通讯开发者社区! 来源: - 即时通讯开发者社区!

上一篇:[已回复] 求教MobileIMSDK h5端vite中掉线频繁是什么原因

本帖已收录至以下技术专辑

推荐方案
评论 3
是的,你说的这种情况是有可能发生的,但MobileIMSDK的服务端有QoS机制兜底的,也就是服务端发出的消息,它如果在超时时间内没有收到接收方的ACK应答,是会报消息送达失败的。

你可以看一下 MobileIMSDK服务端Demo工程里的 MessageQoSEventS2CListnerImpl.java 这个实现类,你注意一下 messagesLost 回调方法,你说的这种情况肯定会在这个回调方法里告诉你,你自已将这条消息存离线就好了

MobileIMSDK现在的消息送达机制下,几乎不可能出现消息去向不明的情况要么有明确的ACK应达告诉你消息送达,要么会通过超时机制告诉你消息送达失败

RainbowChat 为例,它的 messagesLost 代码是这样的实现的,你可以参考一下
        /**
         * 消息未送达的回调事件通知.
         * 
         * @param lostMessages 由MobileIMSDK QoS算法判定出来的未送达消息列表(此列表
         * 中的Protocal对象是原对象的clone(即原对象的深拷贝),请放心使用哦),应用层
         * 可通过指纹特征码找到原消息并可以UI上将其标记为”发送失败“以便即时告之用户
         */
        @Override
        public void messagesLost(final ArrayList<Protocal> lostMessages)
        {
                logger.debug("【QoS_S2C事件[未实时送达]】收到系统的未实时送达事件通知,当前共有" +lostMessages.size()+"个包QoS保证机制结束,判定为【无法实时送达】!");
                
                if(lostMessages.size() > 0) {
                        // 将处理放在独立的线程池中处理以提升处理效率,防止在大用户量时阻塞主服务
                        CommonConcurrentExecutor.getInstance().execute(() -> {
                                // 大数据量的情况下,iterator性能要大大优于普通的数组for循环
                                Iterator<Protocal> pit = lostMessages.iterator();
                                while(pit.hasNext()) {
                                        Protocal p = pit.next();
                                        if(p != null) {
                                                try {
                                                        // 一对一好友聊天的消息因走的是C2C消息路径,所以不需要在QoS机制中处理聊天记录了,
                                                        // 因为它已在 ServerEventListener.onTransferMessage4C2C()中处理,这里再做就会重复哦
                                                        if(p.getTypeu() == UserProtocalsType.MT03_OF_CHATTING_MESSAGE) {
                                                                ChatServerLauncher.getInstance().getServerEventListener().onTransferMessage_RealTimeSendFaild_impl(p, true);
                                                        } else {
                                                                ChatServerLauncher.getInstance().getServerEventListener().onTransferMessage_RealTimeSendFaild_impl(p, false);
                                                        }
                                                } catch (Exception e) {
                                                        logger.warn("【QoS_S2C事件[未实时送达]】离线处理出错了,原因是:"+e.getMessage(), e);
                                                }
                                        }
                                }
                        });
                }
        }
引用:JackJiang 发表于 2026-02-04 19:45
是的,你说的这种情况是有可能发生的,但MobileIMSDK的服务端有QoS机制兜底的,也就是服务端发出的消息,它 ...

好的 感谢 我试了通过这种兜底方式可以解决断网情况下消息丢失的问题
引用:hyf123 发表于 2026-02-05 08:39
好的 感谢 我试了通过这种兜底方式可以解决断网情况下消息丢失的问题

好的
打赏楼主 ×
使用微信打赏! 使用支付宝打赏!

返回顶部