After reviewing features of Jackson 2.6, let’s continue our journey further and consider 2.7. As usual, 2.7 release notes are essential read for all the details; here we will focus on most important additions and changes.

“Single-item minor release”

Compared to, say, 2.6, this version is much more a “minor minor” release, focusing more on bug fixes (over 50) and less on new or improved features… with one notable exception: total rewrite of generic type resolution system. More on this in a bit.

Another thing to note is that this branch is proving to be a long-living one, and the latest patch version by now is 2.7.7. Project team istrying to help frameworks that rely on earlier 2.x versions (2.4, for example, is quite popular with frameworks like Spark) to upgrade to a later version, and 2.7 is currently (September 2016) a good target: it is close to the latest (2.8 has been released but no work started on 2.8) yet has had time to mature and remove minor compatibility problems reported.
Based on progress so far, it looks like 2.7 may well become the most widely used Jackson 2.x version and such should be a good upgrade target for anyone who has been using an earlier version.

Compatibility

JDK 7 for building, still runs on Java 6

To build Jackson 2.7 components, JDK 7 is now required, with exception of streaming (`jackson-core`) and annotations (`jackson-annotations`) which will still only require JDK 6. Core components will also support small number of JDK 7 datatypes formerly only supported via JDK 7 datatype module (see below).

However, Jackson 2.7 still runs on Java 6 as all the support is added dynamically; no new language features are yet used.
Later versions will start using Java 7 language features and support new types directly. Support for Java 8 features may also be rolled out incrementally, using similar strategy.

As a specific goal, 2.7 should work well on Android platform.

Module additions, removals

2.7 adds two new modules:

  • Kotlin module to support datatypes of Kotlin, an excellent JVM-based modern scripting-like programming language
  • PCollections datatype module for collection types of PCollections library

There was also one deprecation: JDK7 module is deprecated and no 2.7 versions (or later) will be released, because support is provided directly by `jackson-databind`

Module improvements

Beyond basic bugfixes, following modules had significant upgrades:

  • CSV dataformat module has a big list of improvements, mostly focusing on error-handling and support for “partial” documents (missing columns, extra columns), including support for “any setters”, to allow access to such “extra values”
  • XML dataformat module contains a few important bug fixes related to handling of List values.
  • Jackson jr significantly improved: of specific note are 2 new sub-modules — `stree` (Simple read-only Tree model) and `retrofit2` Converter implementation (to allow use of `jackson-jr` as the JSON converter for Retrofit 2 REST client)

For these modules, upgrade from previous minor versions is strongly recommended, above and beyond benefits of core component upgrades.

New Features for Core modules

Complete rewrite of the (generic) Type Resolution system

The big thing with 2.7 was the complete rewrite of type resolution system to solve problems with resolving complex generic type hierarchies: for example cases where type aliasing (renaming of type variables) occurs.
Inspiration for the rewrite came from Java Classmate library which was written based on my experiences on type resolution in Jackson and where all then-known problems of Jackson type resolution were solved.
Unfortunately Classmate itself was not directly usable because Jackson type resolver is somewhat closely coupled with the rest of Jackson and adds additional domain-specific limitations (such as special nature of `Map` and `Collection` types).

Work to rewrite type handling system had been planned for a long time — at least since 2.0 — but due to sheer size of the task and risk involved work had been postponed multiple times. But with 2.7 I decided to just bite the bullet (or damn the torpedoes). Results included fixing 2 of the oldest reported bugs (which were impossible to resolve with the old type resolution system), as well as cleaning up of the actual type resolution system — code size was reduced slightly as well.

But despite big effort needed, the change itself is probably mostly invisible to users: not many users were affected by the edge cases. Still, it felt good to finally tackle a difficult, long-standing fundamental problem: I really don’t like closing report bugs as “can’t fix”…

Fix for `JsonInclude.Include.NON_EMPTY` behavior

By far the biggest issue (or at least most vocally reported about…) was that of change in behavior of:

public class Beano {
@JsonInclude(Include.NON_EMPTY)
public int x;
}

(or similarly when specifying default serialization inclusion via `ObjectMapper.setSerializationInclusion(Include)`).

With Jackson 2.5 and earlier, `NON_EMPTY` only affected handling of `Map`s, `Collection`s, arrays and `String`s. With 2.6, “default” values of scalar types like `int`/`Integer`, `boolean` and so on were considered “empty”, so that for default `Beano` as shown above, 2.5 would include value for `x`, but 2.6 would not.
While this change was intended as a simple bug fix — original intent was always to do this — in practice it felt like a change in definition (which was arguably ambiguous or at least under-specified).

With 2.7 behavior of `NON_EMPTY` was rolled back to 2.5; but choice of `Include` values was improved to support 2.6-style behavior:

  • `NON_DEFAULT` now works at all levels (global, per-class, per-property), and for global and per-property case excludes default values (like `0` for `int`) from serialization.
  • When `NON_DEFAULT` is annotated for class, earlier definition of excluding default values _assigned_ to properties (and not default value of the TYPE of property) is still used: “type default” only affects global setting case, or when used directly on property.

Definition of `NON_EMPTY` (and all `JsonInclude.Include` values) should now be fully defined as of 2.7, and should NOT be changed in any way for remainder of 2.x release cycle.

Dataformat-specific Features

Besides type resolver rewrite the most important new feature is probably support for generalized dataformat-specific features. Improvement is that of adding new abstraction, `FormatFeature`, to allow enabling/disabling of format-specific on/off via non-format specific `ObjectMapper`,`ObjectReader`s and `ObjectWriter`s. So features that already existed but that required direct configuration of the module or underlying factory (subtype of `JsonFactory`) may now be set/cleared at databinding level, for example:

CsvMapper mapper = new CsvMapper();
CsvSchema schema = CsvSchema.builder()
.addColumn("id")
.addColumn("amount")
.build();
String result = mapper.writer(schema)
.with(CsvGenerator.Feature.ALWAYS_QUOTE_STRINGS)
.writeValueAsString(new Entry("abc", 1.25));

to force quoting of all String values in CSV document.

The main benefit here is just to make use of `ObjectReader` and `ObjectWriter` more convenient with non-JSON formats.

Support for `@ConstructorProperties` (JDK 7)

Of JDK 7 support included directly in `jackson-databind`, support for `@ConstructorProperties` is the most notable: it allows specifying names of constructor parameters without separate `@JsonProperty` for each argument. In addition many frameworks (like Lombok, Immutables, Auto-value) support automatic generation of this annotation.

PropertyNameStrategy. KEBAB_CASE

Another useful addition was addition of one more `PropertyNameStrategy` choice: KEBAB_CASE. This refers to “Lisp”-style (also used in xml/xslt) of lower-case letters with hyphen as separator: ids like “lower-case” or “first-name”. This is similar to “Snake-case” used in C, but with hyphen used as word separator instead of underscore. Usage is with either per-class annotation

@JsonNaming(PropertyNamingStrategy.KebabCaseStrategy.class)

or as general naming default:

objectMapper.setPropertyNamingStrategy(PropertyNamingStrategy.KEBAB_CASE);

Written by

Open Source developer, most known for Jackson data processor (nee “JSON library”), author of many, many other OSS libraries for Java, from ClassMate to Woodstox

Get the Medium app

A button that says 'Download on the App Store', and if clicked it will lead you to the iOS App store
A button that says 'Get it on, Google Play', and if clicked it will lead you to the Google Play store