如何解决奇怪的!春季靴中的长值取整问题 可能的解决方案
当我尝试使用杰克逊对象映射器将对象序列化为JSON时,它可以正常工作。
{"id":1291741231928705024,"uuid":null,"email":"kannanrbk.r@gmail.com"}
当我尝试使用spring rest控制器访问它时。长值数字四舍五入,最后3位数字。
我阅读了stackoverflow中的现有问题,其中大多数建议将数据类型更改为字符串。但是我们在大多数地方使用Long值引用,更改数据类型将需要一些重构。
我做了初步分析:
- 我们正在使用杰克逊
ObjectMapper
- 从Spring开始,它间接调用
MappingJackson2HttpMessageConverter
- 此问题可能在JSONParser周围的某个地方,它将任何数字都视为双精度数字(15位数字),然后将其四舍五入
有什么办法可以解决此问题?
解决方法
有什么办法可以解决此问题?
Jackson / Java / Spring Boot没问题,但是JavaScript / Browser没问题。
尝试重现该问题,我序列化了同一个对象,并使用curl
进行了此操作:
$ curl localhost:8080
{"id":1291741231928705024,"uuid":null,"email":"kannanrbk.r@gmail.com"}
此处数字已正确序列化。
在Firefox中查看的同一json 会被截断:
但是,“原始数据”标签会正确显示数字:
在JavaScript中,1291741231928705024
不是安全的整数(请参见Number.isSafeInteger()
):
Number.isSafeInteger(1291741231928705024);
false
该数字大于2^53 - 1
,因此会四舍五入。 JavaScript中甚至可能出现更多令人困惑的情况:
> 1291741231928705024 === 1291741231928705022
true
可能的解决方案
首先检查您的客户以防此类问题。如果它可以安全地反序列化此类数字,那么您就安全了。
或者您可以将long
序列化为String
(如您在问题中提到的那样),这就是Twitter在其Twitter IDs (snowflake)文章中提出的建议:
,要允许Javascript和JSON解析器读取ID,在使用JSON响应时,Twitter对象包括任何ID的字符串版本。因此,Twitter API中的状态,用户,直接消息,已保存的搜索以及其他ID在JSON响应中以整数和字符串形式返回。
尝试使用bigInt作为主键
版权声明:本文内容由互联网用户自发贡献,该文观点与技术仅代表作者本人。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如发现本站有涉嫌侵权/违法违规的内容, 请发送邮件至 dio@foxmail.com 举报,一经查实,本站将立刻删除。