WebSocket长连接优化:宠友IM源码中的心跳与断线重连机制
IM系统上线之后最容易被忽略的一类问题不是发送失败而是“看起来在线实际上已经断了”。这种情况用户感知很直接消息发不出去、收不到、需要反复重启应用。宠友信息在「宠友IM」源码里对WebSocket连接这一层做了不少细节处理没有复杂协议但在心跳检测、断线重连、连接状态维护这几个点上比较扎实。这篇只拆一个主题WebSocket连接稳定性优化。一、长连接为什么会“假在线”很多开发阶段的WebSocket实现是这样的建立连接收发消息断开再连问题在于TCP连接不等于真实在线状态常见导致“假在线”的情况手机切后台系统暂停网络网络切换WiFi → 4G路由器NAT回收连接服务端连接未及时释放这类问题不会触发onClose服务端依然认为用户在线。二、心跳机制设计核心宠友IM没有使用复杂协议而是采用最常见的一种客户端主动心跳 服务端检测超时基本策略客户端每30秒发送一次ping服务端记录最后活跃时间超过一定时间未收到心跳 → 判定离线服务端核心逻辑// 简化示例记录用户最后心跳时间 private static final ConcurrentHashMapLong, Long HEARTBEAT_MAP new ConcurrentHashMap(); public void onHeartbeat(Long userId) { HEARTBEAT_MAP.put(userId, System.currentTimeMillis()); } 配合定时任务扫描 // 超时检测60秒未心跳判定离线 public void checkTimeout() { long now System.currentTimeMillis(); HEARTBEAT_MAP.forEach((userId, lastTime) - { if (now - lastTime 60000) { // 关闭连接 清理资源 disconnect(userId); } }); }这种方式简单但足够稳定。三、为什么不能只依赖WebSocket事件很多实现只依赖onOpenonCloseonError问题在于这些事件并不可靠比如用户断网 → 服务端可能长时间收不到onClose网络抖动 → 连接处于半开状态宠友IM的处理方式是WebSocket事件只是“参考”心跳机制才是“最终判定”四、断线重连策略客户端关键逻辑断线不可避免关键是重连策略。常见错误做法立即重连无限重试结果短时间内大量请求服务端压力暴涨宠友IM采用指数退避重连逻辑第1次失败1秒后重连第2次失败2秒第3次失败4秒上限30秒避免雪崩。客户端伪代码let retry 0; function reconnect() { const delay Math.min(30000, Math.pow(2, retry) * 1000); setTimeout(() { connect(); retry; }, delay); }这个策略在网络波动场景下非常关键。五、多端登录下的连接管理宠友IM支持APP小程序H5PC多端意味着 一个用户会有多个连接服务端结构设计不是userId - session而是userId - {设备类型 - session}这样可以做到不同端独立在线消息可以同步推送多个端同时避免新设备登录踢掉旧连接六、连接状态同步问题在单机下维护连接没问题但一旦多节点部署A服务器有连接B服务器不知道宠友IM没有做复杂网关而是用简单方案 Redis记录在线状态 广播机制处理方式用户上线 → 写Redis用户下线 → 删除Redis发送消息时判断目标是否在线这样可以做到跨节点识别在线状态简单扩展七、连接资源清理连接不及时释放会带来两个问题内存泄漏连接数爆满宠友IM的处理策略onClose清理心跳超时强制清理异常捕获统一关闭重点在于不要依赖单一入口释放资源八、消息发送失败处理WebSocket发送不是100%成功连接存在但不可写网络瞬断宠友IM没有假设“发送一定成功”而是 失败后走降级路径策略发送失败 → 写入离线消息用户下次上线拉取这样可以保证消息不丢用户体验一致九、线上遇到的几个典型问题1频繁断开重连原因心跳间隔过短服务端超时过严调整心跳30秒超时60~90秒2连接暴涨原因客户端异常重连没有限流处理增加连接频率限制同IP限流3消息延迟原因连接处于半开状态数据未及时发送解决心跳检测及时断开强制重连4多端状态错乱原因一个端断开误删全部状态解决按设备维度维护连接独立管理生命周期十、这类WebSocket优化的核心思路宠友信息这套实现没有复杂协议也没有引入额外网关层但有几个关键点用心跳替代连接状态判断用重连策略避免流量冲击用简单结构支持多端在线IM系统稳定性问题本质不在“用不用WebSocket”而在于 是否正确处理“连接不可靠”这件事市面上已有成熟的源码⭐宠友IM⭐https://www.chongyou.info/1/product/im.html