領先一步
VMware 提供培訓和認證,助您加速進步。
瞭解更多這是“通往GA之路”系列中的一篇新博文,就在Jackson 3.0.0 GA釋出幾天後,此篇博文分享了更多關於Jackson 3新支援的細節,該支援即將引入到Spring Boot 4及相關的Spring專案組合中。
Jackson是目前JVM上最常用的JSON庫,Spring中引入Jackson 3的支援是我們提供額外增強的機會,這是我在10多年前宣佈的廣受歡迎的Spring中Jackson整合改進的後續!
當 Spring 團隊致力於利用流行開源庫的新版本時,雖然可能不明顯,但部分工作有時是與維護者合作進行改進,這將有益於更廣泛的社群。
Jackson 3 就是一個很好的例子,我要感謝 Tatu Saloranta(Jackson 專案負責人)在釋出候選階段願意聽取我們的反饋——這使得以下改進成為可能:
JsonWriteFeature.ESCAPE_FORWARD_SLASHES 預設值一項不受歡迎的更改@JsonCreator 需求增加的問題一般原則是,自 Spring Boot 4.0 和 Spring Framework 7.0 起,Spring 產品組合將:
主要例外是 Spring AI,它打算在 2026 年上半年釋出的 2.0 版本中引入 Jackson 3 支援。
更具體地說,Spring Boot 4.0 將:
spring-boot-starter-json 和 spring-boot-starter-jackson 啟動器依賴項中使用 Jackson 3升級到 Spring Boot 4.0 時,建議的順序是:
spring.jackson.use-jackson2-defaults仍依賴 Jackson 2 的傳遞依賴項仍受支援,並將受益於 Jackson 2 依賴管理。
本節重點介紹典型 Spring Boot 應用程式最重要的遷移步驟,有關其他方面的更多詳細資訊,請參閱 Jackson 3 遷移指南。相關的 Open Rewrite 配方 可以幫助自動化其中一些更改,而 Spring Application Advisor 將為您的 Spring Boot 應用程式的增量遷移提供最全面的選項。
升級時遇到的第一個破壞性更改可能是 Jackson 包(和依賴項 groupID)從 com.fasterxml.jackson 更改為 tools.jackson,除了 jackson-annotations,它出於向後相容性原因保持不變。
Jackson 3 更改了一些預設設定,與 Jackson 2 相比,因此您應該相應地調整測試(如果可以,建議這樣做),或者自定義 Jackson 3 配置以恢復一些以前的預設設定。
最可能破壞測試的更改如下:
MapperFeature.SORT_PROPERTIES_ALPHABETICALLY 現在設定為 true 的影響。SerializationFeature.WRITE_DATES_AS_TIMESTAMPS 現在稱為 DateTimeFeature.WRITE_DATES_AS_TIMESTAMPS 已更改為 false,以將日期序列化為 ISO-8601 字串。如果您至少最初希望儘可能使用與 Jackson 2 相似的預設設定,則可以使用 spring.jackson.use-jackson2-defaults 屬性。當設定為 true 時,自動配置的 JsonMapper 將具有與 Spring Boot 3 中 Jackson 2 預設設定儘可能一致的預設設定。
一些以前的 Jackson 2 模組現在已內置於 Jackson 3 中,例如 parameter-names 或 datatype-jsr310。以前透過 Jackson2ObjectMapperBuilder 啟用的其他模組現在透過 JDK 服務載入器設施自動發現,用於 Spring Framework 提供的轉換器和編解碼器。
當然,也可以透過 JsonMapper.Builder 配置自定義模組。
Jackson 3 引入了許多更改和增強功能,但從 Spring 的角度來看,最重要的一項是從 Jackson 2 中可變的 ObjectMapper 切換到 Jackson 3 中不可變的 JsonMapper。
JsonMapper 擴充套件了 ObjectMapper,專門用於 JSON 格式,遵循與其他格式(XmlMapper、YAMLMapper、SmileMapper 等)類似的模式,並且 Spring 支援已更新為使用此特定於格式的變體,遵循 Jackson 3 最佳實踐。
此外,由於 Jackson 和 Spring 的預設設定大部分一致,並且引入了第一類 JsonMapper.Builder,Spring Framework 不再提供 Jackson2ObjectMapperBuilder 的等效項,您應該只使用 Jackson 構建器。
例如,對於 Spring Boot 3 及其 Jackson 2 支援,spring.jackson.serialization.indent-output=true 的程式設計等效項是
@Bean
public Jackson2ObjectMapperBuilderCustomizer jacksonCustomizer() {
return builder -> builder.indentOutput(true);
}
對於 Spring Boot 4 及其 Jackson 3 支援,它是
@Bean
JsonMapperBuilderCustomizer jacksonCustomizer() {
return builder -> builder.enable(SerializationFeature.INDENT_OUTPUT);
}
現在已棄用的 MappingJackson2HttpMessageConverter 擴充套件了 GenericHttpMessageConverter,後者無法正確傳遞額外的序列化資訊,例如序列化檢視或 FilterProvider,因此需要 MappingJacksonValue 包裝器。
例如,假設我們使用 @JsonView(Summary.class) 註解 User 記錄,以標識要序列化或反序列化的元件子集
public record User(
@JsonView(Summary.class) String firstname,
@JsonView(Summary.class) String lastname,
LocalDate birthdate,
@JsonView(Summary.class) String email,
String address,
int postalCode,
String city,
String country) {
}
使用 Spring Framework 6 及以前版本,在客戶端您必須使用 MappingJacksonValue 包裝器來指定應使用 Summary JSON 檢視。
var user = new User("Marcel", "Martin", LocalDate.of(1971, 7, 12),
"[email protected]", "1234 rue Gambetta", 69002, "Lyon", "France");
var jacksonValue = new MappingJacksonValue(user);
jacksonValue.setSerializationView(Summary.class);
var response = this.restTemplate.postForObject("https://:8080/create", jacksonValue, String.class);
這允許僅序列化用 @JsonView(Summary.class) 註解的記錄元件
{
"firstname" : "Marcel",
"lastname" : "Martin",
"email" : "[email protected]"
}
從 Spring Framework 7 開始,您可以利用基於 Jackson 3 的新 JacksonJsonHttpMessageConverter 實現了 SmartHttpMessageConverter,它支援序列化提示,因此您可以這樣編寫
var user = new User("Marcel", "Martin", LocalDate.of(1971, 7, 12),
"[email protected]", "1234 rue Gambetta", 69002, "Lyon", "France");
var response = this.restClient.post().uri("https://:8080/create")
.hint(JsonView.class.getName(), Summary.class).body(user)
.retrieve().body(String.class);
不再有可變包裝器,只有可選的提示。
建議遷移到 Spring Boot 4 的應用程式遷移到 Jackson 3,但如果需要,可以繼續使用 Jackson 2,甚至同時使用 Jackson 2 和 3。請注意,這可能需要額外的依賴項和配置改進。
如果您想暫時繼續使用 Jackson 2 支援而不是 Jackson 3,您可以例如:
spring-boot-jackson 的直接或傳遞依賴項(例如,來自 spring-boot-starter-jackson 或 spring-boot-starter-json),並改用 spring-boot-jackson2spring.jackson2 而不是 spring.jacksonJackson 2 自動配置以棄用形式保留了一段時間,僅用於幫助逐步遷移到 Jackson 3。
Spring Security 7.0 引入了Jackson 3 支援,並棄用了 Jackson 2 支援。
它還透過利用 PolymorphicTypeValidator 使 Jackson 支援更安全,其中預設只允許 Spring Security 型別,併為應用程式提供了新增自己型別的能力,例如
ClassLoader loader = getClass().getClassLoader();
BasicPolymorphicTypeValidator.Builder typeValidatorBuilder = BasicPolymorphicTypeValidator.builder()
.allowIfSubType(CustomGrantedAuthority.class);
JsonMapper mapper = JsonMapper.builder()
.addModules(SecurityJacksonModules.getModules(loader, typeValidatorBuilder))
.build();
Jackson 3 支援使用與現在已棄用的 Jackson 2 相容的格式,因此使用 Jackson 2 序列化的類例項應該可以使用 Jackson 3 支援進行反序列化。
Spring Data 4.0 及其核心模組完全支援 Jackson 3。建議遷移到 Spring Data 4 的應用程式遷移到 Jackson 3,但如果需要,可以繼續使用 Jackson 2,甚至同時使用 Jackson 2 和 3。請注意,Jackson 3 附帶了一組不同的預設設定,這可能需要遷移您的持久資料或更新 Jackson 3 預設設定以匹配 Jackson 2 設定。
由於 Spring Data 包含大量專案,讓我們單獨探討每個模組:
Spring Data Commons 添加了對 Jackson 3 的支援,如果類路徑中只有 Jackson 2,則會回退到 Jackson 2。這主要適用於透過 ProjectingJacksonHttpMessageConverter 和 SpringDataWebConfiguration 的 Web 支援。
JacksonResourceReader 和 JacksonRepositoryPopulatorFactoryBean 是 Jackson2ResourceReader 和 Jackson2RepositoryPopulatorFactoryBean 的基於 Jackson 3 的變體。
如果您使用 Jackson 2 以及 Spring Data 的 XML 名稱空間支援 (<repository:jackson2-populator …>),並且您想遷移到 Jackson 3,那麼您將必須在 Java 配置中定義一個 JacksonRepositoryPopulatorFactoryBean bean。
如果您碰巧使用 SpringDataJacksonModules,那麼您需要考慮遷移到 SpringDataJackson3Modules,以實現基於 Jackson 3 的模組安排。
Spring Data Redis 4.0 附帶了用於 Jackson 3 的 JacksonHashMapper、JacksonJsonRedisSerializer 和 GenericJacksonJsonRedisSerializer 實現。在使用 JacksonObjectReader 和 JacksonObjectWriter 時,請確保使用 Jackson2ObjectReader 和 Jackson2ObjectWriter 對您的實現進行改造,因為類命名已對齊以實現一致的方案。
Spring Data REST 本質上是一個圍繞 Jackson 的大型包裝器,不支援使用 Jackson 2 的操作模式。如果您想使用新的 Spring Data REST 版本,則您的應用程式必須遷移到 Jackson 3。Spring HATEOAS 也是如此,因為這兩個框架都大量使用 Jackson。
更大的生態系統正在緩慢追趕 Jackson 3。Couchbase、Elasticsearch 和一些驅動程式內部使用 Jackson 2,並將繼續這樣做。在大多數情況下,這些元件中的 Jackson 用法與您的實體無關,因為它是它們作為 JSON 解析器和寫入器的機制。
Jackson 3 在安全性、API、預設配置和功能方面帶來了巨大的好處,但它也帶來了需要一些遷移工作的破壞性更改,Spring 團隊完全意識到這一點,並投入了大量精力提供最佳的安排和相關指導,併為以前的版本提供行業領先的擴充套件支援,以便您有時間進行升級。
一如既往,我們期待您的反饋,並將盡最大努力改進我們的指導、文件並回答您的相關問題。