DateTimeFormatter的格式化输出结果是否依赖于操作系统?
问题解答
结论
该现象属于预期内的正常行为,并非代码逻辑错误导致。
触发原因
你使用的DateTimeFormatter.ofLocalizedDateTime()方法本身就是为了输出符合对应地区用户习惯的本地化格式,结果受环境配置影响是设计使然,具体差异来源有两个:
- 不同操作系统对
en_AU(澳大利亚英语)区域的中等长度日期格式定义存在原生差异:Windows规则中月份缩写后带英文句号、macOS规则不带句号、Linux/Ubuntu默认规则用斜杠分隔日期字段,Java 8版本默认会优先读取操作系统自带的区域配置生成格式化规则,因此出现了三种不同输出。 - 测试环境的Java小版本不一致:Linux环境使用的
1.8.0_292与另外两个环境的1.8.0_312属于不同补丁版本,Java版本更新时会同步更新内置的区域数据规则,也会进一步放大格式差异。
单元测试兼容方案
如果需要跨环境稳定跑通单元测试,可以根据业务需求选择两种解决方案:
- 若业务要求输出固定格式:放弃
ofLocalizedDateTime方法,改用DateTimeFormatter.ofPattern()方法硬编码指定固定格式模版,比如DateTimeFormatter.ofPattern("d MMM yyyy, h:mm:ss a", locale),完全屏蔽环境配置影响。 - 若确实需要保留本地化格式化逻辑:单元测试不要直接校验完整的输出字符串,改为校验格式化结果解析后对应的时间戳是否正确;也可以给JVM添加启动参数
-Djava.locale.providers=CLDR,强制所有环境统一使用JDK内置的通用区域数据仓库规则,拉齐不同操作系统的输出结果。
内容的提问来源于stack exchange,提问作者Grahame Grieve
相关产品推荐
相关产品推荐

