WebSocket传JSON时Long精度丢失的根本原因是后端未将Long序列化为字符串,导致JS解析数字字面量时超出安全整数范围而失真;必须后端统一用Jackson将Long转为字符串,前端接收后原样使用或显式转BigInt。

WebSocket 传 JSON 时 Long 被 JS 解析成错误数字
直接结论:WebSocket 本身不处理 JSON 序列化逻辑,精度丢失发生在后端序列化成 JSON 字符串、前端用 JSON.parse() 解析的环节——和 HTTP API 完全一致,但更容易被忽略,因为 WebSocket 没有统一的拦截点(比如 Spring 的 @ResponseBody 全局配置)。
典型现象是后端发过去 {"id":1297373218628307972},前端收到后 data.id === 1297373218628307000,末几位变成 000。这不是 WebSocket 协议问题,而是 JSON 文本里写了数字字面量,JS 解析器一读就丢精度。
后端用 Jackson 为 WebSocket 消息做 Long → String 序列化
Spring 中 WebSocket 默认使用 Jackson 处理消息体(如 TextMessage 内容),但不像 REST 接口那样自动走 MappingJackson2HttpMessageConverter。必须显式配置 ObjectMapper 实例并注入到 WebSocketMessageBrokerConfigurer 或自定义 TextMessage 构造逻辑中。
- 全局注册
Long序列化器(推荐):SimpleModule module = new SimpleModule(); module.addSerializer(Long.class, ToStringSerializer.instance); objectMapper.registerModule(module);
- 确保这个
ObjectMapper实例被用于 WebSocket 消息的序列化,例如在发送时:String json = objectMapper.writeValueAsString(data); session.sendMessage(new TextMessage(json));
- 不要依赖
@JsonSerialize注解单独打补丁——WebSocket 场景下字段级注解容易漏掉动态构造的对象或 Map 结构
前端接收后别碰 JSON.parse() 默认行为
即使后端已转成字符串,如果前端自己再用 JSON.parse() 解析一次(比如封装了通用消息处理器),而没注意原始 payload 是字符串还是对象,就可能绕过后端的防护。
- 确认你拿到的是原始
TextMessage字符串,不是已被解析过的对象 - 避免写成:
// ❌ 错误:假设 data 已是 object,但实际可能是 string const parsed = JSON.parse(data); // data 可能已是字符串,再 parse 会报错或二次解析
- 正确做法是统一按字符串接收,再由你控制解析逻辑:
// ✅ 正确:显式处理 socket.onmessage = (event) => { const raw = event.data; // string const obj = JSON.parse(raw); // 现在才 parse,且后端已确保 id 是 string console.log(obj.id); // "1297373218628307972",类型是 string }; - 如果要用
BigInt做运算,必须明确调用:BigInt(obj.id),不能写BigInt(+obj.id)——后者先转 number 再转 bigint,已经丢精度了
为什么不用 BigInt 直接替代后端改 String?
因为 BigInt 不能参与 JSON 序列化:JSON.stringify({id: 1297373218628307972n}) 会抛错。WebSocket 消息本质仍是文本协议,所有数据最终得落回 JSON 字符串。
-
BigInt只能在前端内存中用,不能作为传输格式 - 后端若返回
"id": 1297373218628307972(数字字面量),前端无论如何都救不回来——JSON.parse()第一步就错了 - 第三方库如
json-bigint需要定制JSON.parse()行为,但 WebSocket 场景下无法保证每个接收方都用它,兼容性差
最稳的路径只有一条:后端输出 JSON 时让 Long 变成 "1297373218628307972"(带引号的字符串),前端原样收、原样用,需要计算时再转 BigInt。任何想绕过这一步的方案,都会在某个环节掉精度。


















